Ejemplo n.º 1
0
MaterialSystemMaterial_t GetMatIDFromDisp( mapdispinfo_t *pMapDisp )
{
	texinfo_t *pTexInfo = &texinfo[pMapDisp->face.texinfo];
	dtexdata_t *pTexData = GetTexData( pTexInfo->texdata );
	MaterialSystemMaterial_t matID = FindOriginalMaterial( TexDataStringTable_GetString( pTexData->nameStringTableID ), NULL, true );
	return matID;
}
Ejemplo n.º 2
0
//-----------------------------------------------------------------------------
// Purpose: Finds or adds a texdata for the specified name ( same as below except
//   instead of finding the named texture, copies the settings from the passed
//  in sourceTexture. )
// Used for creation of one off .vmt files for water surface textures
// Input  : *pName - texture name
// Output : int index into dtexdata array
//-----------------------------------------------------------------------------
int FindAliasedTexData( const char *pName_, dtexdata_t *sourceTexture )
{
	char *pName = ( char * )_alloca( strlen( pName_ ) + 1 );
	strcpy( pName, pName_ );
	strlwr( pName );
	int i, output;
	bool found;
	dtexdata_t *pTexData;
	MaterialSystemMaterial_t matID;

	for ( i = 0; i < numtexdata; i++ )
	{
		if ( !strcmp( pName, TexDataStringTable_GetString( GetTexData( i )->nameStringTableID ) ) )
			return i;
	}


	output = numtexdata;
	if ( numtexdata >= MAX_MAP_TEXDATA )
	{
		Error( "Too many unique texture mappings, max = %d\n", MAX_MAP_TEXDATA );
	}
	pTexData = GetTexData( output );
	numtexdata++;

	// Save the name of the material.
	pTexData->nameStringTableID = TexDataStringTable_AddOrFindString( pName );

	// Get the width, height, view_width, view_height, and reflectivity from the material system.
	matID = FindOriginalMaterial( TexDataStringTable_GetString( sourceTexture->nameStringTableID ), &found, false );
	if( matID == MATERIAL_NOT_FOUND || (!found) )
	{
		qprintf( "WARNING: material not found: \"%s\"\n", pName );
		return -1;
	}

	GetMaterialDimensions( matID, &pTexData->width, &pTexData->height );
	pTexData->view_width = pTexData->width;  // undone: what is this?
	pTexData->view_height = pTexData->height;  // undone: what is this?
	
	GetMaterialReflectivity( matID, pTexData->reflectivity.Base() );
	g_SurfaceProperties[output] = GetSurfaceProperties( matID, pName );

	return output;
}
Ejemplo n.º 3
0
//-----------------------------------------------------------------------------
// Builds a list of all texdatas which need fixing up
//-----------------------------------------------------------------------------
void Cubemap_InitCubemapSideData( void )
{
	// This tree is used to prevent re-parsing material vars multiple times
	CUtlRBTree<CubemapInfo_t> lookup( 0, nummapbrushsides, CubemapLessFunc );

	// Fill in specular data.
	for ( int iSide = 0; iSide < nummapbrushsides; ++iSide )
	{
		side_t *pSide = &brushsides[iSide];
		if ( !pSide )
			continue;

		if ( pSide->texinfo == TEXINFO_NODE )
			continue;

		texinfo_t *pTex = &texinfo[pSide->texinfo];
		if ( !pTex )
			continue;

		dtexdata_t *pTexData = GetTexData( pTex->texdata );
		if ( !pTexData )
			continue;

		CubemapInfo_t info;
		info.m_nTableId = pTexData->nameStringTableID;

		// Have we encountered this materal? If so, then copy the data we cached off before
		int i = lookup.Find( info );
		if ( i != lookup.InvalidIndex() )
		{
			s_aCubemapSideData[iSide].bHasEnvMapInMaterial = lookup[i].m_bSpecular;
			continue;
		}

		// First time we've seen this material. Figure out if it uses env_cubemap
		const char *pPatchedMaterialName = TexDataStringTable_GetString( pTexData->nameStringTableID );
		info.m_bSpecular = DoesMaterialOrDependentsUseEnvmap( pPatchedMaterialName );
		s_aCubemapSideData[ iSide ].bHasEnvMapInMaterial = info.m_bSpecular;
		lookup.Insert( info );
	}

	// Fill in cube map data.
	for ( int iCubemap = 0; iCubemap < g_nCubemapSamples; ++iCubemap )
	{
		IntVector_t &sideList = s_EnvCubemapToBrushSides[iCubemap];
		int nSideCount = sideList.Count();
		for ( int iSide = 0; iSide < nSideCount; ++iSide )
		{
			int nSideID = sideList[iSide];
			int nIndex = SideIDToIndex( nSideID );
			if ( nIndex < 0 )
				continue;

			s_aCubemapSideData[nIndex].bManuallyPickedByAnEnvCubemap = true;
		}
	}
}
const char *GetShaderNameForTexInfo( int iTexInfo )
{
	texinfo_t *pTexInfo = &texinfo[iTexInfo];
	dtexdata_t *pTexData = GetTexData( pTexInfo->texdata );
	const char *pMaterialName = TexDataStringTable_GetString( pTexData->nameStringTableID );
	MaterialSystemMaterial_t hMaterial = FindMaterial( pMaterialName, NULL, false );
	const char *pShaderName = GetMaterialShaderName( hMaterial );
	return pShaderName;
}
int CreateBrushVersionOfWorldVertexTransitionMaterial( int originalTexInfo )
{
	// Don't make cubemap tex infos for nodes
	if ( originalTexInfo == TEXINFO_NODE )
		return originalTexInfo;

	texinfo_t *pTexInfo = &texinfo[originalTexInfo];
	dtexdata_t *pTexData = GetTexData( pTexInfo->texdata );
	const char *pOriginalMaterialName = TexDataStringTable_GetString( pTexData->nameStringTableID );

	// Get out of here if the originalTexInfo is already a patched wvt material
	if ( Q_stristr( pOriginalMaterialName, "_wvt_patch" ) )
		return originalTexInfo;

	char patchedMaterialName[1024];
	GeneratePatchedMaterialName( pOriginalMaterialName, patchedMaterialName, 1024 );
//	Warning( "GeneratePatchedMaterialName: %s %s\n", pMaterialName, patchedMaterialName );
	
	// Make sure the texdata doesn't already exist.
	int nTexDataID = FindTexData( patchedMaterialName );
	bool bHasTexData = (nTexDataID != -1);
	if( !bHasTexData )
	{
		// Create the new vmt material file
		CreateWorldVertexTransitionPatchedMaterial( pOriginalMaterialName, patchedMaterialName );

		// Make a new texdata
		nTexDataID = AddCloneTexData( pTexData, patchedMaterialName );
	}

	Assert( nTexDataID != -1 );

	texinfo_t newTexInfo;
	newTexInfo = *pTexInfo;
	newTexInfo.texdata = nTexDataID;

	int nTexInfoID = -1;

	// See if we need to make a new texinfo
	bool bHasTexInfo = false;
	if( bHasTexData )
	{
		nTexInfoID = FindTexInfo( newTexInfo );
		bHasTexInfo = (nTexInfoID != -1);
	}

	// Make a new texinfo if we need to.
	if( !bHasTexInfo )
	{
		nTexInfoID = texinfo.AddToTail( newTexInfo );
	}

	Assert( nTexInfoID != -1 );
	return nTexInfoID;
}
Ejemplo n.º 6
0
//-----------------------------------------------------------------------------
// Finds a texdata for the specified name, returns -1 if not found
//-----------------------------------------------------------------------------
int FindTexData( const char *pName )
{
	// Make sure the texdata doesn't already exist.
	for( int i = 0; i < numtexdata; i++ )
	{
		char const *pTexDataName = TexDataStringTable_GetString( GetTexData( i )->nameStringTableID );
		if ( !Q_stricmp( pTexDataName, pName ) )
			return i;
	}
	return -1;
}
Ejemplo n.º 7
0
//-----------------------------------------------------------------------------
// Purpose: Finds or adds a texdata for the specified name
// Input  : *pName - texture name
// Output : int index into dtexdata array
//-----------------------------------------------------------------------------
int FindTexData( const char *pName_ )
{
	char *pName = ( char * )_alloca( strlen( pName_ ) + 1 );
	strcpy( pName, pName_ );
	int i, output;
	bool found;
	dtexdata_t *pTexData;
	MaterialSystemMaterial_t matID;

	for ( i = 0; i < numtexdata; i++ )
	{
		char const *tableName = TexDataStringTable_GetString( GetTexData( i )->nameStringTableID );

		if ( !strcmp( pName, tableName ) )
		{
			return i;
		}
	}

	output = numtexdata;
	if ( numtexdata >= MAX_MAP_TEXDATA )
	{
		Error( "MAX_MAP_TEXDATA" );
	}
	pTexData = GetTexData( output );
	numtexdata++;


	// Save the name of the material.
	pTexData->nameStringTableID = TexDataStringTable_AddOrFindString( pName );
	// Get the width, height, view_width, view_height, and reflectivity from the material system.
	matID = FindOriginalMaterial( pName, &found );
	if( matID == MATERIAL_NOT_FOUND || (!found) )
	{
		qprintf( "WARNING: material not found: \"%s\"\n", pName );
		return -1;
	}

	GetMaterialDimensions( matID, &pTexData->width, &pTexData->height );
	pTexData->view_width = pTexData->width;  // undone: what is this?
	pTexData->view_height = pTexData->height;  // undone: what is this?
	
	GetMaterialReflectivity( matID, pTexData->reflectivity.Base() );
	g_SurfaceProperties[output] = GetSurfaceProperties( matID, pName );

#if 0
	Msg( "reflectivity: %f %f %f\n", 
		pTexData->reflectivity[0],
		pTexData->reflectivity[1],
		pTexData->reflectivity[2] );
#endif

	return output;
}
Ejemplo n.º 8
0
//-----------------------------------------------------------------------------
// Purpose: Takes the texinfo_t referenced by the .vmt and the computed depth for the
//  surface and looks up or creates a texdata/texinfo for the mangled one-off water .vmt file
// Input  : *pBaseInfo - 
//			depth - 
// Output : int
//-----------------------------------------------------------------------------
int FindOrCreateWaterTexInfo( texinfo_t *pBaseInfo, float depth )
{
	char fullname[ 512 ];
	char materialname[ 512 ];

	// Get the base texture/material name
	char const *name = TexDataStringTable_GetString( GetTexData( pBaseInfo->texdata )->nameStringTableID );

	GetWaterTextureName( mapbase, name, (int)depth, fullname );

	// See if we already have an entry for this depth
	WaterTexInfo lookup;
	lookup.m_FullName = fullname;
	int idx = g_WaterTexInfos.Find( lookup );

	// If so, return the existing entry texinfo index
	if ( idx != g_WaterTexInfos.InvalidIndex() )
	{
		return g_WaterTexInfos[ idx ].m_nTexInfo;
	}

	// Otherwise, fill in the rest of the data
	lookup.m_nWaterDepth = (int)depth;
	// Remember the current material name
	sprintf( materialname, "%s", name );
	strlwr( materialname );
	lookup.m_MaterialName = materialname;

	texinfo_t ti;
	// Make a copy
	ti = *pBaseInfo;
	// Create a texdata that is based on the underlying existing entry
	ti.texdata = FindAliasedTexData( fullname, GetTexData( pBaseInfo->texdata ) );

	// Find or create a new index
	lookup.m_nTexInfo = FindOrCreateTexInfo( ti );

	// Add the new texinfo to the RB tree
	idx = g_WaterTexInfos.Insert( lookup );

	// Msg( "created texinfo for %s\n", lookup.m_FullName.String() );

	// Go ahead and create the new vmt file.
	EmitWaterMaterialFile( &g_WaterTexInfos[idx] );

	// Return the new texinfo
	return g_WaterTexInfos[ idx ].m_nTexInfo;
}
Ejemplo n.º 9
0
/*
==================
MakeTreePortals_r
==================
*/
void MakeTreePortals_r (node_t *node)
{
	int		i;

	CalcNodeBounds (node);
	if (node->mins[0] >= node->maxs[0])
	{
		Warning("WARNING: node without a volume\n");
	}

	for (i=0 ; i<3 ; i++)
	{
		if (node->mins[i] < (MIN_COORD_INTEGER-SIDESPACE) || node->maxs[i] > (MAX_COORD_INTEGER+SIDESPACE))
		{
			const char *pMatName = "<NO BRUSH>";
			// split by brush side
			if ( node->side )
			{
				texinfo_t *pTexInfo = &texinfo[node->side->texinfo];
				dtexdata_t *pTexData = GetTexData( pTexInfo->texdata );
				pMatName = TexDataStringTable_GetString( pTexData->nameStringTableID );
			}
			Vector point = node->portals->winding->p[0];
			Warning("WARNING: BSP node with unbounded volume (material: %s, near %s)\n", pMatName, VecToString(point) );
			break;
		}
	}
	if (node->planenum == PLANENUM_LEAF)
		return;

	MakeNodePortal (node);
	SplitNodePortals (node);

	MakeTreePortals_r (node->children[0]);
	MakeTreePortals_r (node->children[1]);
}
Ejemplo n.º 10
0
//-----------------------------------------------------------------------------
// Create a VMT to override the specified texinfo which references the cubemap entity at the specified origin.
// Returns the index of the new (or preexisting) texinfo referencing that VMT.
//
// Also adds the new cubemap VTF filename to s_DefaultCubemapNames so it can copy the
// default (skybox) cubemap into this file so the cubemap doesn't have the pink checkerboard at
// runtime before they run buildcubemaps.
//-----------------------------------------------------------------------------
static int Cubemap_CreateTexInfo( int originalTexInfo, int origin[3] )
{
	// Don't make cubemap tex infos for nodes
	if ( originalTexInfo == TEXINFO_NODE )
		return originalTexInfo;

	texinfo_t *pTexInfo = &texinfo[originalTexInfo];
	dtexdata_t *pTexData = GetTexData( pTexInfo->texdata );
	const char *pMaterialName = TexDataStringTable_GetString( pTexData->nameStringTableID );
	if ( g_IsCubemapTexData[pTexInfo->texdata] )
	{
		Warning("Multiple references for cubemap on texture %s!!!\n", pMaterialName );
		return originalTexInfo;
	}

	// Get out of here if the originalTexInfo is already a generated material for this position.
	char pStringToSearchFor[512];
	Q_snprintf( pStringToSearchFor, 512, "_%d_%d_%d", origin[0], origin[1], origin[2] );
	if ( Q_stristr( pMaterialName, pStringToSearchFor ) )
		return originalTexInfo;

	// Package up information needed to generate patch names
	PatchInfo_t info;
	info.m_pMapName = mapbase;
	info.m_pOrigin[0] = origin[0];
	info.m_pOrigin[1] = origin[1];
	info.m_pOrigin[2] = origin[2];

	// Generate the name of the patched material
	char pGeneratedTexDataName[1024];
	GeneratePatchedName( pMaterialName, info, true, pGeneratedTexDataName, 1024 );

	// Make sure the texdata doesn't already exist.
	int nTexDataID = FindTexData( pGeneratedTexDataName );
	bool bHasTexData = (nTexDataID != -1);
	if( !bHasTexData )
	{
		// Generate the new "$envmap" texture name.
		char pTextureName[1024];
		GeneratePatchedName( "c", info, false, pTextureName, 1024 );

		// Hook the texture into the material and all dependent materials
		// but if no hooking was necessary, exit out
		if ( !PatchEnvmapForMaterialAndDependents( pMaterialName, info, pTextureName ) )
			return originalTexInfo;
		
		// Store off the name of the cubemap that we need to create since we successfully patched
		char pFileName[1024];
		int nLen = Q_snprintf( pFileName, 1024, "materials/%s.vtf", pTextureName );
		int id = s_DefaultCubemapNames.AddToTail();
		s_DefaultCubemapNames[id] = new char[ nLen + 1 ];
		strcpy( s_DefaultCubemapNames[id], pFileName );

		// Make a new texdata
		nTexDataID = AddCloneTexData( pTexData, pGeneratedTexDataName );
		g_IsCubemapTexData[nTexDataID] = true;
	}

	Assert( nTexDataID != -1 );
	
	texinfo_t newTexInfo;
	newTexInfo = *pTexInfo;
	newTexInfo.texdata = nTexDataID;
	
	int nTexInfoID = -1;

	// See if we need to make a new texinfo
	bool bHasTexInfo = false;
	if( bHasTexData )
	{
		nTexInfoID = FindTexInfo( newTexInfo );
		bHasTexInfo = (nTexInfoID != -1);
	}
	
	// Make a new texinfo if we need to.
	if( !bHasTexInfo )
	{
		nTexInfoID = texinfo.AddToTail( newTexInfo );
	}

	Assert( nTexInfoID != -1 );
	return nTexInfoID;
}
Ejemplo n.º 11
0
//-----------------------------------------------------------------------------
// Places Detail Objects in the level
//-----------------------------------------------------------------------------
void EmitDetailModels()
{
	StartPacifier("Placing detail props : ");

	// Place stuff on each face
	dface_t* pFace = dfaces;
	for (int j = 0; j < numfaces; ++j)
	{
		UpdatePacifier( (float)j / (float)numfaces );

		// Get at the material associated with this face
		texinfo_t* pTexInfo = &texinfo[pFace[j].texinfo];
		dtexdata_t* pTexData = GetTexData( pTexInfo->texdata );

		// Try to get at the material
		bool found;
		MaterialSystemMaterial_t handle = 
			FindOriginalMaterial( TexDataStringTable_GetString( pTexData->nameStringTableID ), 
						  &found, false );
		if (!found)
			continue;

		// See if its got any detail objects on it
		const char* pDetailType = GetMaterialVar( handle, "%detailtype" );
		if (!pDetailType)
			continue;

		// Get the detail type...
		DetailObject_t search;
		search.m_Name = pDetailType;
		int objectType = s_DetailObjectDict.Find(search);
		if (objectType < 0)
		{
			Warning("Material %s uses unknown detail object type %s!\n",	
				TexDataStringTable_GetString( pTexData->nameStringTableID ),
				pDetailType);
			continue;
		}

		// Emit objects on a particular face
		DetailObject_t& detail = s_DetailObjectDict[objectType];

		if (pFace[j].dispinfo < 0)
		{
			EmitDetailObjectsOnFace( &pFace[j], detail );
		}
		else
		{
			// Get a CCoreDispInfo. All we need is the triangles and lightmap texture coordinates.
			mapdispinfo_t *pMapDisp = &mapdispinfo[pFace[j].dispinfo];
			CCoreDispInfo coreDispInfo;
			DispMapToCoreDispInfo( pMapDisp, &coreDispInfo, &pFace[j] );

			EmitDetailObjectsOnDisplacementFace( &pFace[j], detail, coreDispInfo );
		}
	}

	// Emit specifically specified detail props
	Vector origin;
	QAngle angles;
	Vector2D pos[2];
	Vector2D tex[2];
	for (int i = 0; i < num_entities; ++i)
	{
		char* pEntity = ValueForKey(&entities[i], "classname");
		if (!strcmp(pEntity, "detail_prop") || !strcmp(pEntity, "prop_detail"))
		{
			GetVectorForKey( &entities[i], "origin", origin );
			GetAnglesForKey( &entities[i], "angles", angles );
			char* pModelName = ValueForKey( &entities[i], "model" );
			int nOrientation = IntForKey( &entities[i], "detailOrientation" );

			AddDetailToLump( pModelName, origin, angles, nOrientation );

			// strip this ent from the .bsp file
			entities[i].epairs = 0;
			continue;
		}

		if (!strcmp(pEntity, "prop_detail_sprite"))
		{
			GetVectorForKey( &entities[i], "origin", origin );
			GetAnglesForKey( &entities[i], "angles", angles );
			int nOrientation = IntForKey( &entities[i], "detailOrientation" );
			GetVector2DForKey( &entities[i], "position_ul", pos[0] );
			GetVector2DForKey( &entities[i], "position_lr", pos[1] );
			GetVector2DForKey( &entities[i], "tex_ul", tex[0] );
			GetVector2DForKey( &entities[i], "tex_size", tex[1] );
			float flTextureSize = FloatForKey( &entities[i], "tex_total_size" );

			tex[1].x += tex[0].x - 0.5f;
			tex[1].y += tex[0].y - 0.5f;
			tex[0].x += 0.5f;
			tex[0].y += 0.5f;
			tex[0] /= flTextureSize;
			tex[1] /= flTextureSize;

			AddDetailSpriteToLump( origin, angles, nOrientation, pos, tex, 1.0f );

			// strip this ent from the .bsp file
			entities[i].epairs = 0;
			continue;
		}
	}

	EndPacifier( true );
}
Ejemplo n.º 12
0
void Disp_BuildVirtualMesh( int contentsMask )
{
	CUtlVector<CPhysCollide *> virtualMeshes;
	virtualMeshes.EnsureCount( g_CoreDispInfos.Count() );
	for ( int i = 0; i < g_CoreDispInfos.Count(); i++ )	
	{
		CCoreDispInfo *pDispInfo = g_CoreDispInfos[ i ];
		mapdispinfo_t *pMapDisp = &mapdispinfo[ i ];

		virtualMeshes[i] = NULL;
		// not solid for this pass
		if ( !(pMapDisp->contents & contentsMask) )
			continue;

		// Build a triangle list. This shares the tesselation code with the engine.
		CUtlVector<unsigned short> indices;
		CVBSPTesselateHelper helper;
		helper.m_pIndices = &indices;
		helper.m_pActiveVerts = pDispInfo->GetAllowedVerts().Base();
		helper.m_pPowerInfo = pDispInfo->GetPowerInfo();

		::TesselateDisplacement( &helper );

		// validate the collision data
		if ( 1 )
		{
			int triCount = indices.Count() / 3;
			for ( int j = 0; j < triCount; j++ )
			{
				int index = j * 3;
				Vector v0 = pDispInfo->GetVert( indices[index+0] );
				Vector v1 = pDispInfo->GetVert( indices[index+1] );
				Vector v2 = pDispInfo->GetVert( indices[index+2] );
				if ( v0 == v1 || v1 == v2 || v2 == v0 )
				{
					Warning( "Displacement %d has bad geometry near %.2f %.2f %.2f\n", i, v0.x, v0.y, v0.z );
					texinfo_t *pTexInfo = &texinfo[pMapDisp->face.texinfo];
					dtexdata_t *pTexData = GetTexData( pTexInfo->texdata );
					const char *pMatName = TexDataStringTable_GetString( pTexData->nameStringTableID );

					Error( "Can't compile displacement physics, exiting.  Texture is %s\n", pMatName );
				}
			}

		}
		CDispMeshEvent meshHandler( indices.Base(), indices.Count(), pDispInfo );
		virtualmeshparams_t params;
		params.buildOuterHull = true;
		params.pMeshEventHandler = &meshHandler;
		params.userData = &meshHandler;
		virtualMeshes[i] = physcollision->CreateVirtualMesh( params );
	}
	unsigned int totalSize = 0;
	CUtlBuffer buf;
	dphysdisp_t header;
	header.numDisplacements = g_CoreDispInfos.Count();
	buf.PutObjects( &header );

	CUtlVector<char> dispBuf;
	for ( int i = 0; i < header.numDisplacements; i++ )
	{
		if ( virtualMeshes[i] )
		{
			unsigned int testSize = physcollision->CollideSize( virtualMeshes[i] );
			totalSize += testSize;
			buf.PutShort( testSize );
		}
		else
		{
			buf.PutShort( -1 );
		}
	}
	for ( int i = 0; i < header.numDisplacements; i++ )
	{
		if ( virtualMeshes[i] )
		{
			unsigned int testSize = physcollision->CollideSize( virtualMeshes[i] );
			dispBuf.RemoveAll();
			dispBuf.EnsureCount(testSize);

			unsigned int outSize = physcollision->CollideWrite( dispBuf.Base(), virtualMeshes[i], false );
			Assert( outSize == testSize );
			buf.Put( dispBuf.Base(), outSize );
		}
	}
	g_PhysDispSize = totalSize + sizeof(dphysdisp_t) + (sizeof(unsigned short) * header.numDisplacements);
	Assert( buf.TellMaxPut() == g_PhysDispSize );
	g_PhysDispSize = buf.TellMaxPut();
	g_pPhysDisp = new byte[g_PhysDispSize];
	Q_memcpy( g_pPhysDisp, buf.Base(), g_PhysDispSize );
}