muaz-khan / RTCMultiConnection

RTCMultiConnection is a WebRTC JavaScript library for peer-to-peer applications (screen sharing, audio/video conferencing, file sharing, media streaming etc.)
https://muazkhan.com:9001/
MIT License
2.57k stars 1.37k forks source link

How to restart screen sharing during a running session? #993

Open spacearound404 opened 3 years ago

spacearound404 commented 3 years ago

If the room owner starts screen sharing before the guests connect, then everything is fine, screen sharing is displayed for the guests, but if screen sharing is not yet started and there is already a guest in the room, then only the room owner starts screen sharing, and nothing happens for the guest (the guest does not display the owner's screen sharing). I looked at the demo screen sharing and demo video conference + screen sharing code, but it didn't help, especially since screen sharing in demo doesn't work for me at all. There is also no information in issues. On the guest side, nothing happens in the onstream event when screen sharing is restarted.

I use this code to launch screen sharing:

screenShareOn() {
        let thisAdminVC = this.getInstance();

        this.connection.addStream({
            screen: true,
            oneway: true,
            data: true,
            streamCallback: function(stream) {
                thisAdminVC.connection.extra.streamID = stream.id;

                thisAdminVC.connection.updateExtraData();
                thisAdminVC.videoContainerLocal.screen.elementHTML.appendChild(stream);

                const videoTrack = stream.getVideoTracks()[1];
                videoTrack.onended = () => {
                    thisAdminVC.connection.resetTrack();
                }

                thisAdminVC.connection.getAllParticipants().forEach( participant =>
                    thisAdminVC.connection.replaceTrack(videoTrack, participant, true)
                );
            }
        });

        this.connection.renegotiate();
}

I use this code to stop screen sharing:

screenShareOff() {
        this.connection.attachStreams.forEach(function(stream) {
            if (stream.idInstance.indexOf("isScreen") != -1) {
                stream.getTracks().forEach(track => track.stop());
                stream.getTracks().forEach(track => stream.removeTrack(track));
            }
        });
}
spacearound404 commented 3 years ago

In General, I found only such a working solution for myself, I don't know how correct it is. In order that when restarting the screen share of the room owner, the guest can also see it, you need to copy the created stream to a temporary variable, insert a temporary stream in , then everything works and the connection.streamEvents and connection.attachStream array do not overflow.

    screenShareOn() {

        let thisAdminVC = this.getInstance();

        this.connection.addStream({
            screen: true,
            oneway: true,
            data: true,
            streamCallback: function(stream) {

                for (let i = 0; i < thisAdminVC.connection.attachStreams.length; i++) {
                    if (thisAdminVC.connection.attachStreams[i].idInstance.indexOf("isScreen") != -1) {

                        let tmpStreamID = thisAdminVC.connection.attachStreams[i].id,
                        tmpStream = thisAdminVC.connection.streamEvents[tmpStreamID].stream;

                        thisAdminVC.connection.addStream(tmpStream);

                        thisAdminVC.connection.renegotiate();
                    }
                }

                thisAdminVC.connection.extra.streamID = stream.id;

                thisAdminVC.connection.updateExtraData();
                thisAdminVC.videoContainerLocal.screen.elementHTML.appendChild(tmpStream);
            }
        });
        this.connection.renegotiate();
    }