在事件循环启动后删除并创建新的 RTP 流



我正在使用 Live555 流式传输 1 个或多个视频流。按照testH264VideoStreamer.cpp的示例,创建各种对象,然后启动事件循环。以下是我的初始化代码的摘录,该代码处理单个视频流的对象创建:

// Setup usage environment
this->scheduler = BasicTaskScheduler::createNew();
this->env = BasicUsageEnvironment::createNew(*scheduler);
// Setup framed source
this->framedSource = H264FramedSource::createNew(*this->env, 0, 0);
this->discreteFramer = H264VideoStreamDiscreteFramer::createNew(*env, framedSource);
// Setup sockets
this->rtpGroupsock = new Groupsock(
        *this->env,
        this->destinationAddress,
        this->rtpPort,
        this->ttl);
this->rtcpGroupsock = new Groupsock(
        *this->env,
        this->destinationAddress,
        this->rtcpPort,
        this->ttl);
this->videoSink = H264VideoRTPSink::createNew(
        *this->env,
        this->rtpGroupsock,
        DEF_RTP_PT);
this->rtcp = RTCPInstance::createNew(
        *this->env,
        this->rtcpGroupsock,
        DEF_SESSION_BW,
        cname,
        videoSink,
        0,                   // We are a server
        True);               // We are an SSM source
// Create RTSP server
this->rtspServer = RTSPServer::createNew(*this->env, rtsp_port);
this->sms = ServerMediaSession::createNew(
        *this->env, "test",
        ip.c_str(),
        0,
        True);
this->sms->addSubsession(PassiveServerMediaSubsession::createNew(
        *this->videoSink,
        this->rtcp));
this->rtspServer->addServerMediaSession(this->sms);
this->videoSink->startPlaying(*this->discreteFramer, 0, this->videoSink);
this->env->taskScheduler().doEventLoop();

所以我的问题是:假设我希望我的环境/调度程序处理第二个视频流的事件,或者我想删除现有流。我看到我可以向doEventLoop()添加一个参数以允许事件循环退出。然后,我可以清理旧流,启动新流,并重新启动事件循环。 一旦事件循环已经启动,是否可以执行这些操作?停止和重新启动流是否会中断现有会话?(因此我应该为每个视频流使用不同的线程自己的调度程序/环境?

当事件循环运行时,您可以通过几乎 2 种不同的方式执行操作:

  • 使用来自其他线程的触发器
  • 使用计划任务

使用来自其他线程的触发器

  1. 实现事件回调以完成工作
 static void eventCallback(void* clientData) {
  ....
 }
  1. 注册事件回调:

int triggerId = this->scheduler->createEventTrigger(eventCallback);

  1. 需要时调用触发器:

this->scheduler->triggerEvent(m_eventTriggerId, this);

使用计划任务

  1. 创建任务回调
static void TaskCallback(void* clientData) { 
  ...
}
  1. 在运行事件循环之前安排它:

this->scheduler->scheduleDelayedTask(1000000, TaskCallback, this);

在静态回调中,您可以使用包含 this 指针的 clientData 重定向到类实例。

最新更新