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

📄 errdec.cpp

📁 MPEG-4编解码的实现(包括MPEG4视音频编解码)
💻 CPP
📖 第 1 页 / 共 4 页
字号:
		case 1:
			pmbmd->m_intStepDelta = -2;
			break;
		case 2:
			pmbmd->m_intStepDelta = 1;
			break;
		case 3:
			pmbmd->m_intStepDelta = 2;
			break;
		default:
			assert (FALSE);
		}
		pmbmd->m_stepSize += pmbmd->m_intStepDelta;
		if(bUseNewQPForVlcThr)
			pmbmd->m_stepSizeDelayed = pmbmd->m_stepSize;
		Int iQuantMax = (1<<m_volmd.uiQuantPrecision) - 1;
		checkrange (pmbmd->m_stepSize, 1, iQuantMax);
		iCurrentQP = pmbmd->m_stepSize;
	}

	assert (pmbmd != NULL);
	if (pmbmd -> m_rgTranspStatus [0] == ALL) 
		return;

	bUseNewQPForVlcThr = FALSE;

	assert (pmbmd->m_dctMd == INTRA || pmbmd->m_dctMd == INTRAQ);
	Int iQP = pmbmd->m_stepSize;
	for (Int i = 0; i <= 31; i++)	{
		if (iQP <= 4)	{
			m_rgiDcScalerY [i] = 8;
			m_rgiDcScalerC [i] = 8;
		}
		else if (iQP >= 5 && iQP <= 8)	{
			m_rgiDcScalerY [i] = 2 * iQP;
			m_rgiDcScalerC [i] = (iQP + 13) / 2;
		}
		else if (iQP >= 9 && iQP <= 24)	{
			m_rgiDcScalerY [i] = iQP + 8;
			m_rgiDcScalerC [i] = (iQP + 13) / 2;
		}
		else	{
			m_rgiDcScalerY [i] = 2 * iQP - 16;
			m_rgiDcScalerC [i] = iQP - 6;
		}
	}

	assert (iQP > 0);
	assert (pmbmd -> m_stepSizeDelayed > 0);
	if (pmbmd -> m_stepSizeDelayed >= grgiDCSwitchingThreshold [m_vopmd.iIntraDcSwitchThr])
		pmbmd->m_bCodeDcAsAc = TRUE;
	else
		pmbmd->m_bCodeDcAsAc = FALSE;

	for (iBlk = Y_BLOCK1; iBlk < U_BLOCK; iBlk++) {
		if (pmbmd->m_rgTranspStatus [iBlk] != ALL)
			decodeIntraBlockTexture_DataPartitioning (iBlk, pmbmd, piIntraDC);	
	}
	for (iBlk = U_BLOCK; iBlk <= V_BLOCK; iBlk++) {
		decodeIntraBlockTexture_DataPartitioning (iBlk, pmbmd, piIntraDC);	
	}
}

Void CVideoObjectDecoder::decodeMBTextureHeadOfIVOP_DataPartitioning (CMBMode* pmbmd, Int* piMCBPC)
{
	assert (pmbmd->m_rgTranspStatus [0] != ALL);
	Int iBlk = 0, cNonTrnspBlk = 0;
	for (iBlk = (Int) Y_BLOCK1; iBlk <= (Int) Y_BLOCK4; iBlk++) {
		if (pmbmd->m_rgTranspStatus [iBlk] != ALL)	
			cNonTrnspBlk++;
	}
	Int iCBPC = 0;
	Int iCBPY = 0;
// bug fix by toshiba 98-9-24 start
	pmbmd->m_dctMd = INTRA;
	pmbmd->m_bSkip = FALSE; //reset for direct mode 
	if (*piMCBPC > 3)
		pmbmd->m_dctMd = INTRAQ;
// bug fix by toshiba 98-9-24 end
	iCBPC = *piMCBPC % 4;
	pmbmd->m_bACPrediction = m_pbitstrmIn->getBits (1);
	switch (cNonTrnspBlk) {
	case 1:
		iCBPY = m_pentrdecSet->m_pentrdecCBPY1->decodeSymbol ();
		break;
	case 2:
		iCBPY = m_pentrdecSet->m_pentrdecCBPY2->decodeSymbol ();
		break;
	case 3:
		iCBPY = m_pentrdecSet->m_pentrdecCBPY3->decodeSymbol ();
		break;
	case 4:
		iCBPY = m_pentrdecSet->m_pentrdecCBPY->decodeSymbol ();
		break;
	default:
		assert (FALSE);
	}
	setCBPYandC (pmbmd, iCBPC, iCBPY, cNonTrnspBlk);
}

Void CVideoObjectDecoder::decodeTextureIntraMB_DataPartitioning (
	CMBMode* pmbmd, CoordI iMBX, CoordI iMBY, 
	PixelC* ppxlcCurrFrmQY, PixelC* ppxlcCurrFrmQU, PixelC* ppxlcCurrFrmQV, Int* piIntraDC)
{
	assert (pmbmd != NULL);
	if (pmbmd -> m_rgTranspStatus [0] == ALL) 
		return;

	assert (pmbmd->m_dctMd == INTRA || pmbmd->m_dctMd == INTRAQ);
	Int iQP = pmbmd->m_stepSize;
	for (Int i = 0; i <= 31; i++)	{
		if (iQP <= 4)	{
			m_rgiDcScalerY [i] = 8;
			m_rgiDcScalerC [i] = 8;
		}
		else if (iQP >= 5 && iQP <= 8)	{
			m_rgiDcScalerY [i] = 2 * iQP;
			m_rgiDcScalerC [i] = (iQP + 13) / 2;
		}
		else if (iQP >= 9 && iQP <= 24)	{
			m_rgiDcScalerY [i] = iQP + 8;
			m_rgiDcScalerC [i] = (iQP + 13) / 2;
		}
		else	{
			m_rgiDcScalerY [i] = 2 * iQP - 16;
			m_rgiDcScalerC [i] = iQP - 6;
		}
	}

	assert (iQP > 0);
	assert (pmbmd -> m_stepSizeDelayed > 0);
	if (pmbmd -> m_stepSizeDelayed >= grgiDCSwitchingThreshold [m_vopmd.iIntraDcSwitchThr])
		pmbmd->m_bCodeDcAsAc = TRUE;
	else
		pmbmd->m_bCodeDcAsAc = FALSE;

	//for intra pred
	MacroBlockMemory* pmbmLeft = NULL;
	MacroBlockMemory* pmbmTop = NULL;
	MacroBlockMemory* pmbmLeftTop = NULL;
	CMBMode* pmbmdLeft = NULL;
	CMBMode* pmbmdTop = NULL;
	CMBMode* pmbmdLeftTop = NULL;
											 
	Int iMBTop	= iMBY - 1;
	if (iMBTop >= 0)	{
		if(pmbmd->m_iVideoPacketNumber==(pmbmd - m_iNumMBX)->m_iVideoPacketNumber)	{
			pmbmTop  = m_rgpmbmAbove [iMBX];
			pmbmdTop = pmbmd - m_iNumMBX;
		}
	}

	if (iMBX > 0)	{
		if(pmbmd->m_iVideoPacketNumber==(pmbmd - 1)->m_iVideoPacketNumber)	{
			pmbmLeft  = m_rgpmbmCurr [iMBX - 1];
			pmbmdLeft = pmbmd -  1;
		}
	}

	if (iMBTop >= 0 && iMBX > 0)	{
		if(pmbmd->m_iVideoPacketNumber==(pmbmd - m_iNumMBX - 1)->m_iVideoPacketNumber)	{
			pmbmLeftTop  = m_rgpmbmAbove [iMBX - 1];
			pmbmdLeftTop = pmbmd - m_iNumMBX - 1;
		}
	}

	PixelC* rgchBlkDst = NULL;
	Int iWidthDst;
	Int iDcScaler;
	Int* rgiCoefQ;
	for (Int iBlk = Y_BLOCK1; iBlk <= V_BLOCK; iBlk++) {
		if (iBlk < U_BLOCK) {
			if (pmbmd -> m_rgTranspStatus [iBlk] == ALL) 
				continue;
			switch (iBlk) 
			{
			case (Y_BLOCK1): 
				rgchBlkDst = ppxlcCurrFrmQY;
				break;
			case (Y_BLOCK2): 
				rgchBlkDst = ppxlcCurrFrmQY + BLOCK_SIZE;
				break;
			case (Y_BLOCK3): 
				rgchBlkDst = ppxlcCurrFrmQY + m_iFrameWidthYxBlkSize;
				break;
			case (Y_BLOCK4): 
				rgchBlkDst = ppxlcCurrFrmQY + m_iFrameWidthYxBlkSize + BLOCK_SIZE;
				break;
			}
			iWidthDst = m_iFrameWidthY;
			iDcScaler = m_rgiDcScalerY [iQP];
		}
		else {
			iWidthDst = m_iFrameWidthUV;
			rgchBlkDst = (iBlk == U_BLOCK) ? ppxlcCurrFrmQU: ppxlcCurrFrmQV;
			iDcScaler = m_rgiDcScalerC [iQP];
		}
		rgiCoefQ = m_rgpiCoefQ [iBlk - 1];
		const BlockMemory blkmPred = NULL;
		Int iQpPred = iQP; //default to current if no pred (use 128 case)

		decideIntraPred (blkmPred, 
						 pmbmd,
						 iQpPred,
						 (BlockNum) iBlk,
						 pmbmLeft, 
  						 pmbmTop, 
						 pmbmLeftTop,
						 m_rgpmbmCurr[iMBX],
						 pmbmdLeft,
						 pmbmdTop,
						 pmbmdLeftTop);
		decodeIntraBlockTextureTcoef_DataPartitioning (rgchBlkDst,
								 iWidthDst,
								 iQP, 
								 iDcScaler,
								 iBlk,	
								 *(m_rgpmbmCurr + iMBX),
								 pmbmd,
 								 blkmPred, //for intra-pred
								 iQpPred,
								 piIntraDC);
	}
}

