📄 mv.cpp
字号:
/**************************************************************************
mv.cpp
No header comments ????
Revision History:
Nov. 14, 1997: Added/Modified for error resilient mode by Toshiba
December 20, 1997: Interlaced tools added by NextLevel Systems (GI)
X. Chen (xchen@nlvl.com), B. Eifrig (beifrig@nlvl.com)
**************************************************************************/
#include <stdio.h>
#include "typeapi.h"
#include "global.hpp"
#include "codehead.h"
#include "mode.hpp"
#include "vopses.hpp"
#ifdef __MFC_
#ifdef _DEBUG
#undef THIS_FILE
static char BASED_CODE THIS_FILE[] = __FILE__;
#endif
#define new DEBUG_NEW
#endif // __MFC_
inline Int medianof3 (Int a0, Int a1, Int a2)
{
if (a0 > a1) {
if (a1 > a2)
return a1;
else if (a0 > a2)
return a2;
else
return a0;
}
else if (a0 > a2)
return a0;
else if (a1 > a2)
return a2;
else
return a1;
}
Void CVideoObject::find16x16MVpred (CVector& vecPred, const CMotionVector* pmv, Bool bLeftBndry, Bool bRightBndry, Bool bTopBndry) const
{
CVector vctCandMV0, vctCandMV1, vctCandMV2;
if (bLeftBndry)
vctCandMV0.set (0, 0);
else
vctCandMV0 = (pmv - PVOP_MV_PER_REF_PER_MB + gIndexOfCandBlk [1] [0]) -> trueMVHalfPel ();
if (bTopBndry) {
vecPred = vctCandMV0;
return;
}
else {
vctCandMV1 = (pmv - m_iNumOfTotalMVPerRow + gIndexOfCandBlk [1] [1]) -> trueMVHalfPel ();
if (bRightBndry)
vctCandMV2.set (0, 0);
else
vctCandMV2 = (pmv - m_iNumOfTotalMVPerRow + PVOP_MV_PER_REF_PER_MB + gIndexOfCandBlk [1] [2]) -> trueMVHalfPel ();
}
vecPred.x = medianof3 (vctCandMV0.x, vctCandMV1.x, vctCandMV2.x);
vecPred.y = medianof3 (vctCandMV0.y, vctCandMV1.y, vctCandMV2.y);
}
Void CVideoObject::find8x8MVpredAtBoundary (CVector& vecPred, const CMotionVector* pmv, Bool bLeftBndry, Bool bRightBndry, Bool bTopBndry, BlockNum blknCurr) const
{
CVector vctCandMV0, vctCandMV1, vctCandMV2;
switch (blknCurr){
case Y_BLOCK1:
if (bLeftBndry)
vctCandMV0.set (0, 0);
else
vctCandMV0 = (pmv - PVOP_MV_PER_REF_PER_MB + gIndexOfCandBlk [blknCurr] [0]) -> trueMVHalfPel ();
if (bTopBndry){
vecPred = vctCandMV0;
return;
}
else{
vctCandMV1 = (pmv - m_iNumOfTotalMVPerRow + gIndexOfCandBlk [blknCurr] [1])->trueMVHalfPel ();
if (bRightBndry)
vctCandMV2.set (0, 0);
else
vctCandMV2 = (pmv - m_iNumOfTotalMVPerRow + PVOP_MV_PER_REF_PER_MB + gIndexOfCandBlk [blknCurr] [2])->trueMVHalfPel ();
}
break;
case Y_BLOCK2:
vctCandMV0 = (pmv + gIndexOfCandBlk [blknCurr] [0]) -> trueMVHalfPel ();
if (bTopBndry) {
vecPred = vctCandMV0;
return;
}
else{
vctCandMV1 = (pmv - m_iNumOfTotalMVPerRow + gIndexOfCandBlk [blknCurr] [1]) -> trueMVHalfPel ();
if (bRightBndry)
vctCandMV2.set (0, 0);
else
vctCandMV2 = (pmv - m_iNumOfTotalMVPerRow + PVOP_MV_PER_REF_PER_MB + gIndexOfCandBlk [blknCurr] [2]) -> trueMVHalfPel ();
}
break;
case Y_BLOCK3:
if (bLeftBndry)
vctCandMV0.set (0,0);
else
vctCandMV0 = (pmv - PVOP_MV_PER_REF_PER_MB + gIndexOfCandBlk [blknCurr] [0]) -> trueMVHalfPel ();
vctCandMV1 = (pmv + gIndexOfCandBlk [blknCurr] [1]) -> trueMVHalfPel ();
vctCandMV2 = (pmv + gIndexOfCandBlk [blknCurr] [2]) -> trueMVHalfPel ();
break;
case Y_BLOCK4:
vctCandMV0 = (pmv + gIndexOfCandBlk [blknCurr] [0]) -> trueMVHalfPel ();
vctCandMV1 = (pmv + gIndexOfCandBlk [blknCurr] [1]) -> trueMVHalfPel ();
vctCandMV2 = (pmv + gIndexOfCandBlk [blknCurr] [2]) -> trueMVHalfPel ();
break;
default:
break;
}
vecPred.x = medianof3 (vctCandMV0.x, vctCandMV1.x, vctCandMV2.x);
vecPred.y = medianof3 (vctCandMV0.y, vctCandMV1.y, vctCandMV2.y);
}
Void CVideoObject::find8x8MVpredInterior (CVector& vecPred, const CMotionVector* pmv, BlockNum blknCurr) const
{
CVector vctCandMV0, vctCandMV1, vctCandMV2;
switch (blknCurr){
case Y_BLOCK1:
vctCandMV0 = (pmv - PVOP_MV_PER_REF_PER_MB + gIndexOfCandBlk [blknCurr] [0]) -> trueMVHalfPel ();
vctCandMV1 = (pmv - m_iNumOfTotalMVPerRow + gIndexOfCandBlk [blknCurr] [1]) -> trueMVHalfPel ();
vctCandMV2 = (pmv - m_iNumOfTotalMVPerRow + PVOP_MV_PER_REF_PER_MB + gIndexOfCandBlk [blknCurr] [2]) -> trueMVHalfPel ();
break;
case Y_BLOCK2:
vctCandMV0 = (pmv + gIndexOfCandBlk [blknCurr] [0]) -> trueMVHalfPel ();
vctCandMV1 = (pmv - m_iNumOfTotalMVPerRow + gIndexOfCandBlk [blknCurr] [1]) -> trueMVHalfPel ();
vctCandMV2 = (pmv - m_iNumOfTotalMVPerRow + PVOP_MV_PER_REF_PER_MB + gIndexOfCandBlk [blknCurr] [2]) -> trueMVHalfPel ();
break;
case Y_BLOCK3:
vctCandMV0 = (pmv - PVOP_MV_PER_REF_PER_MB + gIndexOfCandBlk [blknCurr] [0]) -> trueMVHalfPel ();
vctCandMV1 = (pmv + gIndexOfCandBlk [blknCurr] [1]) -> trueMVHalfPel ();
vctCandMV2 = (pmv + gIndexOfCandBlk [blknCurr] [2]) -> trueMVHalfPel ();
break;
case Y_BLOCK4:
vctCandMV0 = (pmv + gIndexOfCandBlk [blknCurr] [0]) -> trueMVHalfPel ();
vctCandMV1 = (pmv + gIndexOfCandBlk [blknCurr] [1]) -> trueMVHalfPel ();
vctCandMV2 = (pmv + gIndexOfCandBlk [blknCurr] [2]) -> trueMVHalfPel ();
break;
default:
break;
}
vecPred.x = medianof3 (vctCandMV0.x, vctCandMV1.x, vctCandMV2.x);
vecPred.y = medianof3 (vctCandMV0.y, vctCandMV1.y, vctCandMV2.y);
}
Void CVideoObject::mvLookupUV (const CMBMode* pmbmd, const CMotionVector* pmv,
CoordI& xRefUV, CoordI& yRefUV, CoordI& xRefUV1,CoordI& yRefUV1)
{
Int dx = 0, dy = 0;
UInt uiDivisor = 2; //2 = Y->UV resolution change
if (pmbmd -> m_bhas4MVForward) {
uiDivisor *= 4; //4 = 4 blocks
pmv++;
for (UInt k = 1; k <= 4; k++){
dx += pmv->m_vctTrueHalfPel.x;
dy += pmv->m_vctTrueHalfPel.y;
pmv++;
}
xRefUV = sign (dx) * (grgiMvRound16 [abs (dx) % 16] + (abs (dx) / 16) * 2);
yRefUV = sign (dy) * (grgiMvRound16 [abs (dy) % 16] + (abs (dy) / 16) * 2);
}
// INTERLACE
else if (pmbmd -> m_bFieldMV) {
if(pmbmd->m_bForwardTop) {
dx = pmv [6].m_vctTrueHalfPel.x;
dy = pmv [6].m_vctTrueHalfPel.y;
}
else {
dx = pmv [5].m_vctTrueHalfPel.x;
dy = pmv [5].m_vctTrueHalfPel.y;
}
xRefUV = ((dx & 3) ? ((dx >> 1) | 1) : (dx>>1));
yRefUV = ((dy & 6) ? ((dy >> 1) | 2) : (dy>>1));
if(pmbmd->m_bForwardBottom) {
dx = pmv [8].m_vctTrueHalfPel.x;
dy = pmv [8].m_vctTrueHalfPel.y;
}
else {
dx = pmv [7].m_vctTrueHalfPel.x;
dy = pmv [7].m_vctTrueHalfPel.y;
}
xRefUV1 = ((dx & 3) ? ((dx >> 1) | 1) : (dx>>1));
yRefUV1 = ((dy & 6) ? ((dy >> 1) | 2) : (dy>>1));
}
// ~INTERLACE
else {
dx = pmv->m_vctTrueHalfPel.x;
dy = pmv->m_vctTrueHalfPel.y;
xRefUV = sign (dx) * (grgiMvRound4 [abs (dx) % 4] + (abs (dx) / 4) * 2);
yRefUV = sign (dy) * (grgiMvRound4 [abs (dy) % 4] + (abs (dy) / 4) * 2);
}
}
Void CVideoObject::mvLookupUVWithShape (const CMBMode* pmbmd, const CMotionVector* pmv,
CoordI& xRefUV, CoordI& yRefUV)
{
Int* rgiMvRound = NULL;
Int dx = 0, dy = 0;
UInt uiDivisor = 0; //2 = Y->UV resolution change; another -> full pel
if (pmbmd -> m_bhas4MVForward) {
for (UInt i = Y_BLOCK1; i <= Y_BLOCK4; i++) {
pmv++;
if (pmbmd->m_rgTranspStatus [i] != ALL) {
dx += pmv->m_vctTrueHalfPel.x;
dy += pmv->m_vctTrueHalfPel.y;
uiDivisor += 4;
}
}
switch (uiDivisor) {
case 4:
rgiMvRound = grgiMvRound4;
break;
case 8:
rgiMvRound = grgiMvRound8;
break;
case 12:
rgiMvRound = grgiMvRound12;
break;
case 16:
rgiMvRound = grgiMvRound16;
break;
}
xRefUV = sign (dx) * (rgiMvRound [abs (dx) % uiDivisor] + (abs (dx) / uiDivisor) * 2);
yRefUV = sign (dy) * (rgiMvRound [abs (dy) % uiDivisor] + (abs (dy) / uiDivisor) * 2);
}
else {
dx = pmv->m_vctTrueHalfPel.x;
dy = pmv->m_vctTrueHalfPel.y;
xRefUV = sign (dx) * (grgiMvRound4 [abs (dx) % 4] + (abs (dx) / 4) * 2);
yRefUV = sign (dy) * (grgiMvRound4 [abs (dy) % 4] + (abs (dy) / 4) * 2);
}
}
Void CVideoObject::findMVpredGeneric (CVector& vecPred,
const CMotionVector* pmv,
const CMBMode* pmbmd,
Int iBlk,
Int iXMB, Int iYMB) const
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -