大家好,首先感谢阅读,如果您也对TDA4相关的开发感兴趣,可以私信联系博主,我们这边有个学习交流群,可以入群和大家一起交流学习。
也可以加博主WX :AIR_12 我会拉你入群。保持开源精神,共同分享、进步!
创建了开源的Demo演示案例库,后续会把Demo代码放到这个Gitee库里:
TDA4/TI TDA4https://gitee.com/tda4/ti-tda4 欢迎大家加入,一起维护这个开源库,给更多的朋友提供帮助。
由于这篇博客写的时间靠前,很多概念阐述不是很清楚,当时就想着能用就行,很多概念模糊/定义不清,优先参考最新更新的这篇,链接如下:
[TI TDA4 J721E]TIOVX Image图像相关操作(修正版)_AIRKernel的博客-CSDN博客
下面的这些,可以作为参考代码使用。(仅供参考)
大家在使用TDA4开发板时,可能会遇到对创建好的图像的操作,比如:
//RGB 图像的创建
obj->disp_image = vxCreateImage(obj->context, DISPLAY_WIDTH, DISPLAY_HEIGHT, VX_DF_IMAGE_RGB);
//NV12 图像的创建
obj->disp_image = vxCreateImage(obj->context, DISPLAY_WIDTH, DISPLAY_HEIGHT, VX_DF_IMAGE_NV12);
对于这些创建的图像可能会将需要显示的图片放置到disp_image内。下面对不同图像进行不同的说明,需要注意的是,不同的图像类型,使用的函数是不一样的。
vxCopyImagePatch(RGB、BMP等图像适用)
vxMapImagePatch(NV12图像适用)
一、vxCopyImagePatch 操作图像
示例代码如下:
//Read image from bin file 显示实例图像,经过openGl处理保存4路图像在一张1920*1080图上
FILE *pic_fd = fopen("/home/root/output/mosaic_output_file.bin", "r+");
if (pic_fd)
{
int size_read = fread(obj->pDisplayBuf888, 1, (DISPLAY_WIDTH * DISPLAY_HEIGHT * 3), pic_fd);
if (size_read!=(DISPLAY_WIDTH * DISPLAY_HEIGHT * 3))
{
printf("file read error!\n");
}
}
fclose(pic_fd);
obj->disp_rect.start_x = 0;
obj->disp_rect.start_y = 0;
obj->disp_rect.end_x = DISPLAY_WIDTH;
obj->disp_rect.end_y = DISPLAY_HEIGHT;
status = vxCopyImagePatch(obj->disp_image,
&obj->disp_rect,
0,
&obj->image_addr,
(void *)obj->pDisplayBuf888,
VX_WRITE_ONLY,
VX_MEMORY_TYPE_HOST);
首先要创建一个pDisplayBuf888,此处是为了显示RGB图像,RGB图像大小为DISPLAY_WIDTH * DISPLAY_HEIGHT * 3。
1、示例代码为从文件内读取一个RGB图像
2、将RGB图像,拷贝到pDisplayBuf888内
3、使用vxCopyImagePatch,将pDisplayBuf888数据,拷贝到disp_image内,这样的话,disp_node会自动调用此图像进行显示。
4、可以通过调整disp_rect的参数,调整图像显示的区域。(我这里输出是1920*1080)
5、延伸:
使用BMP(系统内有函数专门从BMP加载图像到RGB的函数,tivx_utils_create_vximage_from_bmpfile)
使用一个disp_image可以显示多个BMP图像。可以对比以下以下的代码段:
obj->disp_rect.start_x = 0;
obj->disp_rect.start_y = 0;
obj->disp_rect.end_x = obj->imgParams.width;
obj->disp_rect.end_y = obj->imgParams.height;
status = vxCopyImagePatch(obj->disp_image,
&obj->disp_rect,
0,
&obj->image_addr,
(void *)obj->pDisplayBuf888,
VX_WRITE_ONLY,
VX_MEMORY_TYPE_HOST);
obj->disp_rect.start_x = obj->imgParams.width;
obj->disp_rect.start_y = 0;
obj->disp_rect.end_x = 2*(obj->imgParams.width);
obj->disp_rect.end_y = obj->imgParams.height;
status = vxCopyImagePatch(obj->disp_image,
&obj->disp_rect,
0,
&obj->image_addr,
(void *)obj->pDisplayBuf888,
VX_WRITE_ONLY,
VX_MEMORY_TYPE_HOST);
显示效果是两张图像并排显示。
PS:
如果需要使用NV12图像实现单屏多显示,请参阅这篇博客
效果如下(花屏的原因是没有对pDisplayBuf888进行初始化,可以不用管,这个是在ti-processor-sdk-rtos-j721e-evm-08_00_00_12/vision_apps/apps/dl_demos/app_tidl的Demo实现的):
二、vxMapImagePatch 操作图像
vxQueryImage((vx_image)obj->input[i], VX_IMAGE_WIDTH, &img_width, sizeof(vx_uint32));
vxQueryImage((vx_image)obj->input[i], VX_IMAGE_HEIGHT, &img_height, sizeof(vx_uint32));
vxQueryImage((vx_image)obj->input[i], VX_IMAGE_FORMAT, &img_format, sizeof(vx_df_image));
rect.start_x = 0;
rect.start_y = 0;
rect.end_x = img_width;
rect.end_y = img_height;
status = vxMapImagePatch((vx_image)obj->input[i],
&rect,
0,
&map_id,
&image_addr,
&data_ptr,
VX_WRITE_ONLY,
VX_MEMORY_TYPE_HOST,
VX_NOGAP_X);
status = vxMapImagePatch((vx_image)obj->input[i],
&rect,
1,
&map_id2,
&image_addr2,
&data_ptr2,
VX_WRITE_ONLY,
VX_MEMORY_TYPE_HOST,
VX_NOGAP_X);
memcpy(data_ptr, pmap, (img_width * img_height));
num_bytes = img_width * img_height;
if (num_bytes != (img_width * img_height))
{
printf("Luma bytes read = %d, expected = %d", num_bytes, img_width * img_height);
}
memcpy(data_ptr2, (pmap + img_width * img_height), img_width * img_height / 2);
num_bytes = img_width * img_height / 2;
if (num_bytes != (img_width * img_height / 2))
{
printf("CbCr bytes read = %d, expected = %d", num_bytes, img_width * img_height / 2);
}
1、首先使用vxvxQueryImage,查询图的widht/height/format等信息
2、使用vxMapImagePatch函数向图像申请内存地址,data_ptr/data_ptr2
3、拷贝数据,pmap数据是提前准备好的一个NV12格式的图像。(使用USB 图像获取的数据,我会单独写一个USB实现YUV图像获取的博客。链接如下)
[TI TDA4]TIOVX USB摄像头获取YUV数据并显示Demo的实现_AIRKernel的博客-CSDN博客
4、特别说明:
NV12图像应该是YUV格式的数据,大小为 Weigh*Height*1.5 ,这个就是图像的大小,所以要做两次拷贝,第一次拷贝数据大小为Weigh*Height,第二次拷贝大小为0.5*Weigh*Height。这里大家可以去查一下各种图像之间的差异。
【声明】
【欢迎转载转发,请注明出处。原创比较辛苦,请尊重原创,祝大家学习愉快!】
【博主专注嵌入式开发,具有多年嵌入式软、硬件开发经验,欢迎大家学习交流!】
【如有嵌入式相关项目需求,欢迎私信】