undefined

Streaming

ConnectyCube Streaming API is built on top of WebRTC protocol and based on top of WebRTC SFU architecture.

Max people per Conference call is 12.

Streaming API is available starting from Hobby plan (you still can play with it on a Free plan).

Features supported

  • Streaming/listening video/audio
  • Join-Rejoin stream functionality
  • Guest rooms
  • Mute/Unmute audio/video stream
  • Display bitrate
  • Switch video input device (camera)

Code samples

To be announced later. Please contact us if you have any requirements.

Prerequisites

Streaming API is based on top of regular Multiparty Video Conferencing API , so it's good to learn its API as well.

Connect SDK

For using Streaming feature you should add a dependency:

implementation "com.connectycube:connectycube-android-sdk-videochat-conference:$sdkVersion"

Streaming sessions

There are two sessions for handling streaming process in a easy way:

ConferenceStreamingSession - is a session within certain video room, managing the streaming current processes.
ConferenceWatchingSession - is a session within certain video room, managing the watching current stream processes.

Common Callbacks

In order to have an ability to receive callbacks about current session instance state and conference events, you should implement appropriate interfaces:

Implement RTCSessionStateCallback for tracking connection state:

RTCSessionStateCallback sessionStateCallback = new RTCSessionStateCallback<ConferenceStreamBaseSession>(){
    /**
    * Called when session state is changed
    */
    void onStateChanged(ConferenceStreamBaseSession session, BaseSession.RTCSessionState state);

    /**
    * Called in case when connection with opponent is established
    */
    void onConnectedToUser(ConferenceStreamBaseSession session, Integer userID);

    /**
    * Called in case when opponent disconnected
    */
    void onDisconnectedFromUser(ConferenceStreamBaseSession session, Integer userID);

    /**
    * Called in case when connection closed with certain user.
    */
    void onConnectionClosedForUser(ConferenceStreamBaseSession session, Integer userID);
}

  currentSession.addSessionCallbacksListener(sessionStateCallback);
//currentSession.removeSessionCallbacksListener(sessionStateCallback);
val sessionStateCallback = object: RTCSessionStateCallback<ConferenceStreamBaseSession> {
    /**
     * Called when session state is changed
     */
    override fun onStateChanged(session: ConferenceStreamBaseSession, state: BaseSession.RTCSessionState) {}

    /**
     * Called in case when opponent disconnected
     */
    override fun onDisconnectedFromUser(session: ConferenceStreamBaseSession, userID: Int) {}

    /**
     * Called in case when connection with opponent is established
     */
    override fun onConnectedToUser(session: ConferenceStreamBaseSession, userID: Int) {}

    /**
     * Called in case when connection closed with certain user.
     */
    override fun onConnectionClosedForUser(session: ConferenceStreamBaseSession, userID: Int) {}
}

  currentSession.addSessionCallbacksListener(sessionStateCallback)
//currentSession.removeSessionCallbacksListener(sessionStateCallback)

Implement ConferenceStateListener for tracking conference events:

ConferenceStateListener<ConferenceStreamBaseSession> stateListener = new ConferenceStateListener<ConferenceStreamBaseSession>() {
    @Override
    public void onSlowLinkReceived(boolean uplink, int nacks) {}
    @Override
    public void onError(WsException e) {
    // e.g. handling exception for watchSession
        if (ex.getCause() != null && ConferenceWatchingSession.SUBSCRIBE_ERROR_CAUSE_NO_STREAM.equals(ex.getCause().getMessage())) {
            watchSession.stopWatching();
        }
    }
    @Override
    public void onSessionClosed(ConferenceStreamBaseSession conferenceBaseSession) {}
};
var stateListener: ConferenceStateListener<ConferenceStreamBaseSession> = object : ConferenceStateListener<ConferenceBaseSession> {
    override fun onSlowLinkReceived(uplink: Boolean, nacks: Int) {}

    override fun onError(e: WsException) {}

    override fun onSessionClosed(conferenceBaseSession: ConferenceStreamBaseSession) {}
}    

Video and Audio tracks

For obtaining video and audio tracks implement interface RTCClientVideoTracksCallback<ConferenceStreamBaseSession> and RTCClientAudioTracksCallback<ConferenceStreamBaseSession>.

For setting video track for ConferenceSession - the ConferenceStreamSurfaceView class is provided.

ConferenceStreamClient

ConferenceStreamClient instance is a client model responsible for managing conference streaming session.

ConferenceStreamingSession

ConferenceStreamingSession streamSession = ConferenceStreamClient.getInstance(context).createStreamSession(currentUser.getId(), RTCTypes.ConferenceType.CONFERENCE_TYPE_VIDEO);
val streamSession = ConferenceStreamClient.getInstance(context).createStreamSession(currentUser.getId(), RTCTypes.ConferenceType.CONFERENCE_TYPE_VIDEO)

Callbacks

ConferenceStreamingSession.ConferenceStreamingListener streamingListener = new ConferenceStreamingSession.ConferenceStreamingListener() {
    @Override
    public void onStartStreaming() {
        //your video/audio is successfully streaming
    }
    @Override
    public void onStopStreaming() {
        //your video/audio has stopped
    }
    @Override
    public void onWatcherReceived(Integer userId) {
        //some user has connected to your stream
    }
    @Override
    public void onWatcherLeft(Integer userId) {
        //some user has disconnected from your stream
    }
};

   streamSession.addEventListener(streamingListener);
// streamSession.removeEventListener(streamingListener);
var streamingListener: ConferenceStreamingSession.ConferenceStreamingListener = object : ConferenceStreamingSession.ConferenceStreamingListener {
    override fun onStartStreaming() {}

    override fun onStopStreaming() {}

    override fun onWatcherReceived(userId: Int) {}

    override fun onWatcherLeft(userId: Int) {}
}
   streamSession.addEventListener(streamingListener);
// streamSession.removeEventListener(streamingListener);

Start and stop streaming

streamSession.startStreaming(roomId);
...
streamSession.stopStreaming();
streamSession.startStreaming(roomId)
...
streamSession.stopStreaming()

ConferenceWatchingSession

ConferenceWatchingSession watchingSession = ConferenceStreamClient.getInstance(context).createWatchingSession(currentUser.getId());
val watchingSession = ConferenceStreamClient.getInstance(context).createWatchingSession(currentUser.getId())

Callbacks

ConferenceWatchingSession.ConferenceWatchingListener watchingListener = new ConferenceWatchingSession.ConferenceWatchingListener() {
    @Override
    public void onStartWatching() {
        //your user successfully has become a watcher of the broadcasting stream
    }
    @Override
    public void onStopWatching() {
        //your user stopped watching the broadcasting stream
    }
    @Override
    public void onPublishersReceived(ArrayList<Integer> userIds) {
        //while you are watching some stream, or ready to, you can get some streaming user, and (if you want) subcribe to it
        //watchingSession.subscribeToPublisher(userIds(0));
    }
    @Override
    public void onPublisherLeft(Integer userId) {
        //your streaming user has left
        watchingSession.stopWatching();
    }
};    
   watchingSession.addEventListener(watchingListener);
// watchingSession.removeEventListener(watchingListener);
val watchingListener: ConferenceWatchingSession.ConferenceWatchingListener = object : ConferenceWatchingSession.ConferenceWatchingListener {
    override fun onStartWatching() {}

    override fun onStopWatching() {}

    override fun onPublishersReceived(userIds: ArrayList<Int>) {}

    override fun onPublisherLeft(userId: Int) {}
}
   watchingSession.addEventListener(watchingListener);
// watchingSession.removeEventListener(watchingListener);

Start and stop watching

watchingSession.startWatching(roomId);
...
watchingSession.stopWatching();
watchingSession.startWatching(roomId)
...
watchingSession.stopWatching()