本文将介绍如何快速完成 Flutter RTC Engine 的接入,实现一个基本的音视频通话。
环境准备
Flutter 3.22 及以上版本。
Android 端开发:
Android Studio Bumblebee (2021.1.1) 及以上版本。
App 要求 Android 4.3(API 级别 18)及以上版本设备
iOS 端开发:
Xcode 13.0 及以上版本。
请确保您的项目已设置有效的开发者签名。
Windows 端开发:
Visual Studio 2019及以上版本。
Mac 端开发:
Xcode 13.0 及以上版本。
步骤1:导入 SDK
1. 通过以下命令安装组件 tencent_rtc_sdk:
flutter pub add tencent_rtc_sdk
2. 在申请麦克风和相机权限时需要增加运行时权限请求依赖 permission_handler,在包含 pubspec.yaml 的 Flutter 工程根目录下执行如下命令:
flutter pub add permission_handler
步骤2:配置项目
增加麦克风和相机权限申请
1. 需要在
Info.plist 的第一级<dict>目录下加入对相机和麦克风的权限申请:<key>NSCameraUsageDescription</key><string>授权摄像头权限才能正常视频通话</string><key>NSMicrophoneUsageDescription</key><string>授权麦克风权限才能正常语音通话</string>
2. 添加字段
io.flutter.embedded_views_preview,并设定值为 YES。注意:
由于 tencent_rtc_sdk 通过 Flutter FFI 调用接口,iOS Release 构建时 Xcode 的符号裁剪优化可能误移除 TRTC 的 C 符号,引发
`symbol not found` 错误。解决方案如下:1. 在项目的 Build Settings 中找到 Deployment Postprocessing,将其设置为 Yes 。

2. 在项目的 Build Settings 中找到 Strip Style,将其中 Release 的值设置为 Non-Global Symbols 。

