⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 umc_vc1_dec_mv_com.cpp

📁 audio-video-codecs.rar语音编解码器
💻 CPP
📖 第 1 页 / 共 2 页
字号:
/* /////////////////////////////////////////////////////////////////////////////
//
//                  INTEL CORPORATION PROPRIETARY INFORMATION
//     This software is supplied under the terms of a license agreement or
//     nondisclosure agreement with Intel Corporation and may not be copied
//     or disclosed except in accordance with the terms of that agreement.
//          Copyright(c) 2004-2007 Intel Corporation. All Rights Reserved.
//
//
//          VC-1 (VC1) MV decoding
//
*/

#include "umc_defs.h"

#if defined (UMC_ENABLE_VC1_VIDEO_DECODER)

#include "umc_vc1_dec_seq.h"
#include "umc_vc1_dec_debug.h"
#include "umc_vc1_common_mvdiff_tbl.h"

void save_MV(VC1Context* pContext)
{
    Ipp32s blk_num = 0;
    VC1MB* pCurrMB = pContext->m_pCurrMB;
    VC1SingletonMB* sMB = pContext->m_pSingleMB;

    for (blk_num = 0; blk_num < 4;blk_num++)
    {
        if(pCurrMB->m_pBlocks[blk_num].blkType & VC1_BLK_INTRA)
        {
            continue;
        }
        pContext->savedMV[(sMB->widthMB * sMB->m_currMBYpos + sMB->m_currMBXpos)*4*2 +blk_num]
                                    = pCurrMB->m_pBlocks[blk_num].mv[0][0];
        pContext->savedMV[(sMB->widthMB * sMB->m_currMBYpos + sMB->m_currMBXpos)*4*2 +blk_num+4]
                                    = pCurrMB->m_pBlocks[blk_num].mv[0][1];
    }
}

void Derive4MV_Field(Ipp32u _MVcount,
                     Ipp16s* xMV, Ipp16s* yMV,
                     Ipp16s* xLuMV, Ipp16s* yLuMV)
{
    switch(_MVcount)
    {
    case 0:
    case 1:
        {
            VM_ASSERT(0);
            return;
        }
    case 2:
        {
            *xMV = (xLuMV[0] + xLuMV[1]) / 2;
            *yMV = (yLuMV[0] + yLuMV[1]) / 2;
            return;
        }
    case 3:
        {
            *xMV = median3(xLuMV);
            *yMV = median3(yLuMV);
            return;
        }
    case 4:
        {
            *xMV = median4(xLuMV);
            *yMV = median4(yLuMV);
            return;
        }
    }
}

void GetPredictProgressiveMV(VC1Block *pA,VC1Block *pB,VC1Block *pC,
                             Ipp16s *pX, Ipp16s *pY,Ipp32s Back)
{
    Ipp16s X=0,  Y=0;
    Ipp16s MV_px[] = {0,0,0};
    Ipp16s MV_py[] = {0,0,0};

    if (pA && (pA->blkType & VC1_BLK_INTER))
    {
        MV_px[0] = pA->mv[Back][0];
        MV_py[0] = pA->mv[Back][1];
    }

    if (pB && (pB->blkType & VC1_BLK_INTER))
    {
        MV_px[1] = pB->mv[Back][0];
        MV_py[1] = pB->mv[Back][1];
    }

    if (pC && (pC->blkType & VC1_BLK_INTER))
    {
        MV_px[2] = pC->mv[Back][0];
        MV_py[2] = pC->mv[Back][1];
    }

    if (pA)
    {
        if (pB == NULL)
        {
            X = MV_px[0];
            Y = MV_py[0];
        }
        else
        {
            X = median3(MV_px);
            Y = median3(MV_py);
        }
    }
    else if (pC)
    {
        X = MV_px[2];
        Y = MV_py[2];
    }

    (*pX) = X;
    (*pY) = Y;
}


void HybridMV(VC1Context* pContext,VC1Block *pA,VC1Block *pC, Ipp16s *pPredMVx,Ipp16s *pPredMVy, Ipp32s Back)
{
    Ipp16s MV_px[] = {0,0};
    Ipp16s MV_py[] = {0,0};
    Ipp16s x,  y;
    Ipp16u sum;
    Ipp32s eHybridPred;

    if ((pA == NULL) || (pC == NULL) || (pContext->m_picLayerHeader->PTYPE == VC1_B_FRAME))
    {
        return;
    }

    x = (*pPredMVx);
    y = (*pPredMVy);

    if (pA && (pA->blkType & VC1_BLK_INTER))
    {
        MV_px[0] = pA->mv[Back][0];
        MV_py[0] = pA->mv[Back][1];
    }

    if (pC && (pC->blkType & VC1_BLK_INTER))
    {
        MV_px[1] = pC->mv[Back][0];
        MV_py[1] = pC->mv[Back][1];
    }

    sum = vc1_abs_16s(x-MV_px[0]) + vc1_abs_16s(y-MV_py[0]);
    if (sum <= 32)
    {
        sum = vc1_abs_16s(x-MV_px[1]) + vc1_abs_16s(y-MV_py[1]);
    }
    if (sum <= 32)
    {
        return;
    }

    VC1_GET_BITS(1,eHybridPred );
    if (eHybridPred)
    {
        x = MV_px[0];
        y = MV_py[0];
    }
    else
    {
        x = MV_px[1];
        y = MV_py[1];
    }

    (*pPredMVx)= x;
    (*pPredMVy)= y;
}

void CalculateMV(Ipp16s x[],Ipp16s y[], Ipp16s *X, Ipp16s* Y)
{
    Ipp16s temp_x[] = {0,0,0};
    Ipp16s temp_y[] = {0,0,0};

    Ipp16u n_intra = ((Ipp16u)(x[0])==VC1_MVINTRA) +
        (((Ipp16u)(x[1])== VC1_MVINTRA)<<1) +
        (((Ipp16u)(x[2])== VC1_MVINTRA)<<2) +
        (((Ipp16u)(x[3])== VC1_MVINTRA)<<3);

    //VM_Debug::GetInstance().vm_debug_frame(-1,VC1_BFRAMES,VM_STRING("history MVs(%d,%d) (%d,%d) (%d,%d) (%d,%d)\n"),x[0],y[0],x[1],y[1],x[2],y[2],x[3],y[3]);

    switch(n_intra)
    {
    case 0x00: //all blocks are inter
        *X = median4(x);
        *Y = median4(y);
        break;
    case 0x01:
        *X = median3(&x[1]);
        *Y = median3(&y[1]);
        break;
    case 0x02:
        temp_x[0] = x[0];
        temp_x[1] = x[2];
        temp_x[2] = x[3];
        temp_y[0] = y[0];
        temp_y[1] = y[2];
        temp_y[2] = y[3];
        *X = median3(temp_x);
        *Y = median3(temp_y);
        break;
    case 0x04:
        temp_x[0] = x[0];
        temp_x[1] = x[1];
        temp_x[2] = x[3];
        temp_y[0] = y[0];
        temp_y[1] = y[1];
        temp_y[2] = y[3];
        *X = median3(temp_x);
        *Y = median3(temp_y);
        break;
    case 0x08:
        *X = median3(x);
        *Y = median3(y);
        break;
    case 0x03:
        *X = (x[2]+ x[3])/2;
        *Y = (y[2]+ y[3])/2;
        break;
    case 0x05:
        *X = (x[1]+ x[3])/2;
        *Y = (y[1]+ y[3])/2;
        break;
    case 0x06:
        *X = (x[0]+ x[3])/2;
        *Y = (y[0]+ y[3])/2;
        break;
    case 0x09:
        *X = (x[1]+ x[2])/2;
        *Y = (y[1]+ y[2])/2;
        break;
    case 0x0C:
        *X = (x[0]+ x[1])/2;
        *Y = (y[0]+ y[1])/2;
        break;
    case 0x0A:
        *X = (x[0]+ x[2])/2;
        *Y = (y[0]+ y[2])/2;
        break;

    default:
        (*X)=VC1_MVINTRA;
        (*Y)=VC1_MVINTRA;
        break;
    }
    //VM_Debug::GetInstance().vm_debug_frame(-1,VC1_BFRAMES,VM_STRING("calculated history MVs(%d,%d)\n"),*X,*Y);

}
void CalculateMV_Interlace(Ipp16s x[],Ipp16s y[], Ipp16s x_bottom[],Ipp16s y_bottom[],Ipp16s *Xt, Ipp16s* Yt,Ipp16s *Xb, Ipp16s* Yb )
{
    Ipp8s n_intra = ((Ipp16u)(x[0])==VC1_MVINTRA);
    if (n_intra) // intra co-located MB
    {
        *Xt = 0;
        *Yt = 0;
        *Xb = 0;
        *Yb = 0;
    }
    else
    {
        *Xt = x[0];
        *Yt = y[0];
        *Xb = x_bottom[0];
        *Yb = y_bottom[0];
    }

}

