diff --git a/components/CustomMaterialIcon.js b/components/CustomMaterialIcon.js index 7b99881..b3ca81f 100644 --- a/components/CustomMaterialIcon.js +++ b/components/CustomMaterialIcon.js @@ -9,7 +9,7 @@ type Props = { icon: string, color: ?string, fontSize: number, - width: number, + width: number|string, } /** diff --git a/components/FetchedDataSectionList.js b/components/FetchedDataSectionList.js index 776b28f..b1e4fed 100644 --- a/components/FetchedDataSectionList.js +++ b/components/FetchedDataSectionList.js @@ -2,10 +2,12 @@ import * as React from 'react'; import WebDataManager from "../utils/WebDataManager"; -import {Container, Tab, TabHeading, Tabs, Text} from "native-base"; +import {Container, H3, Tab, TabHeading, Tabs, Text} from "native-base"; import CustomHeader from "./CustomHeader"; import {RefreshControl, SectionList, View} from "react-native"; import CustomMaterialIcon from "./CustomMaterialIcon"; +import i18n from 'i18n-js'; +import ThemeManager from "../utils/ThemeManager"; type Props = { navigation: Object, @@ -69,6 +71,34 @@ export default class FetchedDataSectionList extends React.Component<Props, State return <View/>; } + getEmptyRenderItem(text: string, icon: string) { + return ( + <View> + <View style={{ + justifyContent: 'center', + alignItems: 'center', + width: '100%', + height: 100, + marginBottom: 20 + }}> + <CustomMaterialIcon + icon={icon} + fontSize={100} + width={100} + color={ThemeManager.getCurrentThemeVariables().fetchedDataSectionListErrorText}/> + </View> + + <H3 style={{ + textAlign: 'center', + marginRight: 20, + marginLeft: 20, + color: ThemeManager.getCurrentThemeVariables().fetchedDataSectionListErrorText + }}> + {text} + </H3> + </View>); + } + /** * Create the dataset to be used in the list from the data fetched * @param fetchedData {Object} @@ -78,11 +108,33 @@ export default class FetchedDataSectionList extends React.Component<Props, State return []; } + createEmptyDataset() { + return [ + { + title: '', + data: [ + { + text: this.state.refreshing ? + i18n.t('general.loading') : + i18n.t('general.networkError'), + icon: this.state.refreshing ? + 'refresh' : + 'access-point-network-off' + } + ], + keyExtractor: (item: Object) => item.text, + } + ]; + } + hasTabs() { return false; } getSectionList(dataset: Array<Object>) { + let isEmpty = dataset[0].data.length === 0; + if (isEmpty) + dataset = this.createEmptyDataset(); return ( <SectionList sections={dataset} @@ -93,12 +145,20 @@ export default class FetchedDataSectionList extends React.Component<Props, State /> } renderSectionHeader={({section: {title}}) => - this.getRenderSectionHeader(title) + isEmpty ? + <View/> : + this.getRenderSectionHeader(title) } renderItem={({item, section}) => - this.getRenderItem(item, section, dataset) + isEmpty ? + this.getEmptyRenderItem(item.text, item.icon) : + this.getRenderItem(item, section, dataset) } style={{minHeight: 300, width: '100%'}} + contentContainerStyle={ + isEmpty ? + {flexGrow: 1, justifyContent: 'center', alignItems: 'center'} : {} + } /> ); } diff --git a/native-base-theme/variables/platform.js b/native-base-theme/variables/platform.js index 5f78f2f..c3f6abc 100644 --- a/native-base-theme/variables/platform.js +++ b/native-base-theme/variables/platform.js @@ -258,6 +258,7 @@ export default { // CUSTOM customMaterialIconColor: "#5d5d5d", + fetchedDataSectionListErrorText : "#898989", // PROXIWASH proxiwashFinishedColor: "rgba(54,165,22,0.31)", diff --git a/native-base-theme/variables/platformDark.js b/native-base-theme/variables/platformDark.js index 1bed5a6..3cdaa77 100644 --- a/native-base-theme/variables/platformDark.js +++ b/native-base-theme/variables/platformDark.js @@ -258,6 +258,7 @@ export default { // CUSTOM customMaterialIconColor: "#b3b3b3", + fetchedDataSectionListErrorText : "#acacac", // PROXIWASH proxiwashFinishedColor: "rgba(12,157,13,0.72)", diff --git a/screens/ProxiwashScreen.js b/screens/ProxiwashScreen.js index c3d1d5b..9c554b3 100644 --- a/screens/ProxiwashScreen.js +++ b/screens/ProxiwashScreen.js @@ -87,12 +87,10 @@ export default class ProxiwashScreen extends FetchedDataSectionList { } getDryersKeyExtractor(item: Object) { - console.log(item !== undefined ? "dryer" + item.number : undefined); return item !== undefined ? "dryer" + item.number : undefined; } getWashersKeyExtractor(item: Object) { - console.log(item !== undefined ? "washer" + item.number : undefined); return item !== undefined ? "washer" + item.number : undefined; } @@ -155,7 +153,6 @@ export default class ProxiwashScreen extends FetchedDataSectionList { reminderNotifTime = parseInt(val); else reminderNotifTime = -1; - console.log(reminderNotifTime); return reminderNotifTime; } diff --git a/translations/en.json b/translations/en.json index cf9a5b7..bd0387f 100644 --- a/translations/en.json +++ b/translations/en.json @@ -85,5 +85,9 @@ "machineRunningTitle": "Laundry running: {{time}} minutes left", "machineRunningBody": "The machine n°{{number}} is still running" } + }, + "general": { + "loading": "Loading...", + "networkError": "Unable to contact servers. Make sure you are connected to Internet." } } diff --git a/translations/fr.json b/translations/fr.json index 7c10450..8224d4e 100644 --- a/translations/fr.json +++ b/translations/fr.json @@ -85,5 +85,9 @@ "machineRunningTitle": "Machine en cours: {{time}} minutes restantes", "machineRunningBody": "La machine n°{{number}} n'est pas encore terminée" } + }, + "general": { + "loading": "Chargement...", + "networkError": "Impossible de contacter les serveurs. Assurez vous d'être connecté à internet." } } diff --git a/utils/AsyncStorageManager.js b/utils/AsyncStorageManager.js index 9bc605a..72a9828 100644 --- a/utils/AsyncStorageManager.js +++ b/utils/AsyncStorageManager.js @@ -55,7 +55,6 @@ export default class AsyncStorageManager { val = this.preferences[key].default; this.preferences[key].current = val; } - console.log(this.preferences); } savePref(key : string, val : string) {