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

📄 grayf.cpp

📁 MPEG-4编解码的实现(包括MPEG4视音频编解码)
💻 CPP
📖 第 1 页 / 共 4 页
字号:
				if (ipxl != opaqueValue && ipxl != transpValue ) {
					bRet = FALSE;
					return bRet;
				}
			}
			ppxlf += width;
		}
	}
	return bRet;
}

CRct CFloatImage::whereVisible () const
{
	CoordI left = where ().right - 1;
	CoordI top = where ().bottom - 1;
	CoordI right = where ().left;
	CoordI bottom = where ().top;
	const PixelF* ppxlfThis = pixels ();
	for (CoordI y = where ().top; y < where ().bottom; y++) {
		for (CoordI x = where ().left; x < where ().right; x++) {
			if (*ppxlfThis != (PixelF) transpValue) {
				left = min (left, x);
				top = min (top, y);
				right = max (right, x);
				bottom = max (bottom, y);
			}								
			ppxlfThis++;
		}
	}
	right++;
	bottom++;
	return CRct (left, top, right, bottom);
}


Bool CFloatImage::atLeastOneValue (Float vl, const CRct& rct) const
{
	CRct rctRegionOfInterest = (!rct.valid ()) ? where () : rct;
	assert (rctRegionOfInterest <= where ());
	if (rctRegionOfInterest == where ()) {
		const PixelF* ppxlf = pixels ();
		UInt area = where ().area ();
		for (UInt ip = 0; ip < area; ip++, ppxlf++) {
			if (*ppxlf == vl) {
				return (TRUE);
			}
		}
	}
	else {
		Int width = where ().width;
		const PixelF* ppxlf = pixels (rctRegionOfInterest.left, rctRegionOfInterest.top);
		for (CoordI y = rctRegionOfInterest.top; y < rctRegionOfInterest.bottom; y++) {
			const PixelF* ppxlfRow = ppxlf;
			for (CoordI x = rctRegionOfInterest.left; x < rctRegionOfInterest.right; x++, ppxlfRow++) {
				if (*ppxlfRow == vl) {
					return (TRUE);
					break;
				}
			}
			ppxlf += width;
		}
	}
	return (FALSE);
}


UInt CFloatImage::numPixelsNotValued (Float vl, const CRct& rct) const // number of pixels not valued vl in region rct
{
	CRct rctInterest = (!rct.valid ()) ? where () : rct;
	assert (rctInterest <= where ());
	UInt nRet = 0;
	if (rctInterest == where ()) {
		const PixelF* ppxlf = pixels ();
		UInt area = where ().area ();
		for (UInt ip = 0; ip < area; ip++, ppxlf++) {
			if (*ppxlf != vl)
				nRet++;
		}
	}
	else {
		Int width = where ().width;
		const PixelF* ppxlf = pixels (rctInterest.left, rctInterest.top);
		for (CoordI y = rctInterest.top; y < rctInterest.bottom; y++) {
			const PixelF* ppxlfRow = ppxlf;
			for (CoordI x = rctInterest.left; x < rctInterest.right; x++, ppxlfRow++) {
				if (*ppxlfRow != vl)
					nRet++;
			}
			ppxlf += width;
		}
	}

	return nRet;
}


Void CFloatImage::setRect (const CRct& rct)
{
	assert (rct.area () == m_rc.area ());
	m_rc = rct;
}

Void CFloatImage::threshold (Float thresh)
{
	PixelF* ppxlThis = (PixelF*) pixels ();
	UInt area = where ().area ();
	for (UInt id = 0; id < area; id++)
	{
		if (fabs (*ppxlThis) < thresh)
			*ppxlThis = (PixelF) 0;
		ppxlThis++;
	}
}

Void CFloatImage::binarize (Float fltThresh)
{
	PixelF* ppxlThis = (PixelF*) pixels ();
	UInt area = where ().area ();
	for (UInt id = 0; id < area; id++)
	{
		if (fabs (*ppxlThis) < fltThresh)
			*ppxlThis = (PixelF) transpValue;
		else
			*ppxlThis = (PixelF) opaqueValue;
		ppxlThis++;
	}
}


