zoukankan      html  css  js  c++  java
  • 视频的裁剪后缩放功能。

    /**
    * 等比例截源图像
    * @param[in] src 源I420图像
    * @param[in] src_width 源I420图像长度
    * @param[in] src_height 源I420图像高度
    * @param[out] dst 输出I420图像
    * @param[in] dst_width 目的I420图像长度
    * @param[in] dst_height 目的I420图像高度
    * @return bool 是否正确裁剪
    */

    bool CutScale(unsigned char* src, int src_width, int src_height, std::string &dst, int dst_width, int dst_height)
    {
    int src_width_ = src_width; //图像宽高
    int src_height_ = src_height;
    int dst_width_ = dst_width; //画布宽高
    int dst_height_ = dst_height;

    // Making sure that destination frame is of sufficient size.

    // We want to preserve aspect ratio instead of stretching the frame.
    // Therefore, we need to crop the source frame. Calculate the largest center
    // aligned region of the source frame that can be used.
    const int cropped_src_width =
    min(src_width_, dst_width_ * src_height_ / dst_height_);
    const int cropped_src_height =
    min(src_height_, dst_height_ * src_width_ / dst_width_);
    // Make sure the offsets are even to avoid rounding errors for the U/V planes.
    const int src_offset_x = ((src_width_ - cropped_src_width) / 2) & ~1;
    const int src_offset_y = ((src_height_ - cropped_src_height) / 2) & ~1;

    //YUV420 image size
    int I420_Y_Size = src_width_ * src_height_;
    int I420_U_Size = src_width_ * src_height_ / 4;

    unsigned char *Y_data_src = src;
    unsigned char *U_data_src = Y_data_src + I420_Y_Size;
    unsigned char *V_data_src = Y_data_src + I420_Y_Size + I420_U_Size;
    int src_stride_Y = src_width_;
    int src_stride_U = (src_width_ + 1) >> 1;
    int src_stride_V = src_stride_U;

    //最终写入目标
    int dest_I420_Y_Size = dst_width_ * dst_height_;
    int dest_I420_U_Size = dst_width_ * dst_height_ / 4;
    unsigned char *Y_data_dest = (unsigned char *)dst.c_str();
    unsigned char *U_data_dest = Y_data_dest + dest_I420_Y_Size;
    unsigned char *V_data_dest = Y_data_dest + dest_I420_Y_Size + dest_I420_U_Size;
    int dest_stride_Y = dst_width_;
    int dest_stride_U = (dst_width_ + 1) >> 1;
    int dest_stride_V = dest_stride_U;

    const uint8_t* y_ptr =
    Y_data_src +
    src_offset_y * src_stride_Y +
    src_offset_x;
    const uint8_t* u_ptr =
    U_data_src +
    src_offset_y / 2 * src_stride_U +
    src_offset_x / 2;
    const uint8_t* v_ptr =
    V_data_src +
    src_offset_y / 2 * src_stride_V +
    src_offset_x / 2;

    bool ret=libyuv::I420Scale(
    y_ptr,
    src_stride_Y,
    u_ptr,
    src_stride_U,
    v_ptr,
    src_stride_V,
    cropped_src_width, cropped_src_height,
    Y_data_dest,
    dest_stride_Y,
    U_data_dest,
    dest_stride_U,
    V_data_dest,
    dest_stride_V,
    dst_width_, dst_height_,
    libyuv::kFilterBox);

    return ret == 0;

    }

  • 相关阅读:
    iOS 页面间几种传值方式(属性,代理,block,单例,通知)
    iOS CocoaPods安装与使用
    iOS UIWebView截获html并修改便签内容
    block的底层实现原理?
    多线程的底层实现是什么?
    tabviewcell的删除注意
    iOS9 新特性总结!!!
    类方法加Static -------不需要初始化变量
    Warning:whose view is not in the window herarchy!
    iOS----录音:真机调试的注意
  • 原文地址:https://www.cnblogs.com/xuhuajie/p/11039216.html
Copyright © 2011-2022 走看看