Void CVideoObjectDecoder::decodeIntraBlockTexture_DataPartitioning (Int iBlk, CMBMode* pmbmd, Int* piIntraDC)
{
	if (!pmbmd->m_bCodeDcAsAc)
		piIntraDC[iBlk - 1] = decodeIntraDCmpeg (iBlk <= Y_BLOCK4 || iBlk >=A_BLOCK1);
}

Void	CVideoObjectDecoder::decodeIntraBlockTextureTcoef_DataPartitioning (PixelC* rgpxlcBlkDst,
								 Int iWidthDst,
								 Int iQP,
								 Int iDcScaler,
								 Int iBlk,
								 MacroBlockMemory* pmbmCurr,
								 CMBMode* pmbmd,
 								 const BlockMemory blkmPred,
								 Int iQpPred,
								 Int* piIntraDC)

{
	Int	iCoefStart = 0;
	if (!pmbmd->m_bCodeDcAsAc) {
		iCoefStart++;
	}

	Int* rgiCoefQ = m_rgpiCoefQ [iBlk - 1];
	rgiCoefQ[0] = piIntraDC [iBlk - 1];
	if (pmbmd->getCodedBlockPattern ((BlockNum) iBlk))	{
		Int* rgiZigzag = grgiStandardZigzag;
		if (pmbmd->m_bACPrediction)	
			rgiZigzag = (pmbmd->m_preddir [iBlk - 1] == HORIZONTAL) ? grgiVerticalZigzag : grgiHorizontalZigzag;
 		if(m_volmd.bReversibleVlc)
 			decodeIntraRVLCTCOEF (rgiCoefQ, iCoefStart, rgiZigzag);
 		else
			decodeIntraTCOEF (rgiCoefQ, iCoefStart, rgiZigzag);
	}
	else
		memset (rgiCoefQ + iCoefStart, 0, sizeof (Int) * (BLOCK_SQUARE_SIZE - iCoefStart));
	inverseDCACPred (pmbmd, iBlk - 1, rgiCoefQ, iQP, iDcScaler, blkmPred, iQpPred);
	inverseQuantizeIntraDc (rgiCoefQ, iDcScaler);
	if (m_volmd.fQuantizer == Q_H263)
		inverseQuantizeDCTcoefH263 (rgiCoefQ, 1, iQP);
	else
		inverseQuantizeIntraDCTcoefMPEG (rgiCoefQ, 1, iQP, iBlk>=A_BLOCK1);

	Int i, j;							//save coefQ (ac) for intra pred
	pmbmCurr->rgblkm [iBlk - 1] [0] = m_rgiDCTcoef [0];	//save recon value of DC for intra pred								//save Qcoef in memory
	for (i = 1, j = 8; i < BLOCK_SIZE; i++, j += BLOCK_SIZE)	{
		pmbmCurr->rgblkm [iBlk - 1] [i] = rgiCoefQ [i];
		pmbmCurr->rgblkm [iBlk - 1] [i + BLOCK_SIZE - 1] = rgiCoefQ [j];
	}


	m_pidct->apply (m_rgiDCTcoef, BLOCK_SIZE, rgpxlcBlkDst, iWidthDst);
}

