这个函数是填充原始YUV边缘的函数。
源码:
Void TComPicYuv::extendPicBorder ()
{
//判断是否填充过
if ( m_bIsBorderExtended )
{
return;
}
for(Int comp=0; comp<getNumberValidComponents(); comp++)
{
const ComponentID compId=ComponentID(comp);
Pel *piTxt=getAddr(compId); // piTxt = point to (0,0) of image within bigger picture.
const Int stride=getStride(compId);
const Int width=getWidth(compId);
const Int height=getHeight(compId);
const Int marginX=getMarginX(compId);
const Int marginY=getMarginY(compId);
//piTxt指向的是各个颜色通达内存的起始地址。
Pel* pi = piTxt;
// do left and right margins
for (Int y = 0; y < height; y++)
{
for (Int x = 0; x < marginX; x++ )
{
//这一部让原始图像的左右两侧填充了marginX的边缘,
//并且将其赋值为pi[0]和pi[width-1]
pi[ -marginX + x ] = pi[0];
pi[ width + x ] = pi[width-1];
}
//pi也要换行
pi += stride;
}
// pi is now the (0,height) (bottom left of image within bigger picture
//pi指向:X:图像真实宽度的起始位置,Y:图像真实高度的末尾位置+1;
//下面这行代码就是调整一下pi的指向。
pi -= (stride + marginX);
// pi is now the (-marginX, height-1)
for (Int y = 0; y < marginY; y++ )
{
//pi此时指向最后一行,想把最后一行的数据复制给在底部填充的marginY行。
// pi + (y+1)*stride指向pi的下一行。
::memcpy( pi + (y+1)*stride, pi, sizeof(Pel)*(width + (marginX<<1)) );
}
// pi is still (-marginX, height-1)
//下面这行操作让pi回到首部位置。
pi -= ((height-1) * stride);
// pi is now (-marginX, 0)
for (Int y = 0; y < marginY; y++ )
{
::memcpy( pi - (y+1)*stride, pi, sizeof(Pel)*(width + (marginX<<1)) );
}
}
m_bIsBorderExtended = true;
}
pi最开始指向真实图像的起始位置如下图
经过下面的操作pi指向如图。
// do left and right margins
for (Int y = 0; y < height; y++)
{
for (Int x = 0; x < marginX; x++ )
{
//这一部让原始图像的左右两侧填充了marginX的边缘,
//并且将其赋值为pi[0]和pi[width-1]
pi[ -marginX + x ] = pi[0];
pi[ width + x ] = pi[width-1];
}
//pi也要换行
pi += stride;
}
pi -= (stride + marginX);后pi
Y方向的填充,分两部,底部填充的内容和最后一行的内容相同,顶部填充的内容和第一行的内容相同。
// pi is now the (-marginX, height-1)
for (Int y = 0; y < marginY; y++ )
{
//pi此时指向最后一行,想把最后一行的数据复制给在底部填充的marginY行。
// pi + (y+1)*stride指向pi的下一行。
::memcpy( pi + (y+1)*stride, pi, sizeof(Pel)*(width + (marginX<<1)) );
}
// pi is still (-marginX, height-1)
//下面这行操作让pi回到首部位置。
pi -= ((height-1) * stride);
// pi is now (-marginX, 0)
for (Int y = 0; y < marginY; y++ )
{
::memcpy( pi - (y+1)*stride, pi, sizeof(Pel)*(width + (marginX<<1)) );
}
}
pi的指向。最后的pi指向了(-marginX, 0),这里不知道为什么不指向填充部分的开始部分。如有错误敬请批评指正。