3. 在 iOS 上,permission_handler 默认会将所有权限编译为关闭状态。如果不开启对应权限的编译宏,Permission.camera.request() 会直接返回拒绝且不会弹出系统授权弹窗(仅配置 Info.plist 的权限描述不足以让权限请求生效)。需要在 ios/Podfile 文件的 post_install 中为相机和麦克风开启编译宏:
post_install do |installer|installer.pods_project.targets.each do |target|flutter_additional_ios_build_settings(target)target.build_configurations.each do |config|config.build_settings['GCC_PREPROCESSOR_DEFINITIONS'] ||= ['$(inherited)',## permission_handler: 启用 摄像头 权限'PERMISSION_CAMERA=1',## permission_handler: 启用 麦克风 权限'PERMISSION_MICROPHONE=1',]endendend
增加麦克风和相机权限申请
1. 打开
/android/app/src/main/AndroidManifest.xml 文件。2. 在其中添加如下权限:
<uses-permission android:name="android.permission.INTERNET" /><uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /><uses-permission android:name="android.permission.ACCESS_WIFI_STATE" /><uses-permission android:name="android.permission.RECORD_AUDIO" /><uses-permission android:name="android.permission.MODIFY_AUDIO_SETTINGS" /><uses-permission android:name="android.permission.BLUETOOTH" /><uses-permission android:name="android.permission.CAMERA" /><uses-feature android:name="android.hardware.camera.autofocus" />
3. 如果您需要编译运行在 Android 平台,您还需要进行如下配置:
首先,需要在工程的
android/app/build.gradle 文件中对应位置添加:android {.....packagingOptions {pickFirst 'lib/**/libliteavsdk.so'}buildTypes {release {......minifyEnabled trueproguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'}}}
在工程的 android/app 目录下创建 proguard-rules.pro 文件,并在 proguard-rules.pro 文件中添加如下代码:
-keep class com.tencent.** { *; }
增加麦克风和相机权限申请
需要在
Info.plist 的第一级<dict>目录下加入对相机和麦克风的权限申请:<key>NSCameraUsageDescription</key><string>授权摄像头权限才能正常视频通话</string><key>NSMicrophoneUsageDescription</key><string>授权麦克风权限才能正常语音通话</string>
添加屏幕分享系统依赖库
1. 打开
.xcworkspace 工程文件后,在 Xcode 的导航栏中点击左侧的 Project Navigator,点击 Runner 并确保在编辑区域选择正确的 TARGETS。2. 在
General 选项卡的 Frameworks, Libraries, and Embedded Content 部分添加 ScreenCaptureKit.framework。
说明:
步骤3:创建 TRTC 实例
1. 声明成员变量
import 'package:tencent_rtc_sdk/trtc_cloud.dart';import 'package:tencent_rtc_sdk/trtc_cloud_def.dart';import 'package:tencent_rtc_sdk/trtc_cloud_listener.dart';
late TRTCCloud trtcCloud;
2. 调用初始化接口创建 TRTC 实例并设置事件回调。
// 创建 TRTC 实例trtcCloud = await TRTCCloud.sharedInstance();// 创建 TRTCCloudListener 实例TRTCCloudListener listener = TRTCCloudListener(// 根据需要实现对应的回调onError: (errCode, errMsg) {// TODO});// 注册监听器,将 listener 绑定到 trtcCloud 实例trtcCloud.registerListener(listener);
步骤4:进入房间
1. 如果您在 Android 设备上运行程序,需要提前请求 CAMERA 和 MICROPHONE 权限。
import 'package:permission_handler/permission_handler.dart';if (!(await Permission.camera.request().isGranted) ||!(await Permission.microphone.request().isGranted)) {print('You need to obtain audio and video permission to enter');return;}
说明:
3. 在设置进房参数 TRTCParams 后,调用
enterRoom 接口函数即可进入房间。主播角色
trtcCloud.enterRoom(TRTCParams(sdkAppId: sdkAppId, // 请替换为您的 SDKAppIDuserId: "userId", // 请替换为您的 useriduserSig: '', // 请替换为您的 userSigrole: TRTCRoleType.anchor,strRoomId: "123abc", // 请替换为您的 strRoomId),TRTCAppScene.live);
观众角色
trtcCloud.enterRoom(TRTCParams(sdkAppId: sdkAppId, // 请替换为您的 SDKAppIDuserId: "userId", // 请替换为您的 useriduserSig: '', // 请替换为您的 userSigrole: TRTCRoleType.audience,strRoomId: "123abc", // 请替换为您的 strRoomId),TRTCAppScene.live);
注意:
如果以观众角色进入房间,sdkAppId 和 strRoomId 需要与主播端相同,而 userId 和 userSig 需要替换为自己的值。
步骤5:打开摄像头
1. 在页面的 build 方法中对应位置添加 TRTCCloudVideoView :
import 'package:tencent_rtc_sdk/trtc_cloud_video_view.dart';
TRTCCloudVideoView(key: valueKey,onViewCreated: (viewId) {localViewId = viewId;// TODO},),
说明:
viewId 为视频渲染控件 TRTCCloudVideoView 的唯一标识符。您可以用您想要的方式存储该标识符。此处使用 localViewId 来存储,用以后续渲染本地采集的视频流。2. 在调用接口
startLocalPreview 打开摄像头预览之前,您可以通过调用接口 setLocalRenderParams 来设置本地预览的渲染参数。参数 | 参数说明 | 取值 | 取值说明 |
图像的顺时针旋转角度。支持 90、180 以及 270 旋转角度,默认值:TRTCVideoRotation.rotation0。 | 不旋转。 | ||
| | 顺时针旋转90度。 | |
| | 顺时针旋转180度。 | |
| | 顺时针旋转270度。 | |
画面填充模式。填充(画面可能会被拉伸裁剪)或适应(画面可能会有黑边),默认值:TRTCVideoFillMode.fill。 | 填充模式:即将画面内容居中等比缩放以充满整个显示区域,超出显示区域的部分将会被裁剪掉,此模式下画面可能不完整。 | ||
| | 适应模式:即按画面长边进行缩放以适应显示区域,短边部分会被填充为黑色,此模式下图像完整但可能留有黑边。 | |
| | 缩放填充模式:即无论画面的宽高比,都会被拉伸或压缩以完全填充显示区域,此模式下画面宽高比可能会被改变,导致渲染画面变形 | |
画面镜像模式。默认值:TRTCVideoMirrorType.auto。 | 自动模式:如果正使用前置摄像头则开启镜像,如果是后置摄像头则不开启镜像(仅适用于移动设备)。 | ||
| | 强制开启镜像,不论当前使用的是前置摄像头还是后置摄像头。 | |
| | 强制关闭镜像,不论当前使用的是前置摄像头还是后置摄像头。 | |
// 设置本地预览渲染参数trtcCloud.setLocalRenderParams(TRTCRenderParams(fillMode: TRTCVideoFillMode.fill,mirrorType: TRTCVideoMirrorType.auto,rotation: TRTCVideoRotation.rotation0,),);// 对前置摄像头采集内容进行本地预览trtcCloud.startLocalPreview(true, localViewId);// 对后置摄像头采集内容进行本地预览trtcCloud.startLocalPreview(false, localViewId);
调用
stopLocalPreview 关闭摄像头预览并停止推送本地视频信息。trtcCloud.stopLocalPreview();
3. 您可以通过调用接口
TXDeviceManager 来完成“切换前后摄像头”、“设置对焦模式”、“闪光灯”等设备扩展功能的使用。import 'package:tencent_rtc_sdk/tx_device_manager.dart';
// 获取设备管理器实例TXDeviceManager manager = trtcCloud.getDeviceManager();// 判断是否为前置摄像头if (manager.isFrontCamera()) {// 切换为后置摄像头manager.switchCamera(false);} else {// 切换为前置摄像头manager.switchCamera(true);}
// 获取设备管理器实例TXDeviceManager manager = trtcCloud.getDeviceManager();// 设备是否支持自动识别人脸位置if (manager.isAutoFocusEnabled()) {// 开启自动对焦功能manager.enableCameraAutoFocus(true);} else {// 关闭自动对焦功能manager.enableCameraAutoFocus(false);}
// 获取设备管理器实例TXDeviceManager manager = trtcCloud.getDeviceManager();// 切换后置摄像头时可开启闪光灯manager.enableCameraTorch(true);// 关闭闪光灯manager.enableCameraTorch(false);
步骤6:打开麦克风
调用
startLocalAudio 开启麦克风采集,请根据您的需求选择以下的一个声音质量参数:参数 | 描述 |
人声模式:单声道;编码码率:18kbps;具备几个模式中最强的网络抗性,适合语音通话为主的场景,例如在线会议,语音通话等。 | |
默认模式:单声道;编码码率:50kbps;介于 Speech 和 Music 之间的档位,SDK 默认档位,推荐选择。 | |
音乐模式:全频带立体声;编码码率:128kbps;适合需要高保真传输音乐的场景,例如在线 K 歌、音乐直播等。 |
// 开启麦克风采集,设置当前场景为:语音模式// 具有高的噪声抑制能力,有强有弱的网络阻力trtcCloud.startLocalAudio(TRTCAudioQuality.speech);
// 开启麦克风采集,设置当前场景为:音乐模式// 为获得高保真度,低音质损失,建议配合专业声卡使用trtcCloud.startLocalAudio(TRTCAudioQuality.music);
调用
stopLocalAudio 关闭麦克风采集并停止推送本地音频信息。trtcCloud.stopLocalAudio();
步骤7:播放/停止视频流
1. 在进入房间之前对 onUserVideoAvailable 进行监听,当您收到
onUserVideoAvailable(userId, true) 通知时,表示该路画面已经有可播放的视频帧到达。说明:
此处假设可播放视频的用户为
denny,预计要将用户 denny 的视频流渲染到唯一标识符为 remoteViewId 的 TRTCCloudVideoView 控件中。2. 您可以通过调用接口
startRemoteView 来播放远端用户的视频画面。// 播放远端用户 denny 的主流视频画面trtcCloud.startRemoteView("denny", TRTCVideoStreamType.big,remoteViewId);
之后,您通过调用接口
stopRemoteView 停止某个远端用户的视频,也可以通过接口 stopAllRemoteView 停止播放所有远端用户的视频。// 停止播放远端用户 denny 的主流视频画面trtcCloud.stopRemoteView("denny", TRTCVideoStreamType.big);// 停止播放所有远端用户的视频画面trtcCloud.stopAllRemoteView();
步骤8:播放/停止音频流
默认情况下,SDK 将自动播放远程音频,因此您不需要调用任何 API 来手动播放它。
但当您不喜欢自动播放音频时,可以调用
muteRemoteAudio/muteAllRemoteAudio 选择播放或停止远端声音。// 仅静音远端用户 dennytrtcCloud.muteRemoteAudio("denny", true);// 静音所有远端用户trtcCloud.muteAllRemoteAudio(true);
// 取消静音远端用户 dennytrtcCloud.muteRemoteAudio("denny", false);// 取消静音所有远端用户trtcCloud.muteAllRemoteAudio(false);
步骤9:退出房间
调用
exitRoom 退出当前的房间:trtcCloud.exitRoom();
TRTC SDK 会在退房结束后通过
onExitRoom 回调事件通知您。TRTCCloudListener listener = TRTCCloudListener(onExitRoom: (reason) {// TODO});trtcCloud.registerListener(listener);
常见问题
说明: