公告

大中华汽车电子生态圈社区并入开发者社区- 更多资讯点击此

Tip / 登入 to post questions, reply, level up, and achieve exciting badges. Know more

cross mob

基于CX3的UVC摄像头应用学习笔记-六(添加多帧率支持)

lock attach
Attachments are accessible only for community members.

基于CX3的UVC摄像头应用学习笔记-六(添加多帧率支持)

YangyangC_06
Employee
Employee
750 replies posted 500 replies posted 250 replies posted

在本篇 blog 中,我们学习如何在同一个分辨率下支持多个帧率的视频传输。

 

  1. 首先,我们需要对 frame descriptor 进行修改。此处,我们配置分辨率为 1920 x 1080,帧率分别为 30 fps 和 60 fps。

    0x22,                               /* Descriptor size */

    CX3_CS_INTRFC_DESCR,                /* Descriptor type*/

    0x05,                               /* Subtype:  frame interface*/

    0x01,                               /* Frame Descriptor Index: 1 */

    0x00,                               /* No Still image capture method supported */

    0x80,0x07,                         /* Width in pixel:  1920 */

    0x38,0x04,                         /* Height in pixel: 1080 */

    0x00,0x00,0xa7,0x76,             /* Max bit rate (bits/s): 1920 x 1080 x 16 x 60 = 0x76a70000 */

    0x00,0x80,0x53,0x3b,             /* Min bit rate (bits/s): 1920 x 1080 x 16 x 30 = 995328000 */

    0x00,0x48,0x3f,0x00,             /* Maximum video or still frame size in bytes(Deprecated): 1920 x 1080 x 2 */

    0x15,0x16,0x05,0x00,             /* Default frame interval (in 100ns units): (1/30)x10^7 */

    0x02,                               /* Frame interval type : No of discrete intervals */

    0x0a,0x8b,0x02,0x00, /* 60 fps */

    0x15,0x16,0x05,0x00,             /* 30 fps */

 

 

2.随后修改 Class-specific Video Streaming Input Header Descriptor  中的长度值。

 

    0x56,0x00,                          /* Total size of Class specific VS descr */

 

和 CyCx3USBSSConfigDscr 中的总长度值。

 

    0xe9,0x00,                         /* Length of this descriptor and all sub descriptors */

 

 

3. 分别配置 30fps 和 60fps 对应的 probe 结构体

/* UVC Probe Control Setting - 1080p_60fps*/

uint8_t const gl1080pProbeCtrl_60fps[CX3_UVC_MAX_PROBE_SETTING] = {

    0x00, 0x00,                         /* bmHint : No fixed parameters */

    0x01,                               /* Use 1st Video format index */

    0x01,                               /* Use 1st Video frame index */

    0x0a,0x8b,0x02,0x00,             /* Desired frame interval in 100ns = (1/30)x10^7 */

    0x00, 0x00,                         /* Key frame rate in key frame/video frame units */

    0x00, 0x00,                         /* PFrame rate in PFrame / key frame units */

    0x00, 0x00,                         /* Compression quality control */

    0x00, 0x00,                         /* Window size for average bit rate */

    0x00, 0x00,                         /* Internal video streaming i/f latency in ms */

    0x00,0x48,0x3f,0x00,             /* Max video frame size in bytes = 1920 x 1080 x 2 */

#ifdef CX3_UVC_1_0_SUPPORT

    0x00, 0x90, 0x00, 0x00              /* No. of bytes device can rx in single payload: 36KB */

#else

    /* UVC 1.1 Probe Control has additional fields from UVC 1.0 */

    0x00, 0x90, 0x00, 0x00,             /* No. of bytes device can rx in single payload: 36KB */

    0x00, 0x60, 0xE3, 0x16,             /* Device Clock */

    0x00,                               /* Framing Information - Ignored for uncompressed format*/

    0x00,                               /* Preferred payload format version */

    0x00,                               /* Minimum payload format version */

    0x00                                /* Maximum payload format version */

#endif

};

 

 

 

/* UVC Probe Control Setting - 1080p_30fps*/

uint8_t const gl1080pProbeCtrl_30fps[CX3_UVC_MAX_PROBE_SETTING] = {

    0x00, 0x00,                         /* bmHint : No fixed parameters */

    0x01,                               /* Use 1st Video format index */

    0x01,                               /* Use 1st Video frame index */

    0x15,0x16,0x05,0x00,             /* Desired frame interval in 100ns = (1/30)x10^7 */

    0x00, 0x00,                         /* Key frame rate in key frame/video frame units */

    0x00, 0x00,                         /* PFrame rate in PFrame / key frame units */

    0x00, 0x00,                         /* Compression quality control */

    0x00, 0x00,                         /* Window size for average bit rate */

    0x00, 0x00,                         /* Internal video streaming i/f latency in ms */

    0x00,0x48,0x3f,0x00,             /* Max video frame size in bytes = 1920 x 1080 x 2 */

#ifdef CX3_UVC_1_0_SUPPORT

    0x00, 0x90, 0x00, 0x00              /* No. of bytes device can rx in single payload: 36KB */

#else

    /* UVC 1.1 Probe Control has additional fields from UVC 1.0 */

    0x00, 0x90, 0x00, 0x00,             /* No. of bytes device can rx in single payload: 36KB */

    0x00, 0x60, 0xE3, 0x16,             /* Device Clock */

    0x00,                               /* Framing Information - Ignored for uncompressed format*/

    0x00,                               /* Preferred payload format version */

    0x00,                               /* Minimum payload format version */

    0x00                                /* Maximum payload format version */

#endif

};

 

 

 

 