Void CFloatImage::checkRange (Float fltMin, Float fltMax)
{
	PixelF* ppxlThis = (PixelF*) pixels ();
	UInt area = where ().area ();
	for (UInt id = 0; id < area; id++, ppxlThis++)
		*ppxlThis = checkrange (*ppxlThis, fltMin, fltMax);
}

own CFloatImage* CFloatImage::decimate (UInt rateX, UInt rateY) const
{
	const CoordI left = where ().left / (CoordI) rateX;
	const CoordI top = where ().top / (CoordI)  rateY;
	const CoordI right = (where ().right >= 0) ? (where ().right + (CoordI) rateX - 1) / (CoordI) rateX 
							: (where ().right - (CoordI) rateX + 1) / (CoordI) rateX;
	const CoordI bottom = (where ().bottom >= 0) ? (where ().bottom + (CoordI) rateX - 1) / (CoordI) rateY
							: (where ().bottom - (CoordI) rateX + 1) / (CoordI) rateY;

	CFloatImage* pfiRet = new CFloatImage (CRct (left, top, right, bottom));
	PixelF* ppxlfRet = (PixelF*) pfiRet -> pixels ();
	const PixelF* ppxlfOrgY = pixels ();
	Int skipY = rateY * where ().width;
	
	for (CoordI y = top; y < bottom; y++) {
		const PixelF* ppxlfOrgX = ppxlfOrgY;
		for (CoordI x = left; x < right; x++) {
			*ppxlfRet++ = *ppxlfOrgX;
			ppxlfOrgX += rateX;
		}
		ppxlfOrgY += skipY;
	}
	return pfiRet;
}

own CFloatImage* CFloatImage::decimateBinaryShape (UInt rateX, UInt rateY) const
{
	const CoordI left = where ().left / (CoordI) rateX;
	const CoordI top = where ().top / (CoordI) rateY;
	Int roundR = (where ().right >= 0) ? rateX - 1 : 1 - rateX;
	Int roundB = (where ().bottom >= 0) ? rateY - 1 : 1 - rateY;
	const CoordI right = (where ().right + roundR) / (CoordI) rateX;
	const CoordI bottom = (where ().bottom + roundB) / (CoordI) rateY;

	CFloatImage* pfiRet = new CFloatImage (CRct (left, top, right, bottom));
	PixelF* ppxlfRet = (PixelF*) pfiRet -> pixels ();
	const PixelF* ppxlfOrgY = pixels ();
	Int skipY = rateY * where ().width;
	CoordI x, y;
	CoordI iXOrigLeft, iYOrigTop;	//left top of a sampling square

	for (y = top, iYOrigTop = where().top; y < bottom; y++, iYOrigTop += rateY) {
		const PixelF* ppxlfOrgX = ppxlfOrgY;
		for (x = left, iXOrigLeft = where().left; x < right; x++, iXOrigLeft += rateX) {

			CoordI iXOrig, iYOrig;						//for scanning of the sampling square
			const PixelF* ppxlfOrigScanY = ppxlfOrgX;	//same
			*ppxlfRet = transpValueF;

			for (iYOrig = iYOrigTop; iYOrig < (iYOrigTop + (Int) rateY); iYOrig++)	{

				if (iYOrig >= where().bottom || *ppxlfRet == opaqueValueF)
					break;
				const PixelF* ppxlfOrigScanX = ppxlfOrigScanY; //for scan also
				for (iXOrig = iXOrigLeft; iXOrig < (iXOrigLeft + (Int) rateX); iXOrig++)	{
					if (iXOrig >= where().right)
						break;
					assert (*ppxlfOrigScanX == transpValueF || *ppxlfOrigScanX == opaqueValueF);
					if (*ppxlfOrigScanX == opaqueValueF)	{
						*ppxlfRet = opaqueValueF;
						break;
					}
					ppxlfOrigScanX++;
				}
				ppxlfOrigScanY += where().width;
			}

			assert (*ppxlfRet == transpValueF || *ppxlfRet == opaqueValueF);			
			ppxlfRet++;
//			*ppxlfRet++ = *ppxlfOrgX;
			ppxlfOrgX += rateX;
		}
		ppxlfOrgY += skipY;
	}
	return pfiRet;
}

own CFloatImage* CFloatImage::zoomup (UInt rateX, UInt rateY) const
{
	const CoordI left = where ().left * rateX; // left-top coordinate remain the same
	const CoordI top = where ().top * rateY;
	const CoordI right = where ().right * rateX;
	const CoordI bottom = where ().bottom * rateY;

	CFloatImage* pfiRet = new CFloatImage (CRct (left, top, right, bottom));
	PixelF* ppxlRet = (PixelF*) pfiRet -> pixels ();
	for (CoordI y = top; y < bottom; y++)
	{
		for (CoordI x = left; x < right; x++)
			*ppxlRet++ = pixel ((CoordI) (x / rateX), (CoordI) (y / rateY));
	}
	return pfiRet;
}

own CFloatImage* CFloatImage::expand (UInt rateX, UInt rateY) const // expand by putting zeros in between
{
	const CoordI left = where ().left * rateX; // left-top coordinate remain the same
	const CoordI top = where ().top * rateY;
	const CoordI right = where ().right * rateX;
	const CoordI bottom = where ().bottom * rateY;

	CFloatImage* pfiRet = new CFloatImage (CRct (left, top, right, bottom));
	PixelF* ppxlRet = (PixelF*) pfiRet -> pixels ();
	const PixelF* ppxlThis = pixels ();
	for (CoordI y = top; y < bottom; y++) {
		for (CoordI x = left; x < right; x++) {
			if (x % rateX == 0 && y % rateY == 0) 
				*ppxlRet++ = *ppxlThis++;
			else
				*ppxlRet++ = (PixelF) 0;
		}
	}
	return pfiRet;
}

own CFloatImage* CFloatImage::biInterpolate () const // bilinearly interpolate the vframe
{
	const CoordI left = where ().left << 1; // left-top coordinate remain the same
	const CoordI top = where ().top << 1;
	const CoordI right = where ().right << 1;
	const CoordI bottom = where ().bottom << 1;
	const CoordI width = right - left;

	CoordI x, y;
	CFloatImage* pfiRet = new CFloatImage (CRct (left, top, right, bottom));
	PixelF* ppxlfRet = (PixelF*) pfiRet -> pixels ();
	const PixelF* ppxlf = pixels ();
	const CoordI right1 = right - 2;
	for (y = top; y < bottom; y += 2) { // x-direction interpolation
		for (x = left; x < right1; x += 2) {
			*ppxlfRet++ = *ppxlf++;
			*ppxlfRet++ = (*ppxlf + *(ppxlf - 1)) * .5f;
		}
		*ppxlfRet++ = *ppxlf;
		*ppxlfRet++ = *ppxlf++; // the last pixel of every row do not need average
		ppxlfRet += width;
	}
	ppxlfRet = (PixelF*) pfiRet -> pixels ();
	ppxlfRet += width; // start from the second row
	const CoordI width2 = width << 1;
	const CoordI bottom1 = bottom - 1;
	for (x = left; x < right; x++) { // y-direction interpolation
		PixelF* ppxlfRett = ppxlfRet++;
		for (y = top + 1; y < bottom1; y += 2) {
			*ppxlfRett = (*(ppxlfRett - width) + *(ppxlfRett + width)) * .5f;
			ppxlfRett += width2;
		}
		*ppxlfRett = *(ppxlfRett - width); // the last pixel of every column do not need average
	}
	return pfiRet;
}

