【HEVC】2、HM-16.7编码一个CU(帧内部分) 1.帧内预测相邻参考像素获取
内容导读
互联网集市收集整理的这篇技术教程文章主要介绍了【HEVC】2、HM-16.7编码一个CU(帧内部分) 1.帧内预测相邻参考像素获取,小编现在分享给大家,供广大互联网技能从业者学习和参考。文章包含6923字,纯文字阅读大概需要10分钟。
内容图文
![【HEVC】2、HM-16.7编码一个CU(帧内部分) 1.帧内预测相邻参考像素获取](/upload/InfoBanner/zyjiaocheng/1227/298a4aa6656e41ef8e6c1046a2731c79.jpg)
HEVC帧内预测的35中预测模式是在PU基础上定义的,实际帧内预测的过程则以TU为单位。PU以四叉树划分TU,一个PU内所有TU共享同一种预测模式。帧内预测分3个步骤:
(1) 判断当前TU相邻像素点是否可用并做相应的处理
(2) 对参考像素进行滤波
(3) 根据滤波后的参考像素计算当前TU的预测像素值。
HM-16.7中fillReferenceSamples()主要实现第一个步骤,真正进行帧内预测之前,使用重建后的Yuv图像对当前PU的相邻样点进行赋值,为接下来进行的角度预测提供参考样点值,对应于draft 8.4.4.2.2的内容。主要过程是:
(1)如果所有相邻点均不可用,则参考样点值均被赋值为DC值;
iDCValue = 1 << (bitDepth - 1),对于8bit像素,该值为128。
(2)如果所有相邻点均可用,则参考样点值都会被赋值为重建Yuv图像中与其位置相同的样点值;
(3)如果不满足上述两个条件,则按照从左下往左上,从左上往右上的扫描顺序进行遍历,如果第一个点不可用,则使用下一个可用点对应的重建Yuv样点值对其进行赋值;对于除第一个点外的其它邻点,如果该点不可用,则使用它的前一个样点值进行赋值(前一个步骤保证了前一个样点值一定是存在的),直到遍历完毕。
1 Void fillReferenceSamples( const Int bitDepth, 2#if O0043_BEST_EFFORT_DECODING 3const Int bitDepthDelta, 4#endif 5const Pel* piRoiOrigin, 6 Pel* piIntraTemp, 7const Bool* bNeighborFlags, 8const Int iNumIntraNeighbor, 9const Int unitWidth, 10const Int unitHeight, 11const Int iAboveUnits, 12const Int iLeftUnits, 13const UInt uiWidth, 14const UInt uiHeight, 15const Int iPicStride ) 16{ 17const Pel* piRoiTemp;//piRoiOrgin指向重建Y指向重建Yuv图像对应于当前PU所在位置的首地址,piRoiTemp用于指向所感兴趣的重建Yuv的位置 18 Int i, j; 19 Int iDCValue = 1 << (bitDepth - 1);//参考像素不可用时的填充值,8bit时候为128. 20const Int iTotalUnits = iAboveUnits + iLeftUnits + 1; //+1 for top-left 21 22if (iNumIntraNeighbor == 0) // all samples are not available 23 { 24// Fill border with DC value 25for (i=0; i<uiWidth; i++) //!< AboveLeft + Above + AboveRight 26 { 27 piIntraTemp[i] = iDCValue; 28 } 29for (i=1; i<uiHeight; i++)//!< Left + BelowLeft 30 { 31 piIntraTemp[i*uiWidth] = iDCValue; 32 } 33 } 34elseif (iNumIntraNeighbor == iTotalUnits)// all samples are available 35 { 36// Fill top-left border and top and top right with rec. samples 37 piRoiTemp = piRoiOrigin - iPicStride - 1; //!< AboveLeft 38 39for (i=0; i<uiWidth; i++) 40 { 41#if O0043_BEST_EFFORT_DECODING 42 piIntraTemp[i] = piRoiTemp[i] << bitDepthDelta; 43#else 44 piIntraTemp[i] = piRoiTemp[i]; 45#endif 46 } 47 48// Fill left and below left border with rec. samples 49 piRoiTemp = piRoiOrigin - 1; 50 51for (i=1; i<uiHeight; i++) 52 { 53#if O0043_BEST_EFFORT_DECODING 54 piIntraTemp[i*uiWidth] = (*(piRoiTemp)) << bitDepthDelta; 55#else 56 piIntraTemp[i*uiWidth] = *(piRoiTemp);//!< 每个参考样点赋值为对应位置重建Yuv样点值 57#endif 58 piRoiTemp += iPicStride;//!< 指向重建Yuv下一行 59 } 60 } 61else// reference samples are partially available 62 { 63// all above units have "unitWidth" samples each, all left/below-left units have "unitHeight" samples each 64//!< neighboring samples的总数 65const Int iTotalSamples = (iLeftUnits * unitHeight) + ((iAboveUnits + 1) * unitWidth); 66 Pel piIntraLine[5 * MAX_CU_SIZE]; 67 Pel *piIntraLineTemp;//!<临时存储用于填充neighboring samples的样点值 68const Bool *pbNeighborFlags; 69 70// Initialize 71for (i=0; i<iTotalSamples; i++) 72 { 73 piIntraLine[i] = iDCValue; 74 } 75 76// Fill top-left sample 77 piRoiTemp = piRoiOrigin - iPicStride - 1;//!< 指向重建Yuv左上角 78 piIntraLineTemp = piIntraLine + (iLeftUnits * unitHeight);//!< piAdiLine的扫描顺序为左下到左上,再从左到右上 79 pbNeighborFlags = bNeighborFlags + iLeftUnits;//!< 标记neighbor可用性的数组同样移动至左上角 80if (*pbNeighborFlags)//!< 如果左上角可用,则左上角4个像素点均赋值为重建Yuv左上角的样点值 81 { 82#if O0043_BEST_EFFORT_DECODING 83 Pel topLeftVal=piRoiTemp[0] << bitDepthDelta; 84#else 85 Pel topLeftVal=piRoiTemp[0]; 86#endif 87for (i=0; i<unitWidth; i++) 88 { 89 piIntraLineTemp[i] = topLeftVal; 90 } 91 } 92 93// Fill left & below-left samples (downwards) 94 piRoiTemp += iPicStride;//!< piRoiTemp指向重建Yuv的左边界 95 piIntraLineTemp--; 96 pbNeighborFlags--; 97 98for (j=0; j<iLeftUnits; j++) 99 { 100if (*pbNeighborFlags) 101 { 102for (i=0; i<unitHeight; i++) 103 { 104#if O0043_BEST_EFFORT_DECODING 105 piIntraLineTemp[-i] = piRoiTemp[i*iPicStride] << bitDepthDelta; 106#else107 piIntraLineTemp[-i] = piRoiTemp[i*iPicStride]; 108#endif109 } 110 } 111 piRoiTemp += unitHeight*iPicStride; 112 piIntraLineTemp -= unitHeight; 113 pbNeighborFlags--; 114 } 115116// Fill above & above-right samples (left-to-right) (each unit has "unitWidth" samples)117 piRoiTemp = piRoiOrigin - iPicStride;//!< piRoiTemp 指向重建Yuv的上边界 118// offset line buffer by iNumUints2*unitHeight (for left/below-left) + unitWidth (for above-left)119 piIntraLineTemp = piIntraLine + (iLeftUnits * unitHeight) + unitWidth; 120 pbNeighborFlags = bNeighborFlags + iLeftUnits + 1; 121for (j=0; j<iAboveUnits; j++) //!< 从左扫描至右上 122 { 123if (*pbNeighborFlags) 124 { 125for (i=0; i<unitWidth; i++) 126 { 127#if O0043_BEST_EFFORT_DECODING 128 piIntraLineTemp[i] = piRoiTemp[i] << bitDepthDelta; 129#else130 piIntraLineTemp[i] = piRoiTemp[i]; 131#endif132 } 133 } 134 piRoiTemp += unitWidth; 135 piIntraLineTemp += unitWidth; 136 pbNeighborFlags++; 137 } 138139// Pad reference samples when necessary140 Int iCurrJnit = 0; 141 Pel *piIntraLineCur = piIntraLine;//!< 指向左下角(纵坐标最大的那个位置,即扫描起点) 142const UInt piIntraLineTopRowOffset = iLeftUnits * (unitHeight - unitWidth); 143144if (!bNeighborFlags[0]) 145 { 146// very bottom unit of bottom-left; at least one unit will be valid.147 { 148 Int iNext = 1; 149while (iNext < iTotalUnits && !bNeighborFlags[iNext]) 150 { 151 iNext++; 152 } 153 Pel *piIntraLineNext = piIntraLine + ((iNext < iLeftUnits) ? (iNext * unitHeight) : (piIntraLineTopRowOffset + (iNext * unitWidth))); 154const Pel refSample = *piIntraLineNext; 155// Pad unavailable samples with new value156 Int iNextOrTop = std::min<Int>(iNext, iLeftUnits); 157// fill left column158while (iCurrJnit < iNextOrTop) //!< 遍历所有neighboring samples 159 { 160for (i=0; i<unitHeight; i++) 161 { 162 piIntraLineCur[i] = refSample; 163 } 164 piIntraLineCur += unitHeight; 165 iCurrJnit++; 166 } 167// fill top row168while (iCurrJnit < iNext) 169 { 170for (i=0; i<unitWidth; i++) 171 { 172 piIntraLineCur[i] = refSample; 173 } 174 piIntraLineCur += unitWidth; 175 iCurrJnit++; 176 } 177 } 178 } 179180// pad all other reference samples.181while (iCurrJnit < iTotalUnits) 182 { 183if (!bNeighborFlags[iCurrJnit]) // samples not available184 { 185 { 186const Int numSamplesInCurrUnit = (iCurrJnit >= iLeftUnits) ? unitWidth : unitHeight; 187const Pel refSample = *(piIntraLineCur-1); 188for (i=0; i<numSamplesInCurrUnit; i++) 189 { 190 piIntraLineCur[i] = refSample; 191 } 192 piIntraLineCur += numSamplesInCurrUnit; 193 iCurrJnit++; 194 } 195 } 196else197 { 198 piIntraLineCur += (iCurrJnit >= iLeftUnits) ? unitWidth : unitHeight; 199 iCurrJnit++; 200 } 201 } 202203// Copy processed samples204205 piIntraLineTemp = piIntraLine + uiHeight + unitWidth - 2; 206// top left, top and top right samples207for (i=0; i<uiWidth; i++) 208 { 209 piIntraTemp[i] = piIntraLineTemp[i]; 210 } 211212 piIntraLineTemp = piIntraLine + uiHeight - 1; 213for (i=1; i<uiHeight; i++) 214 { 215 piIntraTemp[i*uiWidth] = piIntraLineTemp[-i]; 216 } 217 } 218 }
原文:http://www.cnblogs.com/545235abc/p/5190689.html
内容总结
以上是互联网集市为您收集整理的【HEVC】2、HM-16.7编码一个CU(帧内部分) 1.帧内预测相邻参考像素获取全部内容,希望文章能够帮你解决【HEVC】2、HM-16.7编码一个CU(帧内部分) 1.帧内预测相邻参考像素获取所遇到的程序开发问题。 如果觉得互联网集市技术教程内容还不错,欢迎将互联网集市网站推荐给程序员好友。
内容备注
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 gblab@vip.qq.com 举报,一经查实,本站将立刻删除。
内容手机端
扫描二维码推送至手机访问。