4.修改 CyCx3UvcAppGetProbeControlData 以返回相应的 probe 结构体

/*Returns the pointer to the Probe Control structure for the corresponding frame index.*/

uint8_t *

CyCx3UvcAppGetProbeControlData (

        CyU3PUSBSpeed_t usbConType,

        uint8_t         frameIndex,

        uint32_t glCurrentFrameInterval

        )

{

uint32_t frame_fps = 10000000 / glCurrentFrameInterval;

    if (usbConType == CY_U3P_SUPER_SPEED)

    {

       if (frameIndex == 1)

        {

       if(frame_fps == 30)

       {

            /* 1920 x 1080 @30.0 fps */

       CyU3PDebugPrint(4,"\n Line:%d: Return 30 fps structure",__LINE__);

               return ((uint8_t *) gl1080pProbeCtrl_30fps);

       }

       else if(frame_fps == 60)

       {              /* 1920 x 1080 @60.0 fps */

       CyU3PDebugPrint(4,"\n Line:%d Return 60 fps structure",__LINE__);

                  return ((uint8_t *) gl1080pProbeCtrl_60fps);

       }

 

 

        }

    }

    else if (usbConType == CY_U3P_HIGH_SPEED)

    {

    }

    else

    {

 

 

    }

    return NULL;

}

 

 

 

 

 

 

 

 

 

5. 在 Callback 函数中修改 Set_cur 的代码

 

    /* Set Probe Control */

    if (wValue == CX3_UVC_VS_PROBE_CONTROL)

    {

        glCurrentFrameIndex = glCommitCtrl[3];

#ifdef Two_frame_rate

        glCurrentFrameInterval = ((uint32_t)glCommitCtrl[7] << 24) | ((uint32_t)glCommitCtrl[6] << 16) |

((uint32_t)glCommitCtrl[5] << 😎 | ((uint32_t)glCommitCtrl[4] << 0);

        CyU3PDebugPrint(4,"\r\n Line:%d: glCurrentFrameInterval = 0x%x",__LINE__,glCurrentFrameInterval);

#endif

    }

 

 

6. 修改 SetVideoResolution 函数的实现

 

/* Set the video resolution through this function. This function lists all the

*  supported resolutions in SuperSpeed and HighSpeed. The frame index of resolutions

*  supported in Still Capture can be different from the frame index of resolutions supported

*  in Video streaming.

*/

static void

CyCx3UvcAppImageSensorSetVideoResolution(

        uint8_t resolution_index,

        uint32_t frame_Interval

        )

{

CyU3PReturnStatus_t status = CY_U3P_SUCCESS;

uint32_t frameRate= 10000000/frame_Interval;

switch (CyU3PUsbGetSpeed ())

{

case CY_U3P_SUPER_SPEED:

switch (resolution_index)

{

case 0x01:

{

if(frameRate == 30)

{

CyU3PDebugPrint(4,"\r\n Line:%d: Set 30 fps",__LINE__);

/* Write 1080pSettings */

#ifndef FX3_STREAMING

status = CyU3PMipicsiSetIntfParams (&OV5640_YUY2_1080p, CyFalse);

if (status != CY_U3P_SUCCESS)

{

CyU3PDebugPrint (4, "\n\rUSBStpCB:SetIntfParams SS1 Err = 0x%x", status);

}

#endif

CyCx3_ImageSensor_Set_1080p ();

 

 

}

else if (frameRate == 60)

{

CyU3PDebugPrint(4,"\r\n Line:%d: Set 60 fps",__LINE__);

/* Write 1080pSettings */

#ifndef FX3_STREAMING

status = CyU3PMipicsiSetIntfParams (&OV5640_YUY2_1080p, CyFalse);

if (status != CY_U3P_SUCCESS)

{

CyU3PDebugPrint (4, "\n\rUSBStpCB:SetIntfParams SS1 Err = 0x%x", status);

}

#endif

CyCx3_ImageSensor_Set_1080p ();

 

 

}

 

 

}

break;

 

 

}

break;

 

 

case CY_U3P_HIGH_SPEED:

switch (resolution_index)

{

 

 

 

 

}

break;

}

}

 

 

 

 

 

按以上的步骤修改后,将固件下载至Demo 板,进行测试。

 

Snipaste_2019-08-02_17-12-35.png

 

 

Snipaste_2019-08-02_17-12-13.png

 

 

Snipaste_2019-08-02_17-11-58.png

 

可以看到,用户可以在主机端软件中对不同 fps 的配置进行正常切换。用户可以参考附件的工程获取更多细节信息。

 

注:

  • 出于演示的目的,本篇文档所附的固件中,只配置了USB3.0 的配置描述符(以及其他所有相关的 处理函数),没有 设置 USB2.0 及以下速度对应的配置描述符。如有需要,用户可以自行进行添加。
  • 同上,本篇 blog 所附的固件中,实际上当主机设置不同的 fps 时,固件采用相同的参数对 MIPI CSI 模块和 sensor进行配置(即执行相同的代码),只是采用 UART 打印的方式演示函数分支可以正常执行。实际使用中,用户当然需要做不同的配置。
  • 在主机软件的分辨率列表中,同一分辨率只会显示默认的帧率,不会同时列出所有帧率。
  • 在第一步中,需要先定义Max bits/s 后 Min bits/s,先 高帧率 后低帧率,否则烧录固件后不能正常工作。参考 CX3 multiple framerate support in same resolution
附件
2288 次查看