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

📄 mlrtriangleclipping.hpp

📁 机甲指挥官2源代码
💻 HPP
📖 第 1 页 / 共 4 页
字号:
//===========================================================================//
// Copyright (C) Microsoft Corporation. All rights reserved.                 //
//===========================================================================//

#if !defined(MLR_MLRCLIPTRICK_HPP)
	#include <MLR\MLRClipTrick.hpp>
#endif

extern DWORD gEnableTextureSort, gShowClippedPolys, gEnableDetailTexture;
extern unsigned short *indexOffset;	// [MidLevelRenderer::Max_Number_Vertices_Per_Mesh]

#define HUNT_CLIP_ERROR 0

//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//
void
	CLASSNAME::TransformNoClip(Matrix4D *mat, GOSVertexPool *vt, bool db)
{
	Check_Object(this);
	Check_Object(vt);
	Verify(index.GetLength() > 0);

	Start_Timer(Transform_Time);

//	unsigned short stride;
	int stride;

	bool textureAnimation = false;
	Scalar deltaU=0.0f, deltaV=0.0f;
	
	if(state.GetTextureHandle())
	{
		MLRTexture *texture = (*MLRTexturePool::Instance)[state.GetTextureHandle()];
		Check_Object(texture);

		textureAnimation = texture->GetAnimateTexture();
		if(textureAnimation)
		{
			Stuff::AffineMatrix4D &textureMatrix = texture->GetTextureMatrix();
			deltaU = textureMatrix(3, 0);
			deltaV = textureMatrix(3, 1);
		}
	}

	int i, j;

#ifdef I_SAY_YES_TO_TERRAIN
	Scalar terrainUV[2];
#endif	//	I_SAY_YES_TO_TERRAIN

#ifdef I_SAY_YES_TO_MULTI_TEXTURES
	int m;
	gos_PushCurrentHeap(StaticHeap);
	int tex2count[Limits::Max_Number_Of_Multitextures];
	gos_PopCurrentHeap();

	for(m=0;m<currentNrOfPasses;m++)
	{
		tex2count[m] = 0;
	}
#endif	//	I_SAY_YES_TO_MULTI_TEXTURES

	int numVertices = GetNumVertices();
	gos_vertices = vt->GetActualVertexPool(db);

#ifdef I_SAY_YES_TO_DUAL_TEXTURES
	int tex2count = 0;
#endif	//	I_SAY_YES_TO_DUAL_TEXTURES

#ifdef I_SAY_YES_TO_DETAIL_TEXTURES
	Scalar detailTexCoords[2];
#endif	//	I_SAY_YES_TO_DETAIL_TEXTURES

#if defined(I_SAY_YES_TO_DUAL_TEXTURES) || defined(I_SAY_YES_TO_DETAIL_TEXTURES)
	gos_vertices2uv = vt->GetActualVertexPool2UV(db);
#endif

	numGOSVertices = 0;

	Verify(index.GetLength() > 0);
	Verify(coords.GetLength() == visibleIndexedVertices.GetLength());

	if(visibleIndexedVerticesKey == false)
	{
		FindVisibleVertices();
	}

#ifdef _ARMOR
	memset(indexOffset, 0xff, Limits::Max_Number_Vertices_Per_Mesh*sizeof(unsigned short));
#endif	//	_ARMOR

	for(j=0,stride=0;j<numVertices;j++)
	{
		if(visibleIndexedVertices[j] == 0)
		{
			stride++;
		}
		else
		{
#ifdef LAB_ONLY
			Set_Statistic(TransformedVertices, TransformedVertices+1);

			if(db==false)
			{
				Verify (vt->GetLast() + numGOSVertices < Limits::Max_Number_Vertices_Per_Frame);
			}
			else
			{
				Verify (numGOSVertices < 2*Limits::Max_Number_Vertices_Per_Mesh);
			}
#endif	//	LAB_ONLY

			*(int *)(&indexOffset[j]) = (j - stride);

#ifdef I_SAY_YES_TO_TERRAIN
			terrainUV[0] = borderPixelFun + (coords[j].x - minX)*xUVFac;
			terrainUV[1] = borderPixelFun + (coords[j].z - minZ)*zUVFac;
#endif	//	I_SAY_YES_TO_TERRAIN

#ifdef I_SAY_YES_TO_DUAL_TEXTURES
			if(MLRState::GetMultitextureLightMap() == true && state.GetMultiTextureMode()!=MLRState::MultiTextureOffMode)
			{
				gos_vertices2uv[numGOSVertices].GOSTransformNoClip(
					coords[j],
					*mat,
					&texCoords[j][0],
					&texCoords[numVertices + j][0]
	#if FOG_HACK
					,state.GetFogMode()
	#endif	//	FOG_HACK
				);
	#ifdef I_SAY_YES_TO_COLOR
		#if COLOR_AS_DWORD
				gos_vertices2uv[numGOSVertices].argb = (*actualColors)[j];
		#else	//	COLOR_AS_DWORD
				gos_vertices2uv[numGOSVertices].argb = GOSCopyColor(&(*actualColors)[j]);
		#endif	//	COLOR_AS_DWORD
	#else	//	I_SAY_YES_TO_COLOR
				gos_vertices2uv[numGOSVertices].argb = 0xffffffff;
	#endif	//	I_SAY_YES_TO_COLOR
			}
			else
			{
				gos_vertices[numGOSVertices].GOSTransformNoClip(
					coords[j],
					*mat,
					&texCoords[j][0]
	#if FOG_HACK
					,state.GetFogMode()
	#endif	//	FOG_HACK
				);
				(*texCoords2)[tex2count++] = texCoords[numVertices + j];

			
			}
#else //	I_SAY_YES_TO_DUAL_TEXTURES
	#ifdef I_SAY_YES_TO_DETAIL_TEXTURES
			if(	MLRState::GetMultitextureLightMap() == true &&
				state.GetMultiTextureMode()!=MLRState::MultiTextureOffMode &&
				gEnableDetailTexture==1
			)
			{
		#ifdef I_SAY_YES_TO_TERRAIN2
				detailTexCoords[0] = texCoords[j][0]*xScale;
				detailTexCoords[1] = texCoords[j][1]*yScale;
		#else
				detailTexCoords[0] = texCoords[j][0]*xScale + xOffset;
				detailTexCoords[1] = texCoords[j][1]*yScale + yOffset;
		#endif
				Verify(	MLRState::GetHasMaxUVs() ? (detailTexCoords[0]>=-MLRState::GetMaxUV() && detailTexCoords[0]<=MLRState::GetMaxUV()) : 1);
				Verify(	MLRState::GetHasMaxUVs() ? (detailTexCoords[1]>=-MLRState::GetMaxUV() && detailTexCoords[1]<=MLRState::GetMaxUV()) : 1);

				gos_vertices2uv[numGOSVertices].GOSTransformNoClip(
					coords[j],
					*mat,
					&texCoords[j][0],
					&detailTexCoords[0]
		#if FOG_HACK
					,state.GetFogMode()
		#endif	//	FOG_HACK
				);
		#ifdef I_SAY_YES_TO_COLOR
			#if COLOR_AS_DWORD
				gos_vertices2uv[numGOSVertices].argb = (*actualColors)[j];
			#else	//	COLOR_AS_DWORD
				gos_vertices2uv[numGOSVertices].argb = GOSCopyColor(&(*actualColors)[j]);
			#endif	//	COLOR_AS_DWORD
		#else	//	I_SAY_YES_TO_COLOR
				gos_vertices2uv[numGOSVertices].argb = 0xffffffff;
		#endif	//	I_SAY_YES_TO_COLOR

				if(gos_vertices[j].rhw < fadeDetailEnd)
				{
					gos_vertices[j].argb &= 0x00ffffff;
				}
				else
				{
					if(gos_vertices[j].rhw<fadeDetailStart)
					{
						gos_vertices[j].argb &= ((Stuff::Truncate_Float_To_Word((gos_vertices[j].rhw - fadeDetailEnd)*fadeMultiplicator)) << 24) | 0x00ffffff;
					}
				}
			}
			else
	#endif //	I_SAY_YES_TO_DETAIL_TEXTURES
			{
				gos_vertices[numGOSVertices].GOSTransformNoClip(
					coords[j],
					*mat,
	#ifdef I_SAY_YES_TO_TERRAIN
					terrainUV
	#else	//	I_SAY_YES_TO_TERRAIN
					&texCoords[j][0]
	#endif	//	I_SAY_YES_TO_TERRAIN
	#if FOG_HACK
					, state.GetFogMode()
	#endif	//	FOG_HACK
				);

	#ifdef I_SAY_YES_TO_COLOR
		#if COLOR_AS_DWORD
				gos_vertices[numGOSVertices].argb = (*actualColors)[j];
		#else	//	COLOR_AS_DWORD
				gos_vertices[numGOSVertices].argb = GOSCopyColor(&(*actualColors)[j]);
		#endif	//	COLOR_AS_DWORD
	#else	//	I_SAY_YES_TO_COLOR
				gos_vertices[numGOSVertices].argb = 0xffffffff;
	#endif	//	I_SAY_YES_TO_COLOR
			}
#endif //	I_SAY_YES_TO_DUAL_TEXTURES

			if(textureAnimation)
			{
				gos_vertices[numGOSVertices].u += deltaU;
				gos_vertices[numGOSVertices].v += deltaV;
			}

#ifdef I_SAY_YES_TO_MULTI_TEXTURES
			for(m=1;m<currentNrOfPasses;m++)
			{
				extraMultiTexCoords[m][tex2count[m]++] = multiTexCoordsPointers[m][j];
			}
#endif	//	I_SAY_YES_TO_MULTI_TEXTURES
			numGOSVertices++;
		}
	}

#ifdef LAB_ONLY
	Set_Statistic(NonClippedVertices, NonClippedVertices+numGOSVertices);
#endif	//	LAB_ONLY

	Check_Object(vt);

#ifdef I_SAY_YES_TO_DUAL_TEXTURES
	if(MLRState::GetMultitextureLightMap() == false || state.GetMultiTextureMode()==MLRState::MultiTextureOffMode)
	{
		Verify (tex2count == numGOSVertices);


		if(db==false)
		{
			Verify (vt->GetLast() + 2*numGOSVertices < vt->GetLength());
		}
		else
		{
			Verify (2*numGOSVertices < 2*Limits::Max_Number_Vertices_Per_Mesh);
		}

		if(state2.GetTextureHandle())
		{
			MLRTexture *texture = (*MLRTexturePool::Instance)[state.GetTextureHandle()];
			Verify(texture);

			textureAnimation = texture->GetAnimateTexture();
			if(textureAnimation)
			{
				Stuff::AffineMatrix4D &textureMatrix = texture->GetTextureMatrix();
				deltaU = textureMatrix(3, 0);
				deltaV = textureMatrix(3, 1);
			}
		}

		memcpy(gos_vertices + numGOSVertices, gos_vertices, numGOSVertices * sizeof(GOSVertex));

		if(textureAnimation)
		{
			for(i=0,j=numGOSVertices;i<numGOSVertices;i++,j++)
			{
				gos_vertices[j].u = (*texCoords2)[i][0] + deltaU;
				gos_vertices[j].v = (*texCoords2)[i][1] + deltaV;
			}
		}
		else
		{
			for(i=0,j=numGOSVertices;i<numGOSVertices;i++,j++)
			{
				gos_vertices[j].u = (*texCoords2)[i][0];
				gos_vertices[j].v = (*texCoords2)[i][1];
			}
		}

		if(db==false)
		{
			vt->Increase(2*numGOSVertices);
		}
	}
	else
	{
		if(db==false)
		{
			vt->Increase2UV(numGOSVertices);
		}
	}
#else	//	I_SAY_YES_TO_DUAL_TEXTURES
	#ifdef I_SAY_YES_TO_DETAIL_TEXTURES
		if(	gEnableDetailTexture==1)
		{			
			if(MLRState::GetMultitextureLightMap() == false || state.GetMultiTextureMode()==MLRState::MultiTextureOffMode )
			{
				if(db==false)
				{
					Verify (vt->GetLast() + 2*numGOSVertices < vt->GetLength());
				}
				else
				{
					Verify (2*numGOSVertices < 2*Limits::Max_Number_Vertices_Per_Mesh );
				}

				memcpy(gos_vertices + numGOSVertices, gos_vertices, numGOSVertices * sizeof(GOSVertex));

				stride = 0;
				for(i=0,j=numGOSVertices;i<numGOSVertices;i++,j++)
				{
			#ifdef I_SAY_YES_TO_TERRAIN2
					gos_vertices[j].u = gos_vertices[i].u*xScale;
					gos_vertices[j].v = gos_vertices[i].v*yScale;
			#else
					gos_vertices[j].u = gos_vertices[i].u*xScale + xOffset;
					gos_vertices[j].v = gos_vertices[i].v*yScale + yOffset;
			#endif
					Verify(	MLRState::GetHasMaxUVs() ? (gos_vertices[j].u>=-MLRState::GetMaxUV() && gos_vertices[j].u<=MLRState::GetMaxUV()) : 1);
					Verify(	MLRState::GetHasMaxUVs() ? (gos_vertices[j].v>=-MLRState::GetMaxUV() && gos_vertices[j].v<=MLRState::GetMaxUV()) : 1);

					if(gos_vertices[j].rhw < fadeDetailEnd)
					{
						gos_vertices[j].argb &= 0x00ffffff;
					}
					else
					{
						stride++;
						if(gos_vertices[j].rhw<fadeDetailStart)
						{
							gos_vertices[j].argb &= ((Stuff::Truncate_Float_To_Word((gos_vertices[j].rhw - fadeDetailEnd)*fadeMultiplicator)) << 24) | 0x00ffffff;
						}
					}
				}

				if(stride==0)
				{
					detTextureVisible=false;
				}
				else
				{
					detTextureVisible=true;
				}

				if(db==false)
				{
					vt->Increase(2*numGOSVertices);
				}
			}
			else
			{
				if(db==false)
				{
					vt->Increase2UV(numGOSVertices);
				}
			}
		}
		else
		{
			if(db==false)
			{
				vt->Increase(numGOSVertices);
			}
		}
	#else	//	I_SAY_YES_TO_DETAIL_TEXTURES
		if(db==false)
		{
			vt->Increase(numGOSVertices);
		}
	#endif	//	I_SAY_YES_TO_DETAIL_TEXTURES
#endif	//	I_SAY_YES_TO_DUAL_TEXTURES

#ifdef I_SAY_YES_TO_MULTI_TEXTURES
	for(m=1;m<currentNrOfPasses;m++)
	{
		Verify (tex2count[m] == numGOSVertices);
		if(db==false)
		{
			Verify (vt->GetLast() + numGOSVertices < vt->GetLength());
		}
		else
		{
			Verify (numGOSVertices < 2*Limits::Max_Number_Vertices_Per_Mesh);
		}

		memcpy(gos_vertices + numGOSVertices, gos_vertices, numGOSVertices * sizeof(GOSVertex));

		for(i=0,j=numGOSVertices;i<numGOSVertices;i++,j++)
		{
			gos_vertices[j].u = extraMultiTexCoords[m][i][0];
			gos_vertices[j].v = extraMultiTexCoords[m][i][1];
		}

		if(db==false)
		{
			vt->Increase(numGOSVertices);
		}
	}
#endif	//	I_SAY_YES_TO_MULTI_TEXTURES

	gos_indices = vt->GetActualIndexPool(db);
	numGOSIndices = 0;

	int ngi = 0;
	for(i=0,j=0;i<numOfTriangles;j+=3,++i)
	{
		if(testList[i] == 0)
		{
			continue;
		}

		if(db==false)
		{
			Verify((vt->GetLastIndex() + 3 + numGOSIndices) < vt->GetLength());
		}
		else
		{
			Verify(3 + numGOSIndices < 2*Limits::Max_Number_Vertices_Per_Mesh);
		}

		Verify(indexOffset[index[j]] < numGOSVertices);
		gos_indices[ngi++] = indexOffset[index[j]];
		Verify(indexOffset[index[j+2]] < numGOSVertices);
		gos_indices[ngi++] = indexOffset[index[j+2]];
		Verify(indexOffset[index[j+1]] < numGOSVertices);
		gos_indices[ngi++] = indexOffset[index[j+1]];
	}
	numGOSIndices = (unsigned short)ngi;

	Check_Object(vt);
	if(db==false)
	{
		vt->IncreaseIndex(numGOSIndices);
	}

	visible = numGOSVertices ? (unsigned char)1 : (unsigned char)0;

	Stop_Timer(Transform_Time);
}

