@tencent-rtc/mcp 1.4.6 → 1.6.0-beta.1
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/cursor-setting.png +0 -0
- package/knowledge/bm25-cache.js +74 -0
- package/knowledge/bm25-cache.js.map +1 -0
- package/knowledge/bm25.js +148 -0
- package/knowledge/bm25.js.map +1 -0
- package/knowledge/build-index.js +70 -0
- package/knowledge/build-index.js.map +1 -0
- package/knowledge/chunker.js +168 -0
- package/knowledge/chunker.js.map +1 -0
- package/knowledge/content-loader.js +40 -0
- package/knowledge/content-loader.js.map +1 -0
- package/knowledge/doc-url-resolver.js +143 -0
- package/knowledge/doc-url-resolver.js.map +1 -0
- package/knowledge/extractors.js +26 -0
- package/knowledge/extractors.js.map +1 -0
- package/knowledge/path-meta.js +185 -0
- package/knowledge/path-meta.js.map +1 -0
- package/knowledge/search/exact-lookup.js +498 -0
- package/knowledge/search/exact-lookup.js.map +1 -0
- package/knowledge/search/filter-pool.js +105 -0
- package/knowledge/search/filter-pool.js.map +1 -0
- package/knowledge/search/product-scope-intent.js +41 -0
- package/knowledge/search/product-scope-intent.js.map +1 -0
- package/knowledge/search/requires-framework.js +82 -0
- package/knowledge/search/requires-framework.js.map +1 -0
- package/knowledge/search/search-knowledge.js +230 -0
- package/knowledge/search/search-knowledge.js.map +1 -0
- package/mcp-server-prompt.png +0 -0
- package/package.json +1 -1
- package/resource/_schema/feature-aliases.yaml +10 -0
- package/resource/_schema/goal-tags.yaml +72 -0
- package/resource/_schema/products.yaml +19 -0
- package/resource/_schema/trtc-intents.yaml +27 -0
- package/resource/_schema/types.yaml +43 -0
- package/resource/index/component-slugs.json +1 -0
- package/resource/index/doc-source-urls.json +1 -0
- package/resource/index/manifest.json +1 -0
- package/resource/{doc → integration}/callkit/preset/android/integration.md +34 -28
- package/resource/integration/callkit/preset/flutter/integration.md +346 -0
- package/resource/integration/callkit/preset/ios/integration.md +408 -0
- package/resource/integration/callkit/preset/react/integration.md +362 -0
- package/resource/integration/callkit/preset/vue/integration.md +356 -0
- package/resource/integration/chat/preset/android/integration.md +500 -0
- package/resource/integration/chat/preset/flutter/integration.md +370 -0
- package/resource/integration/chat/preset/ios/integration.md +566 -0
- package/resource/integration/chat/preset/react/integration.md +490 -0
- package/resource/integration/chat/preset/vue/integration.md +504 -0
- package/resource/{doc → integration}/livekit/preset/live/vue/live-list-integration.md +26 -22
- package/resource/{doc → integration}/livekit/preset/live/vue/live-player-desk-integration.md +22 -18
- package/resource/integration/livekit/preset/live/vue/live-player-h5-integration.md +309 -0
- package/resource/{doc → integration}/livekit/preset/live/vue/live-pusher-integration.md +47 -39
- package/resource/integration/roomkit/preset/vue/integration.md +562 -0
- package/resource/knowledge/callkit/core-sdk/android/answer-call.md +828 -0
- package/resource/knowledge/callkit/core-sdk/android/make-call.md +897 -0
- package/resource/knowledge/callkit/core-sdk/android/offline-push.md +363 -0
- package/resource/knowledge/callkit/core-sdk/flutter/answer-call.md +1111 -0
- package/resource/knowledge/callkit/core-sdk/flutter/make-call.md +1132 -0
- package/resource/{doc → knowledge}/callkit/core-sdk/flutter/offline-push.md +174 -151
- package/resource/knowledge/callkit/core-sdk/ios/answer-call.md +1084 -0
- package/resource/knowledge/callkit/core-sdk/ios/make-call.md +1252 -0
- package/resource/knowledge/callkit/core-sdk/ios/offline-push.md +534 -0
- package/resource/knowledge/callkit/core-sdk/uni-app/answer-call.md +953 -0
- package/resource/knowledge/callkit/core-sdk/uni-app/make-call.md +1061 -0
- package/resource/knowledge/callkit/faq/android.md +92 -0
- package/resource/{doc/callkit/faq/android-faq.md → knowledge/callkit/faq/common.md} +11 -12
- package/resource/knowledge/callkit/faq/error-code.md +67 -0
- package/resource/knowledge/callkit/faq/flutter.md +52 -0
- package/resource/knowledge/callkit/faq/ios.md +104 -0
- package/resource/knowledge/callkit/faq/web.md +74 -0
- package/resource/knowledge/callkit/preset/android/api.md +412 -0
- package/resource/knowledge/callkit/preset/flutter/api.md +22 -0
- package/resource/knowledge/callkit/preset/ios/api.md +234 -0
- package/resource/knowledge/callkit/preset/web/api.md +83 -0
- package/resource/knowledge/chat/preset/android/features/chat-setting.md +74 -0
- package/resource/knowledge/chat/preset/android/features/contact-list.md +43 -0
- package/resource/knowledge/chat/preset/android/features/conversation-list.md +117 -0
- package/resource/knowledge/chat/preset/android/features/language.md +136 -0
- package/resource/knowledge/chat/preset/android/features/message-input.md +57 -0
- package/resource/knowledge/chat/preset/android/features/message-list.md +142 -0
- package/resource/knowledge/chat/preset/android/features/search.md +64 -0
- package/resource/knowledge/chat/preset/android/features/theme.md +222 -0
- package/resource/knowledge/chat/preset/android-view/integration.md +300 -0
- package/resource/knowledge/chat/preset/flutter/features/chat-setting.md +64 -0
- package/resource/knowledge/chat/preset/flutter/features/contact-list.md +40 -0
- package/resource/knowledge/chat/preset/flutter/features/conversation-list.md +129 -0
- package/resource/knowledge/chat/preset/flutter/features/language.md +104 -0
- package/resource/knowledge/chat/preset/flutter/features/message-input.md +54 -0
- package/resource/knowledge/chat/preset/flutter/features/message-list.md +158 -0
- package/resource/knowledge/chat/preset/flutter/features/search.md +59 -0
- package/resource/knowledge/chat/preset/flutter/features/theme.md +261 -0
- package/resource/knowledge/chat/preset/ios/features/chat-setting.md +94 -0
- package/resource/knowledge/chat/preset/ios/features/contact-list.md +119 -0
- package/resource/knowledge/chat/preset/ios/features/conversation-list.md +134 -0
- package/resource/knowledge/chat/preset/ios/features/language.md +125 -0
- package/resource/knowledge/chat/preset/ios/features/message-input.md +69 -0
- package/resource/knowledge/chat/preset/ios/features/message-list.md +162 -0
- package/resource/knowledge/chat/preset/ios/features/search.md +93 -0
- package/resource/knowledge/chat/preset/ios/features/theme.md +270 -0
- package/resource/{doc/chatkit/ios → knowledge/chat/preset/ios-uikit}/integration.md +160 -158
- package/resource/knowledge/chat/preset/react/features/chat-setting.md +101 -0
- package/resource/{doc/chatkit/react/components → knowledge/chat/preset/react/features}/contact-list.md +43 -41
- package/resource/knowledge/chat/preset/react/features/conversation-actions.md +215 -0
- package/resource/knowledge/chat/preset/react/features/conversation-list.md +339 -0
- package/resource/knowledge/chat/preset/react/features/conversation-preview.md +101 -0
- package/resource/knowledge/chat/preset/react/features/conversation-search.md +61 -0
- package/resource/{doc/chatkit/react/components → knowledge/chat/preset/react/features}/message-input.md +117 -156
- package/resource/knowledge/chat/preset/react/features/message-list.md +297 -0
- package/resource/{doc/chatkit/react/components → knowledge/chat/preset/react/features}/search.md +65 -59
- package/resource/knowledge/chat/preset/react/features/theme.md +93 -0
- package/resource/knowledge/chat/preset/vue/features/chat-header.md +331 -0
- package/resource/knowledge/chat/preset/vue/features/chat-setting.md +79 -0
- package/resource/knowledge/chat/preset/vue/features/contact-list.md +277 -0
- package/resource/knowledge/chat/preset/vue/features/conversation-actions.md +234 -0
- package/resource/knowledge/chat/preset/vue/features/conversation-list.md +331 -0
- package/resource/knowledge/chat/preset/vue/features/conversation-preview.md +216 -0
- package/resource/{doc/chatkit/vue/components → knowledge/chat/preset/vue/features}/conversation-search.md +13 -13
- package/resource/knowledge/chat/preset/vue/features/message-input.md +551 -0
- package/resource/knowledge/chat/preset/vue/features/message-list.md +350 -0
- package/resource/{doc/chatkit/vue/components → knowledge/chat/preset/vue/features}/search.md +79 -73
- package/resource/knowledge/chat/preset/vue/features/theme.md +136 -0
- package/resource/knowledge/chat/urls/error-code.md +17 -0
- package/resource/knowledge/chat/urls/product.md +43 -0
- package/resource/knowledge/chat/urls/restapi.md +204 -0
- package/resource/knowledge/chat/urls/sdk/android.md +80 -0
- package/resource/knowledge/chat/urls/sdk/flutter.md +71 -0
- package/resource/knowledge/chat/urls/sdk/ios.md +80 -0
- package/resource/knowledge/chat/urls/sdk/web.md +80 -0
- package/resource/knowledge/chat/urls/webhook.md +68 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/android/AudioEffectStore.md +286 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/android/BarrageStore.md +174 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/android/BattleStore.md +329 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/android/CameraView.md +55 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/android/CoGuestStore.md +434 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/android/CoHostStore.md +362 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/android/DeviceStore.md +466 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/android/GiftStore.md +173 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/android/LikeStore.md +51 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/android/LiveAudienceStore.md +291 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/android/LiveCoreView.md +78 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/android/LiveSeatStore.md +488 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/android/LoginStore.md +219 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/flutter/AudioEffectStore.md +282 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/flutter/BarrageStore.md +212 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/flutter/BaseBeautyStore.md +153 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/flutter/BattleStore.md +312 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/flutter/CoGuestStore.md +404 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/flutter/CoHostStore.md +334 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/flutter/DeviceStore.md +426 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/flutter/GiftStore.md +166 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/flutter/LikeStore.md +52 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/flutter/LiveAudienceStore.md +281 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/flutter/LiveCoreView.md +150 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/flutter/LiveSeatStore.md +438 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/flutter/LoginStore.md +190 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/ios/AudioEffectStore.md +291 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/ios/BarrageStore.md +192 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/ios/BaseBeautyStore.md +146 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/ios/BattleStore.md +309 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/ios/CoGuestStore.md +370 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/ios/CoHostStore.md +339 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/ios/DeviceStore.md +503 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/ios/GiftStore.md +188 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/ios/LikeStore.md +51 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/ios/LiveAudienceStore.md +289 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/ios/LiveCoreView.md +78 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/ios/LiveSeatStore.md +487 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/ios/LoginStore.md +183 -0
- package/resource/knowledge/livekit/core-sdk/api-reference/web/index.md +736 -0
- package/resource/{doc → knowledge}/livekit/core-sdk/live/android/live-audience-list.md +53 -47
- package/resource/{doc → knowledge}/livekit/core-sdk/live/android/live-audio-effect.md +28 -24
- package/resource/{doc → knowledge}/livekit/core-sdk/live/android/live-barrage.md +22 -18
- package/resource/{doc → knowledge}/livekit/core-sdk/live/android/live-base-beauty.md +17 -15
- package/resource/{doc → knowledge}/livekit/core-sdk/live/android/live-co-guest-interaction.md +19 -18
- package/resource/{doc → knowledge}/livekit/core-sdk/live/android/live-gift.md +102 -89
- package/resource/{doc → knowledge}/livekit/core-sdk/live/android/live-host-interaction.md +41 -37
- package/resource/{doc → knowledge}/livekit/core-sdk/live/android/live-integration.md +45 -43
- package/resource/{doc → knowledge}/livekit/core-sdk/live/android/live-live-list.md +23 -20
- package/resource/{doc → knowledge}/livekit/core-sdk/live/flutter/live-audience-list.md +41 -41
- package/resource/{doc → knowledge}/livekit/core-sdk/live/flutter/live-audio-effect.md +70 -69
- package/resource/{doc → knowledge}/livekit/core-sdk/live/flutter/live-barrage.md +68 -71
- package/resource/{doc → knowledge}/livekit/core-sdk/live/flutter/live-base-beauty.md +43 -47
- package/resource/{doc → knowledge}/livekit/core-sdk/live/flutter/live-co-guest-interaction.md +59 -56
- package/resource/{doc → knowledge}/livekit/core-sdk/live/flutter/live-gift.md +103 -105
- package/resource/knowledge/livekit/core-sdk/live/flutter/live-host-interaction.md +869 -0
- package/resource/{doc → knowledge}/livekit/core-sdk/live/flutter/live-integration.md +84 -87
- package/resource/{doc → knowledge}/livekit/core-sdk/live/flutter/live-live-list.md +43 -40
- package/resource/{doc → knowledge}/livekit/core-sdk/live/ios/live-audience-list.md +11 -10
- package/resource/{doc → knowledge}/livekit/core-sdk/live/ios/live-audio-effect.md +28 -24
- package/resource/{doc → knowledge}/livekit/core-sdk/live/ios/live-barrage.md +22 -18
- package/resource/{doc → knowledge}/livekit/core-sdk/live/ios/live-base-beauty.md +15 -14
- package/resource/{doc → knowledge}/livekit/core-sdk/live/ios/live-co-guest-interaction.md +19 -18
- package/resource/{doc → knowledge}/livekit/core-sdk/live/ios/live-gift.md +54 -50
- package/resource/{doc → knowledge}/livekit/core-sdk/live/ios/live-host-interaction.md +41 -37
- package/resource/{doc → knowledge}/livekit/core-sdk/live/ios/live-integration.md +40 -40
- package/resource/{doc → knowledge}/livekit/core-sdk/live/ios/live-live-list.md +19 -18
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/android/voice-audience-list.md +53 -47
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/android/voice-audio-effect.md +28 -24
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/android/voice-barrage.md +22 -18
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/android/voice-co-guest-interaction.md +41 -33
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/android/voice-gift.md +94 -81
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/android/voice-host-interaction.md +35 -30
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/android/voice-integration.md +45 -42
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/android/voice-room-list.md +23 -20
- package/resource/knowledge/livekit/core-sdk/voice/flutter/voice-audience-list.md +260 -0
- package/resource/knowledge/livekit/core-sdk/voice/flutter/voice-audio-effect.md +598 -0
- package/resource/knowledge/livekit/core-sdk/voice/flutter/voice-barrage.md +490 -0
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/flutter/voice-co-guest-interaction.md +65 -59
- package/resource/knowledge/livekit/core-sdk/voice/flutter/voice-gift.md +424 -0
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/flutter/voice-integration.md +69 -76
- package/resource/knowledge/livekit/core-sdk/voice/flutter/voice-room-list.md +726 -0
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/ios/voice-audience-list.md +11 -10
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/ios/voice-audio-effect.md +28 -24
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/ios/voice-barrage.md +22 -18
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/ios/voice-co-guest-interaction.md +41 -33
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/ios/voice-gift.md +54 -50
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/ios/voice-host-interaction.md +35 -30
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/ios/voice-integration.md +49 -46
- package/resource/{doc → knowledge}/livekit/core-sdk/voice/ios/voice-room-list.md +19 -18
- package/resource/knowledge/livekit/faq/error-code.md +193 -0
- package/resource/{doc/livekit/preset/live/vue/components → knowledge/livekit/preset/live/vue/features}/barrage.md +56 -53
- package/resource/{doc/livekit/preset/live/vue/components → knowledge/livekit/preset/live/vue/features}/live-audience-list.md +22 -21
- package/resource/{doc/livekit/preset/live/vue/components → knowledge/livekit/preset/live/vue/features}/live-view.md +34 -32
- package/resource/knowledge/push/config/android.md +92 -0
- package/resource/knowledge/push/config/harmonyos.md +83 -0
- package/resource/knowledge/push/config/ios.md +254 -0
- package/resource/knowledge/push/config/react-native.md +254 -0
- package/resource/knowledge/push/config/unity.md +209 -0
- package/resource/knowledge/push/config/unreal-engine.md +194 -0
- package/resource/knowledge/push/integration/android.md +404 -0
- package/resource/knowledge/push/integration/flutter.md +465 -0
- package/resource/knowledge/push/integration/harmonyos.md +63 -0
- package/resource/knowledge/push/integration/ios.md +246 -0
- package/resource/knowledge/push/integration/react-native.md +366 -0
- package/resource/knowledge/push/integration/uni-app.md +208 -0
- package/resource/knowledge/push/integration/unity.md +389 -0
- package/resource/knowledge/push/integration/unreal-engine.md +390 -0
- package/resource/knowledge/push/overview/prepare.md +60 -0
- package/resource/knowledge/roomkit/core-sdk/android/call-user-to-room.md +241 -0
- package/resource/knowledge/roomkit/core-sdk/android/room-participant-state.md +588 -0
- package/resource/knowledge/roomkit/core-sdk/android/room-state.md +364 -0
- package/resource/knowledge/roomkit/core-sdk/android/schedule-room.md +340 -0
- package/resource/knowledge/roomkit/core-sdk/flutter/call-user-to-room.md +230 -0
- package/resource/knowledge/roomkit/core-sdk/flutter/room-participant-state.md +797 -0
- package/resource/knowledge/roomkit/core-sdk/flutter/room-state.md +325 -0
- package/resource/knowledge/roomkit/core-sdk/flutter/schedule-room.md +325 -0
- package/resource/knowledge/roomkit/core-sdk/ios/call-user-to-room.md +233 -0
- package/resource/knowledge/roomkit/core-sdk/ios/room-participant-state.md +569 -0
- package/resource/knowledge/roomkit/core-sdk/ios/room-state.md +325 -0
- package/resource/knowledge/roomkit/core-sdk/ios/schedule-room.md +322 -0
- package/resource/knowledge/roomkit/core-sdk/vue/call-user-to-room.md +221 -0
- package/resource/{doc/roomkit/vue/features → knowledge/roomkit/core-sdk/vue}/device-detection.md +49 -48
- package/resource/knowledge/roomkit/core-sdk/vue/device-state.md +461 -0
- package/resource/knowledge/roomkit/core-sdk/vue/free-beauty-panel.md +216 -0
- package/resource/knowledge/roomkit/core-sdk/vue/room-chat.md +370 -0
- package/resource/{doc/roomkit/vue/features → knowledge/roomkit/core-sdk/vue}/room-participant-state.md +61 -60
- package/resource/knowledge/roomkit/core-sdk/vue/room-state.md +280 -0
- package/resource/{doc/roomkit/vue/features → knowledge/roomkit/core-sdk/vue}/room-view.md +57 -56
- package/resource/knowledge/roomkit/core-sdk/vue/schedule-room.md +319 -0
- package/resource/knowledge/roomkit/core-sdk/vue/screen-share.md +267 -0
- package/resource/knowledge/roomkit/core-sdk/vue/virtual-background.md +261 -0
- package/resource/knowledge/roomkit/preset/android/integration.md +396 -0
- package/resource/knowledge/roomkit/preset/flutter/integration.md +404 -0
- package/resource/knowledge/roomkit/preset/ios/integration.md +369 -0
- package/resource/knowledge/roomkit/preset/react/integration.md +576 -0
- package/resource/knowledge/rtcengine/web/how_to_run_web_sdk_demo.md +44 -0
- package/resource/{doc → knowledge}/rtcengine/web/plugin/21-advanced-auto-play-policy.md +8 -2
- package/resource/{doc → knowledge}/rtcengine/web/plugin/22-advanced-audio-mixer.md +19 -1
- package/resource/{doc → knowledge}/rtcengine/web/plugin/23-advanced-support-detection.md +1 -1
- package/resource/{doc → knowledge}/rtcengine/web/plugin/24-advanced-network-quality.md +8 -8
- package/resource/{doc → knowledge}/rtcengine/web/plugin/25-advanced-device-change.md +1 -1
- package/resource/{doc → knowledge}/rtcengine/web/plugin/26-advanced-publish-cdn-stream.md +6 -6
- package/resource/{doc → knowledge}/rtcengine/web/plugin/27-advanced-small-stream.md +3 -3
- package/resource/{doc → knowledge}/rtcengine/web/plugin/29-advanced-water-mark.md +18 -0
- package/resource/{doc → knowledge}/rtcengine/web/plugin/31-advanced-plugins-overview.md +1 -1
- package/resource/{doc → knowledge}/rtcengine/web/plugin/34-advanced-proxy.md +2 -2
- package/resource/{doc → knowledge}/rtcengine/web/plugin/35-advanced-ai-denoiser.md +1 -1
- package/resource/knowledge/trtc/android/TRTCCloud.md +1915 -0
- package/resource/knowledge/trtc/android/TRTCCloudDef.md +1029 -0
- package/resource/knowledge/trtc/android/TRTCCloudListener.md +1095 -0
- package/resource/knowledge/trtc/android/TRTCStatistics.md +68 -0
- package/resource/knowledge/trtc/android/TXAudioEffectManager.md +502 -0
- package/resource/knowledge/trtc/android/TXBeautyManager.md +415 -0
- package/resource/knowledge/trtc/android/TXDeviceManager.md +169 -0
- package/resource/knowledge/trtc/android/TXLiteAVCode.md +125 -0
- package/resource/knowledge/trtc/c++/ITRTCCloud.md +2069 -0
- package/resource/knowledge/trtc/c++/ITRTCStatistics.md +73 -0
- package/resource/knowledge/trtc/c++/ITXAudioEffectManager.md +502 -0
- package/resource/knowledge/trtc/c++/ITXDeviceManager.md +391 -0
- package/resource/knowledge/trtc/c++/TRTCCloudCallback.md +1191 -0
- package/resource/knowledge/trtc/c++/TRTCTypeDef.md +931 -0
- package/resource/knowledge/trtc/c++/TXLiteAVCode.md +127 -0
- package/resource/knowledge/trtc/ios/TRTCCloud.md +2118 -0
- package/resource/knowledge/trtc/ios/TRTCCloudDef.md +975 -0
- package/resource/knowledge/trtc/ios/TRTCCloudDelegate.md +1131 -0
- package/resource/knowledge/trtc/ios/TRTCStatistics.md +68 -0
- package/resource/knowledge/trtc/ios/TXAudioEffectManager.md +423 -0
- package/resource/knowledge/trtc/ios/TXBeautyManager.md +416 -0
- package/resource/knowledge/trtc/ios/TXDeviceManager.md +387 -0
- package/resource/knowledge/trtc/ios/TXLiteAVCode.md +127 -0
- package/server.js +35 -10
- package/server.js.map +1 -1
- package/tools/call/get_native_call_uikit_integration.js +2 -3
- package/tools/call/get_native_call_uikit_integration.js.map +1 -1
- package/tools/call/get_native_callkit_core_integration.js +2 -5
- package/tools/call/get_native_callkit_core_integration.js.map +1 -1
- package/tools/call/get_web_call_uikit_integration.js +2 -3
- package/tools/call/get_web_call_uikit_integration.js.map +1 -1
- package/tools/chat/get_native_chat_uikit_integration.js +2 -3
- package/tools/chat/get_native_chat_uikit_integration.js.map +1 -1
- package/tools/chat/get_web_chat_uikit_integration.js +2 -3
- package/tools/chat/get_web_chat_uikit_integration.js.map +1 -1
- package/tools/common/present_framework_choice.js +19 -13
- package/tools/common/present_framework_choice.js.map +1 -1
- package/tools/common/record_answer.js +19 -25
- package/tools/common/record_answer.js.map +1 -1
- package/tools/common/record_feedback.js +17 -30
- package/tools/common/record_feedback.js.map +1 -1
- package/tools/common/search_trtc_knowledge.js +45 -0
- package/tools/common/search_trtc_knowledge.js.map +1 -0
- package/tools/definitions/get_native_call_uikit_integration_def.js +3 -1
- package/tools/definitions/get_native_call_uikit_integration_def.js.map +1 -1
- package/tools/definitions/get_native_callkit_core_integration_def.js +5 -3
- package/tools/definitions/get_native_callkit_core_integration_def.js.map +1 -1
- package/tools/definitions/get_native_chat_uikit_integration_def.js +5 -2
- package/tools/definitions/get_native_chat_uikit_integration_def.js.map +1 -1
- package/tools/definitions/get_native_livekit_core_integration_def.js +6 -5
- package/tools/definitions/get_native_livekit_core_integration_def.js.map +1 -1
- package/tools/definitions/get_web_call_uikit_integration_def.js +4 -2
- package/tools/definitions/get_web_call_uikit_integration_def.js.map +1 -1
- package/tools/definitions/get_web_chat_uikit_integration_def.js +2 -0
- package/tools/definitions/get_web_chat_uikit_integration_def.js.map +1 -1
- package/tools/definitions/get_web_live_uikit_integration_def.js +5 -5
- package/tools/definitions/get_web_live_uikit_integration_def.js.map +1 -1
- package/tools/definitions/get_web_room_core_integration_def.js +50 -0
- package/tools/definitions/get_web_room_core_integration_def.js.map +1 -0
- package/tools/definitions/get_web_room_uikit_integration_def.js +5 -4
- package/tools/definitions/get_web_room_uikit_integration_def.js.map +1 -1
- package/tools/definitions/integration-boundary.js +6 -0
- package/tools/definitions/integration-boundary.js.map +1 -0
- package/tools/definitions/present_framework_choice_def.js +12 -10
- package/tools/definitions/present_framework_choice_def.js.map +1 -1
- package/tools/definitions/record_answer_def.js +19 -17
- package/tools/definitions/record_answer_def.js.map +1 -1
- package/tools/definitions/record_feedback_def.js +14 -13
- package/tools/definitions/record_feedback_def.js.map +1 -1
- package/tools/definitions/search_trtc_knowledge_def.js +40 -0
- package/tools/definitions/search_trtc_knowledge_def.js.map +1 -0
- package/tools/index.js +5 -36
- package/tools/index.js.map +1 -1
- package/tools/live/get_native_livekit_core_integration.js +1 -3
- package/tools/live/get_native_livekit_core_integration.js.map +1 -1
- package/tools/live/get_web_live_uikit_integration.js +2 -4
- package/tools/live/get_web_live_uikit_integration.js.map +1 -1
- package/tools/room/get_web_room_core_integration.js +48 -0
- package/tools/room/get_web_room_core_integration.js.map +1 -0
- package/tools/room/get_web_room_uikit_integration.js +2 -3
- package/tools/room/get_web_room_uikit_integration.js.map +1 -1
- package/utils/generate-structured-result.js +24 -30
- package/utils/generate-structured-result.js.map +1 -1
- package/utils/get-doc-content.js +14 -8
- package/utils/get-doc-content.js.map +1 -1
- package/utils/report-cls-client.js +18 -20
- package/utils/report-cls-client.js.map +1 -1
- package/utils/report-es-client.js +1 -1
- package/resource/doc/callkit/core-sdk/.gitkeep +0 -0
- package/resource/doc/callkit/core-sdk/android/answer-call.md +0 -852
- package/resource/doc/callkit/core-sdk/android/make-call.md +0 -954
- package/resource/doc/callkit/core-sdk/android/offline-push.md +0 -361
- package/resource/doc/callkit/core-sdk/flutter/answer-call.md +0 -1160
- package/resource/doc/callkit/core-sdk/flutter/make-call.md +0 -1205
- package/resource/doc/callkit/core-sdk/ios/answer-call.md +0 -1090
- package/resource/doc/callkit/core-sdk/ios/make-call.md +0 -1248
- package/resource/doc/callkit/core-sdk/ios/offline-push.md +0 -485
- package/resource/doc/callkit/core-sdk/uni-app/answer-call.md +0 -950
- package/resource/doc/callkit/core-sdk/uni-app/make-call.md +0 -1052
- package/resource/doc/callkit/faq/common/error-code.md +0 -47
- package/resource/doc/callkit/faq/flutter-faq.md +0 -115
- package/resource/doc/callkit/faq/ios-faq.md +0 -115
- package/resource/doc/callkit/faq/web-faq.md +0 -36
- package/resource/doc/callkit/preset/android/api.md +0 -296
- package/resource/doc/callkit/preset/flutter/api.md +0 -410
- package/resource/doc/callkit/preset/flutter/integration.md +0 -164
- package/resource/doc/callkit/preset/ios/api.md +0 -80
- package/resource/doc/callkit/preset/ios/integration.md +0 -187
- package/resource/doc/callkit/preset/react/api.md +0 -501
- package/resource/doc/callkit/preset/react/integration.md +0 -86
- package/resource/doc/callkit/preset/vue/api.md +0 -501
- package/resource/doc/callkit/preset/vue/integration.md +0 -83
- package/resource/doc/chatkit/android/faq.md +0 -111
- package/resource/doc/chatkit/android/features/theme.md +0 -219
- package/resource/doc/chatkit/android/integration.md +0 -490
- package/resource/doc/chatkit/faq/android_sdk/client-api.md +0 -281
- package/resource/doc/chatkit/faq/common/product.md +0 -7
- package/resource/doc/chatkit/faq/common/server.md +0 -44
- package/resource/doc/chatkit/faq/common/server_error_code.md +0 -74
- package/resource/doc/chatkit/faq/flutter_sdk/client-api.md +0 -199
- package/resource/doc/chatkit/faq/flutter_sdk/faq.md +0 -53
- package/resource/doc/chatkit/faq/ios_sdk/client-api.md +0 -235
- package/resource/doc/chatkit/faq/web_sdk/error_code.md +0 -47
- package/resource/doc/chatkit/faq/web_sdk/faq.md +0 -287
- package/resource/doc/chatkit/flutter/faq.md +0 -23
- package/resource/doc/chatkit/flutter/features/theme.md +0 -235
- package/resource/doc/chatkit/flutter/integration.md +0 -344
- package/resource/doc/chatkit/ios/faq.md +0 -111
- package/resource/doc/chatkit/ios/features/theme.md +0 -267
- package/resource/doc/chatkit/react/components/avatar.md +0 -104
- package/resource/doc/chatkit/react/components/chat-header.md +0 -148
- package/resource/doc/chatkit/react/components/chat-setting.md +0 -57
- package/resource/doc/chatkit/react/components/chat.md +0 -38
- package/resource/doc/chatkit/react/components/component-list.md +0 -37
- package/resource/doc/chatkit/react/components/conversation-actions.md +0 -174
- package/resource/doc/chatkit/react/components/conversation-list.md +0 -333
- package/resource/doc/chatkit/react/components/conversation-preview.md +0 -118
- package/resource/doc/chatkit/react/components/conversation-search.md +0 -60
- package/resource/doc/chatkit/react/components/message-list.md +0 -293
- package/resource/doc/chatkit/react/components/tuikit.md +0 -34
- package/resource/doc/chatkit/react/faq.md +0 -26
- package/resource/doc/chatkit/react/integration.md +0 -416
- package/resource/doc/chatkit/vue/components/avatar.md +0 -104
- package/resource/doc/chatkit/vue/components/chat-header.md +0 -148
- package/resource/doc/chatkit/vue/components/chat-setting.md +0 -62
- package/resource/doc/chatkit/vue/components/chat.md +0 -45
- package/resource/doc/chatkit/vue/components/component-list.md +0 -87
- package/resource/doc/chatkit/vue/components/contact-list.md +0 -271
- package/resource/doc/chatkit/vue/components/conversation-actions.md +0 -228
- package/resource/doc/chatkit/vue/components/conversation-list.md +0 -320
- package/resource/doc/chatkit/vue/components/conversation-preview.md +0 -213
- package/resource/doc/chatkit/vue/components/message-input.md +0 -1054
- package/resource/doc/chatkit/vue/components/message-list.md +0 -433
- package/resource/doc/chatkit/vue/components/tuikit.md +0 -31
- package/resource/doc/chatkit/vue/components/userpicker.md +0 -256
- package/resource/doc/chatkit/vue/faq.md +0 -36
- package/resource/doc/chatkit/vue/integration.md +0 -428
- package/resource/doc/livekit/core-sdk/live/flutter/live-host-interaction.md +0 -866
- package/resource/doc/livekit/faq/common/error-code.md +0 -88
- package/resource/doc/livekit/preset/live/vue/api-reference/index.md +0 -780
- package/resource/doc/livekit/preset/live/vue/components/co-guest-panel.md +0 -91
- package/resource/doc/livekit/preset/live/vue/components/live-scene-panel.md +0 -112
- package/resource/doc/livekit/preset/live/vue/components/stream-mixer.md +0 -215
- package/resource/doc/livekit/preset/live/vue/live-player-h5-integration.md +0 -300
- package/resource/doc/roomkit/faq/common/error-code.md +0 -67
- package/resource/doc/roomkit/vue/features/call-user-to-room.md +0 -220
- package/resource/doc/roomkit/vue/features/device-state.md +0 -460
- package/resource/doc/roomkit/vue/features/free-beauty-panel.md +0 -215
- package/resource/doc/roomkit/vue/features/room-chat.md +0 -369
- package/resource/doc/roomkit/vue/features/room-state.md +0 -282
- package/resource/doc/roomkit/vue/features/schedule-room.md +0 -318
- package/resource/doc/roomkit/vue/features/screen-share.md +0 -265
- package/resource/doc/roomkit/vue/features/virtual-background.md +0 -271
- package/resource/doc/roomkit/vue/integration.md +0 -315
- package/resource/doc/rtcengine/faq/common/error_code.md +0 -1
- package/resource/doc/rtcengine/faq/web_sdk/.gitkeep +0 -0
- package/resource/doc/rtcengine/web/.gitkeep +0 -0
- package/resource/doc/rtcengine/web/how_to_run_web_sdk_demo.md +0 -59
- package/resource/doc/trtc/C++/ITRTCCloud.md +0 -1970
- package/resource/doc/trtc/C++/ITRTCStatistics.md +0 -70
- package/resource/doc/trtc/C++/ITXAudioEffectManager.md +0 -469
- package/resource/doc/trtc/C++/ITXDeviceManager.md +0 -387
- package/resource/doc/trtc/C++/TRTCCloudCallback.md +0 -1082
- package/resource/doc/trtc/C++/TRTCTypeDef.md +0 -925
- package/resource/doc/trtc/C++/TXLiteAVCode.md +0 -129
- package/resource/doc/trtc/android/TRTCCloud.md +0 -1815
- package/resource/doc/trtc/android/TRTCCloudDef.md +0 -992
- package/resource/doc/trtc/android/TRTCCloudListener.md +0 -1004
- package/resource/doc/trtc/android/TRTCStatistics.md +0 -65
- package/resource/doc/trtc/android/TXAudioEffectManager.md +0 -469
- package/resource/doc/trtc/android/TXBeautyManager.md +0 -402
- package/resource/doc/trtc/android/TXDeviceManager.md +0 -173
- package/resource/doc/trtc/android/TXLiteAVCode.md +0 -127
- package/resource/doc/trtc/iOS/TRTCCloud.md +0 -2028
- package/resource/doc/trtc/iOS/TRTCCloudDef.md +0 -958
- package/resource/doc/trtc/iOS/TRTCCloudDelegate.md +0 -1046
- package/resource/doc/trtc/iOS/TRTCStatistics.md +0 -65
- package/resource/doc/trtc/iOS/TXAudioEffectManager.md +0 -397
- package/resource/doc/trtc/iOS/TXBeautyManager.md +0 -403
- package/resource/doc/trtc/iOS/TXDeviceManager.md +0 -381
- package/resource/doc/trtc/iOS/TXLiteAVCode.md +0 -130
- package/tools/call/get_callkit_api.js +0 -33
- package/tools/call/get_callkit_api.js.map +0 -1
- package/tools/chat/get_native_chat_uikit_feature_detail.js +0 -35
- package/tools/chat/get_native_chat_uikit_feature_detail.js.map +0 -1
- package/tools/chat/get_web_chat_uikit_component_detail.js +0 -35
- package/tools/chat/get_web_chat_uikit_component_detail.js.map +0 -1
- package/tools/common/get_faq.js +0 -266
- package/tools/common/get_faq.js.map +0 -1
- package/tools/common/record_skill_session.js +0 -69
- package/tools/common/record_skill_session.js.map +0 -1
- package/tools/definitions/get_callkit_api_def.js +0 -29
- package/tools/definitions/get_callkit_api_def.js.map +0 -1
- package/tools/definitions/get_faq_def.js +0 -49
- package/tools/definitions/get_faq_def.js.map +0 -1
- package/tools/definitions/get_native_chat_uikit_feature_detail_def.js +0 -31
- package/tools/definitions/get_native_chat_uikit_feature_detail_def.js.map +0 -1
- package/tools/definitions/get_native_livekit_core_features_def.js +0 -34
- package/tools/definitions/get_native_livekit_core_features_def.js.map +0 -1
- package/tools/definitions/get_native_trtc_sdk_docs_def.js +0 -32
- package/tools/definitions/get_native_trtc_sdk_docs_def.js.map +0 -1
- package/tools/definitions/get_web_chat_uikit_component_detail_def.js +0 -31
- package/tools/definitions/get_web_chat_uikit_component_detail_def.js.map +0 -1
- package/tools/definitions/get_web_livekit_api_def.js +0 -30
- package/tools/definitions/get_web_livekit_api_def.js.map +0 -1
- package/tools/definitions/get_web_livekit_component_detail_def.js +0 -32
- package/tools/definitions/get_web_livekit_component_detail_def.js.map +0 -1
- package/tools/definitions/get_web_roomkit_feature_detail_def.js +0 -31
- package/tools/definitions/get_web_roomkit_feature_detail_def.js.map +0 -1
- package/tools/definitions/get_web_trtc_sdk_api_def.js +0 -27
- package/tools/definitions/get_web_trtc_sdk_api_def.js.map +0 -1
- package/tools/definitions/get_web_trtc_sdk_integration_def.js +0 -27
- package/tools/definitions/get_web_trtc_sdk_integration_def.js.map +0 -1
- package/tools/definitions/get_web_trtc_sdk_plugin_def.js +0 -27
- package/tools/definitions/get_web_trtc_sdk_plugin_def.js.map +0 -1
- package/tools/definitions/record_skill_session_def.js +0 -31
- package/tools/definitions/record_skill_session_def.js.map +0 -1
- package/tools/live/get_native_livekit_core_features.js +0 -68
- package/tools/live/get_native_livekit_core_features.js.map +0 -1
- package/tools/live/get_web_livekit_api.js +0 -33
- package/tools/live/get_web_livekit_api.js.map +0 -1
- package/tools/live/get_web_livekit_component_detail.js +0 -35
- package/tools/live/get_web_livekit_component_detail.js.map +0 -1
- package/tools/room/get_web_roomkit_feature_detail.js +0 -69
- package/tools/room/get_web_roomkit_feature_detail.js.map +0 -1
- package/tools/rtcengine/get_web_trtc_sdk_api.js +0 -32
- package/tools/rtcengine/get_web_trtc_sdk_api.js.map +0 -1
- package/tools/rtcengine/get_web_trtc_sdk_integration.js +0 -32
- package/tools/rtcengine/get_web_trtc_sdk_integration.js.map +0 -1
- package/tools/rtcengine/get_web_trtc_sdk_plugin.js +0 -32
- package/tools/rtcengine/get_web_trtc_sdk_plugin.js.map +0 -1
- package/tools/trtc/get_native_trtc_sdk_docs.js +0 -74
- package/tools/trtc/get_native_trtc_sdk_docs.js.map +0 -1
- package/utils/build-session-directives.js +0 -120
- package/utils/build-session-directives.js.map +0 -1
- package/utils/handle-framework.js +0 -9
- package/utils/handle-framework.js.map +0 -1
- package/utils/handle-state-name.js +0 -29
- package/utils/handle-state-name.js.map +0 -1
- package/utils/report-runtime-error-cls-client.js +0 -91
- package/utils/report-runtime-error-cls-client.js.map +0 -1
- /package/resource/{doc/livekit/preset/live/vue/faq.md → knowledge/push/config/donut.md} +0 -0
- /package/resource/{doc/roomkit/vue/faq.md → knowledge/push/integration/donut.md} +0 -0
- /package/resource/{doc → knowledge}/rtcengine/web/api.md +0 -0
- /package/resource/{doc/rtcengine/faq/web/web.md → knowledge/rtcengine/web/faq.md} +0 -0
- /package/resource/{doc → knowledge}/rtcengine/web/how_to_integrated_web_sdk.md +0 -0
- /package/resource/{doc → knowledge}/rtcengine/web/plugin/20-advanced-customized-capture-rendering.md +0 -0
- /package/resource/{doc → knowledge}/rtcengine/web/plugin/28-advanced-beauty.md +0 -0
- /package/resource/{doc → knowledge}/rtcengine/web/plugin/30-advanced-cross-room-link.md +0 -0
- /package/resource/{doc → knowledge}/rtcengine/web/plugin/36-advanced-virtual-background.md +0 -0
- /package/resource/{doc → knowledge}/rtcengine/web/plugin/37-advanced-voice-changer.md +0 -0
- /package/resource/{doc → knowledge}/rtcengine/web/plugin/39-advanced-video-decoder.md +0 -0
- /package/resource/{doc → knowledge}/rtcengine/web/plugin/40-advanced-video-mixer.md +0 -0
- /package/resource/{doc → knowledge}/rtcengine/web/plugin/41-advanced-small-stream-auto-switcher.md +0 -0
- /package/resource/{doc → knowledge}/rtcengine/web/plugin/42-advanced-realtime-transcriber.md +0 -0
- /package/resource/{doc → knowledge}/rtcengine/web/plugin/43-advanced-face-detection.md +0 -0
|
@@ -1,1205 +0,0 @@
|
|
|
1
|
-
This guide shows you how to use the **AtomicXCore SDK** components — **DeviceStore**, **CallStore**, and **CallCoreView** — to quickly implement an audio/video call feature.
|
|
2
|
-
|
|
3
|
-
## Core Features
|
|
4
|
-
|
|
5
|
-
To build multi-party audio/video call scenarios with **AtomicXCore**, you'll need these three modules:
|
|
6
|
-
|
|
7
|
-
| **Module** | **Description** |
|
|
8
|
-
| --- | --- |
|
|
9
|
-
| [CallCoreView](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_view_call_call_core_view/CallCoreView-class.html) | Core UI component for calls. Automatically observes CallStore data and renders the interface, switching layouts between 1v1 and group calls as needed. |
|
|
10
|
-
| [CallStore](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_call_call_store/CallStore-class.html) | Manages the call lifecycle: make, answer, reject, hang up. Provides real-time status for participants' audio/video, call duration, call history, and more. |
|
|
11
|
-
| [DeviceStore](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_device_device_store/DeviceStore-class.html) | Controls audio/video devices: microphone (toggle/volume), camera (toggle/switch/quality), screen sharing, and monitors device status in real time. |
|
|
12
|
-
|
|
13
|
-
## Preparation
|
|
14
|
-
|
|
15
|
-
### Step 1: Activate the Service
|
|
16
|
-
|
|
17
|
-
To obtain either a trial or paid version of the SDK, follow the instructions in **Activate the Service**.
|
|
18
|
-
|
|
19
|
-
### Step 2: Integrate the SDK
|
|
20
|
-
|
|
21
|
-
**Install the package:** In your project root, run the following command:
|
|
22
|
-
|
|
23
|
-
```bash
|
|
24
|
-
flutter pub add atomic_x_core
|
|
25
|
-
```
|
|
26
|
-
|
|
27
|
-
### Step 3: Initialize and Log in
|
|
28
|
-
|
|
29
|
-
#### Android Configuration
|
|
30
|
-
|
|
31
|
-
1. The SDK uses Java reflection, so you must prevent certain SDK classes from being obfuscated.
|
|
32
|
-
|
|
33
|
-
In your project's `android/app/` directory, update `build.gradle.kts` or `build.gradle` to enable ProGuard rules:
|
|
34
|
-
|
|
35
|
-
**build.gradle.kts:**
|
|
36
|
-
|
|
37
|
-
```kotlin
|
|
38
|
-
android {
|
|
39
|
-
buildTypes {
|
|
40
|
-
release {
|
|
41
|
-
isMinifyEnabled = true
|
|
42
|
-
proguardFiles(
|
|
43
|
-
getDefaultProguardFile("proguard-android.txt"),
|
|
44
|
-
"proguard-rules.pro"
|
|
45
|
-
)
|
|
46
|
-
}
|
|
47
|
-
}
|
|
48
|
-
}
|
|
49
|
-
```
|
|
50
|
-
|
|
51
|
-
**build.gradle:**
|
|
52
|
-
|
|
53
|
-
```groovy
|
|
54
|
-
android {
|
|
55
|
-
buildTypes {
|
|
56
|
-
release {
|
|
57
|
-
minifyEnabled true
|
|
58
|
-
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
|
|
59
|
-
}
|
|
60
|
-
}
|
|
61
|
-
}
|
|
62
|
-
```
|
|
63
|
-
|
|
64
|
-
Create a `proguard-rules.pro` file in `android/app` and add:
|
|
65
|
-
|
|
66
|
-
```proguard
|
|
67
|
-
-keep class com.tencent.** { *; }
|
|
68
|
-
```
|
|
69
|
-
|
|
70
|
-
2. (Optional) To enable CallKit's floating window outside the app, turn on system Picture-in-Picture for `MainActivity` in `AndroidManifest.xml`:
|
|
71
|
-
|
|
72
|
-
```xml
|
|
73
|
-
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
|
|
74
|
-
<application>
|
|
75
|
-
<activity
|
|
76
|
-
android:name=".MainActivity"
|
|
77
|
-
android:supportsPictureInPicture="true"
|
|
78
|
-
</activity>
|
|
79
|
-
</application>
|
|
80
|
-
</manifest>
|
|
81
|
-
```
|
|
82
|
-
|
|
83
|
-
#### iOS Configuration
|
|
84
|
-
|
|
85
|
-
If you encounter a `symbol not found` error in Release on iOS (due to Flutter FFI symbol stripping), do the following:
|
|
86
|
-
|
|
87
|
-
1. In Xcode **Build Settings**, set **Deployment Postprocessing** to **Yes**.
|
|
88
|
-
2. Set **Strip Style** for **Release** to **Non-Global Symbols**.
|
|
89
|
-
|
|
90
|
-
#### Flutter Initialization & Login Process
|
|
91
|
-
|
|
92
|
-
Before you can place calls, complete these steps in order:
|
|
93
|
-
|
|
94
|
-
1. **Create `CallStore`:** `CallStore.shared` initializes the call data layer.
|
|
95
|
-
2. **Log in the user:** call `LoginStore.shared.login(sdkAppId, userId, userSig)` to complete IM login.
|
|
96
|
-
3. **Initialize the call engine:** call `TUICallEngine.instance.init(sdkAppId, userId, userSig)` to initialize the TRTC call signaling engine (**required**; omitting this may prevent calls from being placed or received correctly).
|
|
97
|
-
|
|
98
|
-
Example:
|
|
99
|
-
|
|
100
|
-
```dart
|
|
101
|
-
import 'package:atomic_x_core/atomicxcore.dart';
|
|
102
|
-
import 'package:rtc_room_engine/api/call/tui_call_engine.dart';
|
|
103
|
-
|
|
104
|
-
Future<void> _login() async {
|
|
105
|
-
int sdkAppId = 1400000001; // Enter your SDKAppID
|
|
106
|
-
String userId = 'test_001'; // Enter your UserID
|
|
107
|
-
String userSig = 'xxxxxxxxxxx'; // Use a temporary userSig during development; when MCP is configured with sdkAppId and sdkSecretKey, the tool can issue it for you
|
|
108
|
-
|
|
109
|
-
CallStore.shared;
|
|
110
|
-
final result = await LoginStore.shared.login(sdkAppId, userId, userSig);
|
|
111
|
-
TUICallEngine.instance.init(sdkAppId, userId, userSig);
|
|
112
|
-
if (result.isSuccess) {
|
|
113
|
-
// Login successful
|
|
114
|
-
debugPrint('login success');
|
|
115
|
-
} else {
|
|
116
|
-
// Login failed
|
|
117
|
-
debugPrint('login failed, code: ${result.code}, message: ${result.message}');
|
|
118
|
-
}
|
|
119
|
-
}
|
|
120
|
-
```
|
|
121
|
-
|
|
122
|
-
| **Parameter** | **Type** | **Description** |
|
|
123
|
-
| --- | --- | --- |
|
|
124
|
-
| `userId` | String | Unique user ID, up to **32 bytes**, with **no special characters**; use letters and digits. Avoid simple IDs like `1` or `123` to reduce multi-device conflicts. |
|
|
125
|
-
| `sdkAppId` | int | Get this from the console, usually a 10-digit integer starting with `140` or `160`. |
|
|
126
|
-
| `userSig` | String | Authentication token for TRTC. For development, generate `userSig` locally using [GenerateTestUserSig.genTestUserSig](https://github.com/Tencent-RTC/TUIKit_Flutter/blob/main/call/example/lib/debug/generate_test_user_sig.dart) for temporary use. When the **Tencent RTC MCP Server** is configured with `sdkAppId` and `sdkSecretKey`, the tool can auto-issue a `userSig` for you. For production, always generate `userSig` on your server to protect your secret key. |
|
|
127
|
-
|
|
128
|
-
## Implementation Steps
|
|
129
|
-
|
|
130
|
-
**Make sure you have logged in before initiating a call.** Service is unavailable until login is complete. Follow these 5 steps to implement the "make a call" feature.
|
|
131
|
-
|
|
132
|
-
### Step 1: Create the Call Interface
|
|
133
|
-
|
|
134
|
-
You need a dedicated call page to display when a call is active.
|
|
135
|
-
|
|
136
|
-
1. **Create the call page:** Implement a `StatefulWidget` for your call host page, which will be used for navigation on incoming calls.
|
|
137
|
-
|
|
138
|
-
2. **Add CallCoreView to the call page:** `CallCoreView` takes a `controller` parameter, observes `CallStore` data, and automatically adjusts the layout for 1v1 or multi-party calls.
|
|
139
|
-
|
|
140
|
-
```dart
|
|
141
|
-
import 'package:flutter/material.dart';
|
|
142
|
-
import 'package:atomic_x_core/atomicxcore.dart';
|
|
143
|
-
|
|
144
|
-
// 1. Create call page Widget
|
|
145
|
-
class CallPage extends StatefulWidget {
|
|
146
|
-
const CallPage({super.key});
|
|
147
|
-
|
|
148
|
-
@override
|
|
149
|
-
State<CallPage> createState() => _CallPageState();
|
|
150
|
-
}
|
|
151
|
-
|
|
152
|
-
class _CallPageState extends State<CallPage> {
|
|
153
|
-
late CallCoreController controller;
|
|
154
|
-
|
|
155
|
-
@override
|
|
156
|
-
void initState() {
|
|
157
|
-
super.initState();
|
|
158
|
-
controller = CallCoreController.create();
|
|
159
|
-
}
|
|
160
|
-
|
|
161
|
-
@override
|
|
162
|
-
Widget build(BuildContext context) {
|
|
163
|
-
// 2. Use CallCoreView Widget on the call page
|
|
164
|
-
return CallCoreView(controller: controller);
|
|
165
|
-
}
|
|
166
|
-
}
|
|
167
|
-
```
|
|
168
|
-
|
|
169
|
-
**CallCoreView Widget Features:**
|
|
170
|
-
|
|
171
|
-
| **Feature** | **Description** | **Reference** |
|
|
172
|
-
| --- | --- | --- |
|
|
173
|
-
| Set layout mode | Supports dynamic layout mode switching. If not set, layout auto-adapts by participant count. | Switch Layout Modes |
|
|
174
|
-
| Set avatar | Allows custom avatars for users by passing resource paths. | Custom Default Avatar |
|
|
175
|
-
| Set volume indicator icon | Custom icons for different volume levels. | Custom Volume Indicator Icons |
|
|
176
|
-
| Set network indicator icon | Custom icons for real-time network quality. | Custom Network Indicator Icons |
|
|
177
|
-
| Set waiting animation | Displays GIF animation for users in a waiting state during multi-party calls. | Custom Loading Animation |
|
|
178
|
-
|
|
179
|
-
### Step 2: Add Call Control Buttons
|
|
180
|
-
|
|
181
|
-
Customize your control buttons using [DeviceStore](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_device_device_store/DeviceStore-class.html) and [CallStore](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_call_call_store/CallStore-class.html) APIs:
|
|
182
|
-
|
|
183
|
-
- **DeviceStore:** Controls microphone (toggle/volume), camera (toggle/switch/quality), screen sharing, and monitors device status. Bind button actions to these methods and listen for status changes to update UI in real time.
|
|
184
|
-
- **CallStore:** Handles answering, hanging up, and rejecting calls. Bind these methods to button actions and listen for call status changes to sync UI accordingly.
|
|
185
|
-
- **Button icon resources:** Download the TUICallKit button icons from [GitHub](https://github.com/Tencent-RTC/TUIKit_Flutter/tree/main/atomic-x/call_assets). These are copyright-free.
|
|
186
|
-
|
|
187
|
-
**Available Icon Resources:**
|
|
188
|
-
|
|
189
|
-
| **Resource** | **Description** | **Download** |
|
|
190
|
-
| --- | --- | --- |
|
|
191
|
-
| `callview_ic_hangup.png` | Hang up icon. | [GitHub](https://github.com/Tencent-RTC/TUIKit_Android/blob/main/atomic_x/src/main/res-callview/drawable-xxhdpi/callview_ic_hangup.png) |
|
|
192
|
-
| `callview_ic_handsfree_disable.png` | Hands-free disabled icon. | [GitHub](https://github.com/Tencent-RTC/TUIKit_Android/blob/main/atomic_x/src/main/res-callview/drawable-xxhdpi/callview_ic_handsfree_disable.png) |
|
|
193
|
-
| `callview_ic_handsfree_enable.png` | Hands-free enabled icon. | [GitHub](https://github.com/Tencent-RTC/TUIKit_Android/blob/main/atomic_x/src/main/res-callview/drawable-xxhdpi/callview_ic_handsfree_enable.png) |
|
|
194
|
-
|
|
195
|
-
**Example: Adding hang up, microphone, and camera buttons**
|
|
196
|
-
|
|
197
|
-
1. **Create a container for control buttons:** Place hang up, microphone, and camera buttons at the bottom of your call page.
|
|
198
|
-
|
|
199
|
-
```dart
|
|
200
|
-
import 'package:flutter/material.dart';
|
|
201
|
-
import 'package:atomic_x_core/atomicxcore.dart';
|
|
202
|
-
|
|
203
|
-
// Bottom control button container Widget
|
|
204
|
-
class ControlsContainer extends StatelessWidget {
|
|
205
|
-
const ControlsContainer({super.key});
|
|
206
|
-
|
|
207
|
-
@override
|
|
208
|
-
Widget build(BuildContext context) {
|
|
209
|
-
return Row(
|
|
210
|
-
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
|
|
211
|
-
children: [
|
|
212
|
-
// Add control buttons here
|
|
213
|
-
],
|
|
214
|
-
);
|
|
215
|
-
}
|
|
216
|
-
}
|
|
217
|
-
```
|
|
218
|
-
|
|
219
|
-
2. **Add hang up button:** Call `hangup` to end the call and close the page.
|
|
220
|
-
|
|
221
|
-
```dart
|
|
222
|
-
import 'package:atomic_x_core/atomicxcore.dart';
|
|
223
|
-
import 'package:flutter/material.dart';
|
|
224
|
-
|
|
225
|
-
// Hang up button Widget
|
|
226
|
-
Widget buildHangupButton() {
|
|
227
|
-
return GestureDetector(
|
|
228
|
-
onTap: () {
|
|
229
|
-
// Call hangup API to end the call
|
|
230
|
-
CallStore.shared.hangup();
|
|
231
|
-
},
|
|
232
|
-
child: Container(
|
|
233
|
-
width: 60,
|
|
234
|
-
height: 60,
|
|
235
|
-
decoration: const BoxDecoration(
|
|
236
|
-
color: Colors.red,
|
|
237
|
-
shape: BoxShape.circle,
|
|
238
|
-
),
|
|
239
|
-
child: const Icon(
|
|
240
|
-
Icons.call_end,
|
|
241
|
-
color: Colors.white,
|
|
242
|
-
size: 30,
|
|
243
|
-
),
|
|
244
|
-
),
|
|
245
|
-
);
|
|
246
|
-
}
|
|
247
|
-
```
|
|
248
|
-
|
|
249
|
-
3. **Add microphone toggle button:** Use `openLocalMicrophone` and `closeLocalMicrophone` to toggle the mic.
|
|
250
|
-
|
|
251
|
-
```dart
|
|
252
|
-
import 'package:atomic_x_core/atomicxcore.dart';
|
|
253
|
-
import 'package:flutter/material.dart';
|
|
254
|
-
|
|
255
|
-
// Microphone toggle button Widget
|
|
256
|
-
// Use ValueListenableBuilder to listen for microphone status changes
|
|
257
|
-
Widget buildMicrophoneButton() {
|
|
258
|
-
return ValueListenableBuilder(
|
|
259
|
-
valueListenable: DeviceStore.shared.state.microphoneStatus,
|
|
260
|
-
builder: (context, status, child) {
|
|
261
|
-
final isOn = status == DeviceStatus.on;
|
|
262
|
-
return GestureDetector(
|
|
263
|
-
onTap: () {
|
|
264
|
-
// Toggle microphone based on current status
|
|
265
|
-
if (isOn) {
|
|
266
|
-
DeviceStore.shared.closeLocalMicrophone();
|
|
267
|
-
} else {
|
|
268
|
-
DeviceStore.shared.openLocalMicrophone();
|
|
269
|
-
}
|
|
270
|
-
},
|
|
271
|
-
child: Container(
|
|
272
|
-
width: 60,
|
|
273
|
-
height: 60,
|
|
274
|
-
decoration: BoxDecoration(
|
|
275
|
-
color: Colors.white.withOpacity(0.2),
|
|
276
|
-
shape: BoxShape.circle,
|
|
277
|
-
),
|
|
278
|
-
child: Icon(
|
|
279
|
-
isOn ? Icons.mic : Icons.mic_off,
|
|
280
|
-
color: Colors.white,
|
|
281
|
-
size: 30,
|
|
282
|
-
),
|
|
283
|
-
),
|
|
284
|
-
);
|
|
285
|
-
},
|
|
286
|
-
);
|
|
287
|
-
}
|
|
288
|
-
```
|
|
289
|
-
|
|
290
|
-
4. **Add camera toggle button:** Use `openLocalCamera` and `closeLocalCamera` to toggle the camera.
|
|
291
|
-
|
|
292
|
-
```dart
|
|
293
|
-
import 'package:atomic_x_core/atomicxcore.dart';
|
|
294
|
-
import 'package:flutter/material.dart';
|
|
295
|
-
|
|
296
|
-
// Camera toggle button Widget
|
|
297
|
-
// Use ValueListenableBuilder to listen for camera status changes
|
|
298
|
-
Widget buildCameraButton() {
|
|
299
|
-
return ValueListenableBuilder(
|
|
300
|
-
valueListenable: DeviceStore.shared.state.cameraStatus,
|
|
301
|
-
builder: (context, status, child) {
|
|
302
|
-
final isOn = status == DeviceStatus.on;
|
|
303
|
-
return GestureDetector(
|
|
304
|
-
onTap: () {
|
|
305
|
-
// Toggle camera based on current status
|
|
306
|
-
if (isOn) {
|
|
307
|
-
DeviceStore.shared.closeLocalCamera();
|
|
308
|
-
} else {
|
|
309
|
-
final isFrontCamera = DeviceStore.shared.state.isFrontCamera.value;
|
|
310
|
-
DeviceStore.shared.openLocalCamera(isFrontCamera);
|
|
311
|
-
}
|
|
312
|
-
},
|
|
313
|
-
child: Container(
|
|
314
|
-
width: 60,
|
|
315
|
-
height: 60,
|
|
316
|
-
decoration: BoxDecoration(
|
|
317
|
-
color: Colors.white.withOpacity(0.2),
|
|
318
|
-
shape: BoxShape.circle,
|
|
319
|
-
),
|
|
320
|
-
child: Icon(
|
|
321
|
-
isOn ? Icons.videocam : Icons.videocam_off,
|
|
322
|
-
color: Colors.white,
|
|
323
|
-
size: 30,
|
|
324
|
-
),
|
|
325
|
-
),
|
|
326
|
-
);
|
|
327
|
-
},
|
|
328
|
-
);
|
|
329
|
-
}
|
|
330
|
-
```
|
|
331
|
-
|
|
332
|
-
5. **Update device button status in real time:** Use `ValueListenableBuilder` to react to device status changes.
|
|
333
|
-
|
|
334
|
-
```dart
|
|
335
|
-
import 'package:atomic_x_core/atomicxcore.dart';
|
|
336
|
-
import 'package:flutter/material.dart';
|
|
337
|
-
|
|
338
|
-
// In Flutter, use ValueListenableBuilder for reactive state updates
|
|
339
|
-
// When DeviceStore state changes, UI rebuilds automatically
|
|
340
|
-
Widget buildDeviceControlButtons() {
|
|
341
|
-
return Row(
|
|
342
|
-
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
|
|
343
|
-
children: [
|
|
344
|
-
// Microphone button - reacts to microphoneStatus changes
|
|
345
|
-
ValueListenableBuilder(
|
|
346
|
-
valueListenable: DeviceStore.shared.state.microphoneStatus,
|
|
347
|
-
builder: (context, status, _) {
|
|
348
|
-
final isOn = status == DeviceStatus.on;
|
|
349
|
-
return Text(isOn ? 'Turn off microphone' : 'Turn on microphone');
|
|
350
|
-
},
|
|
351
|
-
),
|
|
352
|
-
// Camera button - reacts to cameraStatus changes
|
|
353
|
-
ValueListenableBuilder(
|
|
354
|
-
valueListenable: DeviceStore.shared.state.cameraStatus,
|
|
355
|
-
builder: (context, status, _) {
|
|
356
|
-
final isOn = status == DeviceStatus.on;
|
|
357
|
-
return Text(isOn ? 'Turn off camera' : 'Turn on camera');
|
|
358
|
-
},
|
|
359
|
-
),
|
|
360
|
-
],
|
|
361
|
-
);
|
|
362
|
-
}
|
|
363
|
-
```
|
|
364
|
-
|
|
365
|
-
### Step 3: Request Microphone/Camera Permissions
|
|
366
|
-
|
|
367
|
-
Check audio/video permissions before placing a call. If anything is missing, guide the user to grant it at runtime.
|
|
368
|
-
|
|
369
|
-
1. **Android permission declaration:**
|
|
370
|
-
|
|
371
|
-
Declare camera and microphone permissions in `AndroidManifest.xml`.
|
|
372
|
-
|
|
373
|
-
```xml
|
|
374
|
-
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
|
|
375
|
-
<!-- Microphone permission -->
|
|
376
|
-
<uses-permission android:name="android.permission.RECORD_AUDIO" />
|
|
377
|
-
<!-- Camera permission -->
|
|
378
|
-
<uses-permission android:name="android.permission.CAMERA" />
|
|
379
|
-
</manifest>
|
|
380
|
-
```
|
|
381
|
-
|
|
382
|
-
2. **iOS permission declaration:**
|
|
383
|
-
|
|
384
|
-
Under the root `<dict>` in your iOS app's `Info.plist`, add:
|
|
385
|
-
|
|
386
|
-
```xml
|
|
387
|
-
<key>NSCameraUsageDescription</key>
|
|
388
|
-
<string>CallingApp needs access to your camera. Video recording requires camera permission.</string>
|
|
389
|
-
<key>NSMicrophoneUsageDescription</key>
|
|
390
|
-
<string>CallingApp needs access to your microphone. Video recording requires microphone permission.</string>
|
|
391
|
-
```
|
|
392
|
-
|
|
393
|
-
3. **Dynamic permission requests:** We recommend the `permission_handler` plugin:
|
|
394
|
-
|
|
395
|
-
```bash
|
|
396
|
-
flutter pub add permission_handler
|
|
397
|
-
```
|
|
398
|
-
|
|
399
|
-
4. **iOS Podfile configuration (required):**
|
|
400
|
-
|
|
401
|
-
On iOS, `permission_handler` uses preprocessor macros per permission type; by default macros are **0** (off). You **must** enable the ones you need in `ios/Podfile` inside `post_install`, or permission requests may return **`denied`** immediately without showing the system dialog.
|
|
402
|
-
|
|
403
|
-
Edit `post_install`:
|
|
404
|
-
|
|
405
|
-
```ruby
|
|
406
|
-
post_install do |installer|
|
|
407
|
-
installer.pods_project.targets.each do |target|
|
|
408
|
-
flutter_additional_ios_build_settings(target)
|
|
409
|
-
target.build_configurations.each do |config|
|
|
410
|
-
config.build_settings['GCC_PREPROCESSOR_DEFINITIONS'] ||= [
|
|
411
|
-
'$(inherited)',
|
|
412
|
-
'PERMISSION_CAMERA=1',
|
|
413
|
-
'PERMISSION_MICROPHONE=1',
|
|
414
|
-
]
|
|
415
|
-
end
|
|
416
|
-
end
|
|
417
|
-
end
|
|
418
|
-
```
|
|
419
|
-
|
|
420
|
-
> **Note:** After changing `Podfile`, run `cd ios && pod install` again so the change takes effect.
|
|
421
|
-
|
|
422
|
-
5. **Request at runtime:** Before placing a call, call:
|
|
423
|
-
|
|
424
|
-
```dart
|
|
425
|
-
import 'package:permission_handler/permission_handler.dart';
|
|
426
|
-
|
|
427
|
-
// Request audio/video permissions
|
|
428
|
-
Future<bool> requestCallPermissions() async {
|
|
429
|
-
// Request microphone and camera permissions
|
|
430
|
-
Map<Permission, PermissionStatus> statuses = await [
|
|
431
|
-
Permission.microphone,
|
|
432
|
-
Permission.camera,
|
|
433
|
-
].request();
|
|
434
|
-
|
|
435
|
-
// Check permission status
|
|
436
|
-
bool micGranted = statuses[Permission.microphone]?.isGranted ?? false;
|
|
437
|
-
bool cameraGranted = statuses[Permission.camera]?.isGranted ?? false;
|
|
438
|
-
|
|
439
|
-
if (micGranted && cameraGranted) {
|
|
440
|
-
// Permissions granted
|
|
441
|
-
return true;
|
|
442
|
-
} else {
|
|
443
|
-
// Some permissions denied, prompt user to enable
|
|
444
|
-
return false;
|
|
445
|
-
}
|
|
446
|
-
}
|
|
447
|
-
```
|
|
448
|
-
|
|
449
|
-
### Step 4: Initiate a Call
|
|
450
|
-
|
|
451
|
-
After calling [calls](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_call_call_store/CallStore/calls.html), navigate to the call interface. Automatically enable microphone and/or camera based on the chosen media type.
|
|
452
|
-
|
|
453
|
-
1. **Initiate the call:** Call `calls` to start.
|
|
454
|
-
2. **Enable media devices:** After calling, enable the microphone; for video calls, enable the camera as well.
|
|
455
|
-
3. **Navigate to the call page:** On success, push the call page.
|
|
456
|
-
|
|
457
|
-
```dart
|
|
458
|
-
import 'package:atomic_x_core/atomicxcore.dart';
|
|
459
|
-
import 'package:flutter/material.dart';
|
|
460
|
-
|
|
461
|
-
// Initiate call
|
|
462
|
-
Future<void> startCall(List<String> userIdList, CallMediaType mediaType) async {
|
|
463
|
-
final handler = await CallStore.shared.calls(userIdList, mediaType, null);
|
|
464
|
-
if (handler.errorCode == 0) {
|
|
465
|
-
// Navigate to call page
|
|
466
|
-
if (mounted) {
|
|
467
|
-
Navigator.push(
|
|
468
|
-
context,
|
|
469
|
-
MaterialPageRoute(builder: (context) => const CallPage()),
|
|
470
|
-
);
|
|
471
|
-
}
|
|
472
|
-
} else {
|
|
473
|
-
debugPrint('Call failed: ${handler.errorCode}, ${handler.errorMessage}');
|
|
474
|
-
}
|
|
475
|
-
}
|
|
476
|
-
```
|
|
477
|
-
|
|
478
|
-
**calls API Parameter Details:**
|
|
479
|
-
|
|
480
|
-
| **Parameter** | **Type** | **Required** | **Description** |
|
|
481
|
-
| --- | --- | --- | --- |
|
|
482
|
-
| `userIdList` | List<String> | Yes | List of target users' `userId`. |
|
|
483
|
-
| `mediaType` | CallMediaType | Yes | Specifies call type: audio or video. `CallMediaType.video`: Video call. `CallMediaType.audio`: Audio call. |
|
|
484
|
-
| `params` | CallParams | No | Additional parameters: room ID, timeout, custom data, group ID, ephemeral flag. |
|
|
485
|
-
|
|
486
|
-
### Step 5: End the Call
|
|
487
|
-
|
|
488
|
-
When you call [hangup](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_call_call_store/CallStore/hangup.html) or the other party ends the call, the [onCallEnded](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_call_call_store/CallEventListener/onCallEnded.html) event fires. Listen for this event and close the call interface accordingly.
|
|
489
|
-
|
|
490
|
-
1. **Listen for call end event:** Subscribe to `onCallEnded`.
|
|
491
|
-
2. **Destroy the call page:** On event, close the call UI.
|
|
492
|
-
|
|
493
|
-
```dart
|
|
494
|
-
import 'package:atomic_x_core/atomicxcore.dart';
|
|
495
|
-
import 'package:flutter/cupertino.dart';
|
|
496
|
-
|
|
497
|
-
void addListener(BuildContext context) {
|
|
498
|
-
CallEventListener listener = CallEventListener(
|
|
499
|
-
onCallEnded: (callId, mediaType, reason, userId) {
|
|
500
|
-
Navigator.of(context).pop();
|
|
501
|
-
}
|
|
502
|
-
);
|
|
503
|
-
CallStore.shared.addListener(listener);
|
|
504
|
-
}
|
|
505
|
-
```
|
|
506
|
-
|
|
507
|
-
**onCallEnded Event Parameter Details:**
|
|
508
|
-
|
|
509
|
-
| **Parameter** | **Type** | **Description** |
|
|
510
|
-
| --- | --- | --- |
|
|
511
|
-
| `callId` | String | Unique identifier for the call. |
|
|
512
|
-
| `mediaType` | CallMediaType | Specifies audio or video call. `CallMediaType.video`: Video. `CallMediaType.audio`: Audio. |
|
|
513
|
-
| `reason` | CallEndReason | Reason for call end. Possible values: `unknown`, `hangup`, `reject`, `noResponse`, `offline`, `lineBusy`, `canceled`, `otherDeviceAccepted`, `otherDeviceReject`, `endByServer`. |
|
|
514
|
-
| `userId` | String | User ID that triggered the end event. |
|
|
515
|
-
|
|
516
|
-
## Customizing the Interface
|
|
517
|
-
|
|
518
|
-
`CallCoreView` supports extensive UI customization, including avatars and volume indicator icons. For fast integration, download TUICallKit icons from [GitHub](https://github.com/Tencent-RTC/TUIKit_Flutter/tree/main/atomic-x/call_assets). All icons are copyright-free.
|
|
519
|
-
|
|
520
|
-
### Custom Volume Indicator Icons
|
|
521
|
-
|
|
522
|
-
Use the [volumeIcons](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_view_call_call_core_view/CallCoreView/volumeIcons.html) parameter in `CallCoreView` to assign icons for each volume level.
|
|
523
|
-
|
|
524
|
-
**Sample usage:**
|
|
525
|
-
|
|
526
|
-
```dart
|
|
527
|
-
Widget _buildCallCoreView() {
|
|
528
|
-
Map<VolumeLevel, Image> volumeIcons = {
|
|
529
|
-
VolumeLevel.mute: Image.asset(''), // Icon for mute
|
|
530
|
-
};
|
|
531
|
-
return CallCoreView(
|
|
532
|
-
controller: CallCoreController.create(),
|
|
533
|
-
volumeIcons: volumeIcons,
|
|
534
|
-
);
|
|
535
|
-
}
|
|
536
|
-
```
|
|
537
|
-
|
|
538
|
-
**volumeIcons Parameter Details:**
|
|
539
|
-
|
|
540
|
-
| **Parameter** | **Type** | **Required** | **Description** |
|
|
541
|
-
| --- | --- | --- | --- |
|
|
542
|
-
| `volumeIcons` | Map | No | Maps volume levels to icons. Keys: `VolumeLevel.mute` (muted), `VolumeLevel.low` (0-25), `VolumeLevel.medium` (25-50), `VolumeLevel.high` (50-75), `VolumeLevel.peak` (75-100). |
|
|
543
|
-
|
|
544
|
-
**Volume Indicator Icons:**
|
|
545
|
-
|
|
546
|
-
| **Resource** | **Description** | **Download** |
|
|
547
|
-
| --- | --- | --- |
|
|
548
|
-
| `callview_ic_audio_input.png` | Volume indicator icon; use for `VolumeLevel.low` or `VolumeLevel.medium`. | [GitHub](https://github.com/Tencent-RTC/TUIKit_Android/blob/main/atomic_x/src/main/res-callview/drawable-xxhdpi/callview_ic_audio_input.png) |
|
|
549
|
-
| `callview_ic_self_mute.png` | Mute icon; use for `VolumeLevel.mute`. | [GitHub](https://github.com/Tencent-RTC/TUIKit_Android/blob/main/atomic_x/src/main/res-callview/drawable-xxhdpi/callview_ic_self_mute.png) |
|
|
550
|
-
|
|
551
|
-
### Custom Network Indicator Icons
|
|
552
|
-
|
|
553
|
-
Use [networkQualityIcons](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_view_call_call_core_view/CallCoreView/networkQualityIcons.html) in `CallCoreView` to set icons for different network states.
|
|
554
|
-
|
|
555
|
-
**Sample usage:**
|
|
556
|
-
|
|
557
|
-
```dart
|
|
558
|
-
Widget _buildCallCoreView() {
|
|
559
|
-
Map<NetworkQuality, Image> networkQualityIcons = {
|
|
560
|
-
NetworkQuality.bad: Image.asset(''), // Icon for poor network
|
|
561
|
-
};
|
|
562
|
-
return CallCoreView(
|
|
563
|
-
controller: CallCoreController.create(),
|
|
564
|
-
networkQualityIcons: networkQualityIcons,
|
|
565
|
-
);
|
|
566
|
-
}
|
|
567
|
-
```
|
|
568
|
-
|
|
569
|
-
**networkQualityIcons Parameter Details:**
|
|
570
|
-
|
|
571
|
-
| **Parameter** | **Type** | **Required** | **Description** |
|
|
572
|
-
| --- | --- | --- | --- |
|
|
573
|
-
| `networkQualityIcons` | Map | No | Maps network quality to icons. Keys: `NetworkQuality.unknown`, `NetworkQuality.excellent`, `NetworkQuality.good`, `NetworkQuality.poor`, `NetworkQuality.bad`, `NetworkQuality.veryBad`, `NetworkQuality.down`. |
|
|
574
|
-
|
|
575
|
-
**Poor Network Indicator Icon:**
|
|
576
|
-
|
|
577
|
-
| **Resource** | **Description** | **Download** |
|
|
578
|
-
| --- | --- | --- |
|
|
579
|
-
| `callview_ic_network_bad.png` | Poor network indicator; use for `NetworkQuality.bad`, `NetworkQuality.veryBad`, or `NetworkQuality.down`. | [GitHub](https://github.com/Tencent-RTC/TUIKit_Android/blob/main/atomic_x/src/main/res-callview/drawable-xxhdpi/callview_ic_network_bad.png) |
|
|
580
|
-
|
|
581
|
-
### Custom Default Avatar
|
|
582
|
-
|
|
583
|
-
Use [defaultAvatar](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_view_call_call_core_view/CallCoreView/defaultAvatar.html) in `CallCoreView` to specify a fallback user avatar. Monitor [allParticipants](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_call_call_store/CallState/allParticipants.html) for custom avatars; show the default avatar if none is set or loading fails.
|
|
584
|
-
|
|
585
|
-
**Sample usage:**
|
|
586
|
-
|
|
587
|
-
```dart
|
|
588
|
-
Widget _buildCallCoreView() {
|
|
589
|
-
Image defaultAvatarImage = Image.asset(''); // Default avatar image
|
|
590
|
-
return CallCoreView(
|
|
591
|
-
controller: CallCoreController.create(),
|
|
592
|
-
defaultAvatar: defaultAvatarImage,
|
|
593
|
-
);
|
|
594
|
-
}
|
|
595
|
-
```
|
|
596
|
-
|
|
597
|
-
**defaultAvatar Parameter Details:**
|
|
598
|
-
|
|
599
|
-
| **Parameter** | **Type** | **Required** | **Description** |
|
|
600
|
-
| --- | --- | --- | --- |
|
|
601
|
-
| `defaultAvatar` | Image | No | Default avatar image. |
|
|
602
|
-
|
|
603
|
-
**Default Avatar Resource:**
|
|
604
|
-
|
|
605
|
-
| **Resource** | **Description** | **Download** |
|
|
606
|
-
| --- | --- | --- |
|
|
607
|
-
| `callview_ic_avatar.png` | Default avatar; use as a placeholder when loading fails or no avatar is set. | [GitHub](https://github.com/Tencent-RTC/TUIKit_Android/blob/main/atomic_x/src/main/res-callview/drawable-xxhdpi/callview_ic_avatar.png) |
|
|
608
|
-
|
|
609
|
-
### Custom Loading Animation
|
|
610
|
-
|
|
611
|
-
Use [loadingAnimation](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_view_call_call_core_view/CallCoreView/loadingAnimation.html) in `CallCoreView` to set a waiting animation for users not yet connected.
|
|
612
|
-
|
|
613
|
-
**Sample usage:**
|
|
614
|
-
|
|
615
|
-
```dart
|
|
616
|
-
Widget _buildCallCoreView() {
|
|
617
|
-
Image loading = Image.asset(''); // Loading animation resource
|
|
618
|
-
return CallCoreView(
|
|
619
|
-
controller: CallCoreController.create(),
|
|
620
|
-
loadingAnimation: loading,
|
|
621
|
-
);
|
|
622
|
-
}
|
|
623
|
-
```
|
|
624
|
-
|
|
625
|
-
**loadingAnimation Parameter Details:**
|
|
626
|
-
|
|
627
|
-
| **Parameter** | **Type** | **Required** | **Description** |
|
|
628
|
-
| --- | --- | --- | --- |
|
|
629
|
-
| `loadingAnimation` | Image | No | GIF animation resource for waiting state. |
|
|
630
|
-
|
|
631
|
-
**Waiting Animation:**
|
|
632
|
-
|
|
633
|
-
| **Resource** | **Description** | **Download** |
|
|
634
|
-
| --- | --- | --- |
|
|
635
|
-
| `callview_ic_loading.gif` | Waiting animation; use for group calls to indicate users in waiting state. | [GitHub](https://github.com/Tencent-RTC/TUIKit_Android/blob/main/atomic_x/src/main/res-callview/drawable-xxhdpi/callview_ic_loading.gif) |
|
|
636
|
-
|
|
637
|
-
### Add Call Duration Indicator
|
|
638
|
-
|
|
639
|
-
You can display call duration in real time using [activeCall](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_call_call_store/CallState/activeCall.html) and its `duration` field.
|
|
640
|
-
|
|
641
|
-
1. **Subscribe to call data:** Listen to `CallStore.shared.state.activeCall` for updates.
|
|
642
|
-
2. **Bind duration to UI:** Use the `activeCall.duration` field in your widget. This value updates reactively — no timer needed.
|
|
643
|
-
|
|
644
|
-
```dart
|
|
645
|
-
import 'package:atomic_x_core/atomicxcore.dart';
|
|
646
|
-
import 'package:flutter/material.dart';
|
|
647
|
-
|
|
648
|
-
class TimerWidget extends StatelessWidget {
|
|
649
|
-
final double? fontSize;
|
|
650
|
-
final FontWeight? fontWeight;
|
|
651
|
-
|
|
652
|
-
const TimerWidget({
|
|
653
|
-
super.key,
|
|
654
|
-
this.fontSize,
|
|
655
|
-
this.fontWeight,
|
|
656
|
-
});
|
|
657
|
-
|
|
658
|
-
@override
|
|
659
|
-
Widget build(BuildContext context) {
|
|
660
|
-
return ValueListenableBuilder(
|
|
661
|
-
valueListenable: CallStore.shared.state.selfInfo,
|
|
662
|
-
builder: (context, info, child) {
|
|
663
|
-
if (info.status == CallParticipantStatus.accept) {
|
|
664
|
-
return ValueListenableBuilder(
|
|
665
|
-
valueListenable: CallStore.shared.state.activeCall,
|
|
666
|
-
builder: (context, activeCall, child) {
|
|
667
|
-
return Text(
|
|
668
|
-
formatDuration(activeCall.duration.toInt()),
|
|
669
|
-
style: TextStyle(
|
|
670
|
-
fontSize: fontSize,
|
|
671
|
-
fontWeight: fontWeight,
|
|
672
|
-
),
|
|
673
|
-
);
|
|
674
|
-
},
|
|
675
|
-
);
|
|
676
|
-
} else {
|
|
677
|
-
return Container();
|
|
678
|
-
}
|
|
679
|
-
}
|
|
680
|
-
);
|
|
681
|
-
}
|
|
682
|
-
|
|
683
|
-
String formatDuration(int timeCount) {
|
|
684
|
-
int hour = timeCount ~/ 3600;
|
|
685
|
-
int minute = (timeCount % 3600) ~/ 60;
|
|
686
|
-
String minuteShow = minute <= 9 ? "0$minute" : "$minute";
|
|
687
|
-
int second = timeCount % 60;
|
|
688
|
-
String secondShow = second <= 9 ? "0$second" : "$second";
|
|
689
|
-
|
|
690
|
-
if (hour > 0) {
|
|
691
|
-
String hourShow = hour <= 9 ? "0$hour" : "$hour";
|
|
692
|
-
return '$hourShow:$minuteShow:$secondShow';
|
|
693
|
-
} else {
|
|
694
|
-
return '$minuteShow:$secondShow';
|
|
695
|
-
}
|
|
696
|
-
}
|
|
697
|
-
}
|
|
698
|
-
```
|
|
699
|
-
|
|
700
|
-
> **Note:**
|
|
701
|
-
>
|
|
702
|
-
> For more reactive call state data, see [CallState](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_call_call_store/CallState-class.html).
|
|
703
|
-
|
|
704
|
-
## More Features
|
|
705
|
-
|
|
706
|
-
### Set Avatar and Nickname
|
|
707
|
-
|
|
708
|
-
Before making a call, set your nickname and avatar via [setSelfInfo](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_login_login_store/LoginStore/setSelfInfo.html):
|
|
709
|
-
|
|
710
|
-
```dart
|
|
711
|
-
UserProfile profile = UserProfile(
|
|
712
|
-
userID: "", // Your UserId
|
|
713
|
-
avatarURL: "", // Avatar URL
|
|
714
|
-
nickname: "", // Nickname to set
|
|
715
|
-
);
|
|
716
|
-
CompletionHandler result = await LoginStore.shared.setSelfInfo(userInfo: profile);
|
|
717
|
-
if (result.errorCode == 0) {
|
|
718
|
-
print("setSelfInfo success");
|
|
719
|
-
} else {
|
|
720
|
-
print("setSelfInfo failed");
|
|
721
|
-
}
|
|
722
|
-
```
|
|
723
|
-
|
|
724
|
-
**setSelfInfo API Parameter Details:**
|
|
725
|
-
|
|
726
|
-
| **Parameter** | **Type** | **Required** | **Description** |
|
|
727
|
-
| --- | --- | --- | --- |
|
|
728
|
-
| `userProfile` | [UserProfile](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_login_login_store/UserProfile-class.html) | Yes | User info struct: `userID` (String), `avatarURL` (String), `nickname` (String). |
|
|
729
|
-
| `completion` | CompletionHandler | No | Callback returns result of set operation. |
|
|
730
|
-
|
|
731
|
-
### Switch Layout Modes
|
|
732
|
-
|
|
733
|
-
Switch layouts flexibly using [setLayoutTemplate](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_view_call_call_core_view/CallCoreController/setLayoutTemplate.html). If not set, `CallCoreView` adapts automatically: 1v1 defaults to `Float`, group calls use `Grid`.
|
|
734
|
-
|
|
735
|
-
| **Mode** | **Layout** | **Interaction** |
|
|
736
|
-
| --- | --- | --- |
|
|
737
|
-
| Float | Full-screen self-view while waiting; after connecting, full-screen remote view with self-view as a floating window. | Floating window supports drag and click-to-swap with the main view. |
|
|
738
|
-
| Grid | Grid layout for all participants, suitable for 2+ users. Supports click-to-enlarge. | Click any participant's view to enlarge. |
|
|
739
|
-
| PIP | 1v1 shows fixed remote view; multi-party uses active-speaker strategy with full screen for the current speaker. | Waiting state shows self-view; after connecting, call duration is displayed. |
|
|
740
|
-
|
|
741
|
-
**Sample usage:**
|
|
742
|
-
|
|
743
|
-
```dart
|
|
744
|
-
CallCoreController controller = CallCoreController.create();
|
|
745
|
-
CallLayoutTemplate template = CallLayoutTemplate.float;
|
|
746
|
-
controller.setLayoutTemplate(template);
|
|
747
|
-
```
|
|
748
|
-
|
|
749
|
-
**setLayoutTemplate API Parameter Details:**
|
|
750
|
-
|
|
751
|
-
| **Parameter** | **Type** | **Required** | **Description** |
|
|
752
|
-
| --- | --- | --- | --- |
|
|
753
|
-
| `template` | CallLayoutTemplate | Yes | Layout mode. `float`: Waiting is self full-screen, answered is remote full-screen / self floating window. `grid`: All participants tiled. `pip`: 1v1 always remote, group uses Active Speaker. |
|
|
754
|
-
|
|
755
|
-
### Set Default Call Timeout
|
|
756
|
-
|
|
757
|
-
Set the `timeout` field in [CallParams](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_call_call_store/CallParams-class.html) when calling [calls](https://liteav.sdk.qcloud.com/doc/product/tuikit/atomic-x/flutter/v1.0/en/api_call_call_store/CallStore/calls.html):
|
|
758
|
-
|
|
759
|
-
```dart
|
|
760
|
-
void startCall(List<String> userIdList, CallMediaType mediaType) {
|
|
761
|
-
CallParams params = CallParams(
|
|
762
|
-
timeout: 30, // Set call waiting timeout (seconds)
|
|
763
|
-
);
|
|
764
|
-
CallStore.shared.calls(userIdList, mediaType, params);
|
|
765
|
-
}
|
|
766
|
-
```
|
|
767
|
-
|
|
768
|
-
**calls API Parameter Details:**
|
|
769
|
-
|
|
770
|
-
| **Parameter** | **Type** | **Required** | **Description** |
|
|
771
|
-
| --- | --- | --- | --- |
|
|
772
|
-
| `userIdList` | List<String> | Yes | List of target userIds. |
|
|
773
|
-
| `mediaType` | CallMediaType | Yes | Specifies call type: audio or video. `CallMediaType.video` / `CallMediaType.audio`. |
|
|
774
|
-
| `params` | CallParams | No | Additional options: room ID, timeout, custom data, group ID, ephemeral flag. |
|
|
775
|
-
|
|
776
|
-
### Implement In-App Floating Window
|
|
777
|
-
|
|
778
|
-
When the call interface is covered (e.g., by navigation), display an in-app floating window that shows key call status (such as duration and participant info) and provides one-tap return to the full call view.
|
|
779
|
-
|
|
780
|
-
```dart
|
|
781
|
-
_buildPipWindowWidget() {
|
|
782
|
-
final pipWidth = MediaQuery.of(context).size.width;
|
|
783
|
-
final pipHeight = MediaQuery.of(context).size.height;
|
|
784
|
-
final scale = pipWidth / originWidth;
|
|
785
|
-
CallCoreController controller = CallCoreController.create();
|
|
786
|
-
controller.setLayoutTemplate(CallLayoutTemplate.pip);
|
|
787
|
-
return Scaffold(
|
|
788
|
-
body: SizedBox(
|
|
789
|
-
width: pipWidth,
|
|
790
|
-
height: pipHeight,
|
|
791
|
-
child: Container(
|
|
792
|
-
width: pipWidth,
|
|
793
|
-
height: pipHeight,
|
|
794
|
-
decoration: const BoxDecoration(color: Colors.transparent),
|
|
795
|
-
child: MediaQuery(
|
|
796
|
-
data: MediaQuery.of(context).copyWith(
|
|
797
|
-
size: Size(originWidth ?? pipWidth, originHeight ?? pipHeight)
|
|
798
|
-
),
|
|
799
|
-
child: ClipRect(
|
|
800
|
-
child: Transform.scale(
|
|
801
|
-
scale: scale,
|
|
802
|
-
alignment: Alignment.center,
|
|
803
|
-
child: OverflowBox(
|
|
804
|
-
maxWidth: originWidth,
|
|
805
|
-
maxHeight: originHeight,
|
|
806
|
-
alignment: Alignment.center,
|
|
807
|
-
child: CallCoreView(
|
|
808
|
-
controller: controller,
|
|
809
|
-
),
|
|
810
|
-
),
|
|
811
|
-
),
|
|
812
|
-
),
|
|
813
|
-
),
|
|
814
|
-
),
|
|
815
|
-
),
|
|
816
|
-
);
|
|
817
|
-
}
|
|
818
|
-
```
|
|
819
|
-
|
|
820
|
-
### Implement Android Picture-in-Picture Outside App
|
|
821
|
-
|
|
822
|
-
Picture-in-Picture requires Android 8.0 (API 26) or above.
|
|
823
|
-
|
|
824
|
-
1. **MainActivity configuration:** Listen for lifecycle changes and enter PiP when needed.
|
|
825
|
-
|
|
826
|
-
```kotlin
|
|
827
|
-
import android.app.PictureInPictureParams
|
|
828
|
-
import android.content.pm.PackageManager
|
|
829
|
-
import android.os.Build
|
|
830
|
-
import android.util.Log
|
|
831
|
-
import android.util.Rational
|
|
832
|
-
import io.flutter.embedding.android.FlutterActivity
|
|
833
|
-
import io.flutter.embedding.engine.FlutterEngine
|
|
834
|
-
import io.flutter.plugin.common.MethodChannel
|
|
835
|
-
|
|
836
|
-
class MainActivity : FlutterActivity() {
|
|
837
|
-
companion object {
|
|
838
|
-
private const val TAG = "MainActivity"
|
|
839
|
-
private const val CHANNEL = "atomic_x/pip"
|
|
840
|
-
}
|
|
841
|
-
|
|
842
|
-
private var enablePictureInPicture = false
|
|
843
|
-
|
|
844
|
-
override fun configureFlutterEngine(flutterEngine: FlutterEngine) {
|
|
845
|
-
super.configureFlutterEngine(flutterEngine)
|
|
846
|
-
|
|
847
|
-
MethodChannel(flutterEngine.dartExecutor.binaryMessenger, CHANNEL).setMethodCallHandler { call, result ->
|
|
848
|
-
when (call.method) {
|
|
849
|
-
"enablePictureInPicture" -> {
|
|
850
|
-
val enable = call.argument<Boolean>("enable") ?: false
|
|
851
|
-
val success = enablePIP(enable)
|
|
852
|
-
result.success(success)
|
|
853
|
-
}
|
|
854
|
-
"enterPictureInPicture" -> {
|
|
855
|
-
val success = enterPIP()
|
|
856
|
-
result.success(success)
|
|
857
|
-
}
|
|
858
|
-
else -> result.notImplemented()
|
|
859
|
-
}
|
|
860
|
-
}
|
|
861
|
-
}
|
|
862
|
-
|
|
863
|
-
override fun onUserLeaveHint() {
|
|
864
|
-
super.onUserLeaveHint()
|
|
865
|
-
// Automatically enter PiP when user presses Home
|
|
866
|
-
if (enablePictureInPicture) {
|
|
867
|
-
enterPIP()
|
|
868
|
-
}
|
|
869
|
-
}
|
|
870
|
-
|
|
871
|
-
private fun enablePIP(enable: Boolean): Boolean {
|
|
872
|
-
Log.i(TAG, "enablePictureInPicture: $enable")
|
|
873
|
-
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O &&
|
|
874
|
-
packageManager.hasSystemFeature(PackageManager.FEATURE_PICTURE_IN_PICTURE)) {
|
|
875
|
-
enablePictureInPicture = enable
|
|
876
|
-
return true
|
|
877
|
-
}
|
|
878
|
-
return false
|
|
879
|
-
}
|
|
880
|
-
|
|
881
|
-
private fun enterPIP(): Boolean {
|
|
882
|
-
if (!enablePictureInPicture) return false
|
|
883
|
-
|
|
884
|
-
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
|
885
|
-
try {
|
|
886
|
-
val aspectRatio = Rational(9, 16)
|
|
887
|
-
val params = PictureInPictureParams.Builder()
|
|
888
|
-
.setAspectRatio(aspectRatio)
|
|
889
|
-
.build()
|
|
890
|
-
return enterPictureInPictureMode(params)
|
|
891
|
-
} catch (e: Exception) {
|
|
892
|
-
Log.e(TAG, "enterPIP failed: ${e.message}")
|
|
893
|
-
}
|
|
894
|
-
}
|
|
895
|
-
return false
|
|
896
|
-
}
|
|
897
|
-
}
|
|
898
|
-
```
|
|
899
|
-
|
|
900
|
-
2. **AndroidManifest.xml configuration:** Enable PiP for `MainActivity`.
|
|
901
|
-
|
|
902
|
-
```xml
|
|
903
|
-
<activity
|
|
904
|
-
android:name=".MainActivity"
|
|
905
|
-
android:exported="true"
|
|
906
|
-
android:launchMode="singleTop"
|
|
907
|
-
android:taskAffinity=""
|
|
908
|
-
android:theme="@style/LaunchTheme"
|
|
909
|
-
android:configChanges="orientation|keyboardHidden|keyboard|screenSize|smallestScreenSize|locale|layoutDirection|fontScale|screenLayout|density|uiMode"
|
|
910
|
-
android:hardwareAccelerated="true"
|
|
911
|
-
android:windowSoftInputMode="adjustResize"
|
|
912
|
-
android:supportsPictureInPicture="true">
|
|
913
|
-
<meta-data
|
|
914
|
-
android:name="io.flutter.embedding.android.NormalTheme"
|
|
915
|
-
android:resource="@style/NormalTheme"
|
|
916
|
-
/>
|
|
917
|
-
<intent-filter>
|
|
918
|
-
<action android:name="android.intent.action.MAIN"/>
|
|
919
|
-
<category android:name="android.intent.category.LAUNCHER"/>
|
|
920
|
-
</intent-filter>
|
|
921
|
-
</activity>
|
|
922
|
-
```
|
|
923
|
-
|
|
924
|
-
3. **Dart layer configuration:**
|
|
925
|
-
|
|
926
|
-
```dart
|
|
927
|
-
import 'package:flutter/services.dart';
|
|
928
|
-
|
|
929
|
-
class PipManager {
|
|
930
|
-
static const MethodChannel _channel = MethodChannel('atomic_x/pip');
|
|
931
|
-
|
|
932
|
-
/// Enable/disable PiP feature
|
|
933
|
-
static Future<bool> enablePictureInPicture(bool enable) async {
|
|
934
|
-
try {
|
|
935
|
-
final result = await _channel.invokeMethod<bool>('enablePictureInPicture', {'enable': enable});
|
|
936
|
-
return result ?? false;
|
|
937
|
-
} catch (e) {
|
|
938
|
-
return false;
|
|
939
|
-
}
|
|
940
|
-
}
|
|
941
|
-
|
|
942
|
-
/// Enter PiP mode immediately
|
|
943
|
-
static Future<bool> enterPictureInPicture() async {
|
|
944
|
-
try {
|
|
945
|
-
final result = await _channel.invokeMethod<bool>('enterPictureInPicture');
|
|
946
|
-
return result ?? false;
|
|
947
|
-
} catch (e) {
|
|
948
|
-
return false;
|
|
949
|
-
}
|
|
950
|
-
}
|
|
951
|
-
}
|
|
952
|
-
```
|
|
953
|
-
|
|
954
|
-
Enable PiP before the call starts, and disable it after the call ends.
|
|
955
|
-
|
|
956
|
-
### Implement iOS Picture-in-Picture Outside App
|
|
957
|
-
|
|
958
|
-
iOS supports Picture-in-Picture outside the app using the underlying TRTC engine. When the app goes to background, the call interface floats over other apps as a system PiP window.
|
|
959
|
-
|
|
960
|
-
> **Note:**
|
|
961
|
-
>
|
|
962
|
-
> - In Xcode, add `Background Modes` under `Signing & Capabilities` and check `Audio, AirPlay, and Picture in Picture`.
|
|
963
|
-
> - Requires iOS 15.0 or above.
|
|
964
|
-
|
|
965
|
-
1. **Enable PiP:**
|
|
966
|
-
|
|
967
|
-
```dart
|
|
968
|
-
import 'package:tencent_rtc_sdk/trtc_cloud.dart';
|
|
969
|
-
|
|
970
|
-
TRTCCloud.sharedInstance().then((trtcCloud) {
|
|
971
|
-
trtcCloud.callExperimentalAPI('''
|
|
972
|
-
{
|
|
973
|
-
"api": "configPictureInPicture",
|
|
974
|
-
"params": {
|
|
975
|
-
"enable": true,
|
|
976
|
-
"cameraBackgroundCapture": true,
|
|
977
|
-
"canvas": {
|
|
978
|
-
"width": 720,
|
|
979
|
-
"height": 1280,
|
|
980
|
-
"backgroundColor": "#111111"
|
|
981
|
-
},
|
|
982
|
-
"regions": [
|
|
983
|
-
{
|
|
984
|
-
"userId": "remoteUserId",
|
|
985
|
-
"userName": "",
|
|
986
|
-
"width": 1.0,
|
|
987
|
-
"height": 1.0,
|
|
988
|
-
"x": 0.0,
|
|
989
|
-
"y": 0.0,
|
|
990
|
-
"fillMode": 0,
|
|
991
|
-
"streamType": "high",
|
|
992
|
-
"backgroundColor": "#111111",
|
|
993
|
-
"backgroundImage": "file:///path/to/avatar.png"
|
|
994
|
-
},
|
|
995
|
-
{
|
|
996
|
-
"userId": "localUserId",
|
|
997
|
-
"userName": "",
|
|
998
|
-
"width": 0.333,
|
|
999
|
-
"height": 0.333,
|
|
1000
|
-
"x": 0.65,
|
|
1001
|
-
"y": 0.05,
|
|
1002
|
-
"fillMode": 0,
|
|
1003
|
-
"streamType": "high",
|
|
1004
|
-
"backgroundColor": "#111111"
|
|
1005
|
-
}
|
|
1006
|
-
]
|
|
1007
|
-
}
|
|
1008
|
-
}
|
|
1009
|
-
''');
|
|
1010
|
-
});
|
|
1011
|
-
```
|
|
1012
|
-
|
|
1013
|
-
2. **Disable PiP:**
|
|
1014
|
-
|
|
1015
|
-
```dart
|
|
1016
|
-
import 'package:tencent_rtc_sdk/trtc_cloud.dart';
|
|
1017
|
-
|
|
1018
|
-
TRTCCloud.sharedInstance().then((trtcCloud) {
|
|
1019
|
-
trtcCloud.callExperimentalAPI('''
|
|
1020
|
-
{
|
|
1021
|
-
"api": "configPictureInPicture",
|
|
1022
|
-
"params": {
|
|
1023
|
-
"enable": false
|
|
1024
|
-
}
|
|
1025
|
-
}
|
|
1026
|
-
''');
|
|
1027
|
-
});
|
|
1028
|
-
```
|
|
1029
|
-
|
|
1030
|
-
### Play Waiting Ringtone
|
|
1031
|
-
|
|
1032
|
-
Monitor call status, play ringtone while waiting for an answer, and stop it when the call is accepted or ends.
|
|
1033
|
-
|
|
1034
|
-
```dart
|
|
1035
|
-
CallStore.shared.state.selfInfo.addListener(() {
|
|
1036
|
-
CallParticipantInfo info = CallStore.shared.state.selfInfo.value;
|
|
1037
|
-
if (info.status == CallParticipantStatus.accept || info.status == CallParticipantStatus.none) {
|
|
1038
|
-
// Stop ringtone
|
|
1039
|
-
return;
|
|
1040
|
-
}
|
|
1041
|
-
if (info.status == CallParticipantStatus.waiting) {
|
|
1042
|
-
// Play ringtone
|
|
1043
|
-
}
|
|
1044
|
-
});
|
|
1045
|
-
```
|
|
1046
|
-
|
|
1047
|
-
### Enable Background Audio/Video Capture
|
|
1048
|
-
|
|
1049
|
-
To ensure call audio/video capture continues when the app goes to background, configure Android and iOS as follows.
|
|
1050
|
-
|
|
1051
|
-
#### Android Configuration
|
|
1052
|
-
|
|
1053
|
-
1. **Permissions and service in `AndroidManifest.xml`:** Starting from Android 9.0 (API 28), foreground service permission is required. Android 14 (API 34) requires specifying service type.
|
|
1054
|
-
|
|
1055
|
-
```xml
|
|
1056
|
-
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
|
|
1057
|
-
|
|
1058
|
-
<uses-permission android:name="android.permission.FOREGROUND_SERVICE" />
|
|
1059
|
-
<uses-permission android:name="android.permission.FOREGROUND_SERVICE_CAMERA" />
|
|
1060
|
-
<uses-permission android:name="android.permission.FOREGROUND_SERVICE_MICROPHONE" />
|
|
1061
|
-
|
|
1062
|
-
<application>
|
|
1063
|
-
<service
|
|
1064
|
-
android:name=".CallForegroundService"
|
|
1065
|
-
android:enabled="true"
|
|
1066
|
-
android:exported="false"
|
|
1067
|
-
android:foregroundServiceType="camera|microphone" />
|
|
1068
|
-
</application>
|
|
1069
|
-
</manifest>
|
|
1070
|
-
```
|
|
1071
|
-
|
|
1072
|
-
2. **Create foreground service class (`CallForegroundService`):**
|
|
1073
|
-
|
|
1074
|
-
```kotlin
|
|
1075
|
-
import android.app.Notification
|
|
1076
|
-
import android.app.NotificationChannel
|
|
1077
|
-
import android.app.NotificationManager
|
|
1078
|
-
import android.app.Service
|
|
1079
|
-
import android.content.Context
|
|
1080
|
-
import android.content.Intent
|
|
1081
|
-
import android.os.Build
|
|
1082
|
-
import android.os.IBinder
|
|
1083
|
-
import androidx.core.app.NotificationCompat
|
|
1084
|
-
|
|
1085
|
-
class CallForegroundService : Service() {
|
|
1086
|
-
companion object {
|
|
1087
|
-
private const val NOTIFICATION_ID = 1001
|
|
1088
|
-
private const val CHANNEL_ID = "call_foreground_channel"
|
|
1089
|
-
fun start(context: Context) {
|
|
1090
|
-
val intent = Intent(context, CallForegroundService::class.java)
|
|
1091
|
-
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
|
1092
|
-
context.startForegroundService(intent)
|
|
1093
|
-
} else {
|
|
1094
|
-
context.startService(intent)
|
|
1095
|
-
}
|
|
1096
|
-
}
|
|
1097
|
-
|
|
1098
|
-
fun stop(context: Context) {
|
|
1099
|
-
val intent = Intent(context, CallForegroundService::class.java)
|
|
1100
|
-
context.stopService(intent)
|
|
1101
|
-
}
|
|
1102
|
-
}
|
|
1103
|
-
|
|
1104
|
-
override fun onCreate() {
|
|
1105
|
-
super.onCreate()
|
|
1106
|
-
createNotificationChannel()
|
|
1107
|
-
// Start foreground notification to ensure background capture permission
|
|
1108
|
-
startForeground(NOTIFICATION_ID, createNotification())
|
|
1109
|
-
}
|
|
1110
|
-
|
|
1111
|
-
override fun onBind(intent: Intent?): IBinder? = null
|
|
1112
|
-
|
|
1113
|
-
private fun createNotification(): Notification {
|
|
1114
|
-
return NotificationCompat.Builder(this, CHANNEL_ID)
|
|
1115
|
-
.setContentTitle("In Call")
|
|
1116
|
-
.setContentText("App is running in background to keep the call alive")
|
|
1117
|
-
.setSmallIcon(android.R.drawable.ic_menu_call) // Replace with your app icon
|
|
1118
|
-
.setPriority(NotificationCompat.PRIORITY_HIGH)
|
|
1119
|
-
.build()
|
|
1120
|
-
}
|
|
1121
|
-
|
|
1122
|
-
private fun createNotificationChannel() {
|
|
1123
|
-
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
|
1124
|
-
val channel = NotificationChannel(
|
|
1125
|
-
CHANNEL_ID,
|
|
1126
|
-
"Call Keep-Alive Service",
|
|
1127
|
-
NotificationManager.IMPORTANCE_HIGH
|
|
1128
|
-
)
|
|
1129
|
-
val manager = getSystemService(NotificationManager::class.java)
|
|
1130
|
-
manager.createNotificationChannel(channel)
|
|
1131
|
-
}
|
|
1132
|
-
}
|
|
1133
|
-
}
|
|
1134
|
-
```
|
|
1135
|
-
|
|
1136
|
-
#### iOS Configuration
|
|
1137
|
-
|
|
1138
|
-
Open your project in Xcode and:
|
|
1139
|
-
|
|
1140
|
-
1. Select your project `Target` > `Signing & Capabilities`.
|
|
1141
|
-
2. Click `+ Capability`.
|
|
1142
|
-
3. Add `Background Modes`.
|
|
1143
|
-
4. Check:
|
|
1144
|
-
- `Audio, AirPlay, and Picture in Picture`
|
|
1145
|
-
- `Voice over IP`
|
|
1146
|
-
- `Remote notifications` (optional for offline push)
|
|
1147
|
-
|
|
1148
|
-
Your `Info.plist` will include:
|
|
1149
|
-
|
|
1150
|
-
```xml
|
|
1151
|
-
<key>UIBackgroundModes</key>
|
|
1152
|
-
<array>
|
|
1153
|
-
<string>audio</string>
|
|
1154
|
-
<string>voip</string>
|
|
1155
|
-
<string>remote-notification</string>
|
|
1156
|
-
</array>
|
|
1157
|
-
```
|
|
1158
|
-
|
|
1159
|
-
**Configure audio session (AVAudioSession):**
|
|
1160
|
-
|
|
1161
|
-
Set up the audio session before the call starts. Recommended in the call interface's `viewDidLoad` or before initiating a call:
|
|
1162
|
-
|
|
1163
|
-
```swift
|
|
1164
|
-
import AVFoundation
|
|
1165
|
-
|
|
1166
|
-
/**
|
|
1167
|
-
* Configure audio session for background audio capture
|
|
1168
|
-
*
|
|
1169
|
-
* Recommended scenarios:
|
|
1170
|
-
* 1. In call interface's viewDidLoad
|
|
1171
|
-
* 2. Before initiating a call (calls)
|
|
1172
|
-
* 3. Before answering a call (accept)
|
|
1173
|
-
*/
|
|
1174
|
-
private func start() {
|
|
1175
|
-
let audioSession = AVAudioSession.sharedInstance()
|
|
1176
|
-
do {
|
|
1177
|
-
// Set session category to play and record
|
|
1178
|
-
// .allowBluetooth: Support Bluetooth headset
|
|
1179
|
-
// .allowBluetoothA2DP: Support high-quality Bluetooth audio (A2DP)
|
|
1180
|
-
try audioSession.setCategory(.playAndRecord, options: [.allowBluetooth, .allowBluetoothA2DP])
|
|
1181
|
-
// Activate audio session
|
|
1182
|
-
try audioSession.setActive(true)
|
|
1183
|
-
} catch {
|
|
1184
|
-
// Audio session configuration failed
|
|
1185
|
-
}
|
|
1186
|
-
}
|
|
1187
|
-
```
|
|
1188
|
-
|
|
1189
|
-
> **Note:**
|
|
1190
|
-
>
|
|
1191
|
-
> Call `start()` via `MethodChannel` at the appropriate time to enable background keep-alive.
|
|
1192
|
-
|
|
1193
|
-
## FAQ
|
|
1194
|
-
|
|
1195
|
-
### Why does my iOS Release build show [symbol not found] at runtime?
|
|
1196
|
-
|
|
1197
|
-
If you see `symbol not found` errors in your iOS Release build, it's likely because Xcode's symbol stripping removed TRTC C symbols used by `tencent_rtc_sdk` (via Flutter FFI). To fix:
|
|
1198
|
-
|
|
1199
|
-
1. In **Build Settings**, set **Deployment Postprocessing** to **Yes**.
|
|
1200
|
-
2. In **Build Settings**, set **Strip Style** for **Release** to **Non-Global Symbols**.
|
|
1201
|
-
|
|
1202
|
-
### If the callee goes offline and returns within the call invite timeout, will they still get the incoming call event?
|
|
1203
|
-
|
|
1204
|
-
- **For single calls:** If the callee comes online within the timeout period, they will receive the incoming call invite.
|
|
1205
|
-
- **For group calls:** If the callee returns within the timeout, up to 20 unprocessed group messages will be pulled; if there is a call invite, the incoming call event will be triggered.
|