zoukankan      html  css  js  c++  java
  • PJMEID学习之视频的捕捉与播放

    pjmedia是pjsip的视频部分,官网明确提示,要想使用pjmedia离不开directshow/sdl/ffmpeg这三个库。

    软件版本的限制:

    ffmpeg不能高于1.25。(建议下载1.01左右的版本)

    pjsip下载版本要高于2.0.

    directshow/sdl/ffmpeg在pjmedia的作用:

    directshow:流媒体开发包,负责音视频的捕捉等。

    ffmpeg:主要用于视频的编解码。

    SDL:用于视频的播放。

    下面贴出一博主建议先熟悉的例子:

    pjmedia_test 视频的捕捉和播放
    pjmedia 的视频捕捉和传输vid_streamutil.c
    simpleua.c 简单的sip 和视频的协作
    pjsip_ua.c 完整的sip 和视频的协作

    上面的例子源码可以在pjmedia_test工程和sample中找到。

    下面简单的实现一下视频的捕捉和播放。

    首先简单了解一些函数:

    pjmedia_vid_dev_get_info   获取端口信息

    pjmedia_vid_dev_default_param  初始化视频设备用特定设备的参数值

    http://www.pjsip.org/pjmedia/docs/html/group__video__device__reference.htm#gafe6d82fb429b088fac5811d01921928a

    enum pjmedia_dir

    关于Media direction.

    Enumerator
    PJMEDIA_DIR_NONE 

    None

    PJMEDIA_DIR_ENCODING 

    Encoding (outgoing to network) stream, also known as capture

    PJMEDIA_DIR_CAPTURE 

    Same as encoding direction.

    PJMEDIA_DIR_DECODING 

    Decoding (incoming from network) stream, also known as playback.

    PJMEDIA_DIR_PLAYBACK 

    Same as decoding.

    PJMEDIA_DIR_RENDER 

    Same as decoding.

    PJMEDIA_DIR_ENCODING_DECODING 

    Incoming and outgoing stream, same as PJMEDIA_DIR_CAPTURE_PLAYBACK

    PJMEDIA_DIR_CAPTURE_PLAYBACK 

    Same as ENCODING_DECODING

    PJMEDIA_DIR_CAPTURE_RENDER 

    Same as ENCODING_DECODING

    关于pjmedia_vid_dev_info结构体各个成员说明:

      pjmedia_vid_dev_index pjmedia_vid_dev_info::id

    The device ID

    char pjmedia_vid_dev_info::name[64]

    The device name

    char pjmedia_vid_dev_info::driver[32]

    The underlying driver name

    pjmedia_dir pjmedia_vid_dev_info::dir

    The supported direction of the video device, i.e. whether it supports capture only, render only, or both.

    pj_bool_t pjmedia_vid_dev_info::has_callback

    Specify whether the device supports callback. Devices that implement "active interface" will actively call the callbacks to give or ask for video frames. If the device doesn't support callback, application must actively request or give video frames from/to the device by using pjmedia_vid_dev_stream_get_frame()/pjmedia_vid_dev_stream_put_frame().

    unsigned pjmedia_vid_dev_info::caps

    Device capabilities, as bitmask combination of pjmedia_vid_dev_cap

    unsigned pjmedia_vid_dev_info::fmt_cnt

    Number of video formats supported by this device

    pjmedia_format pjmedia_vid_dev_info::fmt[PJMEDIA_VID_DEV_INFO_FMT_CNT]

    Array of supported video formats. Some fields in each supported video format may be set to zero or of "unknown" value, to indicate that the value is unknown or should be ignored. When these value are not set to zero, it indicates that the exact format combination is being used.

      1 //video captrue and show
      2 #include<pjmedia.h>
      3 #include<pjmedia_audiodev.h>
      4 #include<pjmedia_videodev.h>
      5 #include<pjmedia-codec.h>
      6 #include<pjlib.h>
      7 pj_pool_factory *mem;
      8 static find_device(pjmedia_dir dir,pj_bool_t has_callback)
      9 {
     10     unsigned i,count=pjmedia_vid_dev_count();
     11 //    printf("count=%d
    ",count);
     12     for(i=0;i<count;i++)
     13     {
     14         pjmedia_vid_dev_info cdi;
     15         if(pjmedia_vid_dev_get_info(i,&cdi)!=PJ_SUCCESS)
     16             continue;
     17         if((cdi.dir & dir)!=0&& cdi.has_callback==has_callback)
     18             return i;
     19     }
     20     return -1;
     21 }
     22 static int capture_render_lookback(pj_bool_t active,int cap_dev_id,int rend_dev_id,const pjmedia_format *fmt)
     23 {
     24     pj_pool_t *pool;
     25     pjmedia_vid_port *capture=NULL,*renderer=NULL;
     26     pjmedia_vid_dev_info cdi,rdi;
     27     pjmedia_vid_port_param param;
     28     pjmedia_video_format_detail *vfd;
     29     pj_status_t status;
     30     int rc=0,i;
     31 
     32     pool=pj_pool_create(mem,"vidportloop",4000,4000,NULL);
     33 /*
     34     status=pjmedia_vid_dev_get_info(rend_dev_id,&cdi);
     35     if(status!=PJ_SUCCESS)
     36     {
     37         printf("cdi failed
    ");
     38     }
     39     status=pjmedia_vid_dev_get_info(rend_dev_id,&rdi);
     40     if(status!=PJ_SUCCESS)
     41     {
     42         printf("rend failed
    ");
     43     }
     44 */
     45     pjmedia_vid_port_param_default(&param);
     46     //create capture
     47     status=pjmedia_vid_dev_default_param(pool,cap_dev_id,&param.vidparam);
     48     if(status!=PJ_SUCCESS)
     49     {
     50         printf("param failed
    ");
     51     }
     52     param.vidparam.dir=PJMEDIA_DIR_CAPTURE;
     53     param.vidparam.fmt=*fmt;
     54     param.active=PJ_TRUE;
     55 
     56     vfd=pjmedia_format_get_video_format_detail(&param.vidparam.fmt,PJ_TRUE);
     57     if(vfd==PJ_SUCCESS)
     58     {
     59         printf("get vfd failed
    ");
     60     }
     61 
     62     status=pjmedia_vid_port_create(pool,&param,&capture);
     63     if(status!=PJ_SUCCESS)
     64     {
     65         printf("vid create failed
    ");
     66     }
     67     //create render
     68     status=pjmedia_vid_dev_default_param(pool,rend_dev_id,&param.vidparam);
     69     if(status!=PJ_SUCCESS)
     70     {
     71         printf("render param failed
    ");
     72     }
     73     param.active=PJ_FALSE;
     74     param.vidparam.dir=PJMEDIA_DIR_RENDER;
     75     param.vidparam.rend_id=rend_dev_id;
     76     param.vidparam.fmt=*fmt;
     77     param.vidparam.disp_size=vfd->size;
     78 
     79     status=pjmedia_vid_port_create(pool,&param,&renderer);
     80     if(status!=PJ_SUCCESS)
     81     {
     82         printf("render vid port create failed
    ");
     83     }
     84 
     85     // set event handler
     86 
     87 
     88     //connect capture to renderer
     89     status=pjmedia_vid_port_connect(capture,pjmedia_vid_port_get_passive_port(renderer),PJ_FALSE);
     90     if(status!=PJ_SUCCESS)
     91     {
     92         printf("connect failed
    ");
     93     }
     94 
     95     status=pjmedia_vid_port_start(renderer);
     96     if(status!=PJ_SUCCESS)
     97     {
     98         printf("renderer start failed
    ");
     99     }
    100 
    101     status=pjmedia_vid_port_start(capture);
    102     if(status!=PJ_SUCCESS)
    103     {
    104         printf("capture start failed
    ");
    105     }
    106 
    107     return rc;
    108 }
    109 int main()
    110 {
    111     int i,j,k,l;
    112     int count;
    113     int cap_id,rend_id;
    114     pj_status_t status;
    115     pj_caching_pool caching_pool;
    116     pj_pool_t *pool;
    117 
    118     pjmedia_format fmt;
    119     pjmedia_format_id test_fmts[]={
    120         PJMEDIA_FORMAT_RGBA,
    121         PJMEDIA_FORMAT_I420,
    122     //    PJMEDIA_FORMAT_H261 
    123     };
    124 
    125 
    126     pj_init();//pjlib init
    127     pj_caching_pool_init(&caching_pool,&pj_pool_factory_default_policy,0);//init
    128     pool=pj_pool_create(&caching_pool.factory,"test",4000,4000,NULL);
    129     mem=&caching_pool.factory;
    130 
    131     pjmedia_video_format_mgr_create(pool, 64, 0, NULL);
    132     pjmedia_converter_mgr_create(pool, NULL);
    133     pjmedia_event_mgr_create(pool, 0, NULL);
    134     pjmedia_vid_codec_mgr_create(pool, NULL);
    135 
    136     status=pjmedia_vid_dev_subsys_init(mem);
    137 
    138 //get the video device's id
    139     cap_id=find_device(PJMEDIA_DIR_CAPTURE,1);
    140     rend_id=find_device(PJMEDIA_DIR_RENDER,0);
    141 
    142     //printf("c=%d,r=%d
    ");
    143 
    144     pjmedia_format_init_video(&fmt,test_fmts[0],640,480,45,1);
    145     capture_render_lookback(1,cap_id,rend_id,&fmt);
    146 
    147     getchar();
    148 
    149 
    150 }
  • 相关阅读:
    centos 7 安装zabbix 4.0
    django Middleware
    初探paramiko
    python中的反射
    python异常处理
    双绞线
    简易的CMDB服务端
    4-初识Django Admin
    数据资产管理实践纲要
    matplotlib 散点图,为不同区域的点添加不同颜色
  • 原文地址:https://www.cnblogs.com/heat-man/p/3662487.html
Copyright © 2011-2022 走看看