@eohjsc/react-native-smart-city 0.3.70 → 0.3.71
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/package.json +1 -1
- package/src/commons/ActionGroup/NumberUpDownActionTemplate.js +0 -1
- package/src/commons/ActionGroup/OnOffTemplate/index.js +22 -11
- package/src/commons/ActionGroup/OptionsDropdownActionTemplate.js +19 -13
- package/src/commons/ActionGroup/SliderRangeTemplate.js +1 -1
- package/src/commons/ActionGroup/ThreeButtonTemplate.js +9 -4
- package/src/commons/ActionGroup/__test__/OptionsDropdownTemplate.test.js +1 -5
- package/src/commons/ActionGroup/__test__/SliderRangeTemplate.test.js +2 -2
- package/src/commons/Device/RainningSensor/CurrentRainSensor.js +7 -16
- package/src/configs/SCConfig.js +1 -0
- package/src/iot/RemoteControl/HomeAssistant.js +2 -11
- package/src/iot/RemoteControl/__test__/HomeAssistant.test.js +1 -33
- package/src/utils/I18n/translations/en.json +2 -1
- package/src/utils/I18n/translations/vi.json +2 -1
package/package.json
CHANGED
|
@@ -56,7 +56,7 @@ const OnOffTemplate = memo(({ actionGroup = {}, doAction, sensor }) => {
|
|
|
56
56
|
const updateStatusFromPusher = useCallback(() => {
|
|
57
57
|
setTimeout(() => {
|
|
58
58
|
setTempIsOn(temp);
|
|
59
|
-
},
|
|
59
|
+
}, 3000);
|
|
60
60
|
}, []);
|
|
61
61
|
|
|
62
62
|
const triggerAction = useCallback(async () => {
|
|
@@ -64,28 +64,39 @@ const OnOffTemplate = memo(({ actionGroup = {}, doAction, sensor }) => {
|
|
|
64
64
|
if (!action_data) {
|
|
65
65
|
return;
|
|
66
66
|
}
|
|
67
|
-
let data
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
}
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
67
|
+
let data;
|
|
68
|
+
if (sensor?.device_type === DEVICE_TYPE.GOOGLE_HOME) {
|
|
69
|
+
data = null;
|
|
70
|
+
} else {
|
|
71
|
+
data = {
|
|
72
|
+
value: isOn ? 0 : 1,
|
|
73
|
+
state: isOn ? 0 : 1, // todo Bang remove this for Zigbee
|
|
74
|
+
};
|
|
75
|
+
if (allow_config_store_value && config) {
|
|
76
|
+
data.config_id = config;
|
|
77
|
+
data.config_value = data.value;
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
if (sensor?.device_type === DEVICE_TYPE.LG_THINQ) {
|
|
81
|
+
setTempIsOn((prev) => !prev);
|
|
74
82
|
}
|
|
75
|
-
setTempIsOn((prev) => !prev);
|
|
76
83
|
await doAction(action_data, data);
|
|
77
84
|
updateStatusFromPusher(); // todo Bang read about this magic
|
|
78
85
|
|
|
79
|
-
sensor?.is_managed_by_backend &&
|
|
86
|
+
sensor?.is_managed_by_backend &&
|
|
87
|
+
config &&
|
|
88
|
+
sensor.device_type === DEVICE_TYPE.LG_THINQ &&
|
|
89
|
+
watchMultiConfigs([config]);
|
|
80
90
|
}, [
|
|
81
91
|
isOn,
|
|
82
92
|
action_off_data,
|
|
83
93
|
action_on_data,
|
|
94
|
+
sensor?.device_type,
|
|
95
|
+
sensor?.is_managed_by_backend,
|
|
84
96
|
allow_config_store_value,
|
|
85
97
|
config,
|
|
86
98
|
doAction,
|
|
87
99
|
updateStatusFromPusher,
|
|
88
|
-
sensor?.is_managed_by_backend,
|
|
89
100
|
]);
|
|
90
101
|
|
|
91
102
|
useUnwatchLGDeviceConfigControl(sensor, [config]);
|
|
@@ -9,7 +9,7 @@ import { useDropdownAction } from './hooks/useDropdownAction';
|
|
|
9
9
|
import { useConfigGlobalState } from '../../iot/states';
|
|
10
10
|
import { useUnwatchLGDeviceConfigControl } from '../../hooks/IoT';
|
|
11
11
|
import styles from './OptionsDropdownActionTemplateStyle';
|
|
12
|
-
import { AccessibilityLabel } from '../../configs/Constants';
|
|
12
|
+
import { AccessibilityLabel, DEVICE_TYPE } from '../../configs/Constants';
|
|
13
13
|
import IconComponent from '../../commons/IconComponent';
|
|
14
14
|
import { useTranslations } from '../../hooks/Common/useTranslations';
|
|
15
15
|
import SvgDoorState from '../../../assets/images/Device/door-state.svg';
|
|
@@ -70,25 +70,31 @@ const OptionsDropdownActionTemplate = ({
|
|
|
70
70
|
const newOption = options[selectedIndex];
|
|
71
71
|
const value = getOptionValue(newOption, allow_config_store_value);
|
|
72
72
|
|
|
73
|
-
let data
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
73
|
+
let data;
|
|
74
|
+
if (sensor?.device_type === DEVICE_TYPE.GOOGLE_HOME) {
|
|
75
|
+
data = value;
|
|
76
|
+
} else {
|
|
77
|
+
data = {
|
|
78
|
+
value: newOption?.value_int, // todo Bang keep only this
|
|
79
|
+
level: value,
|
|
80
|
+
key_code: newOption?.value_int,
|
|
81
|
+
};
|
|
82
|
+
if (allow_config_store_value && config) {
|
|
83
|
+
data.config_id = config;
|
|
84
|
+
data.config_value = newOption?.value_int;
|
|
85
|
+
}
|
|
81
86
|
}
|
|
82
87
|
doAction(action_data, data);
|
|
83
88
|
hideAlertAction();
|
|
84
89
|
}, [
|
|
85
|
-
|
|
90
|
+
options,
|
|
91
|
+
selectedIndex,
|
|
86
92
|
allow_config_store_value,
|
|
87
|
-
|
|
93
|
+
sensor.device_type,
|
|
94
|
+
config,
|
|
88
95
|
doAction,
|
|
96
|
+
action_data,
|
|
89
97
|
hideAlertAction,
|
|
90
|
-
options,
|
|
91
|
-
selectedIndex,
|
|
92
98
|
]);
|
|
93
99
|
|
|
94
100
|
useUnwatchLGDeviceConfigControl(sensor, [configuration.config]);
|
|
@@ -35,7 +35,7 @@ const SliderRangeTemplate = memo(({ actionGroup = {}, doAction, sensor }) => {
|
|
|
35
35
|
async (value) => {
|
|
36
36
|
await doAction(
|
|
37
37
|
configuration?.action_brightness_data || configuration?.action_data,
|
|
38
|
-
JSON.stringify({ value_brness: value })
|
|
38
|
+
JSON.stringify({ value_brness: value, value: value })
|
|
39
39
|
);
|
|
40
40
|
},
|
|
41
41
|
[
|
|
@@ -20,6 +20,9 @@ const ThreeButtonTemplate = memo(({ actionGroup, doAction }) => {
|
|
|
20
20
|
icon1,
|
|
21
21
|
icon2,
|
|
22
22
|
icon3,
|
|
23
|
+
icon_kit1_data,
|
|
24
|
+
icon_kit2_data,
|
|
25
|
+
icon_kit3_data,
|
|
23
26
|
text_door_lock,
|
|
24
27
|
is_display_lock,
|
|
25
28
|
} = configuration || {};
|
|
@@ -28,7 +31,7 @@ const ThreeButtonTemplate = memo(({ actionGroup, doAction }) => {
|
|
|
28
31
|
return icon === 'stop' ? (
|
|
29
32
|
<View style={styles.squareStop} />
|
|
30
33
|
) : (
|
|
31
|
-
<IconComponent icon={
|
|
34
|
+
<IconComponent icon={icon} iconSize={30} />
|
|
32
35
|
);
|
|
33
36
|
};
|
|
34
37
|
const onButton1Press = useCallback(() => {
|
|
@@ -91,7 +94,7 @@ const ThreeButtonTemplate = memo(({ actionGroup, doAction }) => {
|
|
|
91
94
|
underlayColor={Colors.Gray2}
|
|
92
95
|
>
|
|
93
96
|
<View style={styles.imageButton}>
|
|
94
|
-
<IconComponent icon={icon1} iconSize={30} />
|
|
97
|
+
<IconComponent icon={icon_kit1_data?.icon || icon1} iconSize={30} />
|
|
95
98
|
</View>
|
|
96
99
|
<Text style={styles.text}>{text1}</Text>
|
|
97
100
|
</TouchableOpacity>
|
|
@@ -102,7 +105,9 @@ const ThreeButtonTemplate = memo(({ actionGroup, doAction }) => {
|
|
|
102
105
|
onPress={onButton2Press}
|
|
103
106
|
underlayColor={Colors.Gray2}
|
|
104
107
|
>
|
|
105
|
-
<View style={styles.imageButton}>
|
|
108
|
+
<View style={styles.imageButton}>
|
|
109
|
+
{iconCustom(icon_kit2_data?.icon || icon2)}
|
|
110
|
+
</View>
|
|
106
111
|
<Text style={styles.text}>{text2}</Text>
|
|
107
112
|
</TouchableOpacity>
|
|
108
113
|
|
|
@@ -113,7 +118,7 @@ const ThreeButtonTemplate = memo(({ actionGroup, doAction }) => {
|
|
|
113
118
|
underlayColor={Colors.Gray2}
|
|
114
119
|
>
|
|
115
120
|
<View style={styles.imageButton}>
|
|
116
|
-
<IconComponent icon={icon3} iconSize={30} />
|
|
121
|
+
<IconComponent icon={icon_kit3_data?.icon || icon3} iconSize={30} />
|
|
117
122
|
</View>
|
|
118
123
|
<Text style={styles.text}>{text3}</Text>
|
|
119
124
|
</TouchableOpacity>
|
|
@@ -308,10 +308,6 @@ describe('Test OptionsDropdownActionTemplate', () => {
|
|
|
308
308
|
});
|
|
309
309
|
expect(alertAction.props.visible).toBeFalsy();
|
|
310
310
|
|
|
311
|
-
expect(mockDoAction).toHaveBeenCalledWith(action_data,
|
|
312
|
-
value: 1,
|
|
313
|
-
level: 'level-1',
|
|
314
|
-
key_code: 1,
|
|
315
|
-
});
|
|
311
|
+
expect(mockDoAction).toHaveBeenCalledWith(action_data, 'level-1');
|
|
316
312
|
});
|
|
317
313
|
});
|
|
@@ -62,7 +62,7 @@ describe('Test SliderRangeTemplate', () => {
|
|
|
62
62
|
});
|
|
63
63
|
expect(mockDoAction).toHaveBeenCalledWith(
|
|
64
64
|
action_data,
|
|
65
|
-
JSON.stringify({ value_brness: 50 })
|
|
65
|
+
JSON.stringify({ value_brness: 50, value: 50 })
|
|
66
66
|
);
|
|
67
67
|
});
|
|
68
68
|
|
|
@@ -82,7 +82,7 @@ describe('Test SliderRangeTemplate', () => {
|
|
|
82
82
|
});
|
|
83
83
|
expect(mockDoAction).toHaveBeenCalledWith(
|
|
84
84
|
action_data,
|
|
85
|
-
JSON.stringify({ value_brness: 50 })
|
|
85
|
+
JSON.stringify({ value_brness: 50, value: 50 })
|
|
86
86
|
);
|
|
87
87
|
});
|
|
88
88
|
|
|
@@ -1,13 +1,11 @@
|
|
|
1
|
-
import React, { memo
|
|
1
|
+
import React, { memo } from 'react';
|
|
2
2
|
import { View, StyleSheet } from 'react-native';
|
|
3
3
|
import LinearGradient from 'react-native-linear-gradient';
|
|
4
4
|
|
|
5
5
|
import { Colors } from '../../../configs';
|
|
6
6
|
import { CircleView } from '../../../commons';
|
|
7
7
|
import Text from '../../../commons/Text';
|
|
8
|
-
import
|
|
9
|
-
import IconSunny from '../../../../assets/images/Device/sunny.svg';
|
|
10
|
-
import IconSunnyBlack from '../../../../assets/images/Device/inactive-icon.svg';
|
|
8
|
+
import IconComponent from '../../IconComponent';
|
|
11
9
|
|
|
12
10
|
const CurrentRainSensor = memo(({ data = [] }) => {
|
|
13
11
|
const item = data.length
|
|
@@ -15,17 +13,8 @@ const CurrentRainSensor = memo(({ data = [] }) => {
|
|
|
15
13
|
: {
|
|
16
14
|
evaluate: {},
|
|
17
15
|
};
|
|
18
|
-
const { text,
|
|
19
|
-
|
|
20
|
-
let icon = <IconSunny />;
|
|
21
|
-
if (raining) {
|
|
22
|
-
icon = <IconRain />;
|
|
23
|
-
} else {
|
|
24
|
-
const isOn = String(text)?.toLowerCase() === 'on';
|
|
25
|
-
icon = isOn ? <IconSunny /> : <IconSunnyBlack width={32} height={32} />;
|
|
26
|
-
}
|
|
27
|
-
return icon;
|
|
28
|
-
}, [raining, text]);
|
|
16
|
+
const { text, backgroundColor, borderColor, icon, icon_kit_data } =
|
|
17
|
+
item.evaluate || {};
|
|
29
18
|
|
|
30
19
|
return (
|
|
31
20
|
<View style={styles.standard}>
|
|
@@ -42,7 +31,9 @@ const CurrentRainSensor = memo(({ data = [] }) => {
|
|
|
42
31
|
start={{ x: 1, y: 0 }}
|
|
43
32
|
end={{ x: 1, y: 1 }}
|
|
44
33
|
/>
|
|
45
|
-
|
|
34
|
+
<IconComponent
|
|
35
|
+
icon={icon_kit_data?.icon || icon || 'CheckCircleOutlined'}
|
|
36
|
+
/>
|
|
46
37
|
<Text style={styles.text}>{text}</Text>
|
|
47
38
|
</CircleView>
|
|
48
39
|
</View>
|
package/src/configs/SCConfig.js
CHANGED
|
@@ -214,7 +214,6 @@ async function sendCommandSingleAction(connection, ghAction, data) {
|
|
|
214
214
|
if (name && data) {
|
|
215
215
|
message.service_data[name] = data;
|
|
216
216
|
}
|
|
217
|
-
|
|
218
217
|
try {
|
|
219
218
|
await connection.sendMessagePromise(message);
|
|
220
219
|
return true;
|
|
@@ -238,21 +237,13 @@ export async function sendCommandOverHomeAssistant(
|
|
|
238
237
|
|
|
239
238
|
const connection = getDeviceConnection(connections, device);
|
|
240
239
|
if (!connection) {
|
|
241
|
-
ToastBottomHelper.error(t('
|
|
240
|
+
ToastBottomHelper.error(t('home_assistant_device_not_found'));
|
|
242
241
|
return;
|
|
243
242
|
}
|
|
244
243
|
|
|
245
244
|
let triggerSuccess;
|
|
246
245
|
|
|
247
|
-
if (action.
|
|
248
|
-
for (let i = 0; i < action.googlehome_actions.length; i++) {
|
|
249
|
-
triggerSuccess = await sendCommandSingleAction(
|
|
250
|
-
connection,
|
|
251
|
-
action.googlehome_actions[i],
|
|
252
|
-
data
|
|
253
|
-
);
|
|
254
|
-
}
|
|
255
|
-
} else if (action.googlehome_action) {
|
|
246
|
+
if (action.googlehome_action) {
|
|
256
247
|
triggerSuccess = await sendCommandSingleAction(
|
|
257
248
|
connection,
|
|
258
249
|
action.googlehome_action,
|
|
@@ -75,11 +75,6 @@ describe('Remote Control Home Assistant', () => {
|
|
|
75
75
|
|
|
76
76
|
const action = {
|
|
77
77
|
id: 1,
|
|
78
|
-
googlehome_actions: [
|
|
79
|
-
{
|
|
80
|
-
message: 'message',
|
|
81
|
-
},
|
|
82
|
-
],
|
|
83
78
|
googlehome_action: {
|
|
84
79
|
message: 'message',
|
|
85
80
|
},
|
|
@@ -238,38 +233,11 @@ describe('Remote Control Home Assistant', () => {
|
|
|
238
233
|
);
|
|
239
234
|
await sendCommandOverHomeAssistant(connections, sensor, action);
|
|
240
235
|
expect(connection.sendMessagePromise).toBeCalledWith(
|
|
241
|
-
action.
|
|
236
|
+
action.googlehome_action.message
|
|
242
237
|
);
|
|
243
238
|
});
|
|
244
239
|
|
|
245
240
|
it('Send command over Home Assistant will send message to chip with service_data and data', async () => {
|
|
246
|
-
action.googlehome_actions[0].message = {
|
|
247
|
-
type: 'call_service',
|
|
248
|
-
domain: 'climate',
|
|
249
|
-
service: 'set_temperature',
|
|
250
|
-
service_data: {
|
|
251
|
-
temperature: 0,
|
|
252
|
-
entity_id: 'climate.dqsmart_0108f6cdde',
|
|
253
|
-
},
|
|
254
|
-
id: 20,
|
|
255
|
-
};
|
|
256
|
-
mock.onPost(API.DEVICE.ACTIVITY_LOG()).reply(200);
|
|
257
|
-
const connections = await homeAssistantConnect(
|
|
258
|
-
{},
|
|
259
|
-
options,
|
|
260
|
-
mockEstablished,
|
|
261
|
-
mockDisconnected,
|
|
262
|
-
mockReconnected
|
|
263
|
-
);
|
|
264
|
-
await sendCommandOverHomeAssistant(connections, sensor, action, 19);
|
|
265
|
-
action.googlehome_actions[0].message.service_data.temperature = 19;
|
|
266
|
-
expect(connection.sendMessagePromise).toBeCalledWith(
|
|
267
|
-
action.googlehome_actions[0].message
|
|
268
|
-
);
|
|
269
|
-
});
|
|
270
|
-
|
|
271
|
-
it('Send command over Home Assistant action googlehome_action one to one', async () => {
|
|
272
|
-
action.googlehome_actions = null;
|
|
273
241
|
action.googlehome_action.message = {
|
|
274
242
|
type: 'call_service',
|
|
275
243
|
domain: 'climate',
|
|
@@ -155,7 +155,6 @@
|
|
|
155
155
|
"ok": "OK",
|
|
156
156
|
"Status": "Status: ",
|
|
157
157
|
"connected": "Connected",
|
|
158
|
-
"home_assistant_connected": "Home Assistant is connected",
|
|
159
158
|
"don_t_have_an_account": "Don't have an account?",
|
|
160
159
|
"please_enter_your_phone_number": "Please enter your phone number",
|
|
161
160
|
"please_enter_your_password": "Please enter your password",
|
|
@@ -371,6 +370,8 @@
|
|
|
371
370
|
"check_the_wifi": "Check the Wi-Fi/Cellular signal or try to reset it.",
|
|
372
371
|
"check_the_ble": "Check your Bluetooth status and try to use QUICK ACTION to control.",
|
|
373
372
|
"disconnected": "Disconnected",
|
|
373
|
+
"home_assistant_connected": "Home Assistant is connected",
|
|
374
|
+
"home_assistant_device_not_found": "Home Assistant device not found",
|
|
374
375
|
"home_assistant_disconnected": "Home Assistant is disconnected",
|
|
375
376
|
"rename_sub_unit": "Rename sub-unit",
|
|
376
377
|
"select_image": "Select image",
|
|
@@ -206,7 +206,6 @@
|
|
|
206
206
|
"ok": "OK",
|
|
207
207
|
"Status": "Trạng thái: ",
|
|
208
208
|
"connected": "Đã kết nối",
|
|
209
|
-
"home_assistant_connected": "Home Assistant đã kết nối",
|
|
210
209
|
"don_t_have_an_account": "Bạn chưa có tài khoản?",
|
|
211
210
|
"please_enter_your_phone_number": "Vui lòng nhập số điện thoại",
|
|
212
211
|
"please_enter_your_password": "Vui lòng nhập mật khẩu",
|
|
@@ -419,6 +418,7 @@
|
|
|
419
418
|
"check_the_wifi": "Kiểm tra lại Wi-Fi/tín hiệu di động hoặc thử khởi động lại.",
|
|
420
419
|
"check_the_ble": "Kiểm tra trạng thái Bluetooth của bạn và thử sử dụng HÀNH ĐỘNG NHANH để điều khiển",
|
|
421
420
|
"disconnected": "Ngắt kết nối",
|
|
421
|
+
"home_assistant_connected": "Home Assistant đã kết nối",
|
|
422
422
|
"home_assistant_disconnected": "Home Assistant bị ngắt kết nối",
|
|
423
423
|
"rename_sub_unit": "Đổi tên khu vực",
|
|
424
424
|
"select_image": "Chọn ảnh",
|
|
@@ -709,6 +709,7 @@
|
|
|
709
709
|
"this_spot_does_not_support_to_scan": "Vị trí đỗ này không hỗ trợ quét",
|
|
710
710
|
"please_book_by_the_normal_way": "Vui lòng đặt trước bằng cách thông thường",
|
|
711
711
|
"qr_code_invalid": "Mã QR này không hợp lệ",
|
|
712
|
+
"home_assistant_device_not_found": "Không tìm thấy thiết bị Home Assistant",
|
|
712
713
|
"command_send_success_homeassistant": "Lệnh gởi thành công đến Home Assistant",
|
|
713
714
|
"command_send_fail_homeassistant": "Lệnh gởi thất bại đến Home Assistant",
|
|
714
715
|
"command_homeassistant_ready": "Home Assistant kết nối thành công",
|