📄 mcpad.cpp
字号:
/*************************************************************************This software module was originally developed by Ming-Chieh Lee (mingcl@microsoft.com), Microsoft Corporation Simon Winder (swinder@microsoft.com), Microsoft Corporation (date: June, 1997)and edited by Wei Wu (weiwu@stallion.risc.rockwell.com) Rockwell Science Centerin the course of development of the MPEG-4 Video (ISO/IEC 14496-2). This software module is an implementation of a part of one or more MPEG-4 Video tools as specified by the MPEG-4 Video. ISO/IEC gives users of the MPEG-4 Video free license to this software module or modifications thereof for use in hardware or software products claiming conformance to the MPEG-4 Video. Those intending to use this software module in hardware or software products are advised that its use may infringe existing patents. The original developer of this software module and his/her company, the subsequent editors and their companies, and ISO/IEC have no liability for use of this software module or modifications thereof in an implementation. Copyright is not released for non MPEG-4 Video conforming products. Microsoft retains full right to use the code for his/her own purpose, assign or donate the code to a third party and to inhibit third parties from using the code for non MPEG-4 Video conforming products. This copyright notice must be included in all copies or derivative works. Copyright (c) 1996, 1997.Module Name: mcPad.cppAbstract: MB Padding (for motion estimation and compensation).Revision History: May. 9 1998: add field based MC padding by Hyundai Electronics Cheol-Soo Park (cspark@super5.hyundai.co.kr)*************************************************************************/#include "typeapi.h"#include "codehead.h"#include "mode.hpp"#include "vopses.hpp"// size of image for ppxlcAlphaBase is (uiBlkSize X uiBlkSize)#define invalidColour -1// Added for field based MC padding by Hyundai(1998-5-9)#define MB_FIELDY 1#define MB_FIELDC 3// End of Hyundai(1998-5-9)Void CVideoObject::mcPadCurrMB ( PixelC* ppxlcRefMBY, PixelC* ppxlcRefMBU, PixelC* ppxlcRefMBV, PixelC* ppxlcRefMBA ){ mcPadCurr (ppxlcRefMBY, m_ppxlcCurrMBBY, MB_SIZE, m_iFrameWidthY); mcPadCurr (ppxlcRefMBU, m_ppxlcCurrMBBUV, BLOCK_SIZE, m_iFrameWidthUV); mcPadCurr (ppxlcRefMBV, m_ppxlcCurrMBBUV, BLOCK_SIZE, m_iFrameWidthUV); if (m_volmd.fAUsage == EIGHT_BIT) mcPadCurr (ppxlcRefMBA, m_ppxlcCurrMBBY, MB_SIZE, m_iFrameWidthY);}Void CVideoObject::mcPadCurr ( PixelC *ppxlcTextureBase, // (uiStride X ???) const PixelC *ppxlcAlphaBase, // uiBlkSize X uiBlkSize UInt uiBlkSize, UInt uiStride){ Int iUnit = sizeof(PixelC); // NBIT: memcpy CoordI iX,iY,iJ,iLeftX = 0; Bool bEmptyRow = FALSE; Bool bInVop; Int iLeftColour; PixelC *ppxlcTexture = ppxlcTextureBase; const PixelC *ppxlcAlpha = ppxlcAlphaBase; for (iY=0; iY < (CoordI) uiBlkSize; iY++, ppxlcTexture+=uiStride) { bInVop = TRUE; iLeftColour = invalidColour; m_pbEmptyRowArray[iY]=0; for(iX=0;iX<(CoordI)uiBlkSize;iX++,ppxlcAlpha++) { if(bInVop==TRUE && *ppxlcAlpha==transpValue) { // start of stripe or left border bInVop=FALSE; iLeftX=iX; if(iX>0) iLeftColour=ppxlcTexture[iLeftX-1]; } else if(bInVop==FALSE && *ppxlcAlpha!=transpValue) { // end of stripe not right border bInVop=TRUE; if(iLeftColour==invalidColour) iLeftColour=ppxlcTexture[iX]; else iLeftColour=(iLeftColour+ppxlcTexture[iX]+1)>>1; // fill stripe for(iJ=iLeftX;iJ<iX;iJ++) ppxlcTexture[iJ]=(PixelC)iLeftColour; } } if(bInVop==FALSE) { // end of stripe at right border if(iLeftX==0) { // blank stripe so mark m_pbEmptyRowArray[iY]=TRUE; bEmptyRow=TRUE; } else { // fill trailing stripe for(iJ=iLeftX;iJ<iX;iJ++) ppxlcTexture[iJ]=(PixelC)iLeftColour; } } } // fill remaining holes if(bEmptyRow) { ppxlcTexture=ppxlcTextureBase; PixelC *ppxlcUpperRow = NULL; for(iY=0;iY<(CoordI)uiBlkSize;iY++,ppxlcTexture+=uiStride) if(!m_pbEmptyRowArray[iY]) ppxlcUpperRow = ppxlcTexture; else { // empty row, find lower row PixelC *ppxlcLowerRow = ppxlcTexture+uiStride; CoordI iYY; for(iYY=iY+1;iYY<(CoordI)uiBlkSize;iYY++,ppxlcLowerRow+=uiStride) if(!m_pbEmptyRowArray[iYY]) break; if(iYY<(CoordI)uiBlkSize) { if(ppxlcUpperRow==NULL) { // just lower row for(;ppxlcTexture<ppxlcLowerRow;ppxlcTexture+=uiStride) memcpy(ppxlcTexture,ppxlcLowerRow,uiBlkSize*iUnit); } else { // lower row, upper row for(;ppxlcTexture<ppxlcLowerRow;ppxlcTexture+=uiStride) for(iX=0;iX<(CoordI)uiBlkSize;iX++) ppxlcTexture[iX]= (ppxlcUpperRow[iX]+ppxlcLowerRow[iX]+1)>>1; } } else { // just upper row assert(ppxlcUpperRow!=NULL); for(iYY=iY;iYY<(CoordI)uiBlkSize;iYY++,ppxlcTexture+=uiStride) memcpy(ppxlcTexture,ppxlcUpperRow,uiBlkSize*iUnit); } iY=iYY-1; ppxlcTexture -= uiStride; } }}Void CVideoObject::padNeighborTranspMBs ( CoordI xb, CoordI yb, CMBMode* pmbmd, PixelC* ppxlcY, PixelC* ppxlcU, PixelC* ppxlcV, PixelC *ppxlcA){ if (xb > 0) { if ((pmbmd - 1)->m_rgTranspStatus [0] == ALL) { if (!((pmbmd - 1)->m_bPadded)) { mcPadLeftMB (ppxlcY, ppxlcU, ppxlcV, ppxlcA); (pmbmd - 1)->m_bPadded = TRUE; } } } if (yb > 0) { if ((pmbmd - m_iNumMBX)->m_rgTranspStatus [0] == ALL) { if (!((pmbmd - m_iNumMBX)->m_bPadded)) { mcPadTopMB (ppxlcY, ppxlcU, ppxlcV, ppxlcA); (pmbmd - m_iNumMBX)->m_bPadded = TRUE; } } }}Void CVideoObject::padCurrAndTopTranspMBFromNeighbor ( CoordI xb, CoordI yb, CMBMode* pmbmd, PixelC* ppxlcY, PixelC* ppxlcU, PixelC* ppxlcV, PixelC* ppxlcA){ if (xb > 0) { if ((pmbmd - 1)->m_rgTranspStatus [0] != ALL) { mcPadCurrMBFromLeft (ppxlcY, ppxlcU, ppxlcV, ppxlcA); pmbmd->m_bPadded = TRUE; } } if (yb > 0) { if ((pmbmd - m_iNumMBX)->m_rgTranspStatus [0] != ALL) { if (!(pmbmd->m_bPadded)) { mcPadCurrMBFromTop (ppxlcY, ppxlcU, ppxlcV, ppxlcA); pmbmd->m_bPadded = TRUE; } } else if (!(pmbmd - m_iNumMBX)->m_bPadded) mcSetTopMBGray (ppxlcY, ppxlcU, ppxlcV, ppxlcA); } if(yb == m_iNumMBY-1) { if(xb > 0 && (pmbmd-1)->m_rgTranspStatus [0] == ALL && !((pmbmd-1)->m_bPadded)) mcSetLeftMBGray(ppxlcY, ppxlcU, ppxlcV, ppxlcA); if(xb == m_iNumMBX-1 && !(pmbmd->m_bPadded)) mcSetCurrMBGray(ppxlcY, ppxlcU, ppxlcV, ppxlcA); }}Void CVideoObject::mcPadLeftMB (PixelC* ppxlcMBY, PixelC* ppxlcMBU, PixelC* ppxlcMBV, PixelC* ppxlcMBA){ UInt iy; for (iy = 0; iy < BLOCK_SIZE; iy++) { pxlcmemset (ppxlcMBY - MB_SIZE, *ppxlcMBY, MB_SIZE); pxlcmemset (ppxlcMBU - BLOCK_SIZE, *ppxlcMBU, BLOCK_SIZE); pxlcmemset (ppxlcMBV - BLOCK_SIZE, *ppxlcMBV, BLOCK_SIZE); ppxlcMBY += m_iFrameWidthY; ppxlcMBU += m_iFrameWidthUV; ppxlcMBV += m_iFrameWidthUV; pxlcmemset (ppxlcMBY - MB_SIZE, *ppxlcMBY, MB_SIZE); ppxlcMBY += m_iFrameWidthY; } if(m_volmd.fAUsage == EIGHT_BIT) for (iy = 0; iy < BLOCK_SIZE; iy++) { pxlcmemset (ppxlcMBA - MB_SIZE, *ppxlcMBA, MB_SIZE); ppxlcMBA += m_iFrameWidthY; pxlcmemset (ppxlcMBA - MB_SIZE, *ppxlcMBA, MB_SIZE); ppxlcMBA += m_iFrameWidthY; }}Void CVideoObject::mcPadTopMB (PixelC* ppxlcMBY, PixelC* ppxlcMBU, PixelC* ppxlcMBV, PixelC* ppxlcMBA){ UInt ix, iy; for (ix = 0; ix < MB_SIZE; ix++) { PixelC* ppxlcYCol = ppxlcMBY; for (iy = 0; iy < MB_SIZE; iy++) { ppxlcYCol -= m_iFrameWidthY; *ppxlcYCol = *ppxlcMBY; } ppxlcMBY++; } for (ix = 0; ix < BLOCK_SIZE; ix++) { PixelC* ppxlcUCol = ppxlcMBU; PixelC* ppxlcVCol = ppxlcMBV; for (iy = 0; iy < BLOCK_SIZE; iy++) { ppxlcUCol -= m_iFrameWidthUV; ppxlcVCol -= m_iFrameWidthUV; *ppxlcUCol = *ppxlcMBU; *ppxlcVCol = *ppxlcMBV; } ppxlcMBU++; ppxlcMBV++; } if(m_volmd.fAUsage == EIGHT_BIT) for (ix = 0; ix < MB_SIZE; ix++) { PixelC* ppxlcACol = ppxlcMBA; for (iy = 0; iy < MB_SIZE; iy++) { ppxlcACol -= m_iFrameWidthY; *ppxlcACol = *ppxlcMBA; } ppxlcMBA++; }}Void CVideoObject::mcPadCurrMBFromLeft (PixelC* ppxlcMBY, PixelC* ppxlcMBU, PixelC* ppxlcMBV, PixelC* ppxlcMBA){ UInt iy; for (iy = 0; iy < BLOCK_SIZE; iy++) { pxlcmemset (ppxlcMBY, *(ppxlcMBY - 1), MB_SIZE); pxlcmemset (ppxlcMBU, *(ppxlcMBU - 1), BLOCK_SIZE); pxlcmemset (ppxlcMBV, *(ppxlcMBV - 1), BLOCK_SIZE); ppxlcMBY += m_iFrameWidthY; ppxlcMBU += m_iFrameWidthUV; ppxlcMBV += m_iFrameWidthUV; pxlcmemset (ppxlcMBY, *(ppxlcMBY - 1), MB_SIZE); ppxlcMBY += m_iFrameWidthY; } if(m_volmd.fAUsage == EIGHT_BIT) for (iy = 0; iy < BLOCK_SIZE; iy++) { pxlcmemset (ppxlcMBA, *(ppxlcMBA - 1), MB_SIZE); ppxlcMBA += m_iFrameWidthY; pxlcmemset (ppxlcMBA, *(ppxlcMBA - 1), MB_SIZE); ppxlcMBA += m_iFrameWidthY; }}Void CVideoObject::mcPadCurrMBFromTop (PixelC* ppxlcMBY, PixelC* ppxlcMBU, PixelC* ppxlcMBV, PixelC* ppxlcMBA){ UInt ix, iy; for (ix = 0; ix < MB_SIZE; ix++) { PixelC* ppxlcYCol = ppxlcMBY; PixelC pxlcY = *(ppxlcMBY - m_iFrameWidthY); for (iy = 0; iy < MB_SIZE; iy++) { *ppxlcYCol = pxlcY; ppxlcYCol += m_iFrameWidthY; } ppxlcMBY++; } for (ix = 0; ix < BLOCK_SIZE; ix++) { PixelC* ppxlcUCol = ppxlcMBU; PixelC* ppxlcVCol = ppxlcMBV; PixelC pxlcU = *(ppxlcMBU - m_iFrameWidthUV); PixelC pxlcV = *(ppxlcMBV - m_iFrameWidthUV); for (iy = 0; iy < BLOCK_SIZE; iy++) { *ppxlcUCol = pxlcU; *ppxlcVCol = pxlcV; ppxlcUCol += m_iFrameWidthUV; ppxlcVCol += m_iFrameWidthUV; } ppxlcMBU++; ppxlcMBV++; } if(m_volmd.fAUsage == EIGHT_BIT) for (ix = 0; ix < MB_SIZE; ix++) { PixelC* ppxlcACol = ppxlcMBA; PixelC pxlcA = *(ppxlcMBA - m_iFrameWidthY); for (iy = 0; iy < MB_SIZE; iy++) { *ppxlcACol = pxlcA; ppxlcACol += m_iFrameWidthY; } ppxlcMBA++; }}Void CVideoObject::mcSetTopMBGray (PixelC* ppxlcMBY, PixelC* ppxlcMBU, PixelC* ppxlcMBV, PixelC* ppxlcMBA){ PixelC pxlcGrayVal = 128; if(m_volmd.bNot8Bit) pxlcGrayVal = 1<<(m_volmd.nBits-1); UInt iy; for (iy = 0; iy < BLOCK_SIZE; iy++) { ppxlcMBY -= m_iFrameWidthY; ppxlcMBU -= m_iFrameWidthUV; ppxlcMBV -= m_iFrameWidthUV; pxlcmemset (ppxlcMBY, pxlcGrayVal, MB_SIZE); pxlcmemset (ppxlcMBU, pxlcGrayVal, BLOCK_SIZE); pxlcmemset (ppxlcMBV, pxlcGrayVal, BLOCK_SIZE); ppxlcMBY -= m_iFrameWidthY; pxlcmemset (ppxlcMBY, pxlcGrayVal, MB_SIZE); } if(m_volmd.fAUsage == EIGHT_BIT) for (iy = 0; iy < BLOCK_SIZE; iy++) { ppxlcMBA -= m_iFrameWidthY; pxlcmemset (ppxlcMBA, pxlcGrayVal, MB_SIZE); ppxlcMBA -= m_iFrameWidthY; pxlcmemset (ppxlcMBA, pxlcGrayVal, MB_SIZE); }}Void CVideoObject::mcSetLeftMBGray (PixelC* ppxlcMBY, PixelC* ppxlcMBU, PixelC* ppxlcMBV, PixelC* ppxlcMBA){ mcSetCurrMBGray( ppxlcMBY-MB_SIZE, ppxlcMBU-BLOCK_SIZE, ppxlcMBV-BLOCK_SIZE, (m_volmd.fAUsage == EIGHT_BIT) ? ppxlcMBA-MB_SIZE : (PixelC *)NULL );}Void CVideoObject::mcSetCurrMBGray (PixelC* ppxlcMBY, PixelC* ppxlcMBU, PixelC* ppxlcMBV, PixelC* ppxlcMBA){ PixelC pxlcGrayVal = 128; if(m_volmd.bNot8Bit) pxlcGrayVal = 1<<(m_volmd.nBits-1); UInt iy; for (iy = 0; iy < BLOCK_SIZE; iy++) { pxlcmemset (ppxlcMBY, pxlcGrayVal, MB_SIZE); pxlcmemset (ppxlcMBU, pxlcGrayVal, BLOCK_SIZE); pxlcmemset (ppxlcMBV, pxlcGrayVal, BLOCK_SIZE); ppxlcMBY += m_iFrameWidthY; ppxlcMBU += m_iFrameWidthUV; ppxlcMBV += m_iFrameWidthUV; pxlcmemset (ppxlcMBY, pxlcGrayVal, MB_SIZE); ppxlcMBY += m_iFrameWidthY; } if(m_volmd.fAUsage == EIGHT_BIT) for (iy = 0; iy < BLOCK_SIZE; iy++) { pxlcmemset (ppxlcMBA, pxlcGrayVal, MB_SIZE); ppxlcMBA += m_iFrameWidthY; pxlcmemset (ppxlcMBA, pxlcGrayVal, MB_SIZE); ppxlcMBA += m_iFrameWidthY; }}// Added for field based MC padding by Hyundai(1998-5-9)Void CVideoObject::fieldBasedMCPadding (CMBMode* pmbmd, CVOPU8YUVBA* pvopcCurrQ){ Int iMBX, iMBY; PixelC* ppxlcCurrY = (PixelC*) pvopcCurrQ->pixelsY () + m_iStartInRefToCurrRctY; PixelC* ppxlcCurrU = (PixelC*) pvopcCurrQ->pixelsU () + m_iStartInRefToCurrRctUV; PixelC* ppxlcCurrV = (PixelC*) pvopcCurrQ->pixelsV () + m_iStartInRefToCurrRctUV;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -