@@ -17,56 +17,50 @@ import {
1717import {
1818 AudioConfigHelper,
1919 AUDIO_PROFILE,
20- AUDIO_ROUTE,
2120 AUDIO_SCENARIO,
2221 CHANNEL_PROFILE
2322} from '../../util/AudioConfigContant';
2423import { JSON } from '@kit.ArkTS';
2524import { backgroundTaskManager } from '@kit.BackgroundTasksKit';
2625import { BusinessError } from '@kit.BasicServicesKit';
26+ import { AVCastPicker } from '@kit.AVSessionKit';
27+ import { audio } from '@kit.AudioKit';
28+ import image from '@ohos.multimedia.image';
2729
2830const TAG: string = 'JoinAudioChannel'
2931
32+ /**
33+ * 鸿蒙系统不支持音频设备api切换 请参看网址 https://developer.huawei.com/consumer/cn/doc/harmonyos-guides-V5/using-switch-call-devices-V5
34+ * 本场景是通过AVCastPicker选择实现的
35+ */
3036@Entry
3137@Component
3238struct JoinAudioChannel {
3339 private context = getContext(this) as common.UIAbilityContext;
3440 private rtcEngine: RtcEngine | undefined = undefined;
41+ private audioRoutingManager = audio.getAudioManager().getRoutingManager();
3542 @State message: string = 'Hello World';
3643 @State channelName: string = ''
3744 @State isJoin: boolean = false
3845 @State localUid: number = 0
3946 @State remoteUidList: number[] = []
4047 @State isMicophotoOpen: boolean = false
4148 @State isEarMonitorChecked: boolean = false
42- @State routeSelectIndex: number = 0
4349 private channelProfileType = Constants.ChannelProfile.COMMUNICATION
4450 private audioScenarioType = Constants.AudioScenarioType.DEFAULT
4551 private audioProfileType = Constants.AudioProfileType.DEFAULT
52+
53+ @Builder
54+ customPickerBuilder(): void {
55+ Image($r('app.media.ic_connect'))
56+ .width('100%')
57+ .height('100%')
58+ // .fillColor(Color.Blue)
59+ }
4660 handleMicospeakerClick = () => {
4761 this.isMicophotoOpen = !this.isMicophotoOpen
4862 this.rtcEngine?.muteLocalAudioStream(!this.isMicophotoOpen);
4963 }
50- onAudioRouteSelect: OnSelectListener = (index: number, text: string) => {
51- Logger.info(TAG, `onAudioRouteSelect index ${index} text ${text}`)
52- this.routeSelectIndex = index
53- const isCommunication = this.channelProfileType == Constants.ChannelProfile.COMMUNICATION;
54- //todo
55- if (isCommunication) {
56- // const ret = this.rtcEngine.setRouteInCommunicationMode(this.audioRouteType);
57- // ShowToast.shortToast(`setRouteInCommunicationMode route=${this.audioRouteType} ret=${ret}`)
58- } else {
59- let isSpeakerPhone = false
60- const type = AudioConfigHelper.getAudioRouteType(this.routeSelectIndex)
61- if (type == Constants.AudioRouteTypes.AUDIO_ROUTE_EARPIECE) {
62- isSpeakerPhone = false;
63- } else if (type == Constants.AudioRouteTypes.AUDIO_ROUTE_SPEAKERPHONE) {
64- isSpeakerPhone = true;
65- }
66- // const ret = this.rtcEngine?.setEnableSpeakerphone(isSpeakerPhone);
67- // ShowToast.shortToast(`setEnableSpeakerphone enable==${isSpeakerPhone} ret=${ret}`)
68- }
69- }
7064 onInEarMonitorCheck: OnCheckListener = (isCheck: boolean) => {
7165 this.isEarMonitorChecked = isCheck
7266 }
@@ -106,7 +100,6 @@ struct JoinAudioChannel {
106100 }
107101
108102 startServiceTask() {
109-
110103 let wantAgentInfo: wantAgent.WantAgentInfo = {
111104 wants: [
112105 {
@@ -189,11 +182,22 @@ struct JoinAudioChannel {
189182 config.mContext = context;
190183 Logger.info(TAG, "in thread create engine begin: ");
191184 this.rtcEngine = RtcEngine.create(config) as RtcEngineEx
192-
193185 this.rtcEngine.enableAudio()
186+ const retAudio = this.rtcEngine.enableAudioVolumeIndication(1000, 3, true)
187+ Logger.info(TAG, `enableAudioVolumeIndication retAudio ${retAudio}`)
188+
189+ //注册路由监听
190+ this.audioRoutingManager.on('preferOutputDeviceChangeForRendererInfo', {
191+ usage: audio.StreamUsage.STREAM_USAGE_VOICE_COMMUNICATION, rendererFlags: 0
192+ }, (desc: audio.AudioDeviceDescriptors) => {
193+ //https://developer.huawei.com/consumer/cn/doc/harmonyos-references-V5/js-apis-audio-V5#devicetype
194+ //这个回调不是很及时
195+ Logger.info(TAG, `路由切换 设备类型 : ${desc[0].deviceType}`);
196+ });
194197 }
195198
196199 aboutToDisappear(): void {
200+ this.audioRoutingManager.off('preferOutputDeviceChangeForRendererInfo')
197201 if (this.rtcEngine != undefined) {
198202 if (this.isJoin) {
199203 this.rtcEngine.leaveChannel();
@@ -304,17 +308,28 @@ struct JoinAudioChannel {
304308 .align(Alignment.TopStart)
305309
306310 Column({ space: 5 }) {
307- Button((this.isJoin && !this.isMicophotoOpen) ? $r('app.string.open_microphone') :
308- $r('app.string.close_microphone'))
309- .onClick(this.handleMicospeakerClick)
310- .enabled(this.isJoin)
311+ Row() {
312+ Text('鸿蒙音频输出设备切换的API')
313+ Button((this.isJoin && !this.isMicophotoOpen) ? $r('app.string.open_microphone') :
314+ $r('app.string.close_microphone'))
315+ .onClick(this.handleMicospeakerClick)
316+ .enabled(this.isJoin)
317+ }
318+ .width('100%')
319+ .justifyContent(FlexAlign.SpaceBetween)
320+
321+ Row() {
322+ Text($r('app.string.audio_router'))
323+ AVCastPicker({
324+ normalColor: Color.Red,
325+ customPicker: () => this.customPickerBuilder()
326+ })
327+ .width(40)
328+ .height(40)
329+ }
330+ .width('100%')
331+ .justifyContent(FlexAlign.SpaceBetween)
311332
312- AudioChannelSpinner({
313- name: $r('app.string.audio_router'),
314- items: AUDIO_ROUTE,
315- selectIndex: this.routeSelectIndex,
316- onSelect: this.onAudioRouteSelect
317- })
318333 AudioChannelToggle({
319334 isEnable: this.isJoin,
320335 name: $r('app.string.inear_monitor'),
@@ -375,7 +390,6 @@ struct JoinAudioChannel {
375390 Button($r('app.string.leave'))
376391 .id('button_to_leave')
377392 .onClick(() => {
378- this.routeSelectIndex = 0
379393 this.rtcEngine?.stopPreview()
380394 this.rtcEngine?.leaveChannel()
381395 focusControl.requestFocus("button_to_leave")
0 commit comments