Kurento Flutter

679 views
Skip to first unread message

M4TRIX H4CK3R

unread,
Aug 7, 2020, 2:42:14 AM8/7/20
to kur...@googlegroups.com

Hey there.. I just want to know the connectivity of flutter webrtc with KMS. I m using flutter webrtc package and transmitting and receiving data in node js server and successfully shared sdp and ice candidates. But the problem arises with the ice candidate connectivity. As it hangs in the checking state and onAddTrack showing blank screen in the RTCVideoRenderer. I just need help to complete the connection state with ice candidates.


Here is my Flutter code:

import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter_webrtc/webrtc.dart';
import 'package:adhara_socket_io/adhara_socket_io.dart';

class studentCall extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: _homeBody(),
    );
  }
}

class _homeBody extends StatefulWidget {
  @override
  __homeBodyState createState() => __homeBodyState();
}

class __homeBodyState extends State<_homeBody> {
  // Connection Variables
  var room = 'test';
  RTCVideoRenderer _localRenderer = RTCVideoRenderer();
  RTCVideoRenderer _remoteRenderer = RTCVideoRenderer();
  MediaStream _localStream = null;
  RTCPeerConnection _peerConnection = null;
  // IO.Socket socket = null;
  SocketIOManager manager = null;
  SocketIO socket = null;

  // Socket Variables

  bool roomChecked = false;

  // Connection Data Variables

  final Map<Stringdynamic> mediaConstraints = {
    "audio"true,
    "video": {
      "mandatory": {
        "minWidth"'640'// Provide your own width, height and frame rate here
        "minHeight"'480',
        "minFrameRate"'30',
      },
      "facingMode""user",
      "optional": [],
    }
  };

  Map<Stringdynamic> configuration = {
    "iceServers": [
      {"url""stun:stun.l.google.com:19302"},
    ]
  };

  final Map<Stringdynamic> _offer_constraints = {
    "mandatory": {
      "OfferToReceiveAudio"true,
      "OfferToReceiveVideo"true,
    },
    "optional": [],
  };

  final Map<Stringdynamic> constraints = {
    "mandatory": {},
    "optional": [
      {"DtlsSrtpKeyAgreement"true},
    ],
  };

  // Initialize functions

  @override
  void initState() {
    super.initState();
    // _initialize();
  }

  void dispose() {
    super.dispose();
    // _localRenderer.dispose();
    // _remoteRenderer.dispose();
    // manager.clearInstance(socket);
  }

  _initialize() async {
    if (socket != nullreturn;

    _localRenderer.initialize();
    _remoteRenderer.initialize();

    manager = SocketIOManager();
    socket = await manager
        .createInstance(SocketOptions('https://[host]:5000'));
    socket.connect();

    // Socket Listening Functions

    socket.onConnect((data) {
      socket.emit('room-check', [
        {'room': room}
      ]);
    });

    socket.on('room-exists', (data) {
      _createPeer();
    });

    socket.on('room-not-exists', (data) {
      _snackBar('not exists');
    });

    socket.on('studentResponse', (data) async {
      try {
        var answer = data['answer'].toString();
        await _peerConnection
            .setRemoteDescription(RTCSessionDescription(answer, 'answer'));
      } catch (e) {
        _snackBar(e.toString());
      }
    });

    socket.on('candidate', (data) async {
      if (_peerConnection == nullreturn;

      try {
        var map = data['candidate']['candidate'];
        var sdpMid = data['candidate']['sdpMid'];
        var sdpMLineIndex = data['candidate']['sdpMLineIndex'];

        RTCIceCandidate candidate = RTCIceCandidate(map, sdpMid, sdpMLineIndex);

        _snackBar(candidate.candidate);

        _peerConnection.addCandidate(candidate);
      } catch (e) {
        _snackBar(e.toString());
      }
    });
  }

  _createPeer() async {
    try {
      if (_peerConnection != nullreturn;

      navigator.getUserMedia(mediaConstraints).then((stream) {
        _localStream = stream;
        _localRenderer.srcObject = stream;
      });

      _peerConnection = await createPeerConnection(configuration, constraints);

      _peerConnection.onSignalingState = _onSignalingState;
      _peerConnection.onIceGatheringState = _onIceGatheringState;
      _peerConnection.onIceConnectionState = _onIceConnectionState;
      _peerConnection.onAddStream = _onAddStream;
      _peerConnection.onRemoveStream = _onRemoveStream;
      _peerConnection.onIceCandidate = _onCandidate;
      _peerConnection.onRenegotiationNeeded = _onRenegotiationNeeded;

      _peerConnection.addStream(_localStream);

      RTCSessionDescription offer =
          await _peerConnection.createOffer(_offer_constraints);
      _peerConnection.setLocalDescription(offer);

      socket.emit('add-student', [
        {'room': room, 'offer': offer.sdp}
      ]);
    } catch (e) {
      _snackBar(e.toString());
    }
  }

  _onSignalingState(RTCSignalingState state) {
    _snackBar(state.toString());
  }

  _onIceGatheringState(RTCIceGatheringState state) {
    _snackBar(state.toString());
  }

  _onIceConnectionState(RTCIceConnectionState state) {
    _snackBar(state.toString());
  }

  _onAddStream(MediaStream stream) {
    if (stream == null) {
      _snackBar('null');
      return;
    }
    _remoteRenderer.srcObject = stream;
    setState(() {});
  }

  _onRemoveStream(MediaStream stream) {
    _snackBar('remove');
  }

  _onCandidate(RTCIceCandidate candidate) {
    socket.emit('studentCandidate', [
      {
        'room': room,
        'candidate': {
          'candidate': candidate.candidate,
          'sdpMid': candidate.sdpMid,
          'sdpMLineIndex': candidate.sdpMlineIndex
        }
      }
    ]);
  }

  _onRenegotiationNeeded() {
    _snackBar('reneg');
  }

  // Display Functions and Variables

  _snackBar(String msg) {
    Scaffold.of(context).showSnackBar(SnackBar(
      content: Text(msg),
    ));
  }

  Widget _progress = Center(
    child: CircularProgressIndicator(
      valueColor: AlwaysStoppedAnimation<Color>(Colors.white),
    ),
  );

  @override
  Widget build(BuildContext context) {
    return Stack(
      children: <Widget>[
        Container(
          decoration: BoxDecoration(
            color: Colors.white,
          ),
          width: double.infinity,
          height: double.infinity,
          child: RTCVideoView(
            _remoteRenderer,
          ),
        ),
        // _progress,
        Positioned(
          child: Container(
            decoration: BoxDecoration(color: Colors.black, boxShadow: [
              BoxShadow(
                color: Colors.grey,
              )
            ]),
            width: 150,
            height: 200,
            child: RTCVideoView(
              _localRenderer,
            ),
          ),
          bottom: 20,
          right: 30,
        )
      ],
    );
  }
}

hemant vyas

unread,
May 22, 2021, 4:21:11 AM5/22/21
to kurento
Please do update if you find out the solution. :)

Rahman Rezaee

unread,
Apr 5, 2022, 6:30:34 PM4/5/22
to kurento
did u find any solutions??
Reply all
Reply to author
Forward
0 new messages