实时音视频云

  • 发布和订阅

    最近更新时间:2018-08-02 09:42:30

    上一步我们已经介绍了基本的采集媒体流的方法,下面就可以开始发布和订阅的流程了。发布和订阅都属于房间内的操作,所以请先确保调用代码之前已经加入了房间。

    发布

    这里我们假定您已经加入了房间,并通过采集媒体流获取了本地流对象 stream, 使用 publish 来发布媒体流

    try {
        await myRTC.publish(stream);  // myRTC 为加入房间后的 QNRTCSession 实例
    } catch(e) {
        console.log('publish Error!', e);
    }
    // or use Promise
    myRTC.publish(stream))
        .then(() => {
            console.log('publish success');
        }).catch(e => {
            console.log('publish Error!', e);
        });
    

    订阅

    订阅相比发布会复杂很多,发布只需要加入房间采集到媒体流就可以调用了,但是订阅必须在满足一定外部条件的情况下才能调用:

    • 获取订阅目标的用户名 userId
    • 订阅目标必须已经发布了自己的媒体流

    为了能实时地判断何时可以发起订阅,我们需要时刻监听房间内所有用户状态的变化(用户加入/离开,用户发布/取消发布)。具体推荐的方法见下。

    当调用了加入房间的方法之后,我们立刻获得这个房间内已有用户的信息,其中 published 字段代表这个用户是否已经发布了媒体流,此时如果有除自己以外的用户已经发布的话,就满足了订阅条件可以发起订阅了。之后我们再通过事件监听获取之后发生的用户加入/用户发布事件,当满足订阅条件时发起订阅,这样我们就能全局地感知整个房间的用户状态变化了。

    这里需要用到 2 个 API,subscribe 用来订阅其他用户发布的媒体流,事件监听 用来通过事件回调同步房间各种状态的变化,事件列表见此

    // myRTC 为加入房间后的 QNRTCSession 实例
    // user 代表加入房间返回或者事件返回的单个用户对象
    function subscribeUser(myRTC, user) {
      // 如果用户没有发布就直接返回
      if (!user.published) {
        return;
      }
    
        // 根据需要选择是使用 Promise 还是 async/await
      myRTC.subscribe(user.userId).then(remoteStream => {
        // 我们在页面上准备用来显示远端媒体流的元素
        const remotePlayer = document.getElementById('remoteplayer');
        // 在我们准备的元素上播放远端媒体流
        remoteStream.play(remotePlayer);
      }).catch(e => {
        console.log('subscribe error!', e);
      });
    }
    

    以上展示了订阅 API 的基本使用方法,下面是配合事件监听和房间用户完成的自动订阅逻辑

    // 加入房间
    const users = await myRTC.joinRoomWithToken(roomToken);
    console.log('joinRoom success! 当前房间用户:', users);
    // 监听房间里的用户发布事件,一旦有用户发布,就订阅他
    myRTC.on('user-publish', user => {
        subscribeUser(myRTC, user);
    });
    // 判断房间当前的用户是否有可以订阅的
    for (let i = 0; i < users.length; i += 1) {
        const user = users[i];
        // 如果当前房间的用户不是自己并且已经发布
        // 那就订阅他
        if (user.published && user.userId !== myRTC.userId) {
            subscribeUser(myRTC, user);
        }
    }
    
    以上内容是否对您有帮助?
  • Close