@eohjsc/react-native-smart-city 0.5.1 → 0.5.2-rc

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 (36) hide show
  1. package/package.json +1 -1
  2. package/src/commons/ActionGroup/OnOffTemplate/OnOffSimpleTemplateStyle.js +1 -0
  3. package/src/commons/ActionGroup/SliderRangeTemplate.js +10 -3
  4. package/src/commons/ActionGroup/__test__/SliderRangeTemplate.test.js +4 -0
  5. package/src/commons/ProcessingBar/index.js +32 -0
  6. package/src/commons/ProcessingBar/styles.js +57 -0
  7. package/src/configs/AccessibilityLabel.js +8 -0
  8. package/src/navigations/AddMemberStack.js +8 -3
  9. package/src/screens/AddCommon/SelectUnit.js +1 -1
  10. package/src/screens/AddCommon/__test__/SelectUnit.test.js +1 -1
  11. package/src/screens/EnterPassword/index.js +3 -2
  12. package/src/screens/Sharing/Components/CheckBoxConfig.js +44 -0
  13. package/src/screens/Sharing/Components/CheckBoxCustom.js +2 -13
  14. package/src/screens/Sharing/Components/CheckBoxSubUnit.js +35 -0
  15. package/src/screens/Sharing/Components/EndDevice.js +93 -0
  16. package/src/screens/Sharing/Components/Styles/CheckBoxConfigStyles.js +18 -0
  17. package/src/screens/Sharing/Components/Styles/DeviceItemStyles.js +28 -35
  18. package/src/screens/Sharing/Components/index.js +1 -2
  19. package/src/screens/Sharing/InfoMemberUnit.js +5 -3
  20. package/src/screens/Sharing/SelectShareDevice.js +273 -0
  21. package/src/screens/Sharing/SelectUser.js +6 -0
  22. package/src/screens/Sharing/Styles/SelectPermissionStyles.js +2 -11
  23. package/src/screens/Sharing/UnitMemberList.js +2 -1
  24. package/src/screens/Sharing/UpdateShareDevice.js +322 -0
  25. package/src/screens/Sharing/__test__/SelectShareDevice.test.js +215 -0
  26. package/src/screens/Sharing/__test__/UnitMemberList.test.js +1 -1
  27. package/src/screens/Sharing/__test__/UpdateShareDevice.test.js +307 -0
  28. package/src/screens/Sharing/hooks/index.js +5 -0
  29. package/src/screens/SubUnit/AddSubUnit.js +2 -6
  30. package/src/screens/SubUnit/EditSubUnitStyles.js +2 -1
  31. package/src/screens/Unit/AddMenu.js +1 -1
  32. package/src/utils/Route/index.js +2 -1
  33. package/src/screens/Sharing/Components/DeviceItem.js +0 -146
  34. package/src/screens/Sharing/Components/__test__/DeviceItem.test.js +0 -48
  35. package/src/screens/Sharing/SharingSelectPermission.js +0 -409
  36. package/src/screens/Sharing/__test__/SharingSelectPermission.test.js +0 -292