static MLRClippingState theAnd, theOr, theTest;

//	extern void _stdcall CheckVertices( gos_VERTEX* pVertexArray, DWORD NumberVertices, bool PointsLines );
//	extern void _stdcall CheckVertices1( gos_VERTEX_2UV* pVertexArray, DWORD NumberVertices );

//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
// Now it gets serious
int
	CLASSNAME::TransformAndClip(Matrix4D *mat, MLRClippingState clippingFlags, GOSVertexPool *vt, bool db)
{
	Check_Object(this);

	Start_Timer(Transform_Time);

	Verify(numOfTriangles == testList.GetLength());
	Verify(clippingFlags.GetClippingState() != 0);

	//
	//--------------------------------------
	// See if we don't have to draw anything
	//--------------------------------------
	//
	if(numOfTriangles <= 0)
	{
		visible = 0;

		Stop_Timer(Transform_Time);

		return visible;
	}

	Verify(index.GetLength() > 0);
	unsigned short l;

	int i, j, k, ret = 0;

	int len = coords.GetLength();

	if(visibleIndexedVerticesKey == false)
	{
		FindVisibleVertices();
	}

	Stuff::Vector4D *v4d = transformedCoords->GetData();
	Stuff::Point3D *p3d = coords.GetData();
	int *cs = (int *)clipPerVertex->GetData();
	unsigned char *viv = visibleIndexedVertices.GetData();

	for(i=0;i<len;i++,p3d++,v4d++,cs++,viv++)
	{
		if(*viv == 0)
		{
			continue;
		}
		*viv = 0;

		v4d->MultiplySetClip(*p3d, *mat, cs);
#ifdef LAB_ONLY
		Set_Statistic(TransformedVertices, TransformedVertices+1);
#endif	//	LAB_ONLY

//
//--------------------------------------------------------
// I claims all vertices are in. lets check it. who knows
//--------------------------------------------------------
//
#ifdef LAB_ONLY

⌨️ 快捷键说明

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