• 2024-05-10 Ubuntu上面使用libyuv,用于转换、缩放、旋转和其他操作YUV图像数据,测试实例使用I420ToRGB24


    一、简介:libyuv 最初是由Google开发的,主要是为了支持WebRTC项目中的视频处理需求。用于处理YUV格式图像数据的开源库。它提供了一系列的函数,用于转换、缩放、旋转和其他操作YUV图像数据。

    二、执行下面的命令下载和安装libyuv。

    1. git clone https://github.com/lemenkov/libyuv.git
    2. cd libyuv
    3. mkdir build && cd build
    4. cmake ..
    5. make
    6. sudo make install

    三、测试实例convert_yuv_to_rgb.cpp,使用c编译的时候,I420ToRGB24前面就不要有libyuv::。

    1. #include <stdio.h>
    2. #include <stdlib.h>
    3. #include "libyuv/convert_from.h"
    4. #include "libyuv/convert.h"
    5. int main() {
    6. FILE *input_file = fopen("cowboy_girl_1024X1280_yuv420p_i420.yuv", "rb");
    7. if (!input_file) {
    8. printf("Error opening input file.\n");
    9. return 1;
    10. }
    11. int width = 1024;
    12. int height = 1280;
    13. size_t uv_size = (width * height) / 2;
    14. uint8_t *yuv_data = (uint8_t *)malloc(width * height * 3 / 2);
    15. if (!yuv_data) {
    16. printf("Memory allocation error.\n");
    17. fclose(input_file);
    18. return 1;
    19. }
    20. fread(yuv_data, sizeof(uint8_t), width * height * 3 / 2, input_file);
    21. fclose(input_file);
    22. // Convert YUV to RGB24
    23. uint8_t *rgb_data = (uint8_t *)malloc(width * height * 3);
    24. if (!rgb_data) {
    25. printf("Memory allocation error.\n");
    26. free(yuv_data);
    27. return 1;
    28. }
    29. libyuv::I420ToRGB24(yuv_data, width, yuv_data + width * height, width / 2,
    30. yuv_data + width * height * 5 / 4, width / 2,
    31. rgb_data, width * 3, width, height);
    32. /*
    33. libyuv::I420ToRAW(yuv_data, width, yuv_data + width * height, width / 2,
    34. yuv_data + width * height * 5 / 4, width / 2,
    35. rgb_data, width * 3, width, height);
    36. */
    37. // Save RGB image to file
    38. FILE *output_file = fopen("output.rgb", "wb");
    39. if (!output_file) {
    40. printf("Error opening output file.\n");
    41. free(yuv_data);
    42. free(rgb_data);
    43. return 1;
    44. }
    45. fwrite(rgb_data, sizeof(uint8_t), width * height * 3, output_file);
    46. fclose(output_file);
    47. free(yuv_data);
    48. free(rgb_data);
    49. printf("Conversion complete.\n");
    50. return 0;
    51. }

    四、测试运行结果

    1. g++ -o convert_yuv_to_rgb convert_yuv_to_rgb.cpp -lyuv
    2. ./convert_yuv_to_rgb

    五、上面的测试得出的yuv文件显示出来的效果有点异常,R和B对换了,为啥呢?这个问题困扰了我许久。直到我看到我看到libyuv/include/libyuv/convert.h里面有这一段才豁然开朗,因为RGB24ToI420也是存在这个问题,解决方法是使用I420ToRAW、RAWToI420对换。

    1. // RGB little endian (bgr in memory) to I420.
    2. LIBYUV_API
    3. int RGB24ToI420(const uint8_t* src_rgb24,
    4. int src_stride_rgb24,
    5. uint8_t* dst_y,
    6. int dst_stride_y,
    7. uint8_t* dst_u,
    8. int dst_stride_u,
    9. uint8_t* dst_v,
    10. int dst_stride_v,
    11. int width,
    12. int height);

    六、如果运行的时候提示找不到libyuv.so库,按照下面的方法运行sudo ldconfig更新动态链接库缓存。也可以直接用gcc -o yuv yuv.c  /usr/local/lib/libyuv.so这种编译形式。

    1. 编辑配置文件并使新安装的库生效:
    2. sudo vi /etc/ld.so.conf
    3. 在末尾加入如下行:
    4. include /usr/local/lib
    5. sudo ldconfig

  • 相关阅读:
    Java 开发工具 Eclipse
    STM32F103 单片机定时器中断实验
    Linux | 查看系统服务的方法的不完全总结
    3. Vue.js 3.0 响应式系统原理
    NLP领域可以投稿的期刊或会议(不断更新中……)
    编程每日一练(多语言实现)基础篇:满足abcd=(ab+cd)^2的数 (增加Go语言实现)
    PRCV 2023:语言模型与视觉生态如何协同?合合信息瞄准“多模态”技术
    抖音的文案怎么做|成都聚华祥
    语音相似度评价
    《古代汉语》期末复习资料
  • 原文地址:https://blog.csdn.net/qq_37858386/article/details/138653421