@@ -0,0 +1,215 @@
1
+ import { act } from '@testing-library/react-hooks';
2
+ import React from 'react';
3
+ import { Alert } from 'react-native';
4
+ import { create } from 'react-test-renderer';
5
+ import MockAdapter from 'axios-mock-adapter';
6
+ import { ViewButtonBottom } from '../../../commons';
7
+ import { SCProvider } from '../../../context';
8
+ import { mockSCStore } from '../../../context/mockStore';
9
+ import API from '../../../configs/API';
10
+ import api from '../../../utils/Apis/axios';
11
+ import AccessibilityLabel from '../../../configs/AccessibilityLabel';
12
+ import SelectShareDevice from '../SelectShareDevice';
13
+ import Routes from '../../../utils/Route';
14
+
15
+ const mock = new MockAdapter(api.axiosInstance);
16
+ jest.spyOn(Alert, 'alert').mockImplementation(() => {});
17
+ const mockNavigate = jest.fn();
18
+ const mockGoBack = jest.fn();
19
+ jest.mock('@react-navigation/native', () => {
20
+ return {
21
+ ...jest.requireActual('@react-navigation/native'),
22
+ useNavigation: () => ({
23
+ navigate: mockNavigate,
24
+ goBack: mockGoBack,
25
+ }),
26
+ };
27
+ });
28
+
29
+ const wrapComponent = (route) => (
30
+ <SCProvider initState={mockSCStore({})}>
31
+ <SelectShareDevice route={route} />
32
+ </SCProvider>
33
+ );
34
+
35
+ describe('Test SelectShareDevice', () => {
36
+ let tree;
37
+ let route = {
38
+ params: {
39
+ unit: { id: 1, name: 'unit 1' },
40
+ },
41
+ };
42
+ let listDevices = [
43
+ {
44
+ id: 1,
45
+ name: 'Sub unit',
46
+ devices: [
47
+ {
48
+ id: 2,
49
+ actions: [{ id: 3, name: 'action 1' }],
50
+ read_configs: [{ id: 4, name: 'config 1' }],
51
+ name: 'child1',
52
+ },
53
+ {
54
+ id: 5,
55
+ actions: [{ id: 6, name: 'action 2' }],
56
+ read_configs: [{ id: 7, name: 'config 2' }],
57
+ name: 'child2',
58
+ },
59
+ {
60
+ id: 8,
61
+ actions: [],
62
+ read_configs: [],
63
+ name: 'child3',
64
+ },
65
+ ],
66
+ },
67
+ ];
68
+
69
+ afterEach(() => {
70
+ Alert.alert.mockReset();
71
+ mock.resetHistory();
72
+ mockNavigate.mockClear();
73
+ mockGoBack.mockClear();
74
+ });
75
+
76
+ const clickCheckBoxAllDevice = async (instance, statusCheckbox) => {
77
+ const checkBoxAllDevice = instance.find(
78
+ (el) =>
79
+ el.props.accessibilityLabel ===
80
+ `${AccessibilityLabel.CHECK_BOX_CUSTOM}-undefined`
81
+ );
82
+ expect(checkBoxAllDevice.props.isChecked).toEqual(statusCheckbox);
83
+ await act(async () => {
84
+ await checkBoxAllDevice.props.onPress();
85
+ });
86
+ };
87
+
88
+ const clickCheckBoxSubUnit = async (instance, statusCheckbox) => {
89
+ const checkBoxSubunit = instance.find(
90
+ (el) =>
91
+ el.props.accessibilityLabel ===
92
+ `${AccessibilityLabel.CHECK_BOX_CUSTOM}-0`
93
+ );
94
+ expect(checkBoxSubunit.props.isChecked).toEqual(statusCheckbox);
95
+ await act(async () => {
96
+ await checkBoxSubunit.props.onPress();
97
+ });
98
+ };
99
+
100
+ const clickCheckBoxConfig = async (instance, configId, statusCheckbox) => {
101
+ let checkBoxConfig = instance.find(
102
+ (el) =>
103
+ el.props.accessibilityLabel ===
104
+ `${AccessibilityLabel.SHARE_DEVICE.CHECK_BOX_CONFIG}-${configId}`
105
+ );
106
+ expect(checkBoxConfig.props.isChecked).toEqual(statusCheckbox);
107
+ await act(async () => {
108
+ await checkBoxConfig.props.onPress();
109
+ });
110
+ };
111
+
112
+ const clickExpandEndDevice = async (instance, indexEndDevice, statusIcon) => {
113
+ const expandEndDevice = instance.find(
114
+ (el) =>
115
+ el.props.accessibilityLabel ===
116
+ `${AccessibilityLabel.SHARE_DEVICE.EXPAND_END_DEVICE}-${indexEndDevice}`
117
+ );
118
+ expect(expandEndDevice.props.name).toEqual(statusIcon);
119
+ await act(async () => {
120
+ await expandEndDevice.props.onPress();
121
+ });
122
+ };
123
+
124
+ const clickNameEndDevice = async (instance, indexEndDevice) => {
125
+ const nameEndDevice = instance.find(
126
+ (el) =>
127
+ el.props.accessibilityLabel ===
128
+ `${AccessibilityLabel.SHARE_DEVICE.CLICK_NAME_END_DEVICE}-${indexEndDevice}`
129
+ );
130
+ await act(async () => {
131
+ await nameEndDevice.props.onPress();
132
+ });
133
+ };
134
+
135
+ it('test user select share device', async () => {
136
+ mock.onGet(API.SHARE.UNIT_PERMISSIONS(1)).reply(200, listDevices);
137
+
138
+ await act(async () => {
139
+ tree = await create(wrapComponent(route));
140
+ });
141
+ let instance = tree.root;
142
+ await clickNameEndDevice(instance, 0); // click to select all configs in end device index 0
143
+ await clickNameEndDevice(instance, 0); // click again to remove all configs, and coverage expand end device
144
+ await clickCheckBoxConfig(instance, 3, false); // click to select action
145
+ await clickCheckBoxConfig(instance, 3, true); // click again to coverage case status reversal
146
+ await clickCheckBoxConfig(instance, 4, false); // click to select config
147
+ await clickCheckBoxConfig(instance, 4, true); // click again to coverage case status reversal
148
+ await clickExpandEndDevice(instance, 0, 'up');
149
+ await clickExpandEndDevice(instance, 0, 'down'); // click again to coverage case status reversal
150
+
151
+ await clickCheckBoxAllDevice(instance, false); // click to select all device
152
+ await clickCheckBoxSubUnit(instance, true); // click to remove all device in sub unit id 1
153
+ await clickNameEndDevice(instance, 1); // click to select all configs in end device index 1
154
+ await clickNameEndDevice(instance, 2); // click to select all configs in end device index 2
155
+
156
+ const ViewButtonBottomElement = instance.findAllByType(ViewButtonBottom);
157
+ await act(async () => {
158
+ ViewButtonBottomElement[0].props.onRightClick();
159
+ });
160
+ expect(mockNavigate).toBeCalledWith(Routes.SharingInviteMembers, {
161
+ unit: { id: 1, name: 'unit 1' },
162
+ permissions: {
163
+ read_permissions: [
164
+ { id: 5, values: [7] },
165
+ { id: 8, values: [] },
166
+ ],
167
+ control_permissions: [{ id: 5, values: [6] }],
168
+ },
169
+ });
170
+ });
171
+
172
+ it('test no data, api get UNIT_PERMISSIONS false', async () => {
173
+ mock.onGet(API.SHARE.UNIT_PERMISSIONS(1)).reply(400);
174
+
175
+ await act(async () => {
176
+ tree = await create(wrapComponent(route));
177
+ });
178
+ const instance = tree.root;
179
+
180
+ let text = instance.find(
181
+ (el) =>
182
+ el.props.accessibilityLabel === AccessibilityLabel.TEXT_NO_DATA_STATIONS
183
+ );
184
+ expect(text.props.children).toEqual('No data');
185
+ });
186
+
187
+ it('user not choose device click button back', async () => {
188
+ await act(async () => {
189
+ tree = await create(wrapComponent(route));
190
+ });
191
+ const instance = tree.root;
192
+ const ViewButtonBottomElement = instance.findAllByType(ViewButtonBottom);
193
+ expect(ViewButtonBottomElement).toHaveLength(1);
194
+
195
+ await act(async () => {
196
+ ViewButtonBottomElement[0].props.onLeftClick();
197
+ });
198
+ expect(mockGoBack).toBeCalled();
199
+ });
200
+
201
+ it('user not choose device click button next', async () => {
202
+ await act(async () => {
203
+ tree = await create(wrapComponent(route));
204
+ });
205
+ const instance = tree.root;
206
+ const ViewButtonBottomElement = instance.findAllByType(ViewButtonBottom);
207
+ expect(ViewButtonBottomElement).toHaveLength(1);
208
+ await act(async () => {
209
+ ViewButtonBottomElement[0].props.onRightClick();
210
+ });
211
+ expect(Alert.alert.mock.calls[0][1]).toEqual(
212
+ 'Please choose at least one sensor.'
213
+ );
214
+ });
215
+ });
@@ -71,7 +71,7 @@ describe('test MemberList', () => {
71
71
  await memberListButtons[1].props.onPress();
72
72
  });
73
73
  expect(mockedNavigate).toBeCalledWith(Routes.AddMemberStack, {
74
- screen: Routes.SharingSelectPermission,
74
+ screen: Routes.SelectShareDevice,
75
75
  params: { unit: { id: 1 } },
76
76
  });
77
77
  });
@@ -0,0 +1,307 @@
1
+ import { act } from '@testing-library/react-hooks';
2
+ import React from 'react';
3
+ import { Alert } from 'react-native';
4
+ import { create } from 'react-test-renderer';
5
+ import MockAdapter from 'axios-mock-adapter';
6
+ import { ViewButtonBottom } from '../../../commons';
7
+ import { SCProvider } from '../../../context';
8
+ import { mockSCStore } from '../../../context/mockStore';
9
+ import API from '../../../configs/API';
10
+ import api from '../../../utils/Apis/axios';
11
+ import UpdateShareDevice from '../UpdateShareDevice';
12
+ import AccessibilityLabel from '../../../configs/AccessibilityLabel';
13
+
14
+ const mock = new MockAdapter(api.axiosInstance);
15
+ jest.spyOn(Alert, 'alert').mockImplementation(() => {});
16
+ const mockNavigate = jest.fn();
17
+ const mockGoBack = jest.fn();
18
+ jest.mock('@react-navigation/native', () => {
19
+ return {
20
+ ...jest.requireActual('@react-navigation/native'),
21
+ useNavigation: () => ({
22
+ navigate: mockNavigate,
23
+ goBack: mockGoBack,
24
+ }),
25
+ };
26
+ });
27
+
28
+ const wrapComponent = (route) => (
29
+ <SCProvider initState={mockSCStore({})}>
30
+ <UpdateShareDevice route={route} />
31
+ </SCProvider>
32
+ );
33
+
34
+ describe('Test UpdateShareDevice', () => {
35
+ let tree;
36
+ let route = {
37
+ params: {
38
+ unit: { id: 1, name: 'unit 1' },
39
+ member: {
40
+ id: 1,
41
+ name: 'a',
42
+ phone_number: '0901234567',
43
+ email: 'email@gmail.com',
44
+ },
45
+ },
46
+ };
47
+ let listDevices = [
48
+ {
49
+ id: 1,
50
+ name: 'Sub unit',
51
+ devices: [
52
+ {
53
+ id: 2,
54
+ actions: [{ id: 3, name: 'action 1' }],
55
+ read_configs: [{ id: 4, name: 'config 1' }],
56
+ name: 'child1',
57
+ },
58
+ {
59
+ id: 5,
60
+ actions: [{ id: 6, name: 'action 2' }],
61
+ read_configs: [{ id: 7, name: 'config 2' }],
62
+ name: 'child2',
63
+ },
64
+ {
65
+ id: 8,
66
+ actions: [],
67
+ read_configs: [],
68
+ name: 'child3',
69
+ },
70
+ ],
71
+ },
72
+ ];
73
+
74
+ afterEach(() => {
75
+ Alert.alert.mockReset();
76
+ mock.resetHistory();
77
+ mockNavigate.mockClear();
78
+ mockGoBack.mockClear();
79
+ });
80
+
81
+ const clickCheckBoxAllDevice = async (instance, statusCheckbox) => {
82
+ const checkBoxAllDevice = instance.find(
83
+ (el) =>
84
+ el.props.accessibilityLabel ===
85
+ `${AccessibilityLabel.CHECK_BOX_CUSTOM}-undefined`
86
+ );
87
+ expect(checkBoxAllDevice.props.isChecked).toEqual(statusCheckbox);
88
+ await act(async () => {
89
+ await checkBoxAllDevice.props.onPress();
90
+ });
91
+ };
92
+
93
+ const clickCheckBoxSubUnit = async (instance, statusCheckbox) => {
94
+ const checkBoxSubunit = instance.find(
95
+ (el) =>
96
+ el.props.accessibilityLabel ===
97
+ `${AccessibilityLabel.CHECK_BOX_CUSTOM}-0`
98
+ );
99
+ expect(checkBoxSubunit.props.isChecked).toEqual(statusCheckbox);
100
+ await act(async () => {
101
+ await checkBoxSubunit.props.onPress();
102
+ });
103
+ };
104
+
105
+ const clickCheckBoxConfig = async (instance, configId, statusCheckbox) => {
106
+ let checkBoxConfig = instance.find(
107
+ (el) =>
108
+ el.props.accessibilityLabel ===
109
+ `${AccessibilityLabel.SHARE_DEVICE.CHECK_BOX_CONFIG}-${configId}`
110
+ );
111
+ expect(checkBoxConfig.props.isChecked).toEqual(statusCheckbox);
112
+ await act(async () => {
113
+ await checkBoxConfig.props.onPress();
114
+ });
115
+ };
116
+
117
+ const clickExpandEndDevice = async (instance, indexEndDevice, statusIcon) => {
118
+ const expandEndDevice = instance.find(
119
+ (el) =>
120
+ el.props.accessibilityLabel ===
121
+ `${AccessibilityLabel.SHARE_DEVICE.EXPAND_END_DEVICE}-${indexEndDevice}`
122
+ );
123
+ expect(expandEndDevice.props.name).toEqual(statusIcon);
124
+ await act(async () => {
125
+ await expandEndDevice.props.onPress();
126
+ });
127
+ };
128
+
129
+ const clickNameEndDevice = async (instance, indexEndDevice) => {
130
+ const nameEndDevice = instance.find(
131
+ (el) =>
132
+ el.props.accessibilityLabel ===
133
+ `${AccessibilityLabel.SHARE_DEVICE.CLICK_NAME_END_DEVICE}-${indexEndDevice}`
134
+ );
135
+ await act(async () => {
136
+ await nameEndDevice.props.onPress();
137
+ });
138
+ };
139
+
140
+ it('test user update share device by phone', async () => {
141
+ mock.onGet(API.SHARE.UNIT_PERMISSIONS(1)).reply(200, listDevices);
142
+ mock.onGet(API.SHARE.UNIT_MEMBER_SHARE_DEVICE(1, 1)).reply(200, []);
143
+ mock.onPost(API.SHARE.SHARE()).reply(200);
144
+
145
+ await act(async () => {
146
+ tree = await create(wrapComponent(route));
147
+ });
148
+ let instance = tree.root;
149
+ await clickNameEndDevice(instance, 0); // click to select all configs in end device index 0
150
+ await clickNameEndDevice(instance, 0); // click again to remove all configs, and coverage expand end device
151
+ await clickCheckBoxConfig(instance, 3, false); // click to select action
152
+ await clickCheckBoxConfig(instance, 3, true); // click again to coverage case status reversal
153
+ await clickCheckBoxConfig(instance, 4, false); // click to select config
154
+ await clickCheckBoxConfig(instance, 4, true); // click again to coverage case status reversal
155
+ await clickExpandEndDevice(instance, 0, 'up');
156
+ await clickExpandEndDevice(instance, 0, 'down'); // click again to coverage case status reversal
157
+
158
+ await clickCheckBoxAllDevice(instance, false); // click to select all device
159
+ await clickCheckBoxSubUnit(instance, true); // click to remove all device in sub unit id 1
160
+ await clickNameEndDevice(instance, 1); // click to select all configs in end device index 1
161
+ await clickNameEndDevice(instance, 2); // click to select all configs in end device index 2
162
+
163
+ const ViewButtonBottomElement = instance.findAllByType(ViewButtonBottom);
164
+ await act(async () => {
165
+ ViewButtonBottomElement[0].props.onRightClick();
166
+ });
167
+ expect(mockGoBack).toBeCalled();
168
+ expect(mock.history.post[0].data).toEqual(
169
+ JSON.stringify({
170
+ phone: '0901234567',
171
+ email: '',
172
+ unit: 1,
173
+ permissions: {
174
+ read_permissions: [
175
+ { id: 5, values: [7] },
176
+ { id: 8, values: [] },
177
+ ],
178
+ control_permissions: [{ id: 5, values: [6] }],
179
+ },
180
+ is_remove_old_permission: true,
181
+ })
182
+ );
183
+ });
184
+
185
+ it('test user update share device by email', async () => {
186
+ mock.onGet(API.SHARE.UNIT_PERMISSIONS(1)).reply(200, listDevices);
187
+ mock.onGet(API.SHARE.UNIT_MEMBER_SHARE_DEVICE(1, 1)).reply(200, []);
188
+ mock.onPost(API.SHARE.SHARE()).reply(200);
189
+
190
+ route.params.member.phone_number = '';
191
+ await act(async () => {
192
+ tree = await create(wrapComponent(route));
193
+ });
194
+ const instance = tree.root;
195
+ await clickNameEndDevice(instance, 0); // click to select all configs in end device index 0
196
+ const ViewButtonBottomElement = instance.findAllByType(ViewButtonBottom);
197
+ expect(ViewButtonBottomElement).toHaveLength(1);
198
+ await act(async () => {
199
+ ViewButtonBottomElement[0].props.onRightClick();
200
+ });
201
+ expect(mockGoBack).toBeCalled();
202
+ expect(mock.history.post[0].data).toEqual(
203
+ JSON.stringify({
204
+ phone: '',
205
+ email: 'email@gmail.com',
206
+ unit: 1,
207
+ permissions: {
208
+ read_permissions: [{ id: 2, values: [4] }],
209
+ control_permissions: [{ id: 2, values: [3] }],
210
+ },
211
+ is_remove_old_permission: true,
212
+ })
213
+ );
214
+ });
215
+
216
+ it('test user update share device not have phone and email', async () => {
217
+ mock.onGet(API.SHARE.UNIT_PERMISSIONS(1)).reply(200, listDevices);
218
+ mock.onGet(API.SHARE.UNIT_MEMBER_SHARE_DEVICE(1, 1)).reply(200, []);
219
+ mock.onPost(API.SHARE.SHARE()).reply(400);
220
+
221
+ route.params.member.phone_number = '';
222
+ route.params.member.email = '';
223
+ await act(async () => {
224
+ tree = await create(wrapComponent(route));
225
+ });
226
+ const instance = tree.root;
227
+ await clickNameEndDevice(instance, 0); // click to select all configs in end device index 0
228
+ const ViewButtonBottomElement = instance.findAllByType(ViewButtonBottom);
229
+ expect(ViewButtonBottomElement).toHaveLength(1);
230
+ await act(async () => {
231
+ ViewButtonBottomElement[0].props.onRightClick();
232
+ });
233
+ expect(mockGoBack).not.toBeCalled();
234
+ expect(mock.history.post[0].data).toEqual(
235
+ JSON.stringify({
236
+ phone: '',
237
+ email: '',
238
+ unit: 1,
239
+ permissions: {
240
+ read_permissions: [{ id: 2, values: [4] }],
241
+ control_permissions: [{ id: 2, values: [3] }],
242
+ },
243
+ is_remove_old_permission: true,
244
+ })
245
+ );
246
+ });
247
+
248
+ it('test no data, api get UNIT_PERMISSIONS false', async () => {
249
+ mock.onGet(API.SHARE.UNIT_PERMISSIONS(1)).reply(400);
250
+
251
+ await act(async () => {
252
+ tree = await create(wrapComponent(route));
253
+ });
254
+ const instance = tree.root;
255
+
256
+ let text = instance.find(
257
+ (el) =>
258
+ el.props.accessibilityLabel === AccessibilityLabel.TEXT_NO_DATA_STATIONS
259
+ );
260
+ expect(text.props.children).toEqual('No data');
261
+ });
262
+
263
+ it('test api get UNIT_MEMBER_SHARE_DEVICE false', async () => {
264
+ mock.onGet(API.SHARE.UNIT_PERMISSIONS(1)).reply(200, listDevices);
265
+ mock.onGet(API.SHARE.UNIT_MEMBER_SHARE_DEVICE(1, 1)).reply(400);
266
+
267
+ await act(async () => {
268
+ tree = await create(wrapComponent(route));
269
+ });
270
+ const instance = tree.root;
271
+
272
+ let text = instance.findAll(
273
+ (el) =>
274
+ el.props.accessibilityLabel === AccessibilityLabel.TEXT_NO_DATA_STATIONS
275
+ );
276
+ expect(text).toEqual([]);
277
+ });
278
+
279
+ it('user not choose device click button back', async () => {
280
+ await act(async () => {
281
+ tree = await create(wrapComponent(route));
282
+ });
283
+ const instance = tree.root;
284
+ const ViewButtonBottomElement = instance.findAllByType(ViewButtonBottom);
285
+ expect(ViewButtonBottomElement).toHaveLength(1);
286
+
287
+ await act(async () => {
288
+ ViewButtonBottomElement[0].props.onLeftClick();
289
+ });
290
+ expect(mockGoBack).toBeCalled();
291
+ });
292
+
293
+ it('user not choose device click button next', async () => {
294
+ await act(async () => {
295
+ tree = await create(wrapComponent(route));
296
+ });
297
+ const instance = tree.root;
298
+ const ViewButtonBottomElement = instance.findAllByType(ViewButtonBottom);
299
+ expect(ViewButtonBottomElement).toHaveLength(1);
300
+ await act(async () => {
301
+ ViewButtonBottomElement[0].props.onRightClick();
302
+ });
303
+ expect(Alert.alert.mock.calls[0][1]).toEqual(
304
+ 'Please choose at least one sensor.'
305
+ );
306
+ });
307
+ });
@@ -16,6 +16,7 @@ const useDataMember = (unitId, userUnitId = undefined) => {
16
16
  const [loading, setLoading] = useState(true);
17
17
  const user = useSCContextSelector((state) => state?.auth?.account?.user);
18
18
  const { isOwner } = useIsOwnerOfUnit(userUnitId);
19
+ const [isRemoving, setIsRemoving] = useState(false);
19
20
 
20
21
  const insertAndShift = (arr, from, to) => {
21
22
  let cutOut = arr.splice(from, 1)[0]; // cut the element at index 'from'
@@ -50,12 +51,15 @@ const useDataMember = (unitId, userUnitId = undefined) => {
50
51
 
51
52
  const removeMember = useCallback(
52
53
  async (id, name) => {
54
+ setIsRemoving(true);
53
55
  await axiosDelete(API.SHARE.UNITS_MEMBER_DETAIL(unitId, id));
54
56
  ToastBottomHelper.success(
55
57
  t('sharing_removed_user', {
56
58
  name,
57
59
  })
58
60
  );
61
+
62
+ setIsRemoving(false);
59
63
  goBack();
60
64
  },
61
65
  [goBack, t, unitId]
@@ -85,6 +89,7 @@ const useDataMember = (unitId, userUnitId = undefined) => {
85
89
  isRefresh,
86
90
  onRefresh,
87
91
  loading,
92
+ isRemoving,
88
93
  };
89
94
  };
90
95
 
@@ -183,12 +183,8 @@ const AddSubUnit = ({ route }) => {
183
183
  );
184
184
 
185
185
  const validateData = useMemo(() => {
186
- if (isAddUnit) {
187
- return roomName === '' || wallpaper === '' || !location.description;
188
- } else {
189
- return roomName === '' || wallpaper === '';
190
- }
191
- }, [roomName, wallpaper, location, isAddUnit]);
186
+ return roomName === '';
187
+ }, [roomName]);
192
188
 
193
189
  const onChooseLocation = useCallback(() => {
194
190
  navigate(Routes.AddLocationMaps);
@@ -11,6 +11,7 @@ export default StyleSheet.create({
11
11
  flex: 1,
12
12
  },
13
13
  title: {
14
+ paddingTop: 22,
14
15
  paddingLeft: 22,
15
16
  fontSize: 24,
16
17
  lineHeight: 32,
@@ -43,7 +44,7 @@ export default StyleSheet.create({
43
44
  bottom: 0,
44
45
  borderWidth: 0,
45
46
  alignSelf: 'center',
46
- paddingBottom: 16 + getBottomSpace(),
47
+ paddingBottom: 36 + getBottomSpace(),
47
48
  },
48
49
  removeText: {
49
50
  borderBottomWidth: 1,
@@ -54,7 +54,7 @@ const AddMenu = memo(({ unit, afterItemClick, showAdd, setHideAdd }) => {
54
54
  image: <AddMemberIcon width={43} height={43} />,
55
55
  onClick: () =>
56
56
  navigation.navigate(Routes.AddMemberStack, {
57
- screen: Routes.SharingSelectPermission,
57
+ screen: Routes.SelectShareDevice,
58
58
  params: { unit },
59
59
  }),
60
60
  },
@@ -75,7 +75,8 @@ const Routes = {
75
75
  ConnectingWifiGuide: 'ConnectingWifiGuide',
76
76
 
77
77
  UnitMemberList: 'UnitMemberList',
78
- SharingSelectPermission: 'SharingSelectPermission',
78
+ UpdateShareDevice: 'UpdateShareDevice',
79
+ SelectShareDevice: 'SelectShareDevice',
79
80
  SharingInviteMembers: 'SharingInviteMembers',
80
81
  LocationNearMe: 'LocationNearMe',
81
82
  WindSpeed: 'WindSpeed',