Flutter WebRTC视频通话黑屏问题排查与解决求助
排查Flutter WebRTC视频通话黑屏问题
一、本地媒体流初始化检查
- 确认摄像头权限配置到位:Web端要在
web/index.html里加权限声明,移动端要在AndroidManifest.xml(Android)或Info.plist(iOS)配置摄像头、麦克风权限。代码里必须确保getUserMedia调用成功,示例:final mediaConstraints = {'audio': true, 'video': {'facingMode': 'user'}}; try { _localStream = await navigator.mediaDevices.getUserMedia(mediaConstraints); // 绑定本地Renderer前必须先初始化 await _localRenderer.initialize(); _localRenderer.srcObject = _localStream; } catch (e) { print('获取媒体流失败: $e'); } - 本地
RTCVideoRenderer必须先调用initialize()再设置srcObject,且组件已经挂载到页面。
二、信令消息传递完整性
- SDP Offer/Answer要完整转发:信令服务器必须把SDP的
type和sdp字段完整传给对方,不能截断。比如Signalling类发送SDP的代码要确保字段齐全:void sendSdp(RTCSessionDescription sessionDescription) { final data = { 'type': 'sdp', 'sdp': sessionDescription.sdp, 'sdpType': sessionDescription.type.toString(), 'from': _userId, 'to': _targetUserId }; _socket.send(jsonEncode(data)); } - ICE Candidate不能丢:每个生成的ICE Candidate都要及时发对方,接收方要正确添加到PeerConnection:
发送端:
接收端:void onIceCandidate(RTCIceCandidate candidate) { sendIceCandidate(candidate); _peerConnection.addCandidate(candidate); }if (message['type'] == 'ice') { final candidate = RTCIceCandidate( message['candidate'], message['sdpMid'], message['sdpMLineIndex'], ); await _peerConnection.addCandidate(candidate); }
三、PeerConnection配置与状态检查
- 配置有效的ICE服务器:至少加一个STUN服务器,比如
stun:stun.l.google.com:19302,内网测试可能需要TURN服务器。示例:final configuration = { 'iceServers': [ {'urls': 'stun:stun.l.google.com:19302'}, ] }; _peerConnection = await createPeerConnection(configuration); - 正确处理
onTrack事件:远端流必须通过这个事件获取,不能用信令直接传流对象。示例:_peerConnection.onTrack.listen((event) { if (event.streams.isNotEmpty) { final remoteStream = event.streams[0]; await _remoteRenderer.initialize(); _remoteRenderer.srcObject = remoteStream; } }); - 本地流必须添加到PeerConnection:调用
addStream或addTrack把本地流加入连接,否则对方收不到你的流:await _peerConnection.addStream(_localStream);
四、渲染组件问题
- 确认
RTCVideoView绑定正确的Renderer:组件的renderer属性要指向已经初始化、且设置了srcObject的RTCVideoRenderer实例:RTCVideoView(_localRenderer, mirror: true), RTCVideoView(_remoteRenderer), - 移动端要确认用户已授予权限:如果用户没同意摄像头/麦克风权限,
getUserMedia会静默失败,自然没有流。
五、调试技巧
- 加日志打印:在媒体流获取、信令收发、PeerConnection状态变化(比如
onConnectionStateChange、onIceGatheringStateChange)处打日志,确认每个步骤是否正常执行。 - Web端用Chrome调试:打开
chrome://webrtc-internals/查看WebRTC的详细状态,包括ICE连接情况、流的传输统计,快速定位问题。
内容的提问来源于stack exchange,提问作者fahim irfan
相关产品推荐
相关产品推荐

