H.266/VVC代码学习笔记16:VTM6.0中的getTriangleMergeCandidates()函数

本文深入探讨了H.266/VVC标准中的三角预测模式(TPM)技术,并详细介绍了如何通过getTriangleMergeCandidates函数构建三角预测模式的单向Merge列表。此列表用于提高帧间预测效率。

在之前的博客详细讲了一下目前VVC中的TPM技术的详细原理,其中涉及到了三角预测模式的单向Merge列表的构建,链接为:H.266/VVC相关技术学习笔记:帧间预测中的TPM技术(Triangle partition Mode) 本篇博客将这部分函数getTriangleMergeCandidates()的代码附上,本人加了基本的注释,如果有错误或者有疑问的地方可以私信我。

//这里是三角预测模式的Merge列表构建的地方,从普通的Merge列表中派生出来
void PU::getTriangleMergeCandidates( const PredictionUnit &pu, MergeCtx& triangleMrgCtx )
{
  MergeCtx tmpMergeCtx;

  const Slice &slice = *pu.cs->slice;
  const uint32_t maxNumMergeCand = slice.getMaxNumMergeCand();//最大的Merge候选数量

  triangleMrgCtx.numValidMergeCand = 0;


  //三角Merge列表的长度为6,首先对其中的候选都进行初始化
  for (int32_t i = 0; i < TRIANGLE_MAX_NUM_UNI_CANDS; i++)
  {
    triangleMrgCtx.GBiIdx[i] = GBI_DEFAULT;//双向预测权重
    triangleMrgCtx.interDirNeighbours[i] = 0;//相邻块候选的预测方向:单向或者双向,1表示前向,2表示后向,3表示双向
    triangleMrgCtx.mrgTypeNeighbours[i] = MRG_TYPE_DEFAULT_N;//Merge类型
    triangleMrgCtx.mvFieldNeighbours[(i << 1)].refIdx = NOT_VALID;//候选的前向参考索引
    triangleMrgCtx.mvFieldNeighbours[(i << 1) + 1].refIdx = NOT_VALID;//候选的后向参考索引
    triangleMrgCtx.mvFieldNeighbours[(i << 1)].mv = Mv();//候选的前向MV
    triangleMrgCtx.mvFieldNeighbours[(i << 1) + 1].mv = Mv();//候选的后向MV
#if JVET_O0057_ALTHPELIF
    triangleMrgCtx.useAltHpelIf[i] = false;
#endif
  }
  //首先构造普通的长度为6的Merge列表
  PU::getInterMergeCandidates(pu, tmpMergeCtx, 0);

  //对Merge列表中的每一个候选进行遍历,选出满足条件的候选添加进三角的单向预测列表中
  for (int32_t i = 0; i < maxNumMergeCand; i++)
  {
    int parity = i & 1;//奇偶性,判断每个候选的奇偶性,1为奇数,0为偶数
    if (tmpMergeCtx.interDirNeighbours[i] & (0x01 + parity))//这里优先选出普通Merge列表偶数候选的前向MV给当前三角单向Merge候选
                                                            //或者优先选出普通Merge列表奇数候选的后向MV给当前三角单向Merge候选
    {
      triangleMrgCtx.interDirNeighbours[triangleMrgCtx.numValidMergeCand] = 1 + parity;//赋予三角merge候选对应的预测方向
      triangleMrgCtx.mrgTypeNeighbours[triangleMrgCtx.numValidMergeCand] = MRG_TYPE_DEFAULT_N;
      triangleMrgCtx.mvFieldNeighbours[(triangleMrgCtx.numValidMergeCand << 1) + !parity].mv = Mv(0, 0);
      triangleMrgCtx.mvFieldNeighbours[(triangleMrgCtx.numValidMergeCand << 1) + parity].mv = tmpMergeCtx.mvFieldNeighbours[(i << 1) + parity].mv;
      triangleMrgCtx.mvFieldNeighbours[(triangleMrgCtx.numValidMergeCand << 1) + !parity].refIdx = -1;
      triangleMrgCtx.mvFieldNeighbours[(triangleMrgCtx.numValidMergeCand << 1) + parity].refIdx = tmpMergeCtx.mvFieldNeighbours[(i << 1) + parity].refIdx;
      triangleMrgCtx.numValidMergeCand++;
      if (triangleMrgCtx.numValidMergeCand == TRIANGLE_MAX_NUM_UNI_CANDS)
      {
        return;
      }
      continue;
    }

    if (tmpMergeCtx.interDirNeighbours[i] & (0x02 - parity))//若普通Merge列表偶数候选只有后向MV,则将其后向MV给当前三角单向Merge候选
                                                            //若普通Merge列表奇数候选只有前向MV,则将其前向MV给当前三角单向Merge候选
    {
      triangleMrgCtx.interDirNeighbours[triangleMrgCtx.numValidMergeCand] = 2 - parity;
      triangleMrgCtx.mrgTypeNeighbours[triangleMrgCtx.numValidMergeCand] = MRG_TYPE_DEFAULT_N;
      triangleMrgCtx.mvFieldNeighbours[(triangleMrgCtx.numValidMergeCand << 1) + !parity].mv = tmpMergeCtx.mvFieldNeighbours[(i << 1) + !parity].mv;
      triangleMrgCtx.mvFieldNeighbours[(triangleMrgCtx.numValidMergeCand << 1) + parity].mv = Mv(0, 0);
      triangleMrgCtx.mvFieldNeighbours[(triangleMrgCtx.numValidMergeCand << 1) + !parity].refIdx = tmpMergeCtx.mvFieldNeighbours[(i << 1) + !parity].refIdx;
      triangleMrgCtx.mvFieldNeighbours[(triangleMrgCtx.numValidMergeCand << 1) + parity].refIdx = -1;
      triangleMrgCtx.numValidMergeCand++;
      if (triangleMrgCtx.numValidMergeCand == TRIANGLE_MAX_NUM_UNI_CANDS)
      {
        return;
      }
    }
  }
}

### H.266/VVC 学习资料与 VTM6.0 安装指南 #### 关于 H.266/VVC 的学习资源 H.266/VVC 是一种新一代视频压缩标准,旨在提供更高的压缩效率和更好的图像质量。为了深入理解该标准的工作原理及其实现细节,可以参考以下几种类型的资源: 1. **官方文档和技术报告** ITU-T 和 MPEG 提供的技术规范文件是权威的学习材料。这些文档详细描述了 H.266/VVC 的核心技术特性以及算法设计原则。 2. **开源项目和测试模型 (VTM)** VTMVVC Test Model)是由联合视频专家组开发的参考软件,用于验证 H.266/VVC 编码器的功能性和性能表现。通过研究其源代码结构,能够深入了解编码流程中的关键技术模块[^2]。 3. **在线课程与书籍推荐** - 部分高校或科研机构会发布关于最新视频编码技术的教学视频或者讲义。 - 一些专注于多媒体处理领域出版物也可能包含针对初学者到高级工程师不同层次的内容介绍。 #### 如何安装并使用 VTM6.0? 以下是基于先前版本经验总结出来的适用于 Windows 平台上的基本指导步骤;尽管具体操作可能会因新版本有所调整,请始终查阅最新的 README 文件获取最精确指示。 ##### 准备工作环境 - 确认已安装支持 C++ 开发所需的 Microsoft Visual Studio 版本(建议 VS2019 或更高)[^1]. - 获取必要的第三方依赖项如 `CMake` 工具链来完成构建过程. ##### 正式执行搭建程序 1. 下载目标发行版档案至本地存储位置. ```bash wget https://example.com/path_to_vtm_archive.zip unzip path_to_vtm_archive.zip -d /desired/directory/ cd vtm-source-folder/ mkdir build && cd build ``` 2. 利用 cmake 构建解决方案文件(.sln). ```bash cmake .. msbuild ALL_BUILD.vcxproj /p:Configuration=Release ``` 成功完成后应该可以在指定目录找到可运行二进制文件bin\TAppEncoderStatic.exe 及 bin\TAppDecoderStatic.exe . 对于实际应用而言, 用户可以通过命令行参数控制输入输出选项从而定制化自己的实验场景; 更详细的说明参见随附手册README.txt 中列举的例子演示如何调用这两个主要组件来进行完整的端到端测试序列编码解码循环. --- ### 示例代码片段展示简单的命令行调用方式 假设我们已经有了一个yuv格式原始素材sample.yuv , 尺寸为1920x1080像素帧率固定在30fps 上面持续时间大约十秒钟长度,则可以用如下形式启动编码进程: ```batch TAppEncoderStatic ^ -c cfg/encoder_randomaccess_main.cfg ^ --InputFile="sample.yuv" ^ --FrameRate=30 --FramesToBeEncoded=300 ^ --SourceWidth=1920 --SourceHeight=1080 ^ -b output.bit -o rec.yuv ``` 同样道理,在得到比特流之后再利用对应的解码工具将其还原成可视化的图片数据流: ```batch TAppDecoderStatic -b output.bit -o dec.yuv ``` 以上仅作为基础示范用途,更多复杂功能设置需参照完整配置模板进一步探索实践。 ---
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值