You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
610 lines
25 KiB
610 lines
25 KiB
//========= Copyright (c) Valve Corporation, All rights reserved. ============//
|
|
//
|
|
// Purpose:
|
|
//
|
|
// $NoKeywords: $
|
|
//=============================================================================//
|
|
|
|
#include "BaseVSShader.h"
|
|
#include "mathlib/vmatrix.h"
|
|
#include "common_hlsl_cpp_consts.h" // hack hack hack!
|
|
#include "convar.h"
|
|
|
|
#include "customclothing_vs20.inc"
|
|
#include "customclothing_vs30.inc"
|
|
#include "customclothing_ps20b.inc"
|
|
#include "customclothing_ps30.inc"
|
|
|
|
#include "writez_vs20.inc"
|
|
#include "white_ps20.inc"
|
|
#include "white_ps20b.inc"
|
|
|
|
#include "shaderlib/commandbuilder.h"
|
|
|
|
// NOTE: This has to be the last file included!
|
|
#include "tier0/memdbgon.h"
|
|
|
|
static const float kDefaultColor[3] = { 0.5f, 0.5f, 0.5f };
|
|
|
|
#define MODE_3D_PREVIEW 0
|
|
#define MODE_2D_COMPOSITE 1
|
|
#define MODE_3D_POSTCOMPOSITE 2
|
|
|
|
BEGIN_VS_SHADER( CustomClothing, "Help for CustomClothing" )
|
|
|
|
BEGIN_SHADER_PARAMS
|
|
|
|
//always required
|
|
SHADER_PARAM( BASETEXTURE, SHADER_PARAM_TYPE_TEXTURE, "", "" )
|
|
SHADER_PARAM( BUMPMAP, SHADER_PARAM_TYPE_TEXTURE, "", "" )
|
|
|
|
//only for 3d post-composite
|
|
SHADER_PARAM( AOSCREENBUFFER, SHADER_PARAM_TYPE_TEXTURE, "", "" )
|
|
|
|
//composite inputs, only for 3d preview and 2d composite
|
|
SHADER_PARAM( AOMAP, SHADER_PARAM_TYPE_TEXTURE, "", "" )
|
|
SHADER_PARAM( MASKMAP, SHADER_PARAM_TYPE_TEXTURE, "", "" )
|
|
SHADER_PARAM( OFFSETMAP, SHADER_PARAM_TYPE_TEXTURE, "", "" )
|
|
SHADER_PARAM( PATTERN1, SHADER_PARAM_TYPE_TEXTURE, "", "" )
|
|
SHADER_PARAM( PATTERN2, SHADER_PARAM_TYPE_TEXTURE, "", "" )
|
|
SHADER_PARAM( GRIME, SHADER_PARAM_TYPE_TEXTURE, "", "" )
|
|
SHADER_PARAM( LOGOMAP, SHADER_PARAM_TYPE_TEXTURE, "", "" )
|
|
SHADER_PARAM( LOGOX, SHADER_PARAM_TYPE_FLOAT, 0, "" )
|
|
SHADER_PARAM( LOGOY, SHADER_PARAM_TYPE_FLOAT, 0, "" )
|
|
SHADER_PARAM( LOGOSCALE, SHADER_PARAM_TYPE_FLOAT, 0, "" )
|
|
SHADER_PARAM( LOGOROTATE, SHADER_PARAM_TYPE_FLOAT, 0, "" )
|
|
SHADER_PARAM( LOGO2X, SHADER_PARAM_TYPE_FLOAT, 0, "" )
|
|
SHADER_PARAM( LOGO2Y, SHADER_PARAM_TYPE_FLOAT, 0, "" )
|
|
SHADER_PARAM( LOGO2SCALE, SHADER_PARAM_TYPE_FLOAT, 0, "" )
|
|
SHADER_PARAM( LOGO2ROTATE, SHADER_PARAM_TYPE_FLOAT, 0, "" )
|
|
SHADER_PARAM( LOGO2ENABLED, SHADER_PARAM_TYPE_BOOL, 0, "" )
|
|
SHADER_PARAM( LOGOMASKCRISP, SHADER_PARAM_TYPE_FLOAT, 0, "" )
|
|
SHADER_PARAM( LOGOWEAR, SHADER_PARAM_TYPE_FLOAT, 0, "" )
|
|
SHADER_PARAM( PATTERN1COLOR1, SHADER_PARAM_TYPE_VEC3, "", "" )
|
|
SHADER_PARAM( PATTERN1COLOR2, SHADER_PARAM_TYPE_VEC3, "", "" )
|
|
SHADER_PARAM( PATTERN1COLOR3, SHADER_PARAM_TYPE_VEC3, "", "" )
|
|
SHADER_PARAM( PATTERN1COLOR4, SHADER_PARAM_TYPE_VEC3, "", "" )
|
|
SHADER_PARAM( PATTERN1SCALE, SHADER_PARAM_TYPE_FLOAT, 0, "" )
|
|
SHADER_PARAM( PATTERN2COLOR1, SHADER_PARAM_TYPE_VEC3, "", "" )
|
|
SHADER_PARAM( PATTERN2COLOR2, SHADER_PARAM_TYPE_VEC3, "", "" )
|
|
SHADER_PARAM( PATTERN2COLOR3, SHADER_PARAM_TYPE_VEC3, "", "" )
|
|
SHADER_PARAM( PATTERN2COLOR4, SHADER_PARAM_TYPE_VEC3, "", "" )
|
|
SHADER_PARAM( PATTERN2SCALE, SHADER_PARAM_TYPE_FLOAT, 0, "" )
|
|
SHADER_PARAM( SWAPPATTERNMASKS, SHADER_PARAM_TYPE_BOOL, 0, "" )
|
|
SHADER_PARAM( CAVITYCONTRAST, SHADER_PARAM_TYPE_FLOAT, 0, "" )
|
|
SHADER_PARAM( OFFSETAMOUNT, SHADER_PARAM_TYPE_FLOAT, 0, "" )
|
|
|
|
SHADER_PARAM( ENTCENTER, SHADER_PARAM_TYPE_VEC3, "", "" )
|
|
|
|
//sets the behavior of the shader for different purposes
|
|
SHADER_PARAM( COMPOSITEMODE, SHADER_PARAM_TYPE_INTEGER, MODE_3D_PREVIEW, "" )
|
|
|
|
//override parameter for dynamic combo
|
|
SHADER_PARAM( AOPASS, SHADER_PARAM_TYPE_BOOL, 0, "" )
|
|
|
|
END_SHADER_PARAMS
|
|
|
|
SHADER_INIT_PARAMS()
|
|
{
|
|
|
|
SET_PARAM_INT_IF_NOT_DEFINED( COMPOSITEMODE, MODE_3D_PREVIEW )
|
|
|
|
SET_PARAM_INT_IF_NOT_DEFINED( AOPASS, 0 )
|
|
|
|
SET_PARAM_STRING_IF_NOT_DEFINED( BASETEXTURE, "Dev/flat_normal" );
|
|
SET_PARAM_STRING_IF_NOT_DEFINED( BUMPMAP, "Dev/flat_normal" );
|
|
|
|
SET_PARAM_STRING_IF_NOT_DEFINED( AOSCREENBUFFER, "_rt_character_ssao" );
|
|
|
|
if ( params[ COMPOSITEMODE ]->GetIntValue() == MODE_2D_COMPOSITE )
|
|
{
|
|
//we never want lighting to affect a 2D image-space composite
|
|
SET_FLAGS2( MATERIAL_VAR2_LIGHTING_UNLIT );
|
|
}
|
|
else
|
|
{
|
|
SET_FLAGS2( MATERIAL_VAR2_LIGHTING_VERTEX_LIT );
|
|
SET_FLAGS2( MATERIAL_VAR2_SUPPORTS_HW_SKINNING );
|
|
}
|
|
|
|
if ( params[ COMPOSITEMODE ]->GetIntValue() == MODE_3D_PREVIEW && !g_pHardwareConfig->SupportsPixelShaders_3_0() )
|
|
{
|
|
DevWarning( "CustomClothing shader cannot run in preview quality mode on non-sm3 hardware.\n" );
|
|
params[ COMPOSITEMODE ]->SetIntValue( MODE_3D_POSTCOMPOSITE );
|
|
}
|
|
|
|
if ( params[ COMPOSITEMODE ]->GetIntValue() == MODE_3D_PREVIEW || params[ COMPOSITEMODE ]->GetIntValue() == MODE_2D_COMPOSITE )
|
|
{
|
|
SET_PARAM_STRING_IF_NOT_DEFINED( GRIME, "models/player/custom_player/shared/clothing_grime" );
|
|
|
|
// throw some warnings if we can't find necessary composite input maps
|
|
|
|
if ( !params[ AOMAP ]->IsDefined() )
|
|
{
|
|
IMaterial *pOwnerMaterial = params[AOMAP]->GetOwningMaterial();
|
|
char szMaterialName[MAX_PATH] = "unknown CustomClothing material";
|
|
if ( pOwnerMaterial )
|
|
V_strcpy_safe( szMaterialName, pOwnerMaterial->GetName() );
|
|
DevWarning( "Warning: $aomap is undefined in %s\n", szMaterialName );
|
|
}
|
|
|
|
if ( !params[ MASKMAP ]->IsDefined() )
|
|
{
|
|
IMaterial *pOwnerMaterial = params[MASKMAP]->GetOwningMaterial();
|
|
char szMaterialName[MAX_PATH] = "unknown CustomClothing material";
|
|
if ( pOwnerMaterial )
|
|
V_strcpy_safe( szMaterialName, pOwnerMaterial->GetName() );
|
|
DevWarning( "Warning: $maskmap is undefined in %s\n", szMaterialName );
|
|
}
|
|
|
|
SET_PARAM_INT_IF_NOT_DEFINED( SWAPPATTERNMASKS, 0 );
|
|
|
|
//if pattern2 is defined but pattern1 isn't, secretly move pattern2 into pattern1 and flag the pattern masks to swap
|
|
if ( !params[ PATTERN1 ]->IsDefined() && params[ PATTERN2 ]->IsDefined() )
|
|
{
|
|
params[ PATTERN1 ]->SetStringValue( params[ PATTERN2 ]->GetStringValue() );
|
|
params[ PATTERN1COLOR1 ]->SetVecValue( params[ PATTERN2COLOR1 ]->GetVecValue(), 4 );
|
|
params[ PATTERN1COLOR2 ]->SetVecValue( params[ PATTERN2COLOR2 ]->GetVecValue(), 4 );
|
|
params[ PATTERN1COLOR3 ]->SetVecValue( params[ PATTERN2COLOR3 ]->GetVecValue(), 4 );
|
|
params[ PATTERN1COLOR4 ]->SetVecValue( params[ PATTERN2COLOR4 ]->GetVecValue(), 4 );
|
|
params[ PATTERN1SCALE ]->SetFloatValue( params[ PATTERN2SCALE ]->GetFloatValue() );
|
|
params[ PATTERN2 ]->SetUndefined();
|
|
params[ SWAPPATTERNMASKS ]->SetIntValue( params[ SWAPPATTERNMASKS ]->GetIntValue() == 0 ? 1 : 0 );
|
|
}
|
|
|
|
//TODO: detect if pattern1 and pattern2 are the same and bind them to the same sampler
|
|
|
|
SET_PARAM_FLOAT_IF_NOT_DEFINED( LOGOX, 0.5f );
|
|
SET_PARAM_FLOAT_IF_NOT_DEFINED( LOGOY, 0.5f );
|
|
SET_PARAM_FLOAT_IF_NOT_DEFINED( LOGOSCALE, 1 );
|
|
SET_PARAM_FLOAT_IF_NOT_DEFINED( LOGOROTATE, 0 );
|
|
|
|
SET_PARAM_FLOAT_IF_NOT_DEFINED( LOGO2X, 0.5f );
|
|
SET_PARAM_FLOAT_IF_NOT_DEFINED( LOGO2Y, 0.5f );
|
|
SET_PARAM_FLOAT_IF_NOT_DEFINED( LOGO2SCALE, 1 );
|
|
SET_PARAM_FLOAT_IF_NOT_DEFINED( LOGO2ROTATE, 0 );
|
|
|
|
SET_PARAM_FLOAT_IF_NOT_DEFINED( LOGOMASKCRISP, 0.5f );
|
|
SET_PARAM_FLOAT_IF_NOT_DEFINED( LOGOWEAR, 0.5f );
|
|
|
|
SET_PARAM_VEC_IF_NOT_DEFINED( PATTERN1COLOR1, kDefaultColor, 3 );
|
|
SET_PARAM_VEC_IF_NOT_DEFINED( PATTERN1COLOR2, kDefaultColor, 3 );
|
|
SET_PARAM_VEC_IF_NOT_DEFINED( PATTERN1COLOR3, kDefaultColor, 3 );
|
|
SET_PARAM_VEC_IF_NOT_DEFINED( PATTERN1COLOR4, kDefaultColor, 3 );
|
|
SET_PARAM_FLOAT_IF_NOT_DEFINED( PATTERN1SCALE, 1 );
|
|
|
|
SET_PARAM_VEC_IF_NOT_DEFINED( PATTERN2COLOR1, kDefaultColor, 3 );
|
|
SET_PARAM_VEC_IF_NOT_DEFINED( PATTERN2COLOR2, kDefaultColor, 3 );
|
|
SET_PARAM_VEC_IF_NOT_DEFINED( PATTERN2COLOR3, kDefaultColor, 3 );
|
|
SET_PARAM_VEC_IF_NOT_DEFINED( PATTERN2COLOR4, kDefaultColor, 3 );
|
|
SET_PARAM_FLOAT_IF_NOT_DEFINED( PATTERN2SCALE, 1 );
|
|
|
|
SET_PARAM_FLOAT_IF_NOT_DEFINED( CAVITYCONTRAST, 1 );
|
|
SET_PARAM_FLOAT_IF_NOT_DEFINED( OFFSETAMOUNT, 0.2f );
|
|
}
|
|
|
|
}
|
|
|
|
SHADER_FALLBACK
|
|
{
|
|
return 0;
|
|
}
|
|
|
|
SHADER_INIT
|
|
{
|
|
if ( params[AOPASS]->GetIntValue() != 1 )
|
|
{
|
|
if ( params[BASETEXTURE]->IsDefined() ) { LoadTexture( BASETEXTURE ); }
|
|
}
|
|
|
|
if ( params[BUMPMAP]->IsDefined() ) { LoadBumpMap( BUMPMAP ); }
|
|
|
|
if ( params[ COMPOSITEMODE ]->GetIntValue() == MODE_3D_POSTCOMPOSITE )
|
|
{
|
|
if ( params[AOSCREENBUFFER]->IsDefined() ) { LoadTexture( AOSCREENBUFFER ); }
|
|
}
|
|
|
|
if ( params[ COMPOSITEMODE ]->GetIntValue() == MODE_3D_PREVIEW || params[ COMPOSITEMODE ]->GetIntValue() == MODE_2D_COMPOSITE )
|
|
{
|
|
if ( params[AOMAP]->IsDefined() ) { LoadTexture( AOMAP ); }
|
|
if ( params[MASKMAP]->IsDefined() ) { LoadTexture( MASKMAP ); }
|
|
if ( params[PATTERN1]->IsDefined() ) { LoadTexture( PATTERN1 ); }
|
|
if ( params[PATTERN2]->IsDefined() ) { LoadTexture( PATTERN2 ); }
|
|
if ( params[GRIME]->IsDefined() ) { LoadTexture( GRIME ); }
|
|
if ( params[OFFSETMAP]->IsDefined() ) { LoadTexture( OFFSETMAP ); }
|
|
if ( params[LOGOMAP]->IsDefined() ) { LoadTexture( LOGOMAP ); }
|
|
}
|
|
}
|
|
|
|
inline void DrawCustomClothing( IMaterialVar **params, IShaderShadow* pShaderShadow, IShaderDynamicAPI* pShaderAPI, int vertexCompression )
|
|
{
|
|
SHADOW_STATE
|
|
{
|
|
SetInitialShadowState( );
|
|
|
|
int iCompositeMode = params[ COMPOSITEMODE ]->GetIntValue();
|
|
|
|
if ( params[AOPASS]->GetIntValue() != 1 )
|
|
{
|
|
if ( params[BASETEXTURE]->IsDefined() ) { pShaderShadow->EnableTexture( SHADER_SAMPLER0, true ); }
|
|
}
|
|
|
|
//pShaderShadow->EnableSRGBRead( SHADER_SAMPLER0, true );
|
|
if ( params[BUMPMAP]->IsDefined() ) { pShaderShadow->EnableTexture( SHADER_SAMPLER1, true ); }
|
|
|
|
if ( iCompositeMode == MODE_3D_POSTCOMPOSITE )
|
|
{
|
|
if ( params[AOSCREENBUFFER]->IsDefined() ) { pShaderShadow->EnableTexture( SHADER_SAMPLER10, true ); }
|
|
}
|
|
|
|
bool bNeedCompositeInputs = iCompositeMode == MODE_2D_COMPOSITE || iCompositeMode == MODE_3D_PREVIEW;
|
|
|
|
if ( bNeedCompositeInputs )
|
|
{
|
|
if ( params[AOMAP]->IsDefined() ) { pShaderShadow->EnableTexture( SHADER_SAMPLER2, true ); }
|
|
if ( params[MASKMAP]->IsDefined() ) { pShaderShadow->EnableTexture( SHADER_SAMPLER3, true ); }
|
|
if ( params[PATTERN1]->IsDefined() ) { pShaderShadow->EnableTexture( SHADER_SAMPLER4, true ); }
|
|
if ( params[PATTERN2]->IsDefined() ) { pShaderShadow->EnableTexture( SHADER_SAMPLER6, true ); }
|
|
if ( params[GRIME]->IsDefined() ) { pShaderShadow->EnableTexture( SHADER_SAMPLER7, true ); }
|
|
if ( params[OFFSETMAP]->IsDefined() ) { pShaderShadow->EnableTexture( SHADER_SAMPLER8, true ); }
|
|
if ( params[LOGOMAP]->IsDefined() ) { pShaderShadow->EnableTexture( SHADER_SAMPLER9, true ); }
|
|
}
|
|
|
|
if ( iCompositeMode == MODE_2D_COMPOSITE )
|
|
{
|
|
EnableAlphaBlending( SHADER_BLEND_SRC_ALPHA, SHADER_BLEND_ZERO ); //assume we're compositing onto a dirty surface
|
|
}
|
|
else
|
|
{
|
|
EnableAlphaBlending( SHADER_BLEND_SRC_ALPHA, SHADER_BLEND_ONE_MINUS_SRC_ALPHA );
|
|
|
|
pShaderShadow->AlphaFunc( SHADER_ALPHAFUNC_ALWAYS, 0.0f );
|
|
/*
|
|
BlendFunc( SHADER_BLEND_ZERO, SHADER_BLEND_ZERO );
|
|
BlendOp( SHADER_BLEND_OP_ADD );
|
|
EnableBlendingSeparateAlpha( false );
|
|
BlendFuncSeparateAlpha( SHADER_BLEND_ZERO, SHADER_BLEND_ZERO );
|
|
BlendOpSeparateAlpha( SHADER_BLEND_OP_ADD );
|
|
AlphaFunc( SHADER_ALPHAFUNC_GEQUAL, 0.7f );
|
|
*/
|
|
|
|
// Normalizing cube map
|
|
pShaderShadow->EnableTexture( SHADER_SAMPLER5, true );
|
|
}
|
|
|
|
unsigned int flags = VERTEX_POSITION| VERTEX_FORMAT_COMPRESSED;
|
|
if ( iCompositeMode != MODE_2D_COMPOSITE )
|
|
flags |= VERTEX_NORMAL;
|
|
|
|
int nTexCoordCount = 1;
|
|
int userDataSize = 0;
|
|
if (IS_FLAG_SET( MATERIAL_VAR_VERTEXCOLOR ))
|
|
{
|
|
flags |= VERTEX_COLOR;
|
|
}
|
|
pShaderShadow->VertexShaderVertexFormat( flags, nTexCoordCount, NULL, userDataSize );
|
|
|
|
if ( g_pHardwareConfig->SupportsPixelShaders_3_0() )
|
|
{
|
|
DECLARE_STATIC_VERTEX_SHADER( customclothing_vs30 );
|
|
SET_STATIC_VERTEX_SHADER_COMBO( COMPOSITEMODE, iCompositeMode );
|
|
SET_STATIC_VERTEX_SHADER( customclothing_vs30 );
|
|
}
|
|
else
|
|
{
|
|
DECLARE_STATIC_VERTEX_SHADER( customclothing_vs20 );
|
|
SET_STATIC_VERTEX_SHADER_COMBO( COMPOSITEMODE, iCompositeMode );
|
|
SET_STATIC_VERTEX_SHADER( customclothing_vs20 );
|
|
}
|
|
|
|
bool bUsePattern1 = bNeedCompositeInputs && params[ PATTERN1 ]->IsDefined() && params[ PATTERN1 ]->IsTexture();
|
|
bool bUsePattern2 = bNeedCompositeInputs && params[ PATTERN2 ]->IsDefined() && params[ PATTERN2 ]->IsTexture();
|
|
bool bUsePatternOffset = bNeedCompositeInputs && (bUsePattern1 || bUsePattern2) && params[ OFFSETMAP ]->IsDefined() && params[ OFFSETMAP ]->IsTexture();
|
|
bool bUseLogo1 = bNeedCompositeInputs && params[ LOGOMAP ]->IsDefined() && params[ LOGOMAP ]->IsTexture();
|
|
bool bUseLogo2 = bNeedCompositeInputs && bUseLogo1 && params[ LOGO2ENABLED ]->IsDefined() && (params[ LOGO2ENABLED ]->GetIntValue() > 0);
|
|
bool bSwapPatternMasks = bNeedCompositeInputs && bUsePattern2 && (params[ SWAPPATTERNMASKS ]->GetIntValue() > 0);
|
|
|
|
bool bCSMEnabled = g_pHardwareConfig->SupportsCascadedShadowMapping();
|
|
int nCSMQualityComboValue = g_pHardwareConfig->GetCSMShaderMode( materials->GetCurrentConfigForVideoCard().GetCSMQualityMode() );
|
|
|
|
if ( iCompositeMode == MODE_2D_COMPOSITE || !bCSMEnabled || params[ AOPASS ]->GetIntValue() > 0 )
|
|
{
|
|
bCSMEnabled = false;
|
|
nCSMQualityComboValue = 0;
|
|
}
|
|
|
|
if ( params[ AOPASS ]->GetIntValue() > 0 )
|
|
{
|
|
bUsePattern1 = false;
|
|
bUsePattern2 = false;
|
|
bUsePatternOffset = false;
|
|
bUseLogo1 = false;
|
|
bUseLogo2 = false;
|
|
bSwapPatternMasks = false;
|
|
}
|
|
|
|
if( g_pHardwareConfig->SupportsPixelShaders_3_0() )
|
|
{
|
|
DECLARE_STATIC_PIXEL_SHADER( customclothing_ps30 );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( CASCADED_SHADOW_MAPPING, bCSMEnabled );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( COMPOSITEMODE, iCompositeMode );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( CSM_MODE, nCSMQualityComboValue );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( USE_PATTERN1, bUsePattern1 );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( USE_PATTERN2, bUsePattern2 );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( USE_PATTERN_OFFSET, bUsePatternOffset );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( USE_LOGO1, bUseLogo1 );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( USE_LOGO2, bUseLogo2 );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( SWAP_PATTERN_MASKS, bSwapPatternMasks );
|
|
SET_STATIC_PIXEL_SHADER( customclothing_ps30 );
|
|
}
|
|
else
|
|
{
|
|
DECLARE_STATIC_PIXEL_SHADER( customclothing_ps20b );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( COMPOSITEMODE, iCompositeMode );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( USE_PATTERN1, bUsePattern1 );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( USE_PATTERN2, bUsePattern2 );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( USE_PATTERN_OFFSET, bUsePatternOffset );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( USE_LOGO1, bUseLogo1 );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( USE_LOGO2, bUseLogo2 );
|
|
SET_STATIC_PIXEL_SHADER_COMBO( SWAP_PATTERN_MASKS, bSwapPatternMasks );
|
|
SET_STATIC_PIXEL_SHADER( customclothing_ps20b );
|
|
}
|
|
|
|
pShaderShadow->EnableAlphaWrites( true );
|
|
pShaderShadow->EnableDepthWrites( true );
|
|
pShaderShadow->EnableSRGBWrite( true );
|
|
pShaderShadow->EnableBlending( false ); // important for csm shadows
|
|
pShaderShadow->EnableAlphaTest( true ); // for ghillie suits and other leafy things
|
|
|
|
if ( iCompositeMode != MODE_2D_COMPOSITE )
|
|
{
|
|
PI_BeginCommandBuffer();
|
|
PI_SetPixelShaderAmbientLightCube( PSREG_AMBIENT_CUBE );
|
|
PI_SetPixelShaderLocalLighting( PSREG_LIGHT_INFO_ARRAY );
|
|
//pShader->PI_SetModulationPixelShaderDynamicState_LinearColorSpace( 1 );
|
|
PI_EndCommandBuffer();
|
|
}
|
|
|
|
}
|
|
DYNAMIC_STATE
|
|
{
|
|
pShaderAPI->SetDefaultState();
|
|
|
|
SetVertexShaderTextureTransform( VERTEX_SHADER_SHADER_SPECIFIC_CONST_0, BASETEXTURETRANSFORM );
|
|
|
|
int iCompositeMode = params[ COMPOSITEMODE ]->GetIntValue();
|
|
|
|
if ( params[AOPASS]->GetIntValue() != 1 )
|
|
{
|
|
if ( params[BASETEXTURE]->IsDefined() ) { BindTexture( SHADER_SAMPLER0, TEXTURE_BINDFLAGS_SRGBREAD, BASETEXTURE, -1 ); }
|
|
}
|
|
|
|
if ( params[BUMPMAP]->IsDefined() ) { BindTexture( SHADER_SAMPLER1, TEXTURE_BINDFLAGS_NONE, BUMPMAP, -1 ); }
|
|
|
|
if ( iCompositeMode == MODE_3D_POSTCOMPOSITE )
|
|
{
|
|
//TEXTURE_BINDFLAGS_SHADOWDEPTH
|
|
if ( params[AOSCREENBUFFER]->IsDefined() ) { BindTexture( SHADER_SAMPLER10, TEXTURE_BINDFLAGS_NONE, AOSCREENBUFFER, -1 ); }
|
|
}
|
|
|
|
if ( iCompositeMode == MODE_2D_COMPOSITE || iCompositeMode == MODE_3D_PREVIEW )
|
|
{
|
|
if ( params[AOMAP]->IsDefined() ) { BindTexture( SHADER_SAMPLER2, TEXTURE_BINDFLAGS_NONE, AOMAP, -1 ); }
|
|
if ( params[MASKMAP]->IsDefined() ) { BindTexture( SHADER_SAMPLER3, TEXTURE_BINDFLAGS_NONE, MASKMAP, -1 ); }
|
|
if ( params[PATTERN1]->IsDefined() ) { BindTexture( SHADER_SAMPLER4, TEXTURE_BINDFLAGS_NONE, PATTERN1, -1 ); }
|
|
if ( params[PATTERN2]->IsDefined() ) { BindTexture( SHADER_SAMPLER6, TEXTURE_BINDFLAGS_NONE, PATTERN2, -1 ); }
|
|
if ( params[GRIME]->IsDefined() ) { BindTexture( SHADER_SAMPLER7, TEXTURE_BINDFLAGS_NONE, GRIME, -1 ); }
|
|
if ( params[OFFSETMAP]->IsDefined() ) { BindTexture( SHADER_SAMPLER8, TEXTURE_BINDFLAGS_NONE, OFFSETMAP, -1 ); }
|
|
if ( params[LOGOMAP]->IsDefined() ) { BindTexture( SHADER_SAMPLER9, TEXTURE_BINDFLAGS_SRGBREAD, LOGOMAP, -1 ); }
|
|
|
|
|
|
float c0[4] = { SrgbGammaToLinear( params[PATTERN1COLOR1]->GetVecValue()[0] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN1COLOR1]->GetVecValue()[1] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN1COLOR1]->GetVecValue()[2] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN1COLOR4]->GetVecValue()[0] / 255.0 ) };
|
|
|
|
float c1[4] = { SrgbGammaToLinear( params[PATTERN1COLOR2]->GetVecValue()[0] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN1COLOR2]->GetVecValue()[1] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN1COLOR2]->GetVecValue()[2] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN1COLOR4]->GetVecValue()[1] / 255.0 ) };
|
|
|
|
float c2[4] = { SrgbGammaToLinear( params[PATTERN1COLOR3]->GetVecValue()[0] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN1COLOR3]->GetVecValue()[1] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN1COLOR3]->GetVecValue()[2] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN1COLOR4]->GetVecValue()[2] / 255.0 ) };
|
|
|
|
pShaderAPI->SetPixelShaderConstant( 0, c0, 1 );
|
|
pShaderAPI->SetPixelShaderConstant( 1, c1, 1 );
|
|
pShaderAPI->SetPixelShaderConstant( 2, c2, 1 );
|
|
|
|
float c10[4] = { SrgbGammaToLinear( params[PATTERN2COLOR1]->GetVecValue()[0] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN2COLOR1]->GetVecValue()[1] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN2COLOR1]->GetVecValue()[2] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN2COLOR4]->GetVecValue()[0] / 255.0 ) };
|
|
|
|
float c11[4] = { SrgbGammaToLinear( params[PATTERN2COLOR2]->GetVecValue()[0] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN2COLOR2]->GetVecValue()[1] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN2COLOR2]->GetVecValue()[2] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN2COLOR4]->GetVecValue()[1] / 255.0 ) };
|
|
|
|
float c12[4] = { SrgbGammaToLinear( params[PATTERN2COLOR3]->GetVecValue()[0] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN2COLOR3]->GetVecValue()[1] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN2COLOR3]->GetVecValue()[2] / 255.0 ),
|
|
SrgbGammaToLinear( params[PATTERN2COLOR4]->GetVecValue()[2] / 255.0 ) };
|
|
|
|
pShaderAPI->SetPixelShaderConstant( 10, c10, 1 );
|
|
pShaderAPI->SetPixelShaderConstant( 11, c11, 1 );
|
|
pShaderAPI->SetPixelShaderConstant( 12, c12, 1 );
|
|
|
|
float c13[4] = { params[PATTERN1SCALE]->GetFloatValue(),
|
|
params[PATTERN2SCALE]->GetFloatValue(),
|
|
params[CAVITYCONTRAST]->GetFloatValue(),
|
|
params[OFFSETAMOUNT]->GetFloatValue() };
|
|
pShaderAPI->SetPixelShaderConstant( 13, c13, 1 );
|
|
|
|
float c14[4] = { params[LOGOX]->GetFloatValue(),
|
|
params[LOGOY]->GetFloatValue(),
|
|
params[LOGOSCALE]->GetFloatValue(),
|
|
params[LOGOROTATE]->GetFloatValue() };
|
|
pShaderAPI->SetPixelShaderConstant( 14, c14, 1 );
|
|
|
|
float c15[4] = { params[LOGO2X]->GetFloatValue(),
|
|
params[LOGO2Y]->GetFloatValue(),
|
|
params[LOGO2SCALE]->GetFloatValue(),
|
|
params[LOGO2ROTATE]->GetFloatValue() };
|
|
pShaderAPI->SetPixelShaderConstant( 15, c15, 1 );
|
|
|
|
float c16[4] = { 0.5f - params[LOGOMASKCRISP]->GetFloatValue(),
|
|
0.5f + params[LOGOMASKCRISP]->GetFloatValue(),
|
|
params[LOGOWEAR]->GetFloatValue(),
|
|
0 };
|
|
pShaderAPI->SetPixelShaderConstant( 16, c16, 1 );
|
|
|
|
}
|
|
|
|
bool bAOPrePass = params[ AOPASS ]->GetIntValue() > 0;
|
|
|
|
if ( iCompositeMode != MODE_2D_COMPOSITE )
|
|
{
|
|
pShaderAPI->BindStandardTexture( SHADER_SAMPLER5, TEXTURE_BINDFLAGS_NONE, TEXTURE_NORMALIZATION_CUBEMAP_SIGNED );
|
|
|
|
float c18[4];
|
|
pShaderAPI->GetWorldSpaceCameraPosition( c18 );
|
|
|
|
if ( bAOPrePass )
|
|
{
|
|
Vector vecWorldSpaceCamPos = Vector( c18[0], c18[1], c18[2] );
|
|
Vector vecEntityCenter = Vector( params[ ENTCENTER ]->GetVecValue()[0], params[ ENTCENTER ]->GetVecValue()[1], params[ ENTCENTER ]->GetVecValue()[2] );
|
|
c18[3] = (vecWorldSpaceCamPos - vecEntityCenter).Length();
|
|
}
|
|
else
|
|
{
|
|
c18[3] = 0;
|
|
}
|
|
|
|
pShaderAPI->SetPixelShaderConstant( 18, c18, 1 );
|
|
|
|
}
|
|
|
|
if ( iCompositeMode == MODE_3D_POSTCOMPOSITE )
|
|
{
|
|
// Get viewport and render target dimensions and set shader constant to do a 2D mad
|
|
int nViewportX, nViewportY, nViewportWidth, nViewportHeight;
|
|
pShaderAPI->GetCurrentViewport( nViewportX, nViewportY, nViewportWidth, nViewportHeight );
|
|
|
|
int nRtWidth, nRtHeight;
|
|
pShaderAPI->GetCurrentRenderTargetDimensions( nRtWidth, nRtHeight );
|
|
|
|
// Compute viewport mad that takes projection space coords (post divide by W) into normalized screenspace, taking into account the currently set viewport.
|
|
float vViewportMad[4];
|
|
vViewportMad[0] = .5f * ( ( float )nViewportWidth / ( float )nRtWidth );
|
|
vViewportMad[1] = -.5f * ( ( float )nViewportHeight / ( float )nRtHeight );
|
|
vViewportMad[2] = vViewportMad[0] + ( ( float )nViewportX / ( float )nRtWidth );
|
|
vViewportMad[3] = -vViewportMad[1] + ( ( float )nViewportY / ( float )nRtHeight );
|
|
pShaderAPI->SetPixelShaderConstant( 17, vViewportMad, 1 );
|
|
}
|
|
|
|
|
|
int nNumLights = 0;
|
|
if ( !bAOPrePass && iCompositeMode != MODE_2D_COMPOSITE )
|
|
{
|
|
LightState_t lightState = {0, false, false};
|
|
pShaderAPI->GetDX9LightState( &lightState );
|
|
nNumLights = lightState.m_nNumLights;
|
|
}
|
|
|
|
if( g_pHardwareConfig->SupportsPixelShaders_3_0() )
|
|
{
|
|
DECLARE_DYNAMIC_VERTEX_SHADER( customclothing_vs30 );
|
|
SET_DYNAMIC_VERTEX_SHADER_COMBO( SKINNING, pShaderAPI->GetCurrentNumBones() > 0 );
|
|
SET_DYNAMIC_VERTEX_SHADER_COMBO( COMPRESSED_VERTS, (int)vertexCompression );
|
|
SET_DYNAMIC_VERTEX_SHADER_COMBO( NUM_LIGHTS, nNumLights );
|
|
SET_DYNAMIC_VERTEX_SHADER( customclothing_vs30 );
|
|
}
|
|
else
|
|
{
|
|
DECLARE_DYNAMIC_VERTEX_SHADER( customclothing_vs20 );
|
|
SET_DYNAMIC_VERTEX_SHADER_COMBO( SKINNING, pShaderAPI->GetCurrentNumBones() > 0 );
|
|
SET_DYNAMIC_VERTEX_SHADER_COMBO( COMPRESSED_VERTS, (int)vertexCompression );
|
|
SET_DYNAMIC_VERTEX_SHADER_COMBO( NUM_LIGHTS, nNumLights );
|
|
SET_DYNAMIC_VERTEX_SHADER( customclothing_vs20 );
|
|
}
|
|
|
|
bool bCSMEnabled = pShaderAPI->IsCascadedShadowMapping() && (iCompositeMode != MODE_2D_COMPOSITE);
|
|
if ( bCSMEnabled && !bAOPrePass )
|
|
{
|
|
ITexture *pDepthTextureAtlas = NULL;
|
|
const CascadedShadowMappingState_t &cascadeState = pShaderAPI->GetCascadedShadowMappingState( &pDepthTextureAtlas );
|
|
|
|
if ( pDepthTextureAtlas )
|
|
{
|
|
BindTexture( SHADER_SAMPLER15, TEXTURE_BINDFLAGS_SHADOWDEPTH, pDepthTextureAtlas, 0 );
|
|
|
|
//float vCSMTexParams[4] = { cascadeState.m_TexParams3.m_flDistLerpFactorBase, cascadeState.m_TexParams3.m_flDistLerpFactorInvRange, cascadeState.m_TexParams.m_flInvShadowTextureWidth, 0.0f };
|
|
//pShaderAPI->SetPixelShaderConstant( 17, &cascadeState.m_vCamPosition.x, 1 );
|
|
//pShaderAPI->SetPixelShaderConstant( 18, vCSMTexParams, 1 );
|
|
|
|
pShaderAPI->SetPixelShaderConstant( 64, &cascadeState.m_vLightColor.x, CASCADED_SHADOW_MAPPING_CONSTANT_BUFFER_SIZE );
|
|
}
|
|
}
|
|
|
|
if( g_pHardwareConfig->SupportsPixelShaders_3_0() )
|
|
{
|
|
DECLARE_DYNAMIC_PIXEL_SHADER( customclothing_ps30 );
|
|
SET_DYNAMIC_PIXEL_SHADER_COMBO( NUM_LIGHTS, nNumLights );
|
|
SET_DYNAMIC_PIXEL_SHADER_COMBO( DYN_CSM_ENABLED, bCSMEnabled && !bAOPrePass );
|
|
SET_DYNAMIC_PIXEL_SHADER_COMBO( AO_MODE, bAOPrePass );
|
|
SET_DYNAMIC_PIXEL_SHADER( customclothing_ps30 );
|
|
}
|
|
else
|
|
{
|
|
DECLARE_DYNAMIC_PIXEL_SHADER( customclothing_ps20b );
|
|
SET_DYNAMIC_PIXEL_SHADER_COMBO( NUM_LIGHTS, nNumLights );
|
|
SET_DYNAMIC_PIXEL_SHADER_COMBO( DYN_CSM_ENABLED, 0 );
|
|
SET_DYNAMIC_PIXEL_SHADER_COMBO( AO_MODE, bAOPrePass );
|
|
SET_DYNAMIC_PIXEL_SHADER( customclothing_ps20b );
|
|
}
|
|
|
|
}
|
|
Draw();
|
|
}
|
|
|
|
SHADER_DRAW
|
|
{
|
|
DrawCustomClothing( params, pShaderShadow, pShaderAPI, vertexCompression );
|
|
}
|
|
|
|
void ExecuteFastPath( int *dynVSIdx, int *dynPSIdx, IMaterialVar** params, IShaderDynamicAPI * pShaderAPI,
|
|
VertexCompressionType_t vertexCompression, CBasePerMaterialContextData **pContextDataPtr, BOOL bCSMEnabled )
|
|
{
|
|
|
|
//only intended for csm shadow depth pass
|
|
|
|
DECLARE_DYNAMIC_VERTEX_SHADER( writez_vs20 );
|
|
SET_DYNAMIC_VERTEX_SHADER_COMBO( COMPRESSED_VERTS, (int)vertexCompression );
|
|
SET_DYNAMIC_VERTEX_SHADER_COMBO( SKINNING, pShaderAPI->GetCurrentNumBones() > 0 );
|
|
SET_DYNAMIC_VERTEX_SHADER( writez_vs20 );
|
|
|
|
*dynVSIdx = _vshIndex.GetIndex();
|
|
|
|
// No pixel shader on Direct3D, doubles fill rate
|
|
if ( IsOSXOpenGL() )
|
|
{
|
|
DECLARE_DYNAMIC_PIXEL_SHADER( white_ps20 );
|
|
SET_DYNAMIC_PIXEL_SHADER( white_ps20 );
|
|
*dynPSIdx = _pshIndex.GetIndex();
|
|
}
|
|
else
|
|
{
|
|
*dynPSIdx = 0;
|
|
}
|
|
}
|
|
|
|
bool IsTranslucent( IMaterialVar **params ) const
|
|
{
|
|
return false;
|
|
}
|
|
|
|
END_SHADER
|
|
|
|
|