1/*
2 * Copyright (c) 2024 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 *     http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15import { BusinessError } from '@ohos.base';
16import hardwareManager from '@ohos.distributedHardware.hardwareManager';
17import common from '@ohos.app.ability.common';
18import router from '@ohos.router';
19import { Configuration } from '@ohos.app.ability.Configuration';
20import EnvironmentCallback from '@ohos.app.ability.EnvironmentCallback';
21
22const TAG = '[testTag_DHardwareUI] : ';
23PersistentStorage.persistProp('sign', '');
24
25@Entry
26@Component
27struct DHardwareUI {
28  @State deviceName: string = '';
29  @State dhTypeName: string = '';
30  @State bgcImg: PixelMap | null = null;
31  @StorageLink('type') type: number = 0;
32  @StorageLink('srcNetworkId') srcNetworkId: string = '';
33  @StorageLink('deviceName') srcDeviceName: string = '';
34  @StorageLink('sign') sign: string = '';
35  @StorageLink('camera') camera: number = 999;
36  @StorageLink('mic') mic: number = 999;
37  @StorageLink('switchedCamera') switchedCamera: number = 999;
38  @StorageLink('isPause') isPause: boolean = true;
39  @State description: hardwareManager.HardwareDescriptor = {
40    type: this.type,
41    srcNetworkId: this.srcNetworkId
42  }
43  private context = getContext(this) as common.UIAbilityContext;
44  private callbackId: number = 0;
45
46  subscribeConfigurationUpdate() {
47    let systemLanguage: string | undefined = this.context.config.language;
48    let that = this;
49    // 1.get ApplicationContext
50    let applicationContext = this.context.getApplicationContext();
51
52    // 2.Subscribe to environment variable changes through applicationContext
53    let environmentCallback: EnvironmentCallback = {
54      onConfigurationUpdated(newConfig: Configuration) {
55        console.info(TAG + `onConfigurationUpdated systemLanguage is ${systemLanguage}, newConfig: ${JSON.stringify(newConfig)}`);
56
57        if (this.systemLanguage !== newConfig.language) {
58          console.info(TAG + `systemLanguage from ${systemLanguage} changed to ${newConfig.language}`);
59          systemLanguage = newConfig.language;
60          that.getDHTypeStringValue();
61        }
62      },
63      onMemoryLevel(level) {
64        console.info(TAG + `onMemoryLevel level: ${level}`);
65      }
66    }
67
68    this.callbackId = applicationContext.on('environment', environmentCallback);
69  }
70
71  aboutToAppear() {
72    console.info(TAG + 'aboutToAppear() ');
73    this.sign = '';
74    this.subscribeConfigurationUpdate();
75
76    if (this.camera == 0 && this.mic == 0) {
77      try {
78        this.context.terminateSelf((err: BusinessError) => {
79          if (err.code) {
80            console.error(TAG + `terminateSelf failed,code is ${err.code},message is ${err.message}`);
81            return;
82          }
83          console.log(TAG + 'aboutToAppear() : ' + 'terminateSelf succeed');
84        });
85      } catch (err) {
86        let code = (err as BusinessError).code;
87        let message = (err as BusinessError).message;
88        console.error(TAG + `terminateSelf failed,code is ${code},message is ${message}`);
89      }
90    }
91
92    AppStorage.setAndLink('description', this.description);
93
94    console.info(TAG + 'aboutToAppear : this.description : ' + this.description);
95    console.info(TAG + 'aboutToAppear : this.description.type : ' + this.description.type);
96    console.info(TAG + 'aboutToAppear : this.description.srcNetworkId : ' + this.description.srcNetworkId);
97  }
98
99  getDHTypeStringValue() {
100    console.log(TAG + 'getDHTypeStringValue in');
101    if (this.type == 1024) {
102      this.context.resourceManager.getStringValue($r('app.string.DHTypeName_Mic').id, (error, value) => {
103        if (error != null) {
104          console.log(TAG + 'error is ' + error);
105        } else {
106          this.dhTypeName = value;
107          console.info(TAG + 'getDHTypeStringValue : this.dhTypeName : ' + this.dhTypeName);
108        }
109      });
110    } else {
111      this.context.resourceManager.getStringValue($r('app.string.DHTypeName_Camera').id, (error, value) => {
112        if (error != null) {
113          console.log(TAG + 'error is ' + error);
114        } else {
115          this.dhTypeName = value;
116          console.info(TAG + 'getDHTypeStringValue : this.dhTypeName : ' + this.dhTypeName);
117        }
118      });
119    }
120    console.log(TAG + 'getDHTypeStringValue end');
121  }
122
123  onPageShow() {
124    console.log(TAG + 'onPageShow() ');
125    if (this.isPause === false && this.camera === 2) {
126      this.isPause = true;
127      console.info(TAG + 'onPageShow : this.camera ' + this.camera);
128      console.info(TAG + 'onPageShow : this.isPause ' + this.isPause);
129    }
130    this.getDHTypeStringValue();
131  }
132
133  changePauseOrResumeStatus() {
134    this.isPause = !this.isPause;
135    console.log(TAG + 'changePauseOrResumeStatus - this.isPause' + JSON.stringify(this.isPause))
136  }
137
138  stop() {
139    console.info(TAG + 'stop');
140    try {
141      hardwareManager.stopDistributedHardware(this.description).then(() => {
142        console.log('stop distributed hardware successfully');
143      }).catch((error: BusinessError) => {
144        console.error('stop distributed hardware failed, cause:' + error);
145      })
146      console.log('stop distributed hardware successfully');
147    } catch (error) {
148      console.error('stop distributed hardware failed:' + error);
149    }
150  }
151
152  pause() {
153    console.log(TAG + 'pause');
154    try {
155      hardwareManager.pauseDistributedHardware(this.description).then(() => {
156        console.log('pause distributed hardware successfully');
157      }).catch((error: BusinessError) => {
158        console.error('pause distributed hardware failed, cause:' + error);
159      })
160      console.log('pause distributed hardware successfully');
161    } catch (error) {
162      console.error('pause distributed hardware failed:' + error);
163    }
164  }
165
166  resume() {
167    console.log(TAG + 'resume');
168    try {
169      hardwareManager.resumeDistributedHardware(this.description).then(() => {
170        console.log('resume distributed hardware successfully');
171      }).catch((error: BusinessError) => {
172        console.error('resume distributed hardware failed, cause:' + error);
173      })
174      console.log('resume distributed hardware successfully');
175    } catch (error) {
176      console.error('resume distributed hardware failed:' + error);
177    }
178  }
179
180  onPageHide() {
181    console.info(TAG + 'onPageHide');
182  }
183
184  onBackPress() {
185    console.info(TAG + 'onBackPress');
186    this.sign = 'onBackPress';
187  }
188
189  aboutToDisappear() {
190    console.info(TAG + 'aboutToDisappear');
191  }
192
193  build() {
194    Stack() {
195      Stack() {
196        Image($r('app.media.bgcWall'))
197      }
198
199      Row() {
200        Column() {
201          Row() {
202            Image(this.type == 1024 ? $r('app.media.ic_public_voice') : $r('app.media.ic_public_screencap'))
203              .width(28)
204              .height(28)
205              .fillColor(Color.White)
206              .margin({ left: 13 })
207          }.borderRadius(50).width(54).height(54).backgroundColor('rgba(0,0,0,0.15)')
208
209          Text($r('app.string.connected_to', this.srcDeviceName))
210            .fontSize(18)
211            .fontWeight(FontWeight.Medium)
212            .fontColor('#FFFFFF')
213            .margin({ left: 0, top: 16, right: 0 })
214            .textAlign(TextAlign.Center)
215
216          Text($r('app.string.stop_device', this.dhTypeName))
217            .fontSize(16)
218            .fontWeight(FontWeight.Regular)
219            .fontColor('#99FFFFFF')
220            .margin({ top: 2 })
221            .fontStyle(FontStyle.Normal)
222            .textAlign(TextAlign.Center)
223
224          GridRow({ columns: 5, gutter: { x: 24 } }) {
225            GridCol({ span: 1 })
226
227            GridCol({ span: 3 }) {
228              Column() {
229                Button(this.isPause ? $r('app.string.pause') : $r('app.string.continue'), {
230                  type: ButtonType.Capsule,
231                  stateEffect: true
232                })
233                  .backgroundColor('rgba(255,255,255,0.2)')
234                  .height(40)
235                  .fontSize(16)
236                  .margin({ top: 24 })
237                  .width('100%')
238                  .onClick(() => {
239                    console.log(TAG + (this.isPause ? 'click pause button' : 'click continue button'));
240                    if (this.isPause) {
241                      this.pause();
242                      AppStorage.setOrCreate('isPauseTag', true);
243                    } else {
244                      this.resume();
245                      AppStorage.setOrCreate('isPauseTag', false);
246                    }
247                    this.changePauseOrResumeStatus();
248                    console.info(TAG + 'onClick : AppStorage.get<boolean>(isPauseTag) ' + AppStorage.get<boolean>('isPauseTag'));
249                  })
250
251                Button($r('app.string.disconnect'), { type: ButtonType.Capsule, stateEffect: true })
252                  .backgroundColor('#FFFFFF')
253                  .height(40)
254                  .fontSize(16)
255                  .margin({ top: 16 })
256                  .width('100%')
257                  .fontColor('rgba(0,0,0,0.9)')
258                  .onClick(() => {
259                    console.log(TAG + 'click disconnect button')
260                    this.sign = 'stop';
261                    this.stop();
262
263                    try {
264                      this.context.terminateSelf((err: BusinessError) => {
265                        if (err.code) {
266                          console.error(`terminateSelf failed, code is ${err.code}, message is ${err.message}`);
267                          return;
268                        }
269                        console.info(TAG + 'terminateSelf succeed');
270                        router.back();
271                      });
272                    } catch (err) {
273                      let code = (err as BusinessError).code;
274                      let message = (err as BusinessError).message;
275                      console.error(`terminateSelf failed, code is ${code}, message is ${message}`);
276                    }
277                  })
278              }
279            }
280
281            GridCol({ span: 1 })
282          }
283
284        }.width('100%').padding({ left: 24, right: 24 })
285      }.width('100%')
286    }
287
288  }
289}