"не показывает экран" webrt c не может показать скриншот - PullRequest
0 голосов
/ 04 мая 2020

Кто-нибудь может представить, почему не работает мой общий ресурс экрана на базе WebRT C? Я уже проверил это. Вы можете видеть имя, когда находитесь в комнате с кем-то, но почему изображение остается белым, когда вы хотите поделиться своим экраном.

Сокет запущен, и в консоли нет ошибок. Как только я разделю изображение, ты ничего не увидишь. Передача не отображается, в чем может быть проблема.

HTML Код:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <script src="/socket.io/socket.io.js"></script>
    <script src="/assets/javascript/realtime/socketClient.js"></script>
    <script src="https://webrtc.github.io/adapter/adapter-latest.js"></script>
</head>
<body>
<div id="available-users"></div>
<video id="remote-video"></video>
<video id="local-video"></video>
</body>
</html>

Разъем Socket:

import SocketIO from 'socket.io';
import SocketSession from 'express-socket.io-session';

const connections = [];

export function startSocketServer(app, httpServer, session) {
    const socketSession = SocketSession(session, {
        autoSave: true
    });

    const socketServer = SocketIO(httpServer);
    socketServer.use(socketSession);

    socketServer.on('connection', (socket) => handleSocket(socketServer, socket));
}

function handleSocket(server, socket) {
    const userData = socket.handshake.session.userData;
    if(!userData) {
        return;
    }

    connections.push({ data: userData, socket })
    socket.on('disconnect', () => {
        const index = connections.findIndex((v) => v.socket === socket);
        if(index > -1) {
            connections.splice(index, 1);
        } else {
            console.log('WARNING: Unindexed socket disconnected');
        }

        server.emit('available-users', connections.map((v) => v.data));
    });

    socket.on('send-connection-request', (target) => {
        console.log(`Connection request from ${userData.user} to ${target.user}`);
        const fullTarget = connections.find((v) => v.data.id === target.id);

        if(fullTarget) {
            fullTarget.socket.emit('connection-request', userData);
        } else {
            socket.emit('error-message', 'Invalid target user');
        }
    });

    socket.on('rtc-offer', (message) => {
        const fullTarget = connections.find((v) => v.data.id === message.target.id);

        if(fullTarget) {
            fullTarget.socket.emit('rtc-offer', {
                description: message.description,
                sender: userData
            });
        } else {
            socket.emit('error-message', 'Invalid target user');
        }
    });

    socket.on('rtc-answer', (message) => {
        const fullTarget = connections.find((v) => v.data.id === message.target.id);

        if(fullTarget) {
            fullTarget.socket.emit('rtc-answer', message);
        } else {
            socket.emit('error-message', 'Invalid target user');
        }
    });

    server.emit('available-users', connections.map((v) => v.data));
}

Клиент сокета:

const socketClient = io();

socketClient.on('available-users', (users) => {
    const availableUsersElement = document.getElementById('available-users');

    let content = "";
    for (const userDescription of users) {
        content += `<button onclick='connectClicked(${JSON.stringify(userDescription)})'>${userDescription.user}</button>`
    }

    availableUsersElement.innerHTML = content;
});

let remoteUser;
let screenStream;

socketClient.on('connection-request', async (source) => {
    console.log(`Connection request from ${source.user}!`);
    remoteUser = source;

    await createPeerConnection();

    screenStream = await navigator.mediaDevices.getDisplayMedia({
        video: true,
        audio: false
    });

    document.getElementById("local-video").srcObject = screenStream;

    screenStream.getTracks().forEach(
        transceiver = t => peerConnection.addTransceiver(t, {
            streams: [screenStream]
        })
    );
});

socketClient.on('error-message', (message) => {
    endCall();
    console.error(`Error message from server: ${message}`)
});
socketClient.on('rtc-offer', handleRtcOffer);
socketClient.on('rtc-answer', handleRtcAnswer);

function connectClicked(target) {
    console.log(`Requesting connection to ${target.user}...`)
    socketClient.emit('send-connection-request', target);
}

let peerConnection;
let transceiver;

async function createPeerConnection() {
    peerConnection = new RTCPeerConnection({
        iceServers: [
            {
                url: 'stun:stun.stunprotocol.org'
            }
        ]
    });

    peerConnection.onicecandidate = handleICECandidateEvent;
    peerConnection.oniceconnectionstatechange = handleICEConnectionStateChangeEvent;
    peerConnection.onsignalingstatechange = handleSignalingStateChangeEvent;
    peerConnection.onnegotiationneeded = handleNegotiationNeededEvent;
    peerConnection.ontrack = handleTrackEvent;
}

function handleICECandidateEvent(event) {
    if (event.candidate) {
        socketClient.emit('ice-candidate', {
            target: remoteUser,
            candidate: event.candidate
        })
    }
}

function handleICEConnectionStateChangeEvent(event) {
    switch (peerConnection.iceConnectionState) {
        case 'closed':
        case 'failed':
        case 'disconnected':
            endCall();
            break;
    }
}

function handleSignalingStateChangeEvent(event) {
    switch (peerConnection.signalingState) {
        case "closed":
            endCall();
            break;
    }
}

async function handleNegotiationNeededEvent() {
    const offer = peerConnection.createOffer();
    if (peerConnection.signalingState !== 'stable') {
        return;
    }

    await peerConnection.setLocalDescription(offer);

    socketClient.emit('rtc-offer', {
        target: remoteUser,
        description: peerConnection.localDescription
    })
}

function handleTrackEvent(event) {
    console.log('Setting remote track');
    document.getElementById('remote-video').srcObject = event.streams[0];
}

function endCall() {
    console.log('Ending call');
    if (peerConnection) {
        peerConnection.onicecandidate = null;
        peerConnection.oniceconnectionstatechange = null;
        peerConnection.onsignalingstatechange = null;
        peerConnection.onnegotiationneeded = null;
        peerConnection.ontrack = null;

        peerConnection.getTransceivers().forEach((t) => t.stop());

        const localVideo = document.getElementById('local-video');
        if(localVideo.srcObject) {
            localVideo.pause();
            localStorage.srcObject.getTracks().forEach(t => t.stop());
        }

        peerConnection.close();
    }

    peerConnection = null;
    screenStream = null;
}

async function handleRtcOffer(message) {
    remoteUser = message.sender;

    if(!peerConnection) {
        await createPeerConnection();
    }

    const description = new RTCSessionDescription(message.description);

    if (peerConnection.signalingState !== 'stable') {
        await Promise.all([
            peerConnection.setLocalDescription({type: 'rollback'}),
            peerConnection.setRemoteDescription(description)
        ]);

        return;
    }

    await peerConnection.setRemoteDescription(description);

    if (!screenStream) {
        screenStream = await navigator.mediaDevices.getDisplayMedia({
            video: true,
            audio: false
        });
    }

    screenStream.getTracks().forEach(
        transceiver = t => peerConnection.addTransceiver(t, {stream: [screenStream]})
    );

    await peerConnection.setLocalDescription(await peerConnection.createAnswer());

    socketClient.emit('rtc-answer', {
        target: remoteUser,
        description: peerConnection.localDescription
    })
}

async function handleRtcAnswer(message) {
    const description = new RTCSessionDescription(message.description);
    await peerConnection.setRemoteDescription(description);
}
...