@eohjsc/react-native-smart-city 0.4.0 → 0.4.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (84) hide show
  1. package/package.json +2 -8
  2. package/src/commons/ActionGroup/NumberUpDownActionTemplate.js +2 -1
  3. package/src/commons/ActionGroup/NumberUpDownActionTemplateStyle.js +4 -0
  4. package/src/commons/ActionGroup/OptionsDropdownActionTemplate.js +2 -1
  5. package/src/commons/ActionGroup/OptionsDropdownActionTemplateStyle.js +6 -0
  6. package/src/commons/ActionGroup/SliderRangeTemplate.js +4 -2
  7. package/src/commons/ActionGroup/SliderRangeTemplateStyles.js +1 -0
  8. package/src/commons/ActionGroup/StatesGridActionTemplate.js +2 -1
  9. package/src/commons/ActionGroup/StatesGridActionTemplateStyle.js +4 -0
  10. package/src/commons/ActionGroup/ThreeButtonTemplate/components/ThreeButtonDefault.js +7 -1
  11. package/src/commons/ActionGroup/ThreeButtonTemplate/components/ThreeButtonDefaultStyles.js +8 -0
  12. package/src/commons/ActionGroup/ThreeButtonTemplate/index.js +3 -1
  13. package/src/commons/ActionGroup/ThreeButtonTemplate/styles.js +3 -0
  14. package/src/commons/ActionGroup/__test__/OnOffTemplate.test.js +0 -5
  15. package/src/commons/ActionGroup/__test__/OneBigButtonTemplate.test.js +0 -5
  16. package/src/commons/Dashboard/MyUnit/__test__/MyUnit.test.js +24 -42
  17. package/src/commons/Dashboard/MyUnit/index.js +4 -2
  18. package/src/commons/DateTimeRangeChange/index.js +32 -4
  19. package/src/commons/Device/Emergency/EmergencyDetail.js +1 -1
  20. package/src/commons/Device/HistoryChart.js +52 -83
  21. package/src/commons/Device/PMSensor/PMSensorIndicator.js +3 -2
  22. package/src/commons/Device/PMSensor/PMSensorIndicatorStyles.js +3 -0
  23. package/src/commons/Device/ProgressBar/__test__/ProgressBar.test.js +0 -5
  24. package/src/commons/Device/ProgressBar/index.js +2 -2
  25. package/src/commons/Device/ProgressBar/styles.js +5 -0
  26. package/src/commons/Device/RainningSensor/CurrentRainSensor.js +5 -2
  27. package/src/commons/Device/WindDirection/Compass/index.js +9 -1
  28. package/src/commons/Device/WindSpeed/Anemometer/index.js +1 -4
  29. package/src/commons/FlatListDnD/index.js +31 -29
  30. package/src/commons/Form/TextInputPassword.js +2 -0
  31. package/src/commons/SelectActionCard/index.js +1 -1
  32. package/src/commons/SubUnit/OneTap/__test__/SubUnitAutomate.test.js +0 -7
  33. package/src/commons/Text/index.js +2 -2
  34. package/src/context/mockStore.ts +6 -1
  35. package/src/hooks/index.js +2 -1
  36. package/src/hooks/usePrevious.js +9 -0
  37. package/src/navigations/AddGatewayStack.js +0 -5
  38. package/src/screens/AQIGuide/__test__/AQIGuide.test.js +0 -5
  39. package/src/screens/ActivityLog/__test__/index.test.js +0 -9
  40. package/src/screens/AddNewGateway/SelectDeviceType.js +1 -1
  41. package/src/screens/Automate/AddNewAction/ChooseAction.js +19 -2
  42. package/src/screens/Automate/AddNewAction/Components/SelectDevices.js +2 -2
  43. package/src/screens/Automate/AddNewAction/NewActionWrapper.js +11 -7
  44. package/src/screens/Automate/AddNewAction/SelectControlDevices.js +4 -2
  45. package/src/screens/Automate/AddNewAutoSmart/__test__/AddNewAutoSmart.test.js +0 -7
  46. package/src/screens/Automate/EditActionsList/index.js +2 -2
  47. package/src/screens/Automate/OneTap/__test__/AddNewOneTap.test.js +0 -7
  48. package/src/screens/Automate/Scenario/__test__/AddNewOneTap.test.js +0 -7
  49. package/src/screens/Automate/ScriptDetail/__test__/index.test.js +17 -1
  50. package/src/screens/Automate/ScriptDetail/index.js +8 -6
  51. package/src/screens/ChangePosition/__test__/index.test.js +4 -1
  52. package/src/screens/ChangePosition/index.js +24 -21
  53. package/src/screens/ChangePosition/styles.js +19 -4
  54. package/src/screens/Device/__test__/detail.test.js +147 -89
  55. package/src/screens/Device/__test__/mqttDetail.test.js +2 -15
  56. package/src/screens/Device/components/ChartWrapper.js +32 -26
  57. package/src/screens/Device/components/SensorDisplayItem.js +33 -16
  58. package/src/screens/Device/components/VisualChart.js +12 -3
  59. package/src/screens/Device/components/__test__/VisualChart.test.js +0 -7
  60. package/src/screens/Device/detail.js +13 -12
  61. package/src/screens/Device/hooks/useDeviceWatchConfigControl.js +10 -6
  62. package/src/screens/Device/styles.js +1 -1
  63. package/src/screens/Notification/__test__/NotificationItem.test.js +2 -0
  64. package/src/screens/PlayBackCamera/Styles/index.js +1 -1
  65. package/src/screens/PlayBackCamera/index.js +7 -7
  66. package/src/screens/SharedUnit/__test__/ShareUnit.test.js +0 -5
  67. package/src/screens/Sharing/__test__/SelectUser.test.js +0 -7
  68. package/src/screens/SmartAccount/index.js +20 -11
  69. package/src/screens/SubUnit/EditSubUnit.js +1 -2
  70. package/src/screens/SubUnit/__test__/AddSubUnit.test.js +0 -9
  71. package/src/screens/SubUnit/__test__/Detail.test.js +0 -7
  72. package/src/screens/SubUnit/__test__/EditSubUnit.test.js +0 -12
  73. package/src/screens/TDSGuide/__test__/TDSGuide.test.js +0 -6
  74. package/src/screens/UVIndexGuide/__test__/UVIndexGuide.test.js +0 -6
  75. package/src/screens/Unit/__test__/CheckSendEmail.test.js +0 -11
  76. package/src/screens/Unit/__test__/Detail.test.js +0 -12
  77. package/src/screens/Unit/__test__/ManageUnit.test.js +0 -8
  78. package/src/screens/UnitSummary/components/PowerConsumption/index.js +4 -6
  79. package/src/screens/WaterQualityGuide/__test__/index.test.js +0 -5
  80. package/src/utils/I18n/translations/en.js +3 -1
  81. package/src/utils/I18n/translations/vi.js +3 -1
  82. package/src/utils/Route/index.js +0 -1
  83. package/src/screens/AddNewGateway/PlugAndPlay/ConnectRouterGuide.js +0 -49
  84. package/src/screens/AddNewGateway/PlugAndPlay/__test__/ConnectRouterGuide.test.js +0 -68
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@eohjsc/react-native-smart-city",
3
3
  "title": "React Native Smart Home",
4
- "version": "0.4.00",
4
+ "version": "0.4.02",
5
5
  "description": "TODO",
6
6
  "main": "index.js",
7
7
  "files": [
@@ -177,6 +177,7 @@
177
177
  "react-native-image-resizer": "^1.4.5",
178
178
  "react-native-input-credit-card": "^0.5.5",
179
179
  "react-native-iphone-x-helper": "^1.2.1",
180
+ "react-native-keyboard-aware-scroll-view": "^0.9.5",
180
181
  "react-native-linear-gradient": "^2.5.6",
181
182
  "react-native-localize": "^1.4.1",
182
183
  "react-native-maps": "0.27.1",
@@ -199,7 +200,6 @@
199
200
  "react-native-svg": "^12.1.0",
200
201
  "react-native-toast-message": "^2.1.1",
201
202
  "react-native-udp": "^4.1.3",
202
- "react-native-unimodules": "^0.11.0",
203
203
  "react-native-version-check": "^3.4.2",
204
204
  "react-native-vlc-media-player": "^1.0.41",
205
205
  "react-native-webview": "11.17.2",
@@ -207,12 +207,6 @@
207
207
  "react-native-wheel-scrollview-picker": "^1.2.2",
208
208
  "react-native-wifi-reborn": "^4.5.0",
209
209
  "react-navigation": "^2.2.0",
210
- "react-redux": "^7.2.1",
211
- "redux": "^4.0.5",
212
- "redux-logger": "^3.0.6",
213
- "redux-mock-store": "^1.5.4",
214
- "redux-persist": "^6.0.0",
215
- "redux-saga": "^1.1.3",
216
210
  "string-format": "^2.0.0",
217
211
  "sync-directory": "^5.1.7",
218
212
  "timezone-mock": "^1.1.3",
@@ -14,6 +14,7 @@ const NumberUpDownActionTemplate = ({
14
14
  actionGroup = {},
15
15
  doAction,
16
16
  sensor = {},
17
+ isWidgetOrder,
17
18
  }) => {
18
19
  const { configuration = {}, title } = actionGroup;
19
20
  const {
@@ -105,7 +106,7 @@ const NumberUpDownActionTemplate = ({
105
106
  );
106
107
 
107
108
  return (
108
- <View style={styles.wrap}>
109
+ <View style={(isWidgetOrder && styles.wrapOrderItem) || styles.wrap}>
109
110
  {!!title && (
110
111
  <Text left type="Label" style={styles.title}>
111
112
  {title}
@@ -11,6 +11,10 @@ export default StyleSheet.create({
11
11
  borderRadius: 10,
12
12
  flex: 1,
13
13
  },
14
+ wrapOrderItem: {
15
+ flex: 1,
16
+ padding: 16,
17
+ },
14
18
  downButton: {
15
19
  marginRight: 60,
16
20
  },
@@ -27,6 +27,7 @@ const OptionsDropdownActionTemplate = ({
27
27
  actionGroup = {},
28
28
  doAction,
29
29
  sensor = {},
30
+ isWidgetOrder,
30
31
  }) => {
31
32
  const t = useTranslations();
32
33
  const { configuration = {}, title = '' } = actionGroup;
@@ -122,7 +123,7 @@ const OptionsDropdownActionTemplate = ({
122
123
  }, [icon]);
123
124
 
124
125
  return (
125
- <View style={styles.wrap}>
126
+ <View style={(isWidgetOrder && styles.wrapOrderItem) || styles.wrap}>
126
127
  <View style={styles.iconAndText}>
127
128
  {!checkIcon && (
128
129
  <IconComponent
@@ -13,6 +13,12 @@ export default StyleSheet.create({
13
13
  flexDirection: 'row',
14
14
  justifyContent: 'space-between',
15
15
  },
16
+ wrapOrderItem: {
17
+ flex: 1,
18
+ flexDirection: 'row',
19
+ justifyContent: 'space-between',
20
+ padding: 16,
21
+ },
16
22
  iconAndText: {
17
23
  flex: 1,
18
24
  flexDirection: 'row',
@@ -18,7 +18,7 @@ import { DEVICE_TYPE } from '../../configs/Constants';
18
18
  import _TextInput from '../Form/TextInput';
19
19
 
20
20
  const SliderRangeTemplate = memo(
21
- ({ actionGroup = {}, doAction, sensor, item }) => {
21
+ ({ actionGroup = {}, doAction, sensor, item, isWidgetOrder }) => {
22
22
  const t = useTranslations();
23
23
  const { configuration = {} } = actionGroup;
24
24
  const [configValues] = useConfigGlobalState('configValues');
@@ -86,7 +86,9 @@ const SliderRangeTemplate = memo(
86
86
  };
87
87
 
88
88
  return (
89
- <View style={styles.viewBrightness}>
89
+ <View
90
+ style={(isWidgetOrder && styles.wrapOrderItem) || styles.viewBrightness}
91
+ >
90
92
  <Text type="H4" style={styles.LeftTextBrightness}>
91
93
  {actionGroup?.title || item?.label || t('brightness')}
92
94
  </Text>
@@ -10,6 +10,7 @@ export default StyleSheet.create({
10
10
  borderColor: Colors.Gray4,
11
11
  borderRadius: 10,
12
12
  },
13
+ wrapOrderItem: { padding: 16 },
13
14
  trackSlider: {
14
15
  height: 4,
15
16
  },
@@ -111,6 +111,7 @@ const StatesGridActionTemplate = ({
111
111
  actionGroup = {},
112
112
  doAction,
113
113
  sensor = {},
114
+ isWidgetOrder,
114
115
  }) => {
115
116
  const { configuration = {}, title } = actionGroup;
116
117
 
@@ -130,7 +131,7 @@ const StatesGridActionTemplate = ({
130
131
  }, [configuration, configValues]);
131
132
 
132
133
  return (
133
- <View style={styles.wrap}>
134
+ <View style={(isWidgetOrder && styles.wrapOrderItem) || styles.wrap}>
134
135
  {!!title && (
135
136
  <Text type="H4" style={styles.textModeMargin}>
136
137
  {title}
@@ -16,6 +16,10 @@ export default StyleSheet.create({
16
16
  borderBottomRightRadius: 10,
17
17
  borderBottomLeftRadius: 10,
18
18
  },
19
+ wrapOrderItem: {
20
+ display: 'flex',
21
+ justifyContent: 'space-between',
22
+ },
19
23
  wrapOption: {
20
24
  flex: 1,
21
25
  flexDirection: 'row',
@@ -16,6 +16,7 @@ const ThreeButtonDefault = memo(
16
16
  onButton1Press,
17
17
  onButton2Press,
18
18
  onButton3Press,
19
+ isWidgetOrder,
19
20
  }) => {
20
21
  const Icon2CT = () => {
21
22
  return icon2 === 'stop' ? (
@@ -68,7 +69,12 @@ const ThreeButtonDefault = memo(
68
69
  ]);
69
70
 
70
71
  return (
71
- <View style={styles.threeButtonDefault}>
72
+ <View
73
+ style={[
74
+ styles.threeButtonDefault,
75
+ isWidgetOrder && styles.widgetOrderThreeButton,
76
+ ]}
77
+ >
72
78
  {listButton.map((item, index) => {
73
79
  return (
74
80
  <TouchableOpacity
@@ -11,6 +11,14 @@ export default StyleSheet.create({
11
11
  borderColor: Colors.Gray4,
12
12
  borderRadius: 10,
13
13
  },
14
+ widgetOrderThreeButton: {
15
+ alignItems: 'center',
16
+ margin: 0,
17
+ marginTop: 20,
18
+ paddingHorizontal: 8,
19
+ borderWidth: 0,
20
+ borderRadius: 0,
21
+ },
14
22
  buttonAction: {
15
23
  flex: 1,
16
24
  aspectRatio: 1,
@@ -8,7 +8,7 @@ import IconComponent from '../../IconComponent';
8
8
  import ThreeButtonCircle from './components/ThreeButtonCircle';
9
9
  import ThreeButtonDefault from './components/ThreeButtonDefault';
10
10
 
11
- const ThreeButtonTemplate = memo(({ actionGroup, doAction }) => {
11
+ const ThreeButtonTemplate = memo(({ actionGroup, doAction, isWidgetOrder }) => {
12
12
  const { configuration } = actionGroup;
13
13
  const {
14
14
  text1,
@@ -93,6 +93,7 @@ const ThreeButtonTemplate = memo(({ actionGroup, doAction }) => {
93
93
  onButton1Press: onButton1Press,
94
94
  onButton2Press: onButton2Press,
95
95
  onButton3Press: onButton3Press,
96
+ isWidgetOrder: isWidgetOrder,
96
97
  };
97
98
  switch (layout) {
98
99
  case 'circle': {
@@ -115,6 +116,7 @@ const ThreeButtonTemplate = memo(({ actionGroup, doAction }) => {
115
116
  text1,
116
117
  text2,
117
118
  text3,
119
+ isWidgetOrder,
118
120
  ]);
119
121
 
120
122
  return (
@@ -5,6 +5,9 @@ export default StyleSheet.create({
5
5
  flex: 1,
6
6
  marginBottom: 16,
7
7
  },
8
+ wrapOrderItem: {
9
+ flex: 1,
10
+ },
8
11
  lockSwitch: {
9
12
  flexDirection: 'row',
10
13
  justifyContent: 'space-between',
@@ -26,11 +26,6 @@ jest.mock('../../../iot/states', () => ({
26
26
  useConfigGlobalState: () => [{ 5: { value: 2 } }, null],
27
27
  }));
28
28
 
29
- jest.mock('react-redux', () => ({
30
- ...jest.requireActual('react-redux'),
31
- useSelector: jest.fn(),
32
- }));
33
-
34
29
  jest.mock('@react-navigation/native', () => {
35
30
  return {
36
31
  ...jest.requireActual('@react-navigation/native'),
@@ -16,11 +16,6 @@ const wrapComponent = (actionGroup, mockDoAction, sensor) => (
16
16
  </SCProvider>
17
17
  );
18
18
 
19
- jest.mock('react-redux', () => ({
20
- ...jest.requireActual('react-redux'),
21
- useSelector: jest.fn(),
22
- }));
23
-
24
19
  describe('Test OneBigButtonTemplate', () => {
25
20
  const action_data = {
26
21
  color: '#00979D',
@@ -10,33 +10,10 @@ import { mockSCStore } from '../../../../context/mockStore';
10
10
  import api from '../../../../utils/Apis/axios';
11
11
  import { API } from '../../../../configs';
12
12
  import Routes from '../../../../utils/Route';
13
- import { Action } from '../../../../context/actionType';
14
13
 
15
14
  const mock = new MockAdapter(api.axiosInstance);
16
15
 
17
16
  const mockedNavigate = jest.fn();
18
- const mockedDispatch = jest.fn();
19
- const mockedSetAction = jest.fn();
20
-
21
- const mockUseContext = jest.fn().mockImplementation(() => ({
22
- stateData: mockSCStore({}),
23
- setAction: mockedSetAction,
24
- }));
25
-
26
- React.useContext = mockUseContext;
27
-
28
- const mockSetAction = jest.fn();
29
- jest.mock('react', () => {
30
- return {
31
- ...jest.requireActual('react'),
32
- useContext: () => ({
33
- stateData: mockSCStore({
34
- app: { isDeleteUnitSuccessFully: true, isNeedUpdateCache: true },
35
- }),
36
- setAction: mockSetAction,
37
- }),
38
- };
39
- });
40
17
 
41
18
  jest.mock('@react-navigation/native', () => {
42
19
  return {
@@ -49,19 +26,17 @@ jest.mock('@react-navigation/native', () => {
49
26
  };
50
27
  });
51
28
 
52
- jest.mock('react-redux', () => ({
53
- ...jest.requireActual('react-redux'),
54
- useDispatch: () => mockedDispatch,
55
- }));
56
-
57
- const wrapComponent = () => (
58
- <SCProvider initState={mockSCStore({})}>
29
+ const wrapComponent = (data = {}) => (
30
+ <SCProvider initState={mockSCStore(data)}>
59
31
  <MyUnit refreshing={true} />
60
32
  </SCProvider>
61
33
  );
62
34
 
63
35
  describe('Test MyUnit', () => {
64
36
  let tree;
37
+ let storeData = {
38
+ app: { isDeleteUnitSuccessFully: true, isNeedUpdateCache: true },
39
+ };
65
40
  let data = [
66
41
  {
67
42
  id: 1,
@@ -96,6 +71,7 @@ describe('Test MyUnit', () => {
96
71
 
97
72
  beforeEach(() => {
98
73
  mock.resetHistory();
74
+ mockedNavigate.mockClear();
99
75
  });
100
76
 
101
77
  const getElement = (instance) => {
@@ -113,7 +89,7 @@ describe('Test MyUnit', () => {
113
89
 
114
90
  it('MyUnit no Unit', async () => {
115
91
  await act(async () => {
116
- tree = await renderer.create(wrapComponent());
92
+ tree = await renderer.create(wrapComponent(storeData));
117
93
  });
118
94
  const instance = tree.root;
119
95
  const { textNoUnit } = getElement(instance);
@@ -123,7 +99,7 @@ describe('Test MyUnit', () => {
123
99
  it('MyUnit with unit', async () => {
124
100
  mock.onGet(API.UNIT.MY_UNITS()).replyOnce(200, data);
125
101
  await act(async () => {
126
- tree = await renderer.create(wrapComponent());
102
+ tree = await renderer.create(wrapComponent(storeData));
127
103
  });
128
104
  const instance = tree.root;
129
105
  const devices = instance.findAllByType(MyUnitDevice);
@@ -139,19 +115,25 @@ describe('Test MyUnit', () => {
139
115
  params: { unitId: 1 },
140
116
  screen: Routes.UnitDetail,
141
117
  });
142
- expect(mockSetAction).toBeCalledWith(
143
- Action.IS_CHECK_CLEAR_CACHE_UNITS,
144
- false
145
- );
146
118
  });
147
119
 
148
- it('Test isDeleteUnitSuccessFully', async () => {
149
- jest.useFakeTimers();
150
- mock.onGet(API.UNIT.MY_UNITS()).replyOnce(200, data);
120
+ it('Test isNeedUpdateCache = false', async () => {
121
+ mock.onGet(API.UNIT.MY_UNITS()).replyOnce(200, [data[1]]);
151
122
  await act(async () => {
152
- tree = await renderer.create(wrapComponent());
123
+ tree = await renderer.create(
124
+ wrapComponent({ app: { isNeedUpdateCache: false } })
125
+ );
126
+ });
127
+ const instance = tree.root;
128
+ const button = instance.findByProps({
129
+ accessibilityLabel: `${AccessibilityLabel.MY_UNIT_GO_TO_DETAIL}-0`,
130
+ });
131
+ await act(async () => {
132
+ await button.props.onPress(data[1]);
133
+ });
134
+ expect(mockedNavigate).toBeCalledWith('UnitStack', {
135
+ params: { unitId: 2 },
136
+ screen: 'UnitDetail',
153
137
  });
154
- jest.runAllTimers();
155
- expect(mockSetAction).toBeCalledWith(Action.RESET_DELETE_UNIT_ACTION);
156
138
  });
157
139
  });
@@ -34,6 +34,7 @@ import MyUnitDevice from '../../../screens/Unit/components/MyUnitDevice';
34
34
  import { STORAGE_KEY } from '../../../utils/Storage';
35
35
  import { preloadImagesFromUnits } from '../../../utils/Functions/preloadImages';
36
36
  import FImage from '../../FImage';
37
+ import { usePrevious } from '../../../hooks';
37
38
 
38
39
  let screenWidth = Dimensions.get('window').width;
39
40
 
@@ -45,6 +46,7 @@ const MyUnit = ({ refreshing }) => {
45
46
  const isFocused = useIsFocused();
46
47
  const navigation = useNavigation();
47
48
  const [myUnits, setMyUnits] = useState([]);
49
+ const previousMyUnits = usePrevious(myUnits);
48
50
  const [slideIndex, setSlideIndex] = useState(0);
49
51
  const { setAction } = useContext(SCContext);
50
52
  const isDeleteUnitSuccessFully = useSCContextSelector(
@@ -186,14 +188,14 @@ const MyUnit = ({ refreshing }) => {
186
188
  }, [fetchMyUnitDashboard, isFocused, refreshing]);
187
189
 
188
190
  useEffect(() => {
189
- if (isDeleteUnitSuccessFully) {
191
+ if (isDeleteUnitSuccessFully || previousMyUnits?.length > myUnits?.length) {
190
192
  const to = setTimeout(() => {
191
193
  carouselRef?.current?.snapToItem();
192
194
  setAction(Action.RESET_DELETE_UNIT_ACTION);
193
195
  }, 60);
194
196
  return () => clearTimeout(to);
195
197
  }
196
- }, [isDeleteUnitSuccessFully, setAction]);
198
+ }, [isDeleteUnitSuccessFully, setAction, previousMyUnits, myUnits]);
197
199
 
198
200
  return (
199
201
  <>
@@ -18,6 +18,7 @@ const DateTimeRangeChange = memo(
18
18
  selectStart,
19
19
  selectEnd,
20
20
  inline = true,
21
+ isWidgetOrder,
21
22
  }) => {
22
23
  const format = showTime ? DATE_TIME_FORMAT.DMY_HM : DATE_TIME_FORMAT.DMY;
23
24
  const mode = showTime ? 'datetime' : 'date';
@@ -77,20 +78,40 @@ const DateTimeRangeChange = memo(
77
78
  style={[styles.dateTimeView, !inline && styles.spaceBetween, style]}
78
79
  >
79
80
  <View style={[styles.wrap, !inline && styles.buttonWrap]}>
80
- <Text type="Label" color={Colors.Gray7}>
81
+ <Text
82
+ type="Label"
83
+ color={Colors.Gray7}
84
+ style={isWidgetOrder && styles.marginHorizontalEight}
85
+ >
81
86
  {t('from')}
82
87
  </Text>
83
- <DateTimeButton onPress={onStart} style={!inline && styles.button}>
88
+ <DateTimeButton
89
+ onPress={onStart}
90
+ style={
91
+ (isWidgetOrder && styles.widgetOrderButton) ||
92
+ (!inline && styles.button)
93
+ }
94
+ >
84
95
  <Text type={'Label'} color={Colors.Gray8} style={styles.txtTime}>
85
96
  {startDate.format(format)}
86
97
  </Text>
87
98
  </DateTimeButton>
88
99
  </View>
89
100
  <View style={[styles.wrap, !inline && styles.buttonWrap]}>
90
- <Text type="Label" color={Colors.Gray7}>
101
+ <Text
102
+ type="Label"
103
+ color={Colors.Gray7}
104
+ style={isWidgetOrder && styles.marginHorizontalEight}
105
+ >
91
106
  {t('to')}
92
107
  </Text>
93
- <DateTimeButton onPress={onEnd} style={!inline && styles.button}>
108
+ <DateTimeButton
109
+ onPress={onEnd}
110
+ style={
111
+ (isWidgetOrder && styles.widgetOrderButton) ||
112
+ (!inline && styles.button)
113
+ }
114
+ >
94
115
  <Text type={'Label'} color={Colors.Gray8} style={styles.txtTime}>
95
116
  {endDate.format(format)}
96
117
  </Text>
@@ -152,4 +173,11 @@ const styles = StyleSheet.create({
152
173
  marginHorizontal: 0,
153
174
  width: 150,
154
175
  },
176
+ widgetOrderButton: {
177
+ marginHorizontal: 0,
178
+ width: 110,
179
+ },
180
+ marginHorizontalEight: {
181
+ marginHorizontal: 8,
182
+ },
155
183
  });
@@ -16,7 +16,7 @@ const { standardizeHeight } = standardizeCameraScreenSize(
16
16
 
17
17
  const EmergencyDetail = memo(({ item }) => {
18
18
  const t = useTranslations();
19
- const { uri, preview_uri } = item?.configuration?.camera;
19
+ const { uri, preview_uri } = item?.configuration?.camera || {};
20
20
  const groupId = item?.configuration?.device?.group?.id;
21
21
  const isFocused = useIsFocused();
22
22
  const { listContacts, getListContacts } = useEmeragencyContacts();
@@ -1,4 +1,4 @@
1
- import React, { memo, useCallback, useState, useMemo } from 'react';
1
+ import React, { memo, useCallback, useState, useMemo, useEffect } from 'react';
2
2
  import { StyleSheet, View, Dimensions } from 'react-native';
3
3
  import moment from 'moment';
4
4
  import { useTranslations } from '../../hooks/Common/useTranslations';
@@ -31,95 +31,57 @@ const HistoryChart = memo(
31
31
  configuration,
32
32
  }) => {
33
33
  const t = useTranslations();
34
- const [chartOptions, setChartOptions] = useState({
35
- index: -1,
36
- showAll: true,
37
- });
34
+ const [price, setPrice] = useState(null);
35
+
38
36
  const [eventPicker, setEventPicker] = useState({
39
37
  showModalEnd: false,
40
38
  showModalStart: false,
41
39
  startTime: startDate ? startDate : moment().subtract(1, 'day'),
42
40
  endTime: endDate ? endDate : moment(),
43
41
  });
44
- const [price, setPrice] = useState(null);
45
-
46
- const selectStart = useCallback(
47
- (date) => {
48
- setEventPicker((state) => {
49
- if (typeof date === 'number') {
50
- return state;
51
- }
52
- if (moment(date) < state.endTime) {
53
- setStartDate(moment(date));
54
- return {
55
- ...state,
56
- showModalStart: false,
57
- startTime: date ? moment(date) : moment().valueOf(),
58
- };
59
- } else {
60
- setStartDate(moment(date));
61
- setEndDate(moment(date).add(1, 'day'));
62
- return {
63
- ...state,
64
- showModalStart: false,
65
- startTime: date ? moment(date) : moment().valueOf(),
66
- endTime: date ? moment(date).add(1, 'day') : moment().valueOf(),
67
- };
68
- }
69
- });
70
- onCancel();
71
- },
72
- [onCancel, setStartDate, setEndDate]
73
- );
74
-
75
- const selectEnd = useCallback(
76
- (date) => {
77
- setEventPicker((state) => {
78
- if (typeof date === 'number') {
79
- return state;
80
- }
81
- if (moment(date).add(1, 'day') > state.startTime) {
82
- setEndDate(moment(date));
83
- return {
84
- ...state,
85
- showModalEnd: false,
86
- endTime: date ? moment(date) : moment().valueOf(),
87
- };
88
- } else {
89
- setStartDate(moment(date).add(-1, 'day'));
90
- setEndDate(moment(date));
91
- return {
92
- ...state,
93
- showModalEnd: false,
94
- startTime: date
95
- ? moment(date).add(-1, 'day')
96
- : moment().valueOf(),
97
- endTime: date ? moment(date) : moment().valueOf(),
98
- };
99
- }
100
- });
101
- onCancel();
102
- },
103
- [onCancel, setStartDate, setEndDate]
104
- );
105
42
 
106
- const onCancel = useCallback(() => {
107
- setEventPicker((state) => ({
108
- ...state,
109
- showModalEnd: false,
110
- showModalStart: false,
111
- }));
112
- }, []);
113
- const onShowOneChart = useCallback(
114
- (index) => {
115
- if (index === chartOptions.index) {
116
- setChartOptions({ index, showAll: !chartOptions.showAll });
43
+ const selectStart = useCallback((date) => {
44
+ setEventPicker((state) => {
45
+ if (typeof date === 'number') {
46
+ return state;
47
+ }
48
+ if (moment(date) < state.endTime) {
49
+ return {
50
+ ...state,
51
+ showModalStart: false,
52
+ startTime: date ? moment(date) : moment().valueOf(),
53
+ };
117
54
  } else {
118
- setChartOptions({ index, showAll: false });
55
+ return {
56
+ ...state,
57
+ showModalStart: false,
58
+ startTime: date ? moment(date) : moment().valueOf(),
59
+ endTime: date ? moment(date).add(1, 'day') : moment().valueOf(),
60
+ };
119
61
  }
120
- },
121
- [chartOptions]
122
- );
62
+ });
63
+ }, []);
64
+
65
+ const selectEnd = useCallback((date) => {
66
+ setEventPicker((state) => {
67
+ if (typeof date === 'number') {
68
+ return state;
69
+ }
70
+ if (moment(date).add(1, 'day') > state.startTime) {
71
+ return {
72
+ ...state,
73
+ showModalEnd: false,
74
+ endTime: date ? moment(date) : moment().valueOf(),
75
+ };
76
+ }
77
+ return {
78
+ ...state,
79
+ showModalEnd: false,
80
+ startTime: date ? moment(date).add(-1, 'day') : moment().valueOf(),
81
+ endTime: date ? moment(date) : moment().valueOf(),
82
+ };
83
+ });
84
+ }, []);
123
85
 
124
86
  const onCalculateCost = useCallback(() => {
125
87
  setChartConfig((config) => ({
@@ -154,8 +116,15 @@ const HistoryChart = memo(
154
116
  if (configuration.type === 'horizontal_bar_chart') {
155
117
  return <HorizontalBarChart datas={datas} config={chartConfig} />;
156
118
  }
157
- // eslint-disable-next-line react-hooks/exhaustive-deps
158
- }, [configuration, datas, chartOptions, onShowOneChart]);
119
+ }, [chartConfig, configuration.type, datas]);
120
+
121
+ useEffect(() => {
122
+ setStartDate(eventPicker.startTime);
123
+ }, [eventPicker.startTime, setStartDate]);
124
+
125
+ useEffect(() => {
126
+ setEndDate(eventPicker.endTime);
127
+ }, [eventPicker.endTime, setEndDate]);
159
128
 
160
129
  return (
161
130
  <View style={style}>
@@ -5,7 +5,7 @@ import QualityIndicatorItem from '../WaterQualitySensor/QualityIndicatorsItem';
5
5
  import styles from './PMSensorIndicatorStyles';
6
6
  import { keyExtractor, roundNumber } from '../../../utils/Utils';
7
7
 
8
- const PMSensorIndicator = memo(({ data = [], style }) => {
8
+ const PMSensorIndicator = memo(({ data = [], style, isWidgetOrder }) => {
9
9
  const renderItem = useCallback(
10
10
  ({ item }) => {
11
11
  const getValue = ['', null, undefined, NaN].includes(item?.value)
@@ -28,7 +28,7 @@ const PMSensorIndicator = memo(({ data = [], style }) => {
28
28
  const isScrollMode = data.length > 3;
29
29
 
30
30
  return (
31
- <View style={styles.wrap}>
31
+ <View style={[styles.wrap, isWidgetOrder && styles.marginBottomZero]}>
32
32
  <FlatList
33
33
  bounces={false}
34
34
  numColumns={1}
@@ -36,6 +36,7 @@ const PMSensorIndicator = memo(({ data = [], style }) => {
36
36
  contentContainerStyle={[
37
37
  styles.standard,
38
38
  !isScrollMode && styles.centerItem,
39
+ isWidgetOrder && styles.marginBottomZero,
39
40
  ]}
40
41
  data={data}
41
42
  keyExtractor={keyExtractor}