own CFloatImage* CFloatImage::downsampleForSpatialScalability () const
{
	static Int rgiFilterVertical[13] = {2, 0, -4, -3, 5, 19, 26, 19, 5, -3, -4, 0, 2};
	static Int rgiFilterHorizontal[4] = {5, 11, 11, 5};
	Int iWidthSrc = where (). width;
	Int iHeightSrc = where (). height ();
	assert (iWidthSrc % 2 == 0 && iHeightSrc % 2 == 0);
	Int iWidthDst = iWidthSrc / 2;
	Int iHeightDst = iHeightSrc / 2;
	CFloatImage* pfiBuffer = new CFloatImage (CRct (0, 0, iWidthSrc, iHeightDst));
	CFloatImage* pfiRet = new CFloatImage (CRct (0, 0, iWidthDst, iHeightDst));
	assert (pfiBuffer != NULL);
	assert (pfiRet != NULL);

	//filter and downsample vertically
	const PixelF* ppxlfSrc;	
	const PixelF* ppxlfColumnHeadSrc = pixels ();
	PixelF* ppxlfDst = (PixelF*) pfiBuffer->pixels ();
	PixelF* ppxlfColumnHeadDst = (PixelF*) pfiBuffer->pixels ();
	Int i, j, k;
	for (i = 0; i < iWidthSrc; i++)	{
		ppxlfSrc = ppxlfColumnHeadSrc;	
		ppxlfDst = ppxlfColumnHeadDst;	
		for (j = 0; j < iHeightDst; j++)	{
			k = j * 2;         
			const PixelF* ppxlfMinusOne = ( k < 1 ) ? ppxlfSrc : ppxlfSrc - iWidthSrc;		
			const PixelF* ppxlfMinusTwo = ( k < 2 ) ? ppxlfSrc : ppxlfMinusOne - iWidthSrc;
			const PixelF* ppxlfMinusThree = ( k < 3 ) ? ppxlfSrc : ppxlfMinusTwo - iWidthSrc;
			const PixelF* ppxlfMinusFour = ( k < 4 ) ? ppxlfSrc : ppxlfMinusThree - iWidthSrc;
			const PixelF* ppxlfMinusFive = ( k < 5 ) ? ppxlfSrc : ppxlfMinusFour - iWidthSrc;
			const PixelF* ppxlfMinusSix = ( k < 6 ) ? ppxlfSrc : ppxlfMinusFive - iWidthSrc;
			const PixelF* ppxlfPlusOne = ( k >= iHeightSrc - 1) ? ppxlfSrc : ppxlfSrc + iWidthSrc;
			const PixelF* ppxlfPlusTwo = ( k >= iHeightSrc - 2) ? ppxlfPlusOne : ppxlfPlusOne + iWidthSrc;
			const PixelF* ppxlfPlusThree = ( k >= iHeightSrc - 3) ? ppxlfPlusTwo : ppxlfPlusTwo + iWidthSrc;
			const PixelF* ppxlfPlusFour = ( k >= iHeightSrc - 4) ? ppxlfPlusThree : ppxlfPlusThree + iWidthSrc;
			const PixelF* ppxlfPlusFive = ( k >= iHeightSrc - 5) ? ppxlfPlusFour : ppxlfPlusFour + iWidthSrc;
			const PixelF* ppxlfPlusSix = ( k >= iHeightSrc - 6) ? ppxlfPlusFive : ppxlfPlusFive + iWidthSrc;
			*ppxlfDst = checkrange ((*ppxlfMinusSix  * rgiFilterVertical [0] +
									*ppxlfMinusFive * rgiFilterVertical [1] +
									*ppxlfMinusFour * rgiFilterVertical [2] +
									*ppxlfMinusThree* rgiFilterVertical [3] +
									*ppxlfMinusTwo  * rgiFilterVertical [4] +
									*ppxlfMinusOne  * rgiFilterVertical [5] +
									*ppxlfSrc	   * rgiFilterVertical [6] +
									*ppxlfPlusOne   * rgiFilterVertical [7] +
									*ppxlfPlusTwo   * rgiFilterVertical [8] +
									*ppxlfPlusThree * rgiFilterVertical [9] +
									*ppxlfPlusFour  * rgiFilterVertical [10] +
									*ppxlfPlusFive  * rgiFilterVertical [11] +
									*ppxlfPlusSix   * rgiFilterVertical [12]) / 64,
									0.0F, 255.0F);
			ppxlfSrc += 2 * iWidthSrc;
			ppxlfDst += iWidthSrc;	
		}
		ppxlfColumnHeadSrc++;
		ppxlfColumnHeadDst++;
	} 
	//filter and downsample horizontally
	ppxlfSrc = pfiBuffer->pixels ();	
	ppxlfDst = (PixelF*) pfiRet->pixels ();
	for (j = 0; j < iHeightDst; j++)	{
		for (i = 0; i < iWidthDst; i++)	{
			k = i * 2;         
			const PixelF* ppxlfMinusOne = ( k < 1 ) ? ppxlfSrc : ppxlfSrc - 1;		
			const PixelF* ppxlfPlusOne = ( k >= iWidthSrc - 1) ? ppxlfSrc : ppxlfSrc + 1;
			const PixelF* ppxlfPlusTwo = ( k >= iWidthSrc - 2) ? ppxlfSrc : ppxlfSrc + 2;
			*ppxlfDst = checkrange ((*ppxlfMinusOne  * rgiFilterHorizontal [0] +
									*ppxlfSrc	   * rgiFilterHorizontal [1] +
									*ppxlfPlusOne   * rgiFilterHorizontal [2] +
									*ppxlfPlusTwo   * rgiFilterHorizontal [3]) / 32,
									0.0F, 255.0F);
			ppxlfSrc += 2;	
			ppxlfDst++;	
		}
	} 
	delete pfiBuffer;
	return pfiRet;
}

