【问题标题】:WebRTC both remote and local video is displayed with local streamWebRTC 远程和本地视频都以本地流显示
【发布时间】:2019-04-23 04:51:56
【问题描述】:

你好,我是 WebRTC 的新手,我试过这段代码

  const yourVideo = document.querySelector("#face_cam_vid");
 const theirVideo = document.querySelector("#thevid");

 (async () => {
 if (!("mediaDevices" in navigator) || !("RTCPeerConnection" in window)) {
  alert("Sorry, your browser does not support WebRTC.");
  return;
 }
  const stream = await navigator.mediaDevices.getUserMedia({video: true, 
  audio: true});
  yourVideo.srcObject = stream;

  const configuration = {
  iceServers: [{urls: "stun:stun.1.google.com:19302"}]
  };
const yours = new RTCPeerConnection(configuration);
const theirs = new RTCPeerConnection(configuration);

for (const track of stream.getTracks()) {
  yours.addTrack(track, stream);
}
theirs.ontrack = e => theirVideo.srcObject = e.streams[0];

yours.onicecandidate = e => theirs.addIceCandidate(e.candidate);
theirs.onicecandidate = e => yours.addIceCandidate(e.candidate);

const offer = await yours.createOffer();
await yours.setLocalDescription(offer);
await theirs.setRemoteDescription(offer);

const answer = await theirs.createAnswer();
await theirs.setLocalDescription(answer);
await yours.setRemoteDescription(answer);
})();

它有效,但部分有效 https://imgur.com/a/nG7Xif6 。简而言之,我正在创建 ONE-to-ONE 随机视频聊天,就像在 omegle 中一样,但是这段代码在我的本地流中同时显示“远程”(陌生人)和“本地”(“我的”)视频,但我想要的是,用户等待第二个用户进行视频聊天,当第三个用户进入时,它应该等待第四个等等。我希望有人能帮助我

【问题讨论】:

    标签: javascript webrtc


    【解决方案1】:

    您将本地循环演示(您所拥有的)与聊天室混淆了。

    local-loop demo 是一个仅限客户端的短路概念验证,它将同一页面上的两个对等连接相互链接。完全没用,除了证明 API 有效并且浏览器可以与自己对话。

    它包含 localPeerConnectionremotePeerConnection — 或 pc1pc2 — 这不是人们通常编写 WebRTC 代码的方式。它忽略了信号。

    没有服务器的信号很难演示,但我向人们展示了这个tab demo。右键单击并在相邻的两个窗口中打开它,然后单击一个上的Call! 按钮来调用另一个。它使用 localSocket,这是我使用 localStorage 进行信号发送的非生产黑客。

    同样没用,tab-demo 看起来更像真正的代码:

    const pc = new RTCPeerConnection();
    
    call.onclick = async () => {
      video.srcObject = await navigator.mediaDevices.getUserMedia({video:true, audio:true});
      for (const track of video.srcObject.getTracks()) {
        pc.addTrack(track, video.srcObject);
      }
    };
    
    pc.ontrack = e => video.srcObject = e.streams[0];
    pc.oniceconnectionstatechange = e => console.log(pc.iceConnectionState);
    pc.onicecandidate = ({candidate}) => sc.send({candidate});
    pc.onnegotiationneeded = async e => {
      await pc.setLocalDescription(await pc.createOffer());
      sc.send({sdp: pc.localDescription});
    }
    
    const sc = new localSocket();
    sc.onmessage = async ({data: {sdp, candidate}}) => {
      if (sdp) {
        await pc.setRemoteDescription(sdp);
        if (sdp.type == "offer") {
          await pc.setLocalDescription(await pc.createAnswer());
          sc.send({sdp: pc.localDescription});
        }
      } else if (candidate) await pc.addIceCandidate(candidate);
    }
    

    有一个pc——你的一半通话——还有一个onmessage信号回调来正确处理时间关键的非对称提议/应答协商。两边的JS一样。

    这仍然不是 聊天室。为此,您需要服务器逻辑来确定人们如何见面,以及用于发送信号的 Web 套接字服务器。试试this tutorial on MDN,最后是chat demo

    【讨论】:

    • 对于您的 localSocket,只需快速阅读它,但听起来您正在轮询存储。您可能对storage event 感兴趣,它会在其他窗口修改当前窗口的存储区域时通知您。你可以在this Q/A看到这样一个窗口消息系统的粗略演示
    • 实际上我无法理解哪个是 MYVIDEO(本地)和 THEIRVIDEO(远程),我也无法理解为什么我需要 onmessage 事件
    • 实际上我尝试了 MDN,但它有点晦涩,因为也有消息传递系统,所以因为代码是模糊的,这就是我在此处发布的原因,但感谢您的回答,我尝试了连接数组,但确实如此没用所以如果我在这里找到答案我会很高兴顺便说一句谢谢你第二次回答我
    • 传统的消息系统和 WebRTC 共享发现参与者的相同挑战,这在 WebRTC 之外。此外,无论如何都需要消息系统来发送信号。
    • 我也不使用用户名,它只是纯 javascript,整个代码都在用户名上,因为我是新手,我无法像与用户一起工作那样转换 MDN 代码,(我使用 document.hasFocus( )方法)顺便说一句,聊天演示不起作用。我尽了最大努力,但因为我没有达到我的目标我也把它贴在这里你的意思是没有服务器很难向人们展示演示我认为你只需要服务器是iceserver,我是否也需要expressjs ?
    猜你喜欢
    • 2014-08-13
    • 1970-01-01
    • 2017-06-27
    • 2021-06-18
    • 1970-01-01
    • 2015-11-15
    • 1970-01-01
    • 2023-04-03
    • 1970-01-01
    相关资源
    最近更新 更多