void CalculateMV_InterlaceField(VC1Context* pContext,Ipp16s x[],Ipp16s y[], Ipp16s *X, Ipp16s* Y)
{
    Ipp8s n_intra = ((Ipp16u)(x[0])==VC1_MVINTRA);
    Ipp32s count=0;
    Ipp16s* xLuMV;
    Ipp16s* yLuMV;

    Ipp16s xLuMVT[VC1_NUM_OF_LUMA];
    Ipp16s yLuMVT[VC1_NUM_OF_LUMA];

    Ipp16s xLuMVB[VC1_NUM_OF_LUMA];
    Ipp16s yLuMVB[VC1_NUM_OF_LUMA];



    Ipp32u MVcount = 0;
    Ipp32u MVBcount = 0;
    Ipp32u MVTcount = 0;

    Ipp8u* samePolarity = pContext->savedMVSamePolarity_Curr +
        (pContext->m_seqLayerHeader->widthMB*pContext->m_pSingleMB->m_currMBYpos
                +pContext->m_pSingleMB->m_currMBXpos)*4;

    VC1MB* pMB = pContext->m_pCurrMB;
    pContext->m_pCurrMB->m_pBlocks[0].fieldFlag[0] = pContext->m_picLayerHeader->BottomField;

    if (n_intra)
    {
        *X = 0;
        *Y = 0;
        pContext->m_pCurrMB->m_pBlocks[0].mv_s_polarity[0] = 1;
        pContext->m_pCurrMB->m_pBlocks[0].mv_s_polarity[1] = 1;
        pContext->m_pCurrMB->m_pBlocks[0].fieldFlag[0] = pContext->m_picLayerHeader->BottomField;
    }
    else
    {

            for (count=0;count<4;count++)
            {

                if ((samePolarity[count])&&(pContext->m_picLayerHeader->BottomField)||
                    (!samePolarity[count])&&(!pContext->m_picLayerHeader->BottomField))
                {
                    xLuMVB[MVBcount] = x[count];
                    yLuMVB[MVBcount] = y[count];
                    ++MVBcount;
                }
                else
                {
                    xLuMVT[MVTcount] = x[count];
                    yLuMVT[MVTcount] = y[count];
                    ++MVTcount;
                }
            }
            if (MVBcount == MVTcount)
            {
                MVcount = 2;
                pContext->m_pCurrMB->m_pBlocks[0].mv_s_polarity[0] = 1;
                pContext->m_pCurrMB->m_pBlocks[0].mv_s_polarity[1] = 1;
                pContext->m_pCurrMB->m_pBlocks[0].fieldFlag[0] = pContext->m_pCurrMB->fieldFlag[0];

                if (pContext->m_picLayerHeader->BottomField)
                {
                    xLuMV = xLuMVB;
                    yLuMV = yLuMVB;
                } else
                {
                    xLuMV = xLuMVT;
                    yLuMV = yLuMVT;
                }
            } else if (MVBcount > MVTcount)
            {
                if (!pContext->m_picLayerHeader->BottomField)
                {
                    pMB->m_pBlocks[0].mv_s_polarity[0] = 0;
                    pMB->m_pBlocks[0].mv_s_polarity[1] = 0;
                }
                else
                {
                    pMB->m_pBlocks[0].mv_s_polarity[0] = 1;
                    pMB->m_pBlocks[0].mv_s_polarity[1] = 1;
                }

                MVcount = MVBcount;
                xLuMV = xLuMVB;
                yLuMV = yLuMVB;
                pContext->m_pCurrMB->m_pBlocks[0].fieldFlag[0] = 1;
            } else
            {
                if (pContext->m_picLayerHeader->BottomField)
                {
                    pMB->m_pBlocks[0].mv_s_polarity[0] = 0;
                    pMB->m_pBlocks[0].mv_s_polarity[1] = 0;
                }
                else
                {
                    pMB->m_pBlocks[0].mv_s_polarity[0] = 1;
                    pMB->m_pBlocks[0].mv_s_polarity[1] = 1;
                }

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -