问题描述
所以,我试图编写一个 webRTC 移动应用程序。发现一些错误。
import 'dart:convert';
import 'package:Flutter/material.dart';
import 'package:Flutter_webrtc/Flutter_webrtc.dart';
import 'package:sdp_transform/sdp_transform.dart';
import 'package:firebase_core/firebase_core.dart';
import 'package:cloud_firestore/cloud_firestore.dart';
void main() async {
WidgetsFlutterBinding.ensureInitialized();
await Firebase.initializeApp();
runApp(MyApp());
}
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',theme: ThemeData(
primarySwatch: Colors.blue,visualDensity: VisualDensity.adaptivePlatformDensity,),home: MyHomePage(title: 'WebRTC lets learn together'),);
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key,this.title}) : super(key: key);
final String title;
@override
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
CollectionReference firebaseInstance =
FirebaseFirestore.instance.collection("dmeet");
RTCPeerConnection _peerConnection;
MediaStream _localStream;
RTCVideoRenderer _remoteRenderer = RTCVideoRenderer();
var docId = TextEditingController();
var l;
_createOfferSdp() async {
RTCSessionDescription description =
await _peerConnection.createOffer({'offerToReceiveAudio': 1});
var session = parse(description.sdp);
Map<String,dynamic> sdp = {
"sdp": session.toString(),};
var k = firebaseInstance.doc().collection("sdp").doc("offersdp").set(sdp);
print("K val: $k");
_peerConnection.setLocalDescription(description);
// print(session);
}
bool remotesaved = false;
_createAnswerSdp() async {
firebaseInstance
.doc(docId.text)
.collection("sdp")
.doc("offersdp")
.get()
.then((value) async {
print("here");
var temp = (value.data()["sdp"]).toString();
// var session = await jsonDecode(temp.toString());
// print("here3");
// print("session: $session");
// String sdp = write(session,null);
print(temp);
if (temp != null) {
RTCSessionDescription description1 =
RTCSessionDescription(temp,"offer");
await _peerConnection.setRemoteDescription(description1).then((value) {
setState(() {
remotesaved = true;
});
});
}
});
if (remotesaved) {
RTCSessionDescription description = await _peerConnection
.createAnswer({'offerToReceiveVideo': 0,'offerToReceiveAudio': 1});
var session = parse(description.sdp);
firebaseInstance
.doc(docId.text)
.collection("sdp")
.doc("answersdp")
.set(session);
if (l != null) {
firebaseInstance
.doc(docId.text)
.collection("icecandidate")
.doc("answerice")
.set(l);
}
}
}
showAlertDialog(BuildContext context) {
// set up the buttons
Widget cancelButton = FlatButton(
child: Text("Cancel"),onpressed: () {},);
Widget continueButton = FlatButton(
child: Text("Continue"),onpressed: _createAnswerSdp,);
// set up the AlertDialog
AlertDialog alert = AlertDialog(
title: Text("AlertDialog"),content: TextField(
controller: docId,actions: [
cancelButton,continueButton,],);
// show the dialog
showDialog(
context: context,builder: (BuildContext context) {
return alert;
},);
}
@override
void initState() {
_createPeerConnection().then((pc) {
_peerConnection = pc;
});
super.initState();
}
@override
void dispose() {
super.dispose();
}
_getUserMedia() async {
final Map<String,dynamic> mediaConstraints = {
'audio': true,'video': false,};
MediaStream stream = await navigator.getUserMedia(mediaConstraints);
// _localStream = stream;
// _peerConnection.addStream(stream);
return stream;
}
_createPeerConnection() async {
Map<String,dynamic> configuration = {
"iceServers": [
{"url": "stun:stun.l.google.com:19302"},]
};
final Map<String,dynamic> offerSdpConstraints = {
"mandatory": {
"OfferToReceiveAudio": true,"OfferToReceiveVideo": false,},"optional": [],};
_localStream = await _getUserMedia();
RTCPeerConnection pc =
await createPeerConnection(configuration,offerSdpConstraints);
// if (pc != null) print(pc);
pc.addStream(_localStream);
pc.onIceCandidate = (e) {
if (e.candidate != null) {
l = json.encode({
'candidate': e.candidate.toString(),'sdpMid': e.sdpMid.toString(),'sdpMlineIndex': e.sdpMlineIndex,});
print(l);
}
};
pc.onIceConnectionState = (e) {
print(e);
};
pc.onAddStream = (stream) {
print('addStream: ' + stream.id);
_remoteRenderer.srcObject = stream;
};
return pc;
}
@override
Widget build(BuildContext context) {
return Scaffold(
body: Container(
child: Center(
child: Row(
children: [
ElevatedButton(
child: Text("Create"),onpressed: _createOfferSdp,ElevatedButton(
onpressed: () {
showAlertDialog(context);
},child: Text("Join"),)
],);
}
}
因此,在我的手机代码中,将创建一个优惠并将其存储在 Firestore 中。
dmeet->(AUTO ID)->sdp->offersdp->sdp:sdpvaluesstored
所以在那之后我在加入按钮中手动给出了documentId,当我尝试获取offersdp并设置远程描述时。我想出了一些错误
D/FlutterWebRTCPlugin( 7232): peerConnectionSetRemoteDescription(): WEBRTC_SET_REMOTE_DESCRIPTION_ERROR: SessionDescription is NULL.
E/Flutter ( 7232): [ERROR:Flutter/lib/ui/ui_dart_state.cc(186)] Unhandled Exception: Unable to RTCPeerConnection::setRemoteDescription: peerConnectionSetRemoteDescription(): WEBRTC_SET_REMOTE_DESCRIPTION_ERROR: SessionDescription is NULL.
E/Flutter ( 7232): #0 RTCPeerConnectionNative.setRemoteDescription
package:Flutter_webrtc/…/native/rtc_peerconnection_impl.dart:328
E/Flutter ( 7232): <asynchronous suspension>
E/Flutter ( 7232): #1 _MyHomePageState._createAnswerSdp.<anonymous closure>.<anonymous closure> (package:Flutter_voip_calling/main.dart)
我正在使用教程代码,它使用与我将在文本框中粘贴 sdp 并设置远程描述相同的概念,教程代码是 here
解决方法
暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!
如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。
小编邮箱:dio#foxmail.com (将#修改为@)