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

📄 texdata.c

📁 Lido PXA270平台开发板的最新BSP,包括源代码
💻 C
📖 第 1 页 / 共 3 页
字号:

static IMG_VOID TranslateScaleTexture(GLESContext *gc, GLEStexture *psTex, IMG_UINT32 ui32Lod,  
									GLEStextureBuffer *pui8Src, IMG_UINT32 ui32Width, IMG_UINT32 ui32Height, 
									IMG_UINT32 ui32BytesPerPixel, IMG_UINT32 ui32Factor)
{
	IMG_UINT8 *pui8Dest;
	IMG_UINT8 *pui8TmpSrc, *pui8TmpDst;
	IMG_UINT32 ui32LoopX, ui32LoopY, ui32Rx, ui32Ry;
	IMG_UINT32 ui32ByteCount;
	IMG_UINT32 ui32Stride = ui32Width*ui32BytesPerPixel;
	IMG_UINT32 ui32Size;
	
	ui32Size = (ui32Width << ui32Factor) * (ui32Height << ui32Factor) * ui32BytesPerPixel;

	pui8Dest = GLESMalloc(gc, ui32Size);
	
	pui8TmpDst = pui8Dest;
	ui32Rx = (1 << ui32Factor);
	ui32Ry = (1 << ui32Factor);

	for (ui32LoopY = 0; ui32LoopY < ui32Height; ui32LoopY++)
	{
		for (ui32Ry = 0; ui32Ry < (IMG_UINT32)(1 << ui32Factor); ui32Ry++)
		{
			pui8TmpSrc = pui8Src + (ui32Stride * ui32LoopY);

			for (ui32LoopX = 0; ui32LoopX < ui32Width; ui32LoopX++)
			{
				for (ui32Rx = 0; ui32Rx < (IMG_UINT32)(1 << ui32Factor); ui32Rx++)
				{
					for (ui32ByteCount = 0; ui32ByteCount < ui32BytesPerPixel; ui32ByteCount++)
					{
						pui8TmpDst[ui32ByteCount] = pui8TmpSrc[ui32ByteCount];
					}
					pui8TmpDst += ui32BytesPerPixel;
				}

				pui8TmpSrc += ui32BytesPerPixel;
			}
		}	
	}

	TwiddleLoadData(psTex, ui32Width << ui32Factor, ui32Height << ui32Factor, ui32Lod, ui32Lod, pui8Dest);

	GLESFree(gc, pui8Dest);
}

/***********************************************************************************
 Function Name      : TranslateLevel
 Inputs             : gc, psTex, ui32Lod
 Outputs            : psTex
 Returns            : -
 Description        : This is called to translate a given level of the texture object 
					  into the final texture.  It applies the scaleShift and 
					  synthesises upper levels of the map as required.
************************************************************************************/
IMG_VOID TranslateLevel(GLESContext *gc, GLEStexture *psTex, IMG_UINT32 ui32Lod)
{
    GLESmipMapLevel *psMipLevel = &psTex->asMipLevel[ui32Lod];
    const GLEStextureFormat *psTexFmt = psMipLevel->psTexFormat;
	IMG_UINT32 ui32Stride;
	IMG_UINT32 ui32BytesPerPixel;
	IMG_UINT32 ui32HeightScale, ui32WidthScale;
	IMG_UINT32 ui32TmpA, ui32TmpB;
	GLEStextureBuffer *pui8Buffer;
	IMG_UINT32 ui32Width, ui32Height;

	ui32BytesPerPixel = (psTexFmt->ui32BitsPerTexel+7) >> 3;
	ui32HeightScale = psTex->ui32HeightScale;
	ui32WidthScale = psTex->ui32WidthScale;
	
	ui32Width = psMipLevel->ui32Width;
	ui32Height = psMipLevel->ui32Height;
	ui32Stride = ui32Width * ui32BytesPerPixel;

	if (ui32WidthScale | ui32HeightScale)
	{
		
		/*Only adjust scale if previous ui32Lod has width/ui32Height 1*/
		/*If it is, calculate the relevant scale factor for this ui32Lod*/
		
		ui32TmpA = 0;
		ui32TmpB = MIN(ui32HeightScale, ui32Lod);
		
		while(ui32TmpA < ui32TmpB)
		{
			if (psTex->asMipLevel[ui32Lod - ui32TmpA - 1].ui32Height == 1)
				ui32HeightScale--;
			ui32TmpA++;
		}
		
		ui32TmpA = 0;
		ui32TmpB = MIN(ui32WidthScale, ui32Lod);
		
		while(ui32TmpA < ui32TmpB)
		{
			if (psTex->asMipLevel[ui32Lod - ui32TmpA - 1].ui32Width == 1)
				ui32WidthScale--;
			ui32TmpA++;
		}
	}

	if(ui32HeightScale)
	{
		IMG_UINT32 ui32Height2; 
		IMG_UINT32 ui32LoopY, ui32LoopScale;
		
		/* The each scan in the buffered texture image must be repeated 2^HeightScale times 
		 * to fill the texture vertically
		 */

		ui32Height2 = 1 << ui32HeightScale;
	
		pui8Buffer = psMipLevel->pui8Buffer;
	
		for(ui32LoopY = 0; ui32LoopY < ui32Height; ui32LoopY++, pui8Buffer += ui32Stride)
		{
			for(ui32LoopScale = 0; ui32LoopScale < ui32Height2; ui32LoopScale++)
			{
				TwiddleLoadSubData(psTex, ui32Lod, 0, (ui32LoopY*ui32Height2)+ui32LoopScale, ui32Width, 1, pui8Buffer);
			}
		}
		
	}
	else if(ui32WidthScale)
	{
		IMG_UINT32 ui32Width2;
		IMG_UINT32 ui32LoopX, ui32LoopScale;
		/* The each pixel in the buffered texture image must be repeated 2^WidthScale times 
		 * to fill the texture horizontaly
		 */

		ui32Width2 = 1<<ui32WidthScale;
	
		pui8Buffer = psMipLevel->pui8Buffer;

		for(ui32LoopX=0; ui32LoopX < ui32Width; ui32LoopX++, pui8Buffer += ui32BytesPerPixel)
		{
			for(ui32LoopScale=0; ui32LoopScale < ui32Width2; ui32LoopScale++)
			{
				TwiddleLoadSubData(psTex, ui32Lod, (ui32LoopX*ui32Width2)+ui32LoopScale, 0, 1, ui32Height, pui8Buffer);
			}
		}
	}
	else
	{

		TwiddleLoadData(psTex, ui32Width, ui32Height, ui32Lod, ui32Lod + psTex->ui32ScaleShift, psMipLevel->pui8Buffer);
 		
		
		/*
		* If scaleShift is set, we need to synthesise the top levels
		* of the map by replicating pixels (or copying data for PVRTC).
		*/
		if (ui32Lod == 0 && psTex->ui32ScaleShift)
		{
			IMG_UINT32 ui32Scale;
			
			for (ui32Scale = 1; ui32Scale <= psTex->ui32ScaleShift; ui32Scale++)
			{
				if(ui32BytesPerPixel == 8)
				{
					TwiddleLoadData(psTex, ui32Width, ui32Height, 0,
									psTex->ui32ScaleShift - ui32Scale, psMipLevel->pui8Buffer);
			
				}
				else
				{
					TranslateScaleTexture(gc, psTex, psTex->ui32ScaleShift - ui32Scale,
											psMipLevel->pui8Buffer,
											psMipLevel->ui32Width,
											psMipLevel->ui32Height,
											ui32BytesPerPixel, ui32Scale);
				}
			}
		}
	}
}

/***********************************************************************************
 Function Name      : ReadBackTextureData
 Inputs             : gc, ui32SrcLevel, ui32DstLevel
 Outputs            : pvBuffer
 Returns            : -
 Description        : Reads back texture data from a HW texture. Downcales as 
				      appropriate
************************************************************************************/

IMG_VOID ReadBackTextureData(GLEStexture *psTex, IMG_UINT32 ui32SrcLevel, IMG_UINT32 ui32DstLevel, IMG_VOID *pvBuffer)
{
	IMG_UINT32 ui32Width, ui32Height, ui32WidthLog2, ui32HeightLog2;
	IMG_VOID *pvTmpBuffer;
	IMG_UINT32 ui32BytesPerPixel;
	IMG_VOID *pvSrcData;
	IMG_UINT32 i, ui32Offset, ui32Size=0;
	const GLEStextureFormat *psTexFormat = psTex->asMipLevel[ui32DstLevel].psTexFormat;

	ui32BytesPerPixel = (psTexFormat->ui32BitsPerTexel+7) >> 3;
	ui32Width = psTex->asMipLevel[ui32DstLevel].ui32Width;
	ui32Height = psTex->asMipLevel[ui32DstLevel].ui32Height;
	
	ui32WidthLog2 = ((psTex->ui32HWSize & ~MBX1_TSPPL1_TUSIZECLRMASK) >> MBX1_TSPPL1_TUSIZESHIFT) + GLES_MIN_TEXTURE_LEVEL;
	ui32HeightLog2 = ((psTex->ui32HWSize & ~MBX1_TSPPL1_TVSIZECLRMASK) >> MBX1_TSPPL1_TVSIZESHIFT) + GLES_MIN_TEXTURE_LEVEL;

	pvTmpBuffer = pvBuffer;

	if(ui32BytesPerPixel == 8)
	{
		ui32Offset = GetCompressedMipMapOffset(ui32SrcLevel, 1 << ui32WidthLog2, 1 << ui32HeightLog2, 
						 psTexFormat->ui32HWFormat == MBX1_TSPPL1_TPIXFORMPVRTC2 ? IMG_TRUE : IMG_FALSE);
		
		ui32Size =  GetCompressedMipMapOffset(ui32SrcLevel + 1, 1 << ui32WidthLog2, 1 << ui32HeightLog2, 
						 psTexFormat->ui32HWFormat == MBX1_TSPPL1_TPIXFORMPVRTC2 ? IMG_TRUE : IMG_FALSE) - 
						 ui32Offset;

		pvSrcData = (IMG_UINT8 *)psTex->psMemInfo->pvLinAddr + (ui32Offset << 3);
	}
	else
	{
		pvSrcData = (IMG_UINT8 *)psTex->psMemInfo->pvLinAddr + (ui32BytesPerPixel * 
						GetMipMapOffset(ui32SrcLevel, 1 << ui32WidthLog2, 1 << ui32HeightLog2));
	}

	if(ui32SrcLevel > ui32WidthLog2)
		ui32WidthLog2 = 0;
	else
		ui32WidthLog2 -= ui32SrcLevel;

	if(ui32SrcLevel > ui32HeightLog2)
		ui32HeightLog2 = 0;
	else
		ui32HeightLog2 -= ui32SrcLevel;


	if(psTex->ui32WidthScale)
	{
		for(i=0; i < ui32Width; i++)
		{
			psTex->pfnReadBackData(pvTmpBuffer, pvSrcData, ui32WidthLog2, ui32HeightLog2, 
									i<<psTex->ui32WidthScale, 0, 1, ui32Height, ui32Width);

			pvTmpBuffer = (IMG_UINT8 *)pvTmpBuffer + ui32BytesPerPixel;
		}
	}
	else if(psTex->ui32HeightScale)
	{
		for(i=0; i < ui32Height; i++)
		{
			psTex->pfnReadBackData(pvTmpBuffer, pvSrcData, ui32WidthLog2, ui32HeightLog2, 
									0, i << psTex->ui32HeightScale, ui32Width, 1, ui32Width);

			pvTmpBuffer = (IMG_UINT8 *)pvTmpBuffer + (ui32Width * ui32BytesPerPixel);
		}
	}
	else
	{
		if(ui32BytesPerPixel == 8)
		{
			HostMemCopy(pvTmpBuffer, pvSrcData, (ui32Size << 3));
		}
		else
		{

			psTex->pfnReadBackData(pvTmpBuffer, pvSrcData, ui32WidthLog2, ui32HeightLog2, 
									0, 0, ui32Width, ui32Height, ui32Width);
		}
	}
}

/***********************************************************************************
 Function Name      : SetupTwiddleFns
 Inputs             : psTex
 Outputs            : psTex
 Returns            : -
 Description        : Sets up the appropriate twiddle,subtwiddle and readback 
					  functions based on a texture's bit depth.
************************************************************************************/

IMG_VOID SetupTwiddleFns(GLEStexture *psTex)
{
	switch(psTex->psFormat->ui32BitsPerTexel)
	{
		case 8:
			psTex->pfnTextureTwiddle = DeTwiddleAddress8bpp;
			psTex->pfnSubTextureTwiddle = TwiddleAddress8bpp;
			psTex->pfnReadBackData = ReadBackTwiddle8bpp;
			break;
		case 16:
			psTex->pfnTextureTwiddle = DeTwiddleAddress16bpp;
			psTex->pfnSubTextureTwiddle = TwiddleAddress16bpp;
			psTex->pfnReadBackData = ReadBackTwiddle16bpp;
			break;
		case 32:
			psTex->pfnTextureTwiddle = DeTwiddleAddress32bpp;
			psTex->pfnSubTextureTwiddle = TwiddleAddress32bpp;
			psTex->pfnReadBackData = ReadBackTwiddle32bpp;
			break;
		default:
			/* May get here for PVRTC - shouldn't use these fn pointers anyway */
			break;
	}

}

/***********************************************************************************
 Function Name      : CopyTextureData
 Inputs             : gc, psSrcInfo
 Outputs            : psDstInfo
 Returns            : -
 Description        : Copies texture data from one texture to another. (Could be
					  accelerated by HW).
************************************************************************************/

IMG_VOID CopyTextureData(GLESContext *gc, PVRSRV_MEM_INFO *psDstInfo, PVRSRV_MEM_INFO *psSrcInfo)
{
	GLES_TIME_START(GLES_TIMER_TEXTURE_GHOST_LOAD_TIME);

	HostMemCopy(psDstInfo->pvLinAddr, psSrcInfo->pvLinAddr, psSrcInfo->ui32AllocSize);

	GLES_TIME_STOP(GLES_TIMER_TEXTURE_GHOST_LOAD_TIME);
}

⌨️ 快捷键说明

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