Void CVideoObjectDecoder::decodePVOP_DataPartitioning ()
{
//	assert (m_volmd.nBits==8);
	Int iMBX, iMBY;
	//CoordI y = 0; 
	CMBMode* pmbmd = m_rgmbmd;
	CMotionVector* pmv = m_rgmv;
	PixelC* ppxlcCurrQY = (PixelC*) m_pvopcRefQ1->pixelsY () + m_iStartInRefToCurrRctY;
	PixelC* ppxlcCurrQU = (PixelC*) m_pvopcRefQ1->pixelsU () + m_iStartInRefToCurrRctUV;
	PixelC* ppxlcCurrQV = (PixelC*) m_pvopcRefQ1->pixelsV () + m_iStartInRefToCurrRctUV;

	Int iCurrentQP  = m_vopmd.intStep;		
	Int	iVideoPacketNumber = 0;
	m_iVPMBnum = 0;
	Bool bLeftBndry;
	Bool bRightBndry;
	Bool bTopBndry;

	m_piMCBPC = new Int[m_iNumMBX*m_iNumMBY];
	Int*	piMCBPC = m_piMCBPC;
	m_piIntraDC = new Int[m_iNumMBX*m_iNumMBY*V_BLOCK];
	Int*	piIntraDC = m_piIntraDC;
	//	End Toshiba

	Int	i;
	Int	mbn = 0, mbnFirst = 0;

	CoordI x = 0;
	CoordI y = 0;
	PixelC* ppxlcCurrQMBY = NULL;
	PixelC* ppxlcCurrQMBU = NULL;
	PixelC* ppxlcCurrQMBV = NULL;

	Bool bMBBackup = FALSE;
	CMBMode* pmbmdBackup = NULL;
	Int iMBXBackup = 0, iMBYBackup = 0;
	CMotionVector* pmvBackup = 0;
	PixelC* ppxlcCurrQMBYBackup = NULL;
	PixelC* ppxlcCurrQMBUBackup = NULL;
	PixelC* ppxlcCurrQMBVBackup = NULL;

	Bool bRestartDelayedQP = TRUE;

	do{
		CMBMode* pmbmdFirst = pmbmd;
		CMotionVector* pmvFirst = pmv;
		Int* piMCBPCFirst = piMCBPC;
		Int* piIntraDCFirst = piIntraDC;
		mbnFirst = mbn;

		if( checkResyncMarker() ){
			decodeVideoPacketHeader(iCurrentQP);
			iVideoPacketNumber++;
			bRestartDelayedQP = TRUE;
		}

		do{
			pmbmd->m_iVideoPacketNumber = iVideoPacketNumber;
			iMBX = mbn % m_iNumMBX;
			iMBY = mbn / m_iNumMBX;

			pmbmd->m_bSkip = m_pbitstrmIn->getBits (1);
			if (!pmbmd->m_bSkip) {
				*piMCBPC = m_pentrdecSet->m_pentrdecMCBPCinter->decodeSymbol ();
				assert (*piMCBPC >= 0 && *piMCBPC <= 20);			
				Int iMBtype = *piMCBPC / 4;					//per H.263's MBtype
				switch (iMBtype) {			
				case 0:
					pmbmd->m_dctMd = INTER;
					pmbmd -> m_bhas4MVForward = FALSE;
					break;
				case 1:
					pmbmd->m_dctMd = INTERQ;
					pmbmd -> m_bhas4MVForward = FALSE;
					break;
				case 2:
					pmbmd -> m_dctMd = INTER;
					pmbmd -> m_bhas4MVForward = TRUE;
					break;
				case 3:
					pmbmd->m_dctMd = INTRA;
					break;
				case 4:
					pmbmd->m_dctMd = INTRAQ;
					break;
				default:
					assert (FALSE);
				}
			} else	{									//skipped
				pmbmd->m_dctMd = INTER;
				pmbmd -> m_bhas4MVForward = FALSE;
			}
				if(iMBX == 0) {
					bLeftBndry = TRUE;
				} else {
					bLeftBndry = !((pmbmd - 1) -> m_iVideoPacketNumber == pmbmd -> m_iVideoPacketNumber);
				}
				if(iMBY == 0) {
					bTopBndry = TRUE;
				} else {
					bTopBndry = !((pmbmd - m_iNumMBX) -> m_iVideoPacketNumber == pmbmd -> m_iVideoPacketNumber);
				}
				if((iMBX == m_iNumMBX - 1) || (iMBY == 0)) {
					bRightBndry = TRUE;

⌨️ 快捷键说明

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