@eohjsc/react-native-smart-city 0.3.10 → 0.3.13
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.
- package/index.js +2 -0
- package/package.json +1 -1
- package/src/commons/Action/ItemQuickAction.js +1 -1
- package/src/commons/ActionGroup/NumberUpDownActionTemplate.js +2 -0
- package/src/commons/ActionGroup/__test__/NumberUpDownTemplate.test.js +1 -1
- package/src/commons/ActionGroup/__test__/index.test.js +1 -1
- package/src/commons/Device/HistoryChart.js +2 -2
- package/src/commons/Device/ItemDevice.js +2 -2
- package/src/commons/OneTapTemplate/NumberUpDownActionTemplate.js +5 -1
- package/src/commons/SubUnit/Favorites/index.js +6 -2
- package/src/configs/API.js +4 -0
- package/src/configs/SCConfig.js +1 -1
- package/src/context/actionType.ts +5 -2
- package/src/context/mockStore.ts +17 -3
- package/src/context/reducer.ts +38 -4
- package/src/hooks/IoT/__test__/useValueEvaluation.test.js +58 -0
- package/src/hooks/IoT/index.js +2 -1
- package/src/hooks/IoT/useValueEvaluation.js +45 -0
- package/src/hooks/useReceiveNotifications.js +12 -18
- package/src/navigations/UnitStack.js +8 -0
- package/src/screens/AddNewAction/SelectAction.js +3 -2
- package/src/screens/AddNewAction/SetupSensor.js +3 -2
- package/src/screens/Device/detail.js +18 -27
- package/src/screens/Device/hooks/useEvaluateValue.js +97 -0
- package/src/screens/Device/hooks/useFavoriteDevice.js +2 -2
- package/src/screens/ScriptDetail/index.js +13 -3
- package/src/screens/Unit/Detail.js +10 -5
- package/src/screens/Unit/SelectAddress.js +1 -3
- package/src/screens/Unit/SelectDevices.js +158 -0
- package/src/screens/Unit/SelectDevicesStyles.js +40 -0
- package/src/screens/Unit/Summaries.js +1 -1
- package/src/screens/Unit/__test__/SelectAddress.test.js +90 -1
- package/src/screens/Unit/__test__/SelectDevices.test.js +110 -0
- package/src/screens/UnitSummary/components/RunningDevices/index.js +3 -1
- package/src/utils/Apis/axios.js +6 -0
- package/src/utils/I18n/translations/en.json +2 -0
- package/src/utils/I18n/translations/vi.json +2 -0
- package/src/utils/Route/index.js +1 -0
- package/src/utils/Validation.js +3 -0
package/index.js
CHANGED
|
@@ -17,6 +17,7 @@ import NotificationStack from './src/navigations/NotificationStack';
|
|
|
17
17
|
import MyPinnedSharedUnit from './src/commons/Dashboard/MyPinnedSharedUnit';
|
|
18
18
|
import MyUnit from './src/commons/Dashboard/MyUnit';
|
|
19
19
|
import SharedUnit from './src/commons/Unit/SharedUnit';
|
|
20
|
+
import { Action } from './src/context/actionType';
|
|
20
21
|
|
|
21
22
|
export {
|
|
22
23
|
AddSubUnitStack,
|
|
@@ -40,4 +41,5 @@ export {
|
|
|
40
41
|
SharedUnit,
|
|
41
42
|
MyUnit,
|
|
42
43
|
SCWrapper,
|
|
44
|
+
Action,
|
|
43
45
|
};
|
package/package.json
CHANGED
|
@@ -7,7 +7,7 @@ import { useRemoteControl } from '../../hooks/IoT';
|
|
|
7
7
|
import { useConfigGlobalState } from '../../iot/states';
|
|
8
8
|
import IconComponent from '../IconComponent';
|
|
9
9
|
|
|
10
|
-
const ItemQuickAction = memo(({ sensor, wrapperStyle, setStatus
|
|
10
|
+
const ItemQuickAction = memo(({ sensor, wrapperStyle, setStatus }) => {
|
|
11
11
|
const [isSendingCommand, setIsSendingCommand] = useState(false);
|
|
12
12
|
const [action, setAction] = useState(sensor.action);
|
|
13
13
|
// eslint-disable-next-line no-unused-vars
|
|
@@ -47,6 +47,8 @@ const NumberUpDownActionTemplate = ({ actionGroup, doAction, sensor }) => {
|
|
|
47
47
|
const configValue = configValues[config];
|
|
48
48
|
if (configValue !== null && configValue !== undefined) {
|
|
49
49
|
setValue(configValue);
|
|
50
|
+
} else {
|
|
51
|
+
setValue(valueDefault);
|
|
50
52
|
}
|
|
51
53
|
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
52
54
|
}, [JSON.stringify(configValues)]);
|
|
@@ -326,7 +326,7 @@ describe('Test NumberUpDownActionTemplate', () => {
|
|
|
326
326
|
});
|
|
327
327
|
const instance = wrapper.root;
|
|
328
328
|
const text = instance.findAllByType(ActivityIndicator);
|
|
329
|
-
expect(text).toHaveLength(
|
|
329
|
+
expect(text).toHaveLength(0);
|
|
330
330
|
});
|
|
331
331
|
test('action up sensor device type is GOOGLE_HOME', async () => {
|
|
332
332
|
const mockDoAction = jest.fn();
|
|
@@ -363,7 +363,7 @@ describe('Test ActionGroup', () => {
|
|
|
363
363
|
});
|
|
364
364
|
const instance = wrapper.root;
|
|
365
365
|
const activity = instance.findAllByType(ActivityIndicator);
|
|
366
|
-
expect(activity.length).toEqual(
|
|
366
|
+
expect(activity.length).toEqual(0);
|
|
367
367
|
});
|
|
368
368
|
|
|
369
369
|
test('render ActionGroup StatesGridActionTemplate', async () => {
|
|
@@ -234,7 +234,7 @@ const HistoryChart = memo(
|
|
|
234
234
|
)}
|
|
235
235
|
<DateTimePickerModal
|
|
236
236
|
isVisible={eventPicker.showModalStart}
|
|
237
|
-
date={eventPicker.startTime
|
|
237
|
+
date={eventPicker.startTime?._d}
|
|
238
238
|
mode={formatType || 'datetime'}
|
|
239
239
|
onConfirm={onConfirmStart}
|
|
240
240
|
onCancel={onCancel}
|
|
@@ -244,7 +244,7 @@ const HistoryChart = memo(
|
|
|
244
244
|
/>
|
|
245
245
|
<DateTimePickerModal
|
|
246
246
|
isVisible={eventPicker.showModalEnd}
|
|
247
|
-
date={eventPicker.endTime
|
|
247
|
+
date={eventPicker.endTime?._d}
|
|
248
248
|
mode={formatType || 'datetime'}
|
|
249
249
|
onConfirm={onConfirmEnd}
|
|
250
250
|
onCancel={onCancel}
|
|
@@ -82,7 +82,7 @@ const ItemDevice = memo(
|
|
|
82
82
|
const textConnected = isConnected
|
|
83
83
|
? t('connected')
|
|
84
84
|
: isConnecting
|
|
85
|
-
? ''
|
|
85
|
+
? t('connecting')
|
|
86
86
|
: t('disconnected');
|
|
87
87
|
|
|
88
88
|
return (
|
|
@@ -98,7 +98,7 @@ const ItemDevice = memo(
|
|
|
98
98
|
<TouchableOpacity onPress={goToSensorDisplay}>
|
|
99
99
|
<IconComponent icon={sensor.icon} iconKit={sensor.icon_kit} />
|
|
100
100
|
</TouchableOpacity>
|
|
101
|
-
<ItemQuickAction sensor={sensor} unit={unit} />
|
|
101
|
+
{!isConnecting && <ItemQuickAction sensor={sensor} unit={unit} />}
|
|
102
102
|
</View>
|
|
103
103
|
<TouchableOpacity onPress={goToSensorDisplay}>
|
|
104
104
|
<Text
|
|
@@ -19,16 +19,20 @@ const NumberUpDownActionTemplate = memo(({ data, onSelectAction }) => {
|
|
|
19
19
|
const { configuration, template, title } = data;
|
|
20
20
|
const { config, text_format, min_value, max_value, action } = configuration;
|
|
21
21
|
const [configValues] = useConfigGlobalState('configValues');
|
|
22
|
-
const [value, setValue] = useState(
|
|
22
|
+
const [value, setValue] = useState();
|
|
23
23
|
const [actionName, setActionName] = useState(null);
|
|
24
|
+
const valueDefault = 28;
|
|
24
25
|
|
|
25
26
|
useEffect(() => {
|
|
26
27
|
if (!config) {
|
|
28
|
+
setValue(valueDefault);
|
|
27
29
|
return;
|
|
28
30
|
}
|
|
29
31
|
const configValue = configValues[config];
|
|
30
32
|
if (configValue !== null && configValue !== undefined) {
|
|
31
33
|
setValue(configValue);
|
|
34
|
+
} else {
|
|
35
|
+
setValue(valueDefault);
|
|
32
36
|
}
|
|
33
37
|
}, [configValues, config]);
|
|
34
38
|
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import React from 'react';
|
|
2
2
|
import { View } from 'react-native';
|
|
3
|
+
import { useNavigation } from '@react-navigation/native';
|
|
3
4
|
import { useTranslations } from '../../../hooks/Common/useTranslations';
|
|
4
5
|
import { useSensorsStatus } from '../../../hooks/Common';
|
|
5
6
|
|
|
@@ -8,7 +9,7 @@ import ItemDevice from '../../Device/ItemDevice';
|
|
|
8
9
|
import ItemOneTap from '../OneTap/ItemOneTap';
|
|
9
10
|
import ItemAddNew from '../../Device/ItemAddNew';
|
|
10
11
|
import styles from './styles';
|
|
11
|
-
import
|
|
12
|
+
import Routes from '../../../utils/Route';
|
|
12
13
|
|
|
13
14
|
const SubUnitFavorites = ({
|
|
14
15
|
isOwner,
|
|
@@ -18,11 +19,14 @@ const SubUnitFavorites = ({
|
|
|
18
19
|
wrapItemStyle,
|
|
19
20
|
}) => {
|
|
20
21
|
const t = useTranslations();
|
|
22
|
+
const { navigate } = useNavigation();
|
|
21
23
|
|
|
22
24
|
const { getStatus, serverDown } = useSensorsStatus(unit, favoriteDevices);
|
|
23
25
|
|
|
24
26
|
const handleOnAddNew = () => {
|
|
25
|
-
|
|
27
|
+
navigate(Routes.SelectDevices, {
|
|
28
|
+
unitId: unit.id,
|
|
29
|
+
});
|
|
26
30
|
};
|
|
27
31
|
|
|
28
32
|
return (
|
package/src/configs/API.js
CHANGED
|
@@ -29,6 +29,9 @@ const API = {
|
|
|
29
29
|
CHANGE_OWNER: (id) => `/property_manager/units/${id}/change_owner/`,
|
|
30
30
|
FAVOURITE_DEVICES: (id) =>
|
|
31
31
|
`/property_manager/units/${id}/favourite_devices/`,
|
|
32
|
+
DEVICES: (id) => `/property_manager/units/${id}/devices/`,
|
|
33
|
+
ADD_DEVICES_TO_FAVORITES: (id) =>
|
|
34
|
+
`/property_manager/units/${id}/add_devices_to_favourites/`,
|
|
32
35
|
},
|
|
33
36
|
SUB_UNIT: {
|
|
34
37
|
REMOVE_SUB_UNIT: (unitId, id) =>
|
|
@@ -173,6 +176,7 @@ const API = {
|
|
|
173
176
|
`/notifications/eoh/?page=${page}&type=${type}`,
|
|
174
177
|
SET_READ: (id) => `/notifications/eoh/${id}/set_read/`,
|
|
175
178
|
},
|
|
179
|
+
VALUE_EVALUATIONS: () => '/property_manager/config_value_evaluations/',
|
|
176
180
|
EXTERNAL: {
|
|
177
181
|
GOOGLE_MAP: {
|
|
178
182
|
AUTO_COMPLETE:
|
package/src/configs/SCConfig.js
CHANGED
|
@@ -112,7 +112,7 @@ export class SCConfig {
|
|
|
112
112
|
|
|
113
113
|
export const initSCConfig = (config) => {
|
|
114
114
|
api.setBaseURL(config.apiRoot ?? SCDefaultConfig.apiRoot);
|
|
115
|
-
LocaleConfig.defaultLocale = config.language;
|
|
115
|
+
LocaleConfig.defaultLocale = config.language ?? SCConfig.language;
|
|
116
116
|
SCConfig.language = config.language ?? SCConfig.language;
|
|
117
117
|
SCConfig.apiRoot = config.apiRoot ?? SCDefaultConfig.apiRoot;
|
|
118
118
|
SCConfig.GOOGLE_MAP_API_KEY =
|
|
@@ -12,14 +12,16 @@ export const Action = {
|
|
|
12
12
|
CAMERA_STATUS_CHANGE: 'CAMERA_STATUS_CHANGE',
|
|
13
13
|
CLOSE_ALL_CAMERA: 'CLOSE_ALL_CAMERA',
|
|
14
14
|
SET_FAVORITE_DEVICES: 'SET_FAVORITE_DEVICES',
|
|
15
|
-
|
|
16
|
-
|
|
15
|
+
ADD_DEVICES_TO_FAVORITES: 'ADD_DEVICE_TO_FAVORITES',
|
|
16
|
+
REMOVE_DEVICES_FROM_FAVORITES: 'REMOVE_DEVICE_FROM_FAVORITES',
|
|
17
17
|
SET_STARRED_SCRIPTS: 'SET_STARRED_SCRIPTS',
|
|
18
18
|
STAR_SCRIPT: 'STAR_SCRIPT',
|
|
19
19
|
UNSTAR_SCRIPT: 'UNSTAR_SCRIPT',
|
|
20
20
|
CONNECTING_GOOGLE_HOME: 'CONNECTING_GOOGLE_HOME',
|
|
21
21
|
SET_GOOGLE_HOME_CONNECTIONS: 'SET_GOOGLE_HOME_CONNECTIONS',
|
|
22
22
|
CHANGE_GOOGLE_HOME_CONN_STATE: 'CHANGE_GOOGLE_HOME_CONN_STATE',
|
|
23
|
+
UPDATE_VALUE_EVALUATIONS: 'UPDATE_VALUE_EVALUATIONS',
|
|
24
|
+
ON_RECEIVE_NOTIFICATION: 'ON_RECEIVE_NOTIFICATION',
|
|
23
25
|
};
|
|
24
26
|
|
|
25
27
|
export type AuthData = {
|
|
@@ -76,6 +78,7 @@ export type AppType = {
|
|
|
76
78
|
isBluetoothEnabled: boolean;
|
|
77
79
|
isNetworkConnected: boolean;
|
|
78
80
|
camera_opened: any[];
|
|
81
|
+
notificationData: any;
|
|
79
82
|
};
|
|
80
83
|
|
|
81
84
|
export type IoTType = {
|
package/src/context/mockStore.ts
CHANGED
|
@@ -31,11 +31,23 @@ export const mockDataStore: ContextData = {
|
|
|
31
31
|
automate: {
|
|
32
32
|
starredScriptIds: [],
|
|
33
33
|
},
|
|
34
|
+
app: {
|
|
35
|
+
isFirstOpenCamera: true,
|
|
36
|
+
isLavidaSource: false,
|
|
37
|
+
isConnectWifiGateway: false,
|
|
38
|
+
isBluetoothEnabled: true,
|
|
39
|
+
isNetworkConnected: true,
|
|
40
|
+
camera_opened: [],
|
|
41
|
+
},
|
|
34
42
|
iot: {
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
43
|
+
googlehome: {
|
|
44
|
+
isFirstTimeConnect: true,
|
|
45
|
+
isConnecting: false,
|
|
46
|
+
connections: {},
|
|
47
|
+
},
|
|
38
48
|
},
|
|
49
|
+
valueEvaluations: {},
|
|
50
|
+
fetchedValueEvaluationUnits: [],
|
|
39
51
|
};
|
|
40
52
|
|
|
41
53
|
export const mockSCStore = (data: ContextData): ContextData => {
|
|
@@ -83,5 +95,7 @@ export const mockSCStore = (data: ContextData): ContextData => {
|
|
|
83
95
|
connections: {},
|
|
84
96
|
},
|
|
85
97
|
},
|
|
98
|
+
valueEvaluations: {},
|
|
99
|
+
fetchedValueEvaluationUnits: [],
|
|
86
100
|
};
|
|
87
101
|
};
|
package/src/context/reducer.ts
CHANGED
|
@@ -12,7 +12,7 @@ import {
|
|
|
12
12
|
AppType,
|
|
13
13
|
IoTType,
|
|
14
14
|
} from './actionType';
|
|
15
|
-
import { uniq } from 'lodash';
|
|
15
|
+
import { uniq, reduce } from 'lodash';
|
|
16
16
|
|
|
17
17
|
export type ContextData = {
|
|
18
18
|
auth: AuthData;
|
|
@@ -24,6 +24,8 @@ export type ContextData = {
|
|
|
24
24
|
automate: AutomateType;
|
|
25
25
|
app: AppType;
|
|
26
26
|
iot: IoTType;
|
|
27
|
+
valueEvaluations: {};
|
|
28
|
+
fetchedValueEvaluationUnits: Array<number>;
|
|
27
29
|
};
|
|
28
30
|
|
|
29
31
|
export type Action = {
|
|
@@ -57,6 +59,7 @@ export const initialState = {
|
|
|
57
59
|
isBluetoothEnabled: false,
|
|
58
60
|
isNetworkConnected: false,
|
|
59
61
|
camera_opened: [],
|
|
62
|
+
notificationData: null,
|
|
60
63
|
},
|
|
61
64
|
iot: {
|
|
62
65
|
googlehome: {
|
|
@@ -65,6 +68,8 @@ export const initialState = {
|
|
|
65
68
|
connections: {},
|
|
66
69
|
},
|
|
67
70
|
},
|
|
71
|
+
valueEvaluations: {},
|
|
72
|
+
fetchedValueEvaluationUnits: [],
|
|
68
73
|
};
|
|
69
74
|
|
|
70
75
|
export const reducer = (currentState: ContextData, action: Action) => {
|
|
@@ -201,7 +206,7 @@ export const reducer = (currentState: ContextData, action: Action) => {
|
|
|
201
206
|
favoriteDeviceIds: payload,
|
|
202
207
|
},
|
|
203
208
|
};
|
|
204
|
-
case Action.
|
|
209
|
+
case Action.ADD_DEVICES_TO_FAVORITES:
|
|
205
210
|
return {
|
|
206
211
|
...currentState,
|
|
207
212
|
unit: {
|
|
@@ -211,13 +216,13 @@ export const reducer = (currentState: ContextData, action: Action) => {
|
|
|
211
216
|
),
|
|
212
217
|
},
|
|
213
218
|
};
|
|
214
|
-
case Action.
|
|
219
|
+
case Action.REMOVE_DEVICES_FROM_FAVORITES:
|
|
215
220
|
return {
|
|
216
221
|
...currentState,
|
|
217
222
|
unit: {
|
|
218
223
|
...currentState.unit,
|
|
219
224
|
favoriteDeviceIds: currentState.unit.favoriteDeviceIds.filter(
|
|
220
|
-
(deviceId) => deviceId
|
|
225
|
+
(deviceId) => !payload.includes(deviceId)
|
|
221
226
|
),
|
|
222
227
|
},
|
|
223
228
|
};
|
|
@@ -294,6 +299,35 @@ export const reducer = (currentState: ContextData, action: Action) => {
|
|
|
294
299
|
},
|
|
295
300
|
};
|
|
296
301
|
|
|
302
|
+
case Action.UPDATE_VALUE_EVALUATIONS:
|
|
303
|
+
// eslint-disable-next-line no-case-declarations
|
|
304
|
+
const { data, unitId } = payload;
|
|
305
|
+
return {
|
|
306
|
+
...currentState,
|
|
307
|
+
fetchedValueEvaluationUnits:
|
|
308
|
+
currentState.fetchedValueEvaluationUnits.indexOf(unitId) !== -1
|
|
309
|
+
? currentState.fetchedValueEvaluationUnits
|
|
310
|
+
: [...currentState.fetchedValueEvaluationUnits, unitId],
|
|
311
|
+
valueEvaluations: reduce(
|
|
312
|
+
data,
|
|
313
|
+
(dict, item) => {
|
|
314
|
+
// eslint-disable-next-line no-param-reassign
|
|
315
|
+
dict[item.config] = item;
|
|
316
|
+
return dict;
|
|
317
|
+
},
|
|
318
|
+
currentState.valueEvaluations
|
|
319
|
+
),
|
|
320
|
+
};
|
|
321
|
+
|
|
322
|
+
case Action.ON_RECEIVE_NOTIFICATION:
|
|
323
|
+
return {
|
|
324
|
+
...currentState,
|
|
325
|
+
app: {
|
|
326
|
+
...currentState.app,
|
|
327
|
+
notificationData: payload,
|
|
328
|
+
},
|
|
329
|
+
};
|
|
330
|
+
|
|
297
331
|
default:
|
|
298
332
|
return currentState;
|
|
299
333
|
}
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { renderHook } from '@testing-library/react-hooks';
|
|
3
|
+
import MockAdapter from 'axios-mock-adapter';
|
|
4
|
+
import { SCProvider } from '../../../context';
|
|
5
|
+
import { mockSCStore } from '../../../context/mockStore';
|
|
6
|
+
import { useValueEvaluations } from '../index';
|
|
7
|
+
import api from '../../../utils/Apis/axios';
|
|
8
|
+
import { API } from '../../../configs';
|
|
9
|
+
|
|
10
|
+
const mock = new MockAdapter(api.axiosInstance);
|
|
11
|
+
|
|
12
|
+
const mockedSetAction = jest.fn();
|
|
13
|
+
|
|
14
|
+
const wrapper = ({ children }) => <SCProvider>{children}</SCProvider>;
|
|
15
|
+
|
|
16
|
+
const mockUseContext = jest.fn().mockImplementation(() => ({
|
|
17
|
+
stateData: mockSCStore({}),
|
|
18
|
+
setAction: mockedSetAction,
|
|
19
|
+
}));
|
|
20
|
+
|
|
21
|
+
React.useContext = mockUseContext;
|
|
22
|
+
|
|
23
|
+
describe('Test useValueEvaluation', () => {
|
|
24
|
+
beforeEach(() => {
|
|
25
|
+
mock.resetHistory();
|
|
26
|
+
});
|
|
27
|
+
|
|
28
|
+
it('test unitId null', async () => {
|
|
29
|
+
renderHook(() => useValueEvaluations(null), {
|
|
30
|
+
wrapper,
|
|
31
|
+
});
|
|
32
|
+
expect(mock.history.get.length).toBe(0);
|
|
33
|
+
});
|
|
34
|
+
|
|
35
|
+
it('test unitId not null request success', async () => {
|
|
36
|
+
mock.onGet(API.VALUE_EVALUATIONS()).replyOnce(200, {
|
|
37
|
+
results: [],
|
|
38
|
+
next: 'link',
|
|
39
|
+
});
|
|
40
|
+
mock.onGet(API.VALUE_EVALUATIONS()).replyOnce(200, {
|
|
41
|
+
results: [],
|
|
42
|
+
});
|
|
43
|
+
renderHook(() => useValueEvaluations(1), {
|
|
44
|
+
wrapper,
|
|
45
|
+
});
|
|
46
|
+
expect(mock.history.get.length).toBe(1);
|
|
47
|
+
});
|
|
48
|
+
|
|
49
|
+
it('test request failed', async () => {
|
|
50
|
+
mock.onGet(API.VALUE_EVALUATIONS()).replyOnce(400, {
|
|
51
|
+
results: [],
|
|
52
|
+
});
|
|
53
|
+
renderHook(() => useValueEvaluations(1), {
|
|
54
|
+
wrapper,
|
|
55
|
+
});
|
|
56
|
+
expect(mock.history.get.length).toBe(1);
|
|
57
|
+
});
|
|
58
|
+
});
|
package/src/hooks/IoT/index.js
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import useGGHomeConnection from './useGGHomeConnection';
|
|
2
2
|
import useRemoteControl from './useRemoteControl';
|
|
3
|
+
import useValueEvaluations from './useValueEvaluation';
|
|
3
4
|
|
|
4
|
-
export { useGGHomeConnection, useRemoteControl };
|
|
5
|
+
export { useGGHomeConnection, useRemoteControl, useValueEvaluations };
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
import { useCallback, useContext, useEffect } from 'react';
|
|
2
|
+
import { API } from '../../configs';
|
|
3
|
+
import { SCContext, useSCContextSelector } from '../../context';
|
|
4
|
+
import { Action } from '../../context/actionType';
|
|
5
|
+
import { axiosGet } from '../../utils/Apis/axios';
|
|
6
|
+
|
|
7
|
+
const useValueEvaluations = (unitId) => {
|
|
8
|
+
const { setAction } = useContext(SCContext);
|
|
9
|
+
|
|
10
|
+
const fetchConfigValueEvaluations = useCallback(
|
|
11
|
+
async (page = 1) => {
|
|
12
|
+
if (!unitId) {
|
|
13
|
+
return;
|
|
14
|
+
}
|
|
15
|
+
const params = new URLSearchParams();
|
|
16
|
+
params.append('config__end_device__station__unit', unitId);
|
|
17
|
+
params.append('page', page);
|
|
18
|
+
const { success, data } = await axiosGet(API.VALUE_EVALUATIONS(), {
|
|
19
|
+
params,
|
|
20
|
+
});
|
|
21
|
+
if (success) {
|
|
22
|
+
setAction(Action.UPDATE_VALUE_EVALUATIONS, {
|
|
23
|
+
unitId,
|
|
24
|
+
data: data.results,
|
|
25
|
+
});
|
|
26
|
+
if (data.next) {
|
|
27
|
+
await fetchConfigValueEvaluations(page + 1);
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
},
|
|
31
|
+
[unitId, setAction]
|
|
32
|
+
);
|
|
33
|
+
|
|
34
|
+
const fetchedValueEvaluationUnits = useSCContextSelector((state) => {
|
|
35
|
+
return state.fetchedValueEvaluationUnits || [];
|
|
36
|
+
});
|
|
37
|
+
|
|
38
|
+
useEffect(() => {
|
|
39
|
+
if (!(fetchedValueEvaluationUnits.indexOf(unitId) !== -1)) {
|
|
40
|
+
fetchConfigValueEvaluations();
|
|
41
|
+
}
|
|
42
|
+
}, [unitId, fetchConfigValueEvaluations, fetchedValueEvaluationUnits]);
|
|
43
|
+
};
|
|
44
|
+
|
|
45
|
+
export default useValueEvaluations;
|
|
@@ -1,26 +1,20 @@
|
|
|
1
|
-
import { useEffect, useState
|
|
2
|
-
import
|
|
1
|
+
import { useEffect, useState } from 'react';
|
|
2
|
+
import { useSCContextSelector } from '../context';
|
|
3
3
|
|
|
4
4
|
const useReceiveNotifications = (callBack) => {
|
|
5
|
-
const [
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
setDataNofitication(additionalData);
|
|
10
|
-
}, []);
|
|
5
|
+
const [dataNotification, setDataNotification] = useState(null);
|
|
6
|
+
const notificationData = useSCContextSelector(
|
|
7
|
+
(state) => state.app.notificationData
|
|
8
|
+
);
|
|
11
9
|
|
|
12
10
|
useEffect(() => {
|
|
13
|
-
|
|
14
|
-
(
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
callBack && callBack();
|
|
19
|
-
}
|
|
20
|
-
);
|
|
21
|
-
}, [callBack, onReceived]);
|
|
11
|
+
if (notificationData) {
|
|
12
|
+
setDataNotification(notificationData);
|
|
13
|
+
callBack && callBack();
|
|
14
|
+
}
|
|
15
|
+
}, [callBack, notificationData]);
|
|
22
16
|
|
|
23
|
-
return {
|
|
17
|
+
return { dataNotification };
|
|
24
18
|
};
|
|
25
19
|
|
|
26
20
|
export default useReceiveNotifications;
|
|
@@ -51,6 +51,7 @@ import EmergencySetting from '../screens/EmergencySetting';
|
|
|
51
51
|
import ConfirmUnitDeletion from '../screens/ConfirmUnitDeletion';
|
|
52
52
|
import InfoMemberUnit from '../screens/Sharing/InfoMemberUnit';
|
|
53
53
|
import EnterPassword from '../screens/EnterPassword';
|
|
54
|
+
import SelectDevices from '../screens/Unit/SelectDevices';
|
|
54
55
|
import { HanetCameraStack } from './HanetCameraStack';
|
|
55
56
|
import { axiosGet } from '../utils/Apis/axios';
|
|
56
57
|
import { API } from '../configs';
|
|
@@ -400,6 +401,13 @@ export const UnitStack = memo((props) => {
|
|
|
400
401
|
headerShown: false,
|
|
401
402
|
}}
|
|
402
403
|
/>
|
|
404
|
+
<Stack.Screen
|
|
405
|
+
name={Route.SelectDevices}
|
|
406
|
+
component={SelectDevices}
|
|
407
|
+
options={{
|
|
408
|
+
headerShown: false,
|
|
409
|
+
}}
|
|
410
|
+
/>
|
|
403
411
|
</Stack.Navigator>
|
|
404
412
|
);
|
|
405
413
|
});
|
|
@@ -134,6 +134,7 @@ const SelectAction = memo(({ route }) => {
|
|
|
134
134
|
value: itemTemp?.value,
|
|
135
135
|
config_id: itemTemp?.id,
|
|
136
136
|
config_name: itemTemp?.name,
|
|
137
|
+
sensor_type: itemTemp?.sensor_type,
|
|
137
138
|
},
|
|
138
139
|
scriptName,
|
|
139
140
|
});
|
|
@@ -300,9 +301,9 @@ const SelectAction = memo(({ route }) => {
|
|
|
300
301
|
if (isNumberValue) {
|
|
301
302
|
return `${item?.name} ${
|
|
302
303
|
item?.title ? item.title : t('is_below') + ' (<)'
|
|
303
|
-
}
|
|
304
|
+
} ${item?.value} ${item?.unit}`;
|
|
304
305
|
}
|
|
305
|
-
return t(stateConditionData?.stateValue[item?.value
|
|
306
|
+
return t(stateConditionData?.stateValue[item?.value]);
|
|
306
307
|
},
|
|
307
308
|
[t]
|
|
308
309
|
);
|
|
@@ -56,7 +56,7 @@ const SetUpSensor = () => {
|
|
|
56
56
|
modalNumberConditionData[0]
|
|
57
57
|
);
|
|
58
58
|
const [itemActiveStateModal, setItemActiveStateModal] = useState(
|
|
59
|
-
modalStateConditionData?.stateValue[
|
|
59
|
+
modalStateConditionData?.stateValue[1]
|
|
60
60
|
);
|
|
61
61
|
const [value, setValue] = useState(parseFloat(item?.value || 0));
|
|
62
62
|
const [minimum] = useState(isHasLimit ? parseInt(item?.range_min, 10) : 0);
|
|
@@ -226,7 +226,8 @@ const SetUpSensor = () => {
|
|
|
226
226
|
<View style={styles.modalContent}>
|
|
227
227
|
{(isNumberValue
|
|
228
228
|
? modalNumberConditionData
|
|
229
|
-
:
|
|
229
|
+
: /* Disable picking not_active/not_dectect option -> temporaly remove not_acitve option */
|
|
230
|
+
modalStateConditionData?.stateValue.slice(1)
|
|
230
231
|
).map((i, index) => (
|
|
231
232
|
<>
|
|
232
233
|
<TouchableOpacity
|
|
@@ -44,12 +44,13 @@ import {
|
|
|
44
44
|
useBoolean,
|
|
45
45
|
useGGHomeDeviceConnected,
|
|
46
46
|
} from '../../hooks/Common';
|
|
47
|
-
import { useGGHomeConnection } from '../../hooks/IoT';
|
|
47
|
+
import { useGGHomeConnection, useValueEvaluations } from '../../hooks/IoT';
|
|
48
48
|
import { SensorDisplayItem } from './components/SensorDisplayItem';
|
|
49
49
|
import { useSCContextSelector } from '../../context';
|
|
50
50
|
import { EmergencyCountdown } from './components/EmergencyCountdown';
|
|
51
51
|
import { SensorConnectStatusViewHeader } from './components/SensorConnectStatusViewHeader';
|
|
52
52
|
import { useDisconnectedDevice } from './hooks/useDisconnectedDevice';
|
|
53
|
+
import { useEvaluateValue } from './hooks/useEvaluateValue';
|
|
53
54
|
import { Card } from '../../commons/CardShadow';
|
|
54
55
|
import PreventAccess from '../../commons/PreventAccess';
|
|
55
56
|
import { notImplemented } from '../../utils/Utils';
|
|
@@ -117,6 +118,8 @@ const DeviceDetail = ({ route }) => {
|
|
|
117
118
|
});
|
|
118
119
|
}, [display]);
|
|
119
120
|
|
|
121
|
+
useValueEvaluations(unitId || unitData?.id);
|
|
122
|
+
|
|
120
123
|
useDisconnectedDevice(sensorName, isDeviceHasBle, serverDown);
|
|
121
124
|
|
|
122
125
|
const isShowSetupEmergencyContact = useMemo(
|
|
@@ -438,21 +441,32 @@ const DeviceDetail = ({ route }) => {
|
|
|
438
441
|
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
439
442
|
}, [sensor, unit, isNetworkConnected, fetchDataDeviceDetail]);
|
|
440
443
|
|
|
444
|
+
const evaluateValue = useEvaluateValue();
|
|
445
|
+
|
|
441
446
|
const getData = useCallback(
|
|
442
447
|
(item) => {
|
|
443
448
|
if (!item.configuration) {
|
|
444
449
|
return;
|
|
445
450
|
}
|
|
446
451
|
const data = item.configuration.configs.map((config) => {
|
|
447
|
-
const
|
|
448
|
-
|
|
452
|
+
const configValue = configValues[config.id];
|
|
453
|
+
const displayValue = displayValues.find((k) => k.id === config.id);
|
|
454
|
+
if (!configValue && !displayValue) {
|
|
449
455
|
return;
|
|
450
456
|
}
|
|
457
|
+
const value = configValue
|
|
458
|
+
? {
|
|
459
|
+
id: config.id,
|
|
460
|
+
value: configValue,
|
|
461
|
+
evaluate: evaluateValue(config.id, configValue),
|
|
462
|
+
}
|
|
463
|
+
: displayValue;
|
|
464
|
+
|
|
451
465
|
return { ...config, ...value };
|
|
452
466
|
});
|
|
453
467
|
return data.filter((value) => value);
|
|
454
468
|
},
|
|
455
|
-
[displayValues]
|
|
469
|
+
[configValues, displayValues, evaluateValue]
|
|
456
470
|
);
|
|
457
471
|
|
|
458
472
|
useEffect(() => {
|
|
@@ -509,29 +523,6 @@ const DeviceDetail = ({ route }) => {
|
|
|
509
523
|
}
|
|
510
524
|
}, [sensor, display]);
|
|
511
525
|
|
|
512
|
-
useEffect(() => {
|
|
513
|
-
setDisplayValues((currentDisplayValues) => {
|
|
514
|
-
for (const [configId, value] of Object.entries(configValues)) {
|
|
515
|
-
const intId = parseInt(configId, 10);
|
|
516
|
-
const index = currentDisplayValues.findIndex(
|
|
517
|
-
(element) => element.id === intId
|
|
518
|
-
);
|
|
519
|
-
|
|
520
|
-
const item = currentDisplayValues[index];
|
|
521
|
-
if (index !== -1) {
|
|
522
|
-
currentDisplayValues[index].value = value;
|
|
523
|
-
currentDisplayValues[index].evaluate = item.evaluate;
|
|
524
|
-
} else {
|
|
525
|
-
currentDisplayValues.push({
|
|
526
|
-
id: intId,
|
|
527
|
-
value: value,
|
|
528
|
-
});
|
|
529
|
-
}
|
|
530
|
-
}
|
|
531
|
-
return currentDisplayValues;
|
|
532
|
-
});
|
|
533
|
-
}, [configValues, setDisplayValues]);
|
|
534
|
-
|
|
535
526
|
const isShowEmergencyResolve =
|
|
536
527
|
display.items.filter(
|
|
537
528
|
(item) =>
|