own CFloatImage* CFloatImage::upsampleForSpatialScalability () const
{
	CRct rctDst = where () * 2;
	Int iWidthSrc = where (). width;
	Int iHeightSrc = where (). height ();
	Int iHeightDst = iHeightSrc * 2;
	CFloatImage* pfiBuffer = new CFloatImage (CRct (where().left, rctDst.top, 
													 where().right, rctDst.bottom));
	CFloatImage* pfiRet = new CFloatImage (CRct (rctDst.left, rctDst.top, 
												  rctDst.right, rctDst.bottom));

	//upsample vertically
	const PixelF* ppxlfSrc;	
	const PixelF* ppxlfSrcPlusOne;	
	const PixelF* ppxlfColumnHeadSrc = pixels ();
	PixelF* ppxlfDst;
	PixelF* ppxlfColumnHeadDst = (PixelF*) pfiBuffer->pixels ();
	Int i, j;
	for (i = 0; i < iWidthSrc; i++)	{
		ppxlfSrc = ppxlfColumnHeadSrc;	
		ppxlfSrcPlusOne = ppxlfSrc + iWidthSrc;
		ppxlfDst = ppxlfColumnHeadDst;	
		for (j = 0; j < iHeightSrc; j++)	{
			*ppxlfDst = checkrange ( (*ppxlfSrc * 3 + *ppxlfSrcPlusOne) / 4,
									0.0F, 255.0F);
			ppxlfDst += iWidthSrc;
			*ppxlfDst = checkrange ( (*ppxlfSrc + *ppxlfSrcPlusOne * 3) / 4,
									0.0F, 255.0F);
			ppxlfDst += iWidthSrc;
			ppxlfSrc += iWidthSrc;
			ppxlfSrcPlusOne = (j >= iHeightSrc - 2) ? ppxlfSrc : ppxlfSrc + iWidthSrc;
		}
		ppxlfColumnHeadSrc++;
		ppxlfColumnHeadDst++;
	} 

	//upsample horizontally	
	ppxlfSrc = pfiBuffer->pixels ();
	ppxlfDst = (PixelF*) pfiRet->pixels ();
	for (j = 0; j < iHeightDst; j++)	{
		ppxlfSrcPlusOne = ppxlfSrc + 1;
		for (i = 0; i < iWidthSrc; i++)	{

⌨️ 快捷键说明

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