webrtc封装sdk(二)call api的使用

为什么使用Call Api

目前新版webrtc的api和以前已经有很大不同,如果希望封装webrtc为一个音视频sdk,
目前最简单的方法就是了解并使用call类的api。

本文简单介绍Webrtc::Call的基本使用方法。

文中提到的代码可以参考我的开源项目:

Call简介

Call类的头文件为webrtc/call.h

Call类的基本功能为管理rtp媒体流,负责整个音视频通话的管理。

使用Call类的好处是,Call将会回调给你原始的rtp/rtcp数据,并且能将收到的网络rtp/rtcp数据流直接传给Call进行处理。

这样避免了去研究webrtc中的会话管理的协议部分,如PeerConnection类,减轻了研究的复杂度。

Call主要负责管理四种数据流(即Stream):

  • VideoSendStream:负责产生本地视频数据

  • VideoReceiveStream:负责处理远端某一个端的视频数据

  • AudioSendStream:负责产生本地音频数据

  • AudioReceiveStream:负责接收远端某一个端的语音数据

下面演示一下call的创建方法

在初始化音视频sdk时需要创建一个call对象

Call::Config callConfig;

gVoe = VoiceEngine::Create();

webrtc::AudioState::Config audioStateConfig;

audioStateConfig.voice_engine = gVoe;

callConfig.audio_state = AudioState::Create(audioStateConfig);

callConfig.bitrate_config.max_bitrate_bps = 500*1000;

callConfig.bitrate_config.min_bitrate_bps = 100*1000;

callConfig.bitrate_config.start_bitrate_bps = 250*1000;

g_call = Call::Create(callConfig); 

我们可以通过VoiceEngie的实例gVoe来对声音进行各种操作,创建完Call的实例就可以开始创建4种Stream了。

VideoSendStream

一般创建一个VideoSendStream即可,发送本地一个视频流

首先需要配置视频编码参数,创建编码器

  VideoSendStream::Config streamConfig(g_transport);
  streamConfig.encoder_settings.payload_name = "VP9";
  streamConfig.encoder_settings.payload_type = PT_VP9;
  streamConfig.rtp.max_packet_size = 1350;
  streamConfig.encoder_settings.encoder =
  webrtc::VideoEncoder::Create(VideoEncoder::kVp9);
  VideoEncoderConfig encodeConfig;
  VideoSendStream* stream = g_call->CreateVideoSendStream(
  std::move(streamConfig), std::move(encodeConfig));

VideoReceiveStream

多人会话中,需要根据远端的ssrc来创建多个对应的VideoReceiveStream
对某一个远端视频流的管理通过ssrc对应的VideoReceiveStream接口来操作

  VideoReceiveStreamInfo* info = new VideoReceiveStreamInfo(id, remoteSsrc);
  VideoReceiveStream::Config streamConfig(g_transport);
  VideoReceiveStream* stream = g_call->CreateVideoReceiveStream(std::move(streamConfig));

AudioSendStream

一般创建一个AudioSendStream即可,发送本地一个语音流
需要先使用VoiceEngine创建一个channel,后续也可以根据channel id通过g_Voe提供的接口操作这个通道

  AudioSendStream::Config streamConfig(g_transport);
  streamConfig.voe_channel_id = VoEBase::GetInterface(g_Voe)->CreateChannel();
  streamConfig.rtp.ssrc = ssrc;
  AudioSendStream* stream =
  g_call->CreateAudioSendStream(std::move(streamConfig));

AudioReceiveStream

多人会话中,需要根据远端的ssrc来创建多个对应的AudioReceiveStream
对某一个远端语音流的管理通过ssrc对应的AudioReceiveStream接口来操作

  rtc::scoped_refptr<webrtc::AudioDecoderFactory> g_audioDecoderFactory = CreateBuiltinAudioDecoderFactory();
  AudioReceiveStream::Config streamConfig;
  streamConfig.rtp.local_ssrc = localSsrc;
  streamConfig.rtp.remote_ssrc = remoteSsrc;
  streamConfig.rtcp_send_transport = &info->transport;
  streamConfig.voe_channel_id = VoEBase::GetInterface(g_Voe)->CreateChannel();
  streamConfig.decoder_factory = g_audioDecoderFactory;
  AudioReceiveStream* stream =
  g_call->CreateAudioReceiveStream(std::move(streamConfig));

Transport

代码中出现的g_transport是Transport类的具体实现
通过该对象,创建的所有stream可以回调要发出的rtp/rtcp包
你需要自己实现这个对象,完成将数据流传输到媒体服务器的功能

class Transport {
 public:
  virtual bool SendRtp(const uint8_t* packet,
   size_t length,
   const PacketOptions& options) = 0;
  virtual bool SendRtcp(const uint8_t* packet, size_t length) = 0;

 protected:
  virtual ~Transport() {}
};

接收远端rtp/rtcp数据

接收到的远端数据直接传递给Call对象即可

PacketTime pt;
g_call->Receiver()->DeliverPacket(MediaType::ANY, (const uint8_t*)data, len,
  pt);

视频的采集和渲染

VideoSendStream的原始图像是通过VideoCaptureModule采集到的

VideoSendStreaam本身不负责采集,只负责编码和发送视频帧

所以需要自己去开启采集功能

视频的渲染也不由VideoReceiveSteam负责,它会将解码后的videoFrame回调上来

可以参考rtc::VideoSourceInterface类和rtc::VideoSourceInterface类

关键词:webrtc native api c++ call stream

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 199,711评论 5 468
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 83,932评论 2 376
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 146,770评论 0 330
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 53,799评论 1 271
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 62,697评论 5 359
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,069评论 1 276
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,535评论 3 390
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,200评论 0 254
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,353评论 1 294
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,290评论 2 317
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,331评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,020评论 3 315
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,610评论 3 303
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,694评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,927评论 1 255
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,330评论 2 346
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 41,904评论 2 341

推荐阅读更多精彩内容

  • 一 前言 RTP/RTCP协议是流媒体通信的基石。RTP协议定义流媒体数据在互联网上传输的数据包格式,而RTCP协...
    weizhenwei阅读 33,248评论 4 47
  • 本文在文章[1]的基础上,从源代码实现角度对WebRTC的GCC算法进行分析。主要内容包括: RTCP RR的数据...
    weizhenwei阅读 11,730评论 8 20
  • Spring Cloud为开发人员提供了快速构建分布式系统中一些常见模式的工具(例如配置管理,服务发现,断路器,智...
    卡卡罗2017阅读 134,563评论 18 139
  • 本文实现一个简易的单向webrtc网关,使用chrome浏览器浏览服务器上的h264视频文件。代码地址 https...
    little_wang阅读 17,048评论 6 20
  • 昨晚参加了六子老师的文案写作课,以前从未参加过这么好玩的课程,老师和所有小伙伴都那么牛逼,想想自己都弱爆了,总感觉...
    兔子77阅读 460评论 1 0