简体   繁体   中英

Getting images in second peer using WebRTC (without a server)

I'm creating one direction call, but I can't receive the images in the second peer.

My application has the following code:

HTML

<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <title>WebRTC</title>
    <style>
        body,
        html {
            margin: 0;
            padding: 0;
            height: 100%;
            display: flex;
            flex-direction: column;
            justify-content: center;
            align-items: center;
            background-color: #20262E;
        }

        video {
            width: 100%
        }
    </style>
</head>

<body>
    <button id="initialize">initialize</button>
    <video autoplay></video>
    <script src="https://webrtc.github.io/adapter/adapter-latest.js"></script>
    <script src="carai.js"></script>
</body>

</html>

Javascript

const startButton = document.querySelector('button#initialize')
const video = document.querySelector('video')
const confPeer = {}
const channel = new BroadcastChannel('loc')
const peer = new RTCPeerConnection(confPeer)

//
// SIMULATE WEBSOCKET
//

channel.addEventListener('message', message => {
    let {
        action,
        value
    } = message.data

    switch (action) {
        case 'offer':
            startButton.remove()
            answer(value)
            break

        case 'answer':
            done(value)
            break

        default:
            console.error('wtf')
    }
})

// 
// START CALL
// 

const start = async () => {
    console.log('----- start')

    const localStream = await navigator.mediaDevices.getUserMedia({
        // audio: true,
        video: true
    })

    video.srcObject = localStream

    localStream.getTracks().forEach(track => peer.addTrack(track, localStream));

    let offer = await peer.createOffer()

    peer.setLocalDescription(offer)

    channel.postMessage({
        action: 'offer',
        value: JSON.stringify(offer)
    })
}

//
// ANSWER CALL
//

const done = receivedAnswer => {
    console.log('----- done')
    peer.setRemoteDescription(JSON.parse(receivedAnswer))
}

//
// ESTABLISH CALL
// 

const answer = async receivedOffer => {
    console.log('----- answer')

    peer.ontrack = e => {
        console.log('----- ontrack', e)
        video.srcObject = e.streams[0];
    }

    receivedOffer = JSON.parse(receivedOffer)

    let desc = new RTCSessionDescription(receivedOffer)

    peer.setRemoteDescription(desc)

    let answer = await peer.createAnswer()

    await peer.setLocalDescription(answer)

    channel.postMessage({
        action: 'answer',
        value: JSON.stringify(answer)
    })
}

//
// INITIALIZE
//

startButton.addEventListener('click', start)

The caller() saves the information in a localStorage, which called() reads and uses to accept the call, which receives getRemoteStreams, but I can´t play it in the video element.

can anyone help-me with this?

This is my first time using WebRTC, I know I'm missing something.


It works in Chrome when I click the start button a second time, but it displays the following depreciation message in the terminal:

折旧消息

localStorage as a signaling-channel is a neat trick to demo calls between two tabs.

But you've only completed half the circle of the offer/answer exchange. You need to get the answer back to the caller. Eg

localStorage.setItem('b', JSON.stringify(answer))

...and then add code that receives it and calls setRemoteDescription(answer) on the 1st peer.

You also need to exchange of ICE candidates, which complicates things.

FWIW I've written localSocket helper class that helps with this. Here's a demo (open in 2 tabs).

Lastly, getRemoteStreams() is deprecated , and isn't needed here since you use ontrack .

Thanks to the great @jib I understood what I was doing wrong. here is the correct code for those are passing to the same situation.

MUITO OBRIGADO @jig

const startButton = document.querySelector('button#initialize')
const video = document.querySelector('video')
const confPeer = {}
const channel = new BroadcastChannel('loc')
const peer = new RTCPeerConnection(confPeer)

//
// SIMULATE WEBSOCKET
//

channel.addEventListener('message', message => {
    let {
        action,
        value
    } = message.data

    switch (action) {
        case 'offer':
            startButton.remove()
            answer(value)
            break

        case 'icecandidate':
            icecandidate(value)
            break

        case 'answer':
            done(value)
            break

        default:
            console.error('wtf')
    }
})

// 
// PEER A: START CALL
// 

const start = async () => {
    console.log('----- start')

    const localStream = await navigator.mediaDevices.getUserMedia({
        // audio: true,
        video: true
    })

    peer.onicecandidate = ev => {
        console.log('candidate', ev.candidate)
        channel.postMessage({
            action: 'icecandidate',
            value: JSON.stringify(ev.candidate)
        })
    }

    video.srcObject = localStream

    localStream.getTracks().forEach(track => peer.addTrack(track, localStream));

    let offer = await peer.createOffer()

    peer.setLocalDescription(offer)

    channel.postMessage({
        action: 'offer',
        value: JSON.stringify(offer)
    })
}

//
// PEER A: ANSWER CALL
//

const done = receivedAnswer => {
    console.log('----- done')
    peer.setRemoteDescription(JSON.parse(receivedAnswer))
}

//
// PEER B: ICE CANDIDATE
//

const icecandidate = receivedIcecandidate => {
    let candidate = JSON.parse(receivedIcecandidate)
    console.log('received icecandidate', candidate)
    peer.addIceCandidate(candidate)
}

//
// PEER B: ESTABLISH CALL
// 

const answer = async receivedOffer => {
    console.log('----- answer')

    peer.ontrack = e => {
        console.log('----- ontrack', e)
        video.srcObject = e.streams[0];
    }

    receivedOffer = JSON.parse(receivedOffer)

    let desc = new RTCSessionDescription(receivedOffer)

    peer.setRemoteDescription(desc)

    let answer = await peer.createAnswer()

    await peer.setLocalDescription(answer)

    channel.postMessage({
        action: 'answer',
        value: JSON.stringify(answer)
    })
}

//
// INITIALIZE
//

startButton.addEventListener('click', start)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM