mirror of
https://github.com/electronicarts/CnC_Generals_Zero_Hour.git
synced 2025-12-19 00:51:41 -05:00
Initial commit of Command & Conquer Generals and Command & Conquer Generals Zero Hour source code.
This commit is contained in:
@@ -0,0 +1,238 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shd6bumpdiff.cpp $*
|
||||
* *
|
||||
* $Org Author:: Kenny_m
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 7/11/02 10:36p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include "dx8fvf.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "assetmgr.h"
|
||||
#include "rinfo.h"
|
||||
#include "camera.h"
|
||||
|
||||
#include "shdbumpdiff.h"
|
||||
#include "shd6bumpdiff.h"
|
||||
#include "shd6bumpdiff_constants.h"
|
||||
#include "shdclassids.h"
|
||||
|
||||
// shader code declarations
|
||||
#include "shd6bumpdiff.vsh_code.h"
|
||||
|
||||
|
||||
ShdHWVertexShader Shd6BumpDiffClass::Vertex_Shader;
|
||||
Matrix4x4 Shd6BumpDiffClass::View_Projection_Matrix;
|
||||
|
||||
Shd6BumpDiffClass::Shd6BumpDiffClass(const ShdDefClass* def)
|
||||
: ShdInterfaceClass(def,SHDDEF_CLASSID_BUMPDIFF),
|
||||
Texture(NULL)
|
||||
{
|
||||
ShdBumpDiffDefClass* Definition=(ShdBumpDiffDefClass*)def;
|
||||
|
||||
Texture=WW3DAssetManager::Get_Instance()->Get_Texture
|
||||
(
|
||||
Definition->Get_Texture_Name()
|
||||
);
|
||||
|
||||
const Vector3& a=Definition->Get_Ambient();
|
||||
Ambient.Set(a.X,a.Y,a.Z,1.0f);
|
||||
|
||||
const Vector3& d=Definition->Get_Diffuse();
|
||||
Diffuse.Set(d.X,d.Y,d.Z,1.0f);
|
||||
}
|
||||
|
||||
Shd6BumpDiffClass::~Shd6BumpDiffClass()
|
||||
{
|
||||
REF_PTR_RELEASE(Texture);
|
||||
}
|
||||
|
||||
void Shd6BumpDiffClass::Init()
|
||||
{
|
||||
// Create vertex shader
|
||||
DWORD vertex_shader_declaration[]=
|
||||
{
|
||||
D3DVSD_STREAM(0),
|
||||
(D3DVSD_REG(0, D3DVSDT_FLOAT3)), // vertex position
|
||||
(D3DVSD_REG(1, D3DVSDT_FLOAT3)), // vertex normal
|
||||
(D3DVSD_REG(2, D3DVSDT_D3DCOLOR)), // vertex color
|
||||
(D3DVSD_REG(3, D3DVSDT_FLOAT2)), // vertex texture coords
|
||||
D3DVSD_END()
|
||||
};
|
||||
|
||||
Vertex_Shader.Create
|
||||
(
|
||||
shd6bumpdiff_vsh_code,
|
||||
vertex_shader_declaration
|
||||
);
|
||||
}
|
||||
|
||||
void Shd6BumpDiffClass::Shutdown()
|
||||
{
|
||||
Vertex_Shader.Destroy();
|
||||
}
|
||||
|
||||
|
||||
/**********************************************************************************************
|
||||
//! Apply shared states for 1 pass DX6 (no bump)
|
||||
/*! 7/10/02 5:39p KJM Created
|
||||
*/
|
||||
void Shd6BumpDiffClass::Apply_Shared(int pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
// vertex processing behavior
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_SOFTWAREVERTEXPROCESSING,!Vertex_Shader.Is_Using_Hardware());
|
||||
|
||||
// fixed function uses pass through by default
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_PASSTHRU);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_PASSTHRU);
|
||||
|
||||
// set vertex shader
|
||||
DX8Wrapper::Set_Vertex_Shader(Vertex_Shader.Peek_Shader());
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLOROP, D3DTOP_MODULATE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLOROP, D3DTOP_DISABLE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAOP, D3DTOP_DISABLE );
|
||||
|
||||
// set constants
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_CONST, D3DXVECTOR4(0.0f, 1.0f, 0.5f, 2.0f), 1);
|
||||
|
||||
// calculate shader view projection matrix
|
||||
Matrix4x4 view_matrix;
|
||||
DX8Wrapper::Get_Transform(D3DTS_VIEW, view_matrix);
|
||||
|
||||
Matrix4x4 proj_matrix;
|
||||
DX8Wrapper::Get_Transform(D3DTS_PROJECTION, proj_matrix);
|
||||
|
||||
Matrix4x4::Multiply(proj_matrix, view_matrix, &View_Projection_Matrix);
|
||||
}
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Apply per instance states for 1 pass DX6 specular with gloss map (no bump)
|
||||
/*! 7/10/02 5:39p KJM Created
|
||||
*/
|
||||
void Shd6BumpDiffClass::Apply_Instance(int cur_pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
DX8Wrapper::Set_Texture(0, Texture);
|
||||
|
||||
// set vertex shader constants
|
||||
Matrix4x4 world;
|
||||
DX8Wrapper::Get_Transform(D3DTS_WORLD, world);
|
||||
|
||||
Matrix4x4 world_view_proj_matrix;
|
||||
|
||||
Matrix4x4::Multiply(View_Projection_Matrix,world,&world_view_proj_matrix);
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_WORLD_VIEW_PROJECTION, &world_view_proj_matrix, 4);
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_WORLD, &world, 4);
|
||||
|
||||
ShdHWVertexShader::Light
|
||||
(
|
||||
rinfo,
|
||||
Ambient,
|
||||
Diffuse
|
||||
);
|
||||
}
|
||||
|
||||
unsigned Shd6BumpDiffClass::Get_Vertex_Stream_Count() const
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
unsigned Shd6BumpDiffClass::Get_Vertex_Size(unsigned stream) const
|
||||
{
|
||||
return sizeof(VertexFormatXYZNDUV1);
|
||||
}
|
||||
|
||||
void Shd6BumpDiffClass::Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
)
|
||||
{
|
||||
VertexFormatXYZNDUV1* verts=(VertexFormatXYZNDUV1*)dest_buffer;
|
||||
|
||||
for (unsigned i=0; i<vertex_count; ++i)
|
||||
{
|
||||
if (vss.Locations)
|
||||
{
|
||||
verts[i].x=vss.Locations[i][0];
|
||||
verts[i].y=vss.Locations[i][1];
|
||||
verts[i].z=vss.Locations[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].x=0.0f;
|
||||
verts[i].y=0.0f;
|
||||
verts[i].z=0.0f;
|
||||
}
|
||||
|
||||
if (vss.DiffuseInt)
|
||||
{
|
||||
verts[i].diffuse=vss.DiffuseInt[i];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].diffuse=0xffffffff;
|
||||
}
|
||||
|
||||
if (vss.Normals)
|
||||
{
|
||||
verts[i].nx=vss.Normals[i][0];
|
||||
verts[i].ny=vss.Normals[i][1];
|
||||
verts[i].nz=vss.Normals[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].nx=0.0f;
|
||||
verts[i].ny=0.0f;
|
||||
verts[i].nz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.UV[0])
|
||||
{
|
||||
verts[i].u1=vss.UV[0][i].U;
|
||||
verts[i].v1=vss.UV[0][i].V;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].u1=0.0f;
|
||||
verts[i].v1=0.0f;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,90 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shd6bumpdiff.h $*
|
||||
* *
|
||||
* $Org Author:: Kenny_m
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 7/11/02 10:36p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHD6BUMPDIFF_H
|
||||
#define SHD6BUMPDIFF_H
|
||||
|
||||
#ifndef SHDINTERFACE_H
|
||||
#include "shdinterface.h"
|
||||
#endif
|
||||
|
||||
#ifndef SHDHWSHADER_H
|
||||
#include "shdhwshader.h"
|
||||
#endif
|
||||
|
||||
|
||||
class Shd6BumpDiffClass : public ShdInterfaceClass
|
||||
{
|
||||
public:
|
||||
Shd6BumpDiffClass(const ShdDefClass* def);
|
||||
virtual ~Shd6BumpDiffClass();
|
||||
|
||||
static void Init();
|
||||
static void Shutdown();
|
||||
|
||||
virtual int Get_Pass_Count() { return 1; }
|
||||
|
||||
virtual int Get_Texture_Count() const { return 1; }
|
||||
virtual TextureClass* Peek_Texture(int idx) const { return Texture; }
|
||||
|
||||
virtual void Apply_Shared(int cur_pass, RenderInfoClass& rinfo);
|
||||
virtual void Apply_Instance(int cur_pass, RenderInfoClass& rinfo);
|
||||
|
||||
virtual unsigned Get_Vertex_Stream_Count() const;
|
||||
virtual unsigned Get_Vertex_Size(unsigned stream) const;
|
||||
virtual bool Use_HW_Vertex_Processing() const { return Vertex_Shader.Is_Using_Hardware(); }
|
||||
virtual void Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
);
|
||||
|
||||
protected:
|
||||
|
||||
static ShdHWVertexShader Vertex_Shader;
|
||||
static Matrix4x4 View_Projection_Matrix;
|
||||
|
||||
TextureClass* Texture;
|
||||
|
||||
Vector4 Ambient;
|
||||
Vector4 Diffuse;
|
||||
};
|
||||
|
||||
#endif // SHD6BUMPDIFF_H
|
||||
@@ -0,0 +1,84 @@
|
||||
//
|
||||
// Command & Conquer Generals Zero Hour(tm)
|
||||
// Copyright 2025 Electronic Arts Inc.
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
//
|
||||
|
||||
// DX6 vertex shader (no bump)
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
vs.1.1
|
||||
|
||||
#include "shdhw_constants.h"
|
||||
|
||||
#include "shd6bumpdiff_constants.h"
|
||||
|
||||
// In:
|
||||
// v0 - object space vertex position
|
||||
// v1 - object space normal
|
||||
// v2 - color
|
||||
// v3 - texture coords
|
||||
|
||||
// object space vertex position -> screen (early as possible for view clipping)
|
||||
dp4 oPos.x, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_0]
|
||||
dp4 oPos.y, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_1]
|
||||
dp4 oPos.z, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_2]
|
||||
dp4 oPos.w, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_3]
|
||||
|
||||
dp3 WORLD_NORMAL.x, V_NORMAL, c[CV_WORLD_0]
|
||||
dp3 WORLD_NORMAL.y, V_NORMAL, c[CV_WORLD_1]
|
||||
dp3 WORLD_NORMAL.z, V_NORMAL, c[CV_WORLD_2]
|
||||
|
||||
// Normalize the world normal vector
|
||||
dp3 WORLD_NORMAL.w, WORLD_NORMAL, WORLD_NORMAL
|
||||
rsq WORLD_NORMAL.w, WORLD_NORMAL.w
|
||||
mul WORLD_NORMAL, WORLD_NORMAL, WORLD_NORMAL.w
|
||||
|
||||
// calculate light 0 factor
|
||||
dp3 LIGHT_0.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_0] // L.N
|
||||
max LIGHT_0.w, LIGHT_0.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_0.w, LIGHT_0.w, c[CV_LIGHT_COLOR_0].w // light attentuation factor
|
||||
|
||||
// calculate light 1 factor
|
||||
dp3 LIGHT_1.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_1] // L.N
|
||||
max LIGHT_1.w, LIGHT_1.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_1.w, LIGHT_1.w, c[CV_LIGHT_COLOR_1].w // light attentuation factor
|
||||
|
||||
// calculate light 2 factor
|
||||
dp3 LIGHT_2.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_2] // L.N
|
||||
max LIGHT_2.w, LIGHT_2.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_2.w, LIGHT_2.w, c[CV_LIGHT_COLOR_2].w // light attentuation factor
|
||||
|
||||
// calculate light 3 factor
|
||||
dp3 LIGHT_3.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_3] // L.N
|
||||
max LIGHT_3.w, LIGHT_3.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_3.w, LIGHT_3.w, c[CV_LIGHT_COLOR_3].w // light attentuation factor
|
||||
|
||||
// accumulate light colors
|
||||
mul COL, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
mad COL, c[CV_LIGHT_COLOR_1], LIGHT_1.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_2], LIGHT_2.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_3], LIGHT_3.w, COL
|
||||
|
||||
// apply vertex color and diffuse and ambient material terms
|
||||
mul COL, COL, V_DIFFUSE
|
||||
mul COL, COL, c[CV_DIFFUSE]
|
||||
add oD0, COL, c[CV_AMBIENT]
|
||||
|
||||
|
||||
|
||||
mov oT0, V_TEXTURE
|
||||
|
||||
|
||||
@@ -0,0 +1,100 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
// bump diffuse shader constants (no bump)
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
#ifndef SHD6BUMPDIFF_CONSTANTS_H
|
||||
#define SHD6BUMPDIFF_CONSTANTS_H
|
||||
|
||||
// vertex shader macros
|
||||
|
||||
|
||||
#define CV_WORLD_VIEW_PROJECTION 1
|
||||
|
||||
#define CV_WORLD_VIEW_PROJECTION_0 1
|
||||
#define CV_WORLD_VIEW_PROJECTION_1 2
|
||||
#define CV_WORLD_VIEW_PROJECTION_2 3
|
||||
#define CV_WORLD_VIEW_PROJECTION_3 4
|
||||
|
||||
|
||||
//#define CV_WORLD_VIEW 5
|
||||
|
||||
//#define CV_WORLD_VIEW_0 5
|
||||
//#define CV_WORLD_VIEW_1 6
|
||||
//#define CV_WORLD_VIEW_2 7
|
||||
//#define CV_WORLD_VIEW_3 8
|
||||
|
||||
|
||||
//#define CV_WORLD_VIEW_INVERSE_TRANSPOSE 9
|
||||
|
||||
//#define CV_WORLD_VIEW_INVERSE_TRANSPOSE_0 9
|
||||
//#define CV_WORLD_VIEW_INVERSE_TRANSPOSE_1 10
|
||||
//#define CV_WORLD_VIEW_INVERSE_TRANSPOSE_2 11
|
||||
|
||||
|
||||
|
||||
#define CV_WORLD 12
|
||||
|
||||
#define CV_WORLD_0 12
|
||||
#define CV_WORLD_1 13
|
||||
#define CV_WORLD_2 14
|
||||
#define CV_WORLD_3 15
|
||||
|
||||
// 16-26 lighting constants
|
||||
|
||||
#define CV_BUMPINESS 27
|
||||
|
||||
#define CV_EYE_WORLD 28
|
||||
|
||||
|
||||
// inputs
|
||||
#define V_POSITION v0
|
||||
#define V_NORMAL v1
|
||||
#define V_DIFFUSE v2
|
||||
#define V_TEXTURE v3
|
||||
#define V_S v4
|
||||
#define V_T v5
|
||||
#define V_SxT v6
|
||||
|
||||
|
||||
// registers
|
||||
#define HALF_ANGLE r0
|
||||
#define S_WORLD r1
|
||||
#define T_WORLD r2
|
||||
#define SxT_WORLD r3
|
||||
#define LIGHT_LOCAL r4
|
||||
#define LIGHT_0 r5
|
||||
#define LIGHT_1 r6
|
||||
#define LIGHT_2 r7
|
||||
#define LIGHT_3 r8
|
||||
#define COL r9
|
||||
#define WORLD_VERTEX r10
|
||||
#define EYE_VECTOR r11
|
||||
|
||||
#define WORLD_NORMAL r1
|
||||
|
||||
|
||||
#define OUTPUT_REG r0
|
||||
|
||||
// texture stages
|
||||
#define TEX_CUBEMAP t0
|
||||
|
||||
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,280 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shd6bumpspec.cpp $*
|
||||
* *
|
||||
* $Org Author:: Kenny_m
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 7/11/02 10:36p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include "dx8fvf.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "assetmgr.h"
|
||||
#include "rinfo.h"
|
||||
#include "camera.h"
|
||||
|
||||
#include "shdbumpspec.h"
|
||||
#include "shd6bumpspec.h"
|
||||
#include "shd6bumpspec_constants.h"
|
||||
#include "shdclassids.h"
|
||||
|
||||
// shader code declarations
|
||||
#include "shd6bumpspec.vsh_code.h"
|
||||
|
||||
ShdHWVertexShader Shd6BumpSpecClass::Vertex_Shader;
|
||||
Matrix4x4 Shd6BumpSpecClass::View_Projection_Matrix;
|
||||
|
||||
Shd6BumpSpecClass::Shd6BumpSpecClass(const ShdDefClass* def)
|
||||
: ShdInterfaceClass(def,SHDDEF_CLASSID_BUMPSPEC),
|
||||
Texture(NULL)
|
||||
{
|
||||
ShdBumpSpecDefClass* Definition=(ShdBumpSpecDefClass*)def;
|
||||
|
||||
Texture=WW3DAssetManager::Get_Instance()->Get_Texture
|
||||
(
|
||||
Definition->Get_Texture_Name()
|
||||
);
|
||||
|
||||
const Vector3& a=Definition->Get_Ambient();
|
||||
Ambient.Set(a.X,a.Y,a.Z,1.0f);
|
||||
|
||||
const Vector3& d=Definition->Get_Diffuse();
|
||||
Diffuse.Set(d.X,d.Y,d.Z,1.0f);
|
||||
|
||||
const Vector3& s=Definition->Get_Specular();
|
||||
Specular.Set(s.X,s.Y,s.Z,1.0f);
|
||||
}
|
||||
|
||||
Shd6BumpSpecClass::~Shd6BumpSpecClass()
|
||||
{
|
||||
REF_PTR_RELEASE(Texture);
|
||||
}
|
||||
|
||||
void Shd6BumpSpecClass::Init()
|
||||
{
|
||||
// Create vertex shader
|
||||
DWORD vertex_shader_declaration[]=
|
||||
{
|
||||
D3DVSD_STREAM(0),
|
||||
(D3DVSD_REG(0, D3DVSDT_FLOAT3)), // vertex position
|
||||
(D3DVSD_REG(1, D3DVSDT_FLOAT3)), // vertex normal
|
||||
(D3DVSD_REG(2, D3DVSDT_D3DCOLOR)), // vertex color
|
||||
(D3DVSD_REG(3, D3DVSDT_FLOAT2)), // vertex texture coords
|
||||
D3DVSD_END()
|
||||
};
|
||||
|
||||
Vertex_Shader.Create
|
||||
(
|
||||
shd6bumpspec_vsh_code,
|
||||
vertex_shader_declaration
|
||||
);
|
||||
}
|
||||
|
||||
void Shd6BumpSpecClass::Shutdown()
|
||||
{
|
||||
Vertex_Shader.Destroy();
|
||||
}
|
||||
|
||||
|
||||
/**********************************************************************************************
|
||||
//! Apply shared states for 1 pass DX6 specular with gloss map (no bump)
|
||||
/*! 7/10/02 5:39p KJM Created
|
||||
*/
|
||||
void Shd6BumpSpecClass::Apply_Shared(int pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
// vertex processing behavior
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_SOFTWAREVERTEXPROCESSING,!Vertex_Shader.Is_Using_Hardware());
|
||||
|
||||
// fixed function uses pass through by default
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_PASSTHRU);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_PASSTHRU);
|
||||
|
||||
// set vertex shader
|
||||
DX8Wrapper::Set_Vertex_Shader(Vertex_Shader.Peek_Shader());
|
||||
|
||||
const Matrix3D& cam=rinfo.Camera.Get_Transform();
|
||||
|
||||
// set constants
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant
|
||||
(
|
||||
CV_EYE_WORLD,
|
||||
D3DXVECTOR4
|
||||
(
|
||||
cam.Get_X_Translation(),
|
||||
cam.Get_Y_Translation(),
|
||||
cam.Get_Z_Translation(),
|
||||
1.0f
|
||||
),
|
||||
1
|
||||
);
|
||||
|
||||
// set texture stage settings
|
||||
if (DX8Wrapper::Get_Current_Caps()->Support_ModAlphaAddClr())
|
||||
{
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLOROP, D3DTOP_MODULATE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_ALPHAARG1, D3DTA_TEXTURE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1 );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLORARG1, D3DTA_CURRENT );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLOROP, D3DTOP_MODULATEALPHA_ADDCOLOR);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLORARG2, D3DTA_SPECULAR );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAARG1, D3DTA_CURRENT);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1 );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(2, D3DTSS_COLOROP, D3DTOP_DISABLE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(2, D3DTSS_ALPHAOP, D3DTOP_DISABLE );
|
||||
}
|
||||
else
|
||||
{
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLOROP, D3DTOP_MODULATE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLOROP, D3DTOP_DISABLE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAOP, D3DTOP_DISABLE );
|
||||
}
|
||||
|
||||
// set constants
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_CONST, D3DXVECTOR4(0.0f, 1.0f, 0.5f, 2.0f), 1);
|
||||
|
||||
// calculate shader view projection matrix
|
||||
Matrix4x4 view_matrix;
|
||||
DX8Wrapper::Get_Transform(D3DTS_VIEW, view_matrix);
|
||||
|
||||
Matrix4x4 proj_matrix;
|
||||
DX8Wrapper::Get_Transform(D3DTS_PROJECTION, proj_matrix);
|
||||
|
||||
Matrix4x4::Multiply(proj_matrix, view_matrix, &View_Projection_Matrix);
|
||||
}
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Apply per instance states for 1 pass DX6 specular with gloss map (no bump)
|
||||
/*! 7/10/02 5:39p KJM Created
|
||||
*/
|
||||
void Shd6BumpSpecClass::Apply_Instance(int cur_pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
DX8Wrapper::Set_Texture(0, Texture);
|
||||
|
||||
// set vertex shader constants
|
||||
Matrix4x4 world;
|
||||
DX8Wrapper::Get_Transform(D3DTS_WORLD, world);
|
||||
|
||||
Matrix4x4 world_view_proj_matrix;
|
||||
|
||||
Matrix4x4::Multiply(View_Projection_Matrix,world,&world_view_proj_matrix);
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_WORLD_VIEW_PROJECTION, &world_view_proj_matrix, 4);
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_WORLD, &world, 4);
|
||||
|
||||
ShdHWVertexShader::Light
|
||||
(
|
||||
rinfo,
|
||||
Ambient,
|
||||
Diffuse,
|
||||
Specular
|
||||
);
|
||||
}
|
||||
|
||||
unsigned Shd6BumpSpecClass::Get_Vertex_Stream_Count() const
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
unsigned Shd6BumpSpecClass::Get_Vertex_Size(unsigned stream) const
|
||||
{
|
||||
return sizeof(VertexFormatXYZNDUV1);
|
||||
}
|
||||
|
||||
void Shd6BumpSpecClass::Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
)
|
||||
{
|
||||
VertexFormatXYZNDUV1* verts=(VertexFormatXYZNDUV1*)dest_buffer;
|
||||
|
||||
for (unsigned i=0; i<vertex_count; ++i)
|
||||
{
|
||||
if (vss.Locations)
|
||||
{
|
||||
verts[i].x=vss.Locations[i][0];
|
||||
verts[i].y=vss.Locations[i][1];
|
||||
verts[i].z=vss.Locations[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].x=0.0f;
|
||||
verts[i].y=0.0f;
|
||||
verts[i].z=0.0f;
|
||||
}
|
||||
|
||||
if (vss.DiffuseInt)
|
||||
{
|
||||
verts[i].diffuse=vss.DiffuseInt[i];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].diffuse=0xffffffff;
|
||||
}
|
||||
|
||||
if (vss.Normals)
|
||||
{
|
||||
verts[i].nx=vss.Normals[i][0];
|
||||
verts[i].ny=vss.Normals[i][1];
|
||||
verts[i].nz=vss.Normals[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].nx=0.0f;
|
||||
verts[i].ny=0.0f;
|
||||
verts[i].nz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.UV[0])
|
||||
{
|
||||
verts[i].u1=vss.UV[0][i].U;
|
||||
verts[i].v1=vss.UV[0][i].V;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].u1=0.0f;
|
||||
verts[i].v1=0.0f;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,91 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shd6bumpspec.h $*
|
||||
* *
|
||||
* $Org Author:: Kenny_m
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 7/11/02 10:36p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHD6BUMPSPEC_H
|
||||
#define SHD6BUMPSPEC_H
|
||||
|
||||
#ifndef SHDINTERFACE_H
|
||||
#include "shdinterface.h"
|
||||
#endif
|
||||
|
||||
#ifndef SHDHWSHADER_H
|
||||
#include "shdhwshader.h"
|
||||
#endif
|
||||
|
||||
|
||||
class Shd6BumpSpecClass : public ShdInterfaceClass
|
||||
{
|
||||
public:
|
||||
Shd6BumpSpecClass(const ShdDefClass* def);
|
||||
virtual ~Shd6BumpSpecClass();
|
||||
|
||||
static void Init();
|
||||
static void Shutdown();
|
||||
|
||||
virtual int Get_Pass_Count() { return 1; }
|
||||
|
||||
virtual int Get_Texture_Count() const { return 1; }
|
||||
virtual TextureClass* Peek_Texture(int idx) const { return Texture; }
|
||||
|
||||
virtual void Apply_Shared(int cur_pass, RenderInfoClass& rinfo);
|
||||
virtual void Apply_Instance(int cur_pass, RenderInfoClass& rinfo);
|
||||
|
||||
virtual unsigned Get_Vertex_Stream_Count() const;
|
||||
virtual unsigned Get_Vertex_Size(unsigned stream) const;
|
||||
virtual bool Use_HW_Vertex_Processing() const { return Vertex_Shader.Is_Using_Hardware(); }
|
||||
virtual void Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
);
|
||||
|
||||
protected:
|
||||
|
||||
static ShdHWVertexShader Vertex_Shader;
|
||||
static Matrix4x4 View_Projection_Matrix;
|
||||
|
||||
TextureClass* Texture;
|
||||
|
||||
Vector4 Ambient;
|
||||
Vector4 Diffuse;
|
||||
Vector4 Specular;
|
||||
};
|
||||
|
||||
#endif // SHD7BUMPSPEC_H
|
||||
@@ -0,0 +1,140 @@
|
||||
//
|
||||
// Command & Conquer Generals Zero Hour(tm)
|
||||
// Copyright 2025 Electronic Arts Inc.
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
//
|
||||
|
||||
// DX6 specular mask vertex shader (no bump)
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
vs.1.1
|
||||
|
||||
#include "shdhw_constants.h"
|
||||
|
||||
#include "shd6bumpspec_constants.h"
|
||||
|
||||
// In:
|
||||
// v0 - object space vertex position
|
||||
// v1 - object space normal
|
||||
// v2 - color
|
||||
// v3 - texture coords
|
||||
|
||||
// object space vertex position -> screen (early as possible for view clipping)
|
||||
dp4 oPos.x, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_0]
|
||||
dp4 oPos.y, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_1]
|
||||
dp4 oPos.z, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_2]
|
||||
dp4 oPos.w, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_3]
|
||||
|
||||
dp3 WORLD_NORMAL.x, V_NORMAL, c[CV_WORLD_0]
|
||||
dp3 WORLD_NORMAL.y, V_NORMAL, c[CV_WORLD_1]
|
||||
dp3 WORLD_NORMAL.z, V_NORMAL, c[CV_WORLD_2]
|
||||
|
||||
// Normalize the world normal vector
|
||||
dp3 WORLD_NORMAL.w, WORLD_NORMAL, WORLD_NORMAL
|
||||
rsq WORLD_NORMAL.w, WORLD_NORMAL.w
|
||||
mul WORLD_NORMAL, WORLD_NORMAL, WORLD_NORMAL.w
|
||||
|
||||
// calculate light 0 factor
|
||||
dp3 LIGHT_0.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_0] // L.N
|
||||
max LIGHT_0.w, LIGHT_0.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_0.w, LIGHT_0.w, c[CV_LIGHT_COLOR_0].w // light attentuation factor
|
||||
|
||||
// calculate light 1 factor
|
||||
dp3 LIGHT_1.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_1] // L.N
|
||||
max LIGHT_1.w, LIGHT_1.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_1.w, LIGHT_1.w, c[CV_LIGHT_COLOR_1].w // light attentuation factor
|
||||
|
||||
// calculate light 2 factor
|
||||
dp3 LIGHT_2.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_2] // L.N
|
||||
max LIGHT_2.w, LIGHT_2.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_2.w, LIGHT_2.w, c[CV_LIGHT_COLOR_2].w // light attentuation factor
|
||||
|
||||
// calculate light 3 factor
|
||||
dp3 LIGHT_3.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_3] // L.N
|
||||
max LIGHT_3.w, LIGHT_3.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_3.w, LIGHT_3.w, c[CV_LIGHT_COLOR_3].w // light attentuation factor
|
||||
|
||||
// accumulate light colors
|
||||
mul COL, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
mad COL, c[CV_LIGHT_COLOR_1], LIGHT_1.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_2], LIGHT_2.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_3], LIGHT_3.w, COL
|
||||
|
||||
// apply vertex color and diffuse and ambient material terms
|
||||
mul COL, COL, V_DIFFUSE
|
||||
mul COL, COL, c[CV_DIFFUSE]
|
||||
add oD0, COL, c[CV_AMBIENT]
|
||||
|
||||
|
||||
// calculate half angle
|
||||
// transform vertex position to world space
|
||||
// to calculate V, vector to viewer in world
|
||||
// space.
|
||||
dp4 WORLD_VERTEX.x, V_POSITION, c[CV_WORLD_0]
|
||||
dp4 WORLD_VERTEX.y, V_POSITION, c[CV_WORLD_1]
|
||||
dp4 WORLD_VERTEX.z, V_POSITION, c[CV_WORLD_2]
|
||||
//dp4 WORLD_VERTEX.w, V_POSITION, c[CV_WORLD_3]
|
||||
|
||||
// Half angle vector is (L+V)/||L+V|| or Normalize( L+V )
|
||||
// ||a|| is magnitude of a
|
||||
// L = vec to light from vertex point
|
||||
// V = vec to viewer from vertex point
|
||||
|
||||
// vertex position - eye position
|
||||
// eye position - vertex position
|
||||
add EYE_VECTOR, c[CV_EYE_WORLD], -WORLD_VERTEX.xyz
|
||||
|
||||
// Normalize the eye vector
|
||||
dp3 EYE_VECTOR.w, EYE_VECTOR, EYE_VECTOR
|
||||
rsq EYE_VECTOR.w, EYE_VECTOR.w
|
||||
mul EYE_VECTOR, EYE_VECTOR, EYE_VECTOR.w
|
||||
|
||||
// Add them to average & create half angle vector
|
||||
add HALF_ANGLE, c[CV_LIGHT_DIRECTION_0], EYE_VECTOR
|
||||
|
||||
|
||||
// Normalize the half angle vector
|
||||
dp3 HALF_ANGLE.w, HALF_ANGLE, HALF_ANGLE
|
||||
rsq HALF_ANGLE.w, HALF_ANGLE.w
|
||||
mul HALF_ANGLE, HALF_ANGLE, HALF_ANGLE.w
|
||||
|
||||
// calculate light 0 factor
|
||||
dp3 WORLD_NORMAL.x, V_NORMAL, c[CV_WORLD_0]
|
||||
dp3 WORLD_NORMAL.y, V_NORMAL, c[CV_WORLD_1]
|
||||
dp3 WORLD_NORMAL.z, V_NORMAL, c[CV_WORLD_2]
|
||||
|
||||
// Normalize the world normal vector
|
||||
dp3 WORLD_NORMAL.w, WORLD_NORMAL, WORLD_NORMAL
|
||||
rsq WORLD_NORMAL.w, WORLD_NORMAL.w
|
||||
mul WORLD_NORMAL, WORLD_NORMAL, WORLD_NORMAL.w
|
||||
|
||||
dp3 LIGHT_0.w, HALF_ANGLE, WORLD_NORMAL // N.H
|
||||
max LIGHT_0.w, LIGHT_0.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_0.w, LIGHT_0.w, c[CV_LIGHT_COLOR_0].w // light attentuation factor
|
||||
|
||||
// raise to 8th power
|
||||
mul LIGHT_0.w, LIGHT_0, LIGHT_0
|
||||
mul LIGHT_0.w, LIGHT_0, LIGHT_0
|
||||
mul LIGHT_0.w, LIGHT_0, LIGHT_0
|
||||
|
||||
// accumulate light colors
|
||||
mul COL, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
|
||||
mul oD1, COL, c[CV_SPECULAR]
|
||||
|
||||
|
||||
mov oT0, V_TEXTURE
|
||||
|
||||
|
||||
@@ -0,0 +1,100 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
// bump specular with gloss map shader constants (no bump)
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
#ifndef SHD6BUMPSPEC_CONSTANTS_H
|
||||
#define SHD6BUMPSPEC_CONSTANTS_H
|
||||
|
||||
// vertex shader macros
|
||||
|
||||
|
||||
#define CV_WORLD_VIEW_PROJECTION 1
|
||||
|
||||
#define CV_WORLD_VIEW_PROJECTION_0 1
|
||||
#define CV_WORLD_VIEW_PROJECTION_1 2
|
||||
#define CV_WORLD_VIEW_PROJECTION_2 3
|
||||
#define CV_WORLD_VIEW_PROJECTION_3 4
|
||||
|
||||
|
||||
//#define CV_WORLD_VIEW 5
|
||||
|
||||
//#define CV_WORLD_VIEW_0 5
|
||||
//#define CV_WORLD_VIEW_1 6
|
||||
//#define CV_WORLD_VIEW_2 7
|
||||
//#define CV_WORLD_VIEW_3 8
|
||||
|
||||
|
||||
//#define CV_WORLD_VIEW_INVERSE_TRANSPOSE 9
|
||||
|
||||
//#define CV_WORLD_VIEW_INVERSE_TRANSPOSE_0 9
|
||||
//#define CV_WORLD_VIEW_INVERSE_TRANSPOSE_1 10
|
||||
//#define CV_WORLD_VIEW_INVERSE_TRANSPOSE_2 11
|
||||
|
||||
|
||||
|
||||
#define CV_WORLD 12
|
||||
|
||||
#define CV_WORLD_0 12
|
||||
#define CV_WORLD_1 13
|
||||
#define CV_WORLD_2 14
|
||||
#define CV_WORLD_3 15
|
||||
|
||||
// 16-26 lighting constants
|
||||
|
||||
#define CV_BUMPINESS 27
|
||||
|
||||
#define CV_EYE_WORLD 28
|
||||
|
||||
|
||||
// inputs
|
||||
#define V_POSITION v0
|
||||
#define V_NORMAL v1
|
||||
#define V_DIFFUSE v2
|
||||
#define V_TEXTURE v3
|
||||
#define V_S v4
|
||||
#define V_T v5
|
||||
#define V_SxT v6
|
||||
|
||||
|
||||
// registers
|
||||
#define HALF_ANGLE r0
|
||||
#define S_WORLD r1
|
||||
#define T_WORLD r2
|
||||
#define SxT_WORLD r3
|
||||
#define LIGHT_LOCAL r4
|
||||
#define LIGHT_0 r5
|
||||
#define LIGHT_1 r6
|
||||
#define LIGHT_2 r7
|
||||
#define LIGHT_3 r8
|
||||
#define COL r9
|
||||
#define WORLD_VERTEX r10
|
||||
#define EYE_VECTOR r11
|
||||
|
||||
#define WORLD_NORMAL r1
|
||||
|
||||
|
||||
#define OUTPUT_REG r0
|
||||
|
||||
// texture stages
|
||||
#define TEX_CUBEMAP t0
|
||||
|
||||
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,350 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WW3D *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/ww3d2/shd7bumpdiff.cpp $*
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 6/06/02 11:18p $*
|
||||
* *
|
||||
* $Revision:: 2 $*
|
||||
* *
|
||||
* 06/06/02 KM added software vertex shader fallback check
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include "dx8fvf.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "assetmgr.h"
|
||||
#include "rinfo.h"
|
||||
#include "camera.h"
|
||||
#include "shdhwshader.h"
|
||||
|
||||
#include "shdbumpdiff.h"
|
||||
#include "shd7bumpdiff.h"
|
||||
#include "shd7bumpdiff_constants.h"
|
||||
#include "shdclassids.h"
|
||||
|
||||
// shader code declarations
|
||||
#include "shd7bumpdiffpass0.vsh_code.h"
|
||||
#include "shd7bumpdiffpass1.vsh_code.h"
|
||||
|
||||
|
||||
ShdHWVertexShader Shd7BumpDiffClass::Pass_0_Vertex_Shader;
|
||||
ShdHWVertexShader Shd7BumpDiffClass::Pass_1_Vertex_Shader;
|
||||
Matrix4x4 Shd7BumpDiffClass::View_Projection_Matrix;
|
||||
|
||||
|
||||
Shd7BumpDiffClass::Shd7BumpDiffClass(const ShdDefClass* def)
|
||||
: ShdInterfaceClass(def,SHDDEF_CLASSID_BUMPDIFF),
|
||||
Texture(NULL),
|
||||
NormalMap(NULL)
|
||||
{
|
||||
ShdBumpDiffDefClass* Definition=(ShdBumpDiffDefClass*)def;
|
||||
|
||||
Texture=WW3DAssetManager::Get_Instance()->Get_Texture
|
||||
(
|
||||
Definition->Get_Texture_Name()
|
||||
);
|
||||
|
||||
NormalMap=WW3DAssetManager::Get_Instance()->Get_Texture
|
||||
(
|
||||
Definition->Get_Bump_Map_Name()
|
||||
);
|
||||
|
||||
const Vector3& a=Definition->Get_Ambient();
|
||||
Ambient.Set(a.X,a.Y,a.Z,1.0f);
|
||||
|
||||
const Vector3& d=Definition->Get_Diffuse();
|
||||
Diffuse.Set(d.X,d.Y,d.Z,1.0f);
|
||||
|
||||
const Vector2& db=Definition->Get_Diffuse_Bumpiness();
|
||||
Bumpiness.Set(db.X,db.Y,0.0f,0.0f);
|
||||
}
|
||||
|
||||
Shd7BumpDiffClass::~Shd7BumpDiffClass()
|
||||
{
|
||||
REF_PTR_RELEASE(Texture);
|
||||
REF_PTR_RELEASE(NormalMap);
|
||||
}
|
||||
|
||||
void Shd7BumpDiffClass::Init()
|
||||
{
|
||||
// Create vertex shader
|
||||
DWORD vertex_shader_declaration[]=
|
||||
{
|
||||
D3DVSD_STREAM(0),
|
||||
(D3DVSD_REG(0, D3DVSDT_FLOAT3)), // vertex position
|
||||
(D3DVSD_REG(1, D3DVSDT_FLOAT3)), // vertex normal
|
||||
(D3DVSD_REG(2, D3DVSDT_D3DCOLOR)), // vertex color
|
||||
(D3DVSD_REG(3, D3DVSDT_FLOAT2)), // vertex texture coords
|
||||
(D3DVSD_REG(4, D3DVSDT_FLOAT3)), // vertex S basis
|
||||
(D3DVSD_REG(5, D3DVSDT_FLOAT3)), // vertex T basis
|
||||
(D3DVSD_REG(6, D3DVSDT_FLOAT3)), // vertex SxT basis
|
||||
D3DVSD_END()
|
||||
};
|
||||
|
||||
Pass_0_Vertex_Shader.Create
|
||||
(
|
||||
shd7bumpdiffpass0_vsh_code,
|
||||
vertex_shader_declaration
|
||||
);
|
||||
|
||||
Pass_1_Vertex_Shader.Create
|
||||
(
|
||||
shd7bumpdiffpass1_vsh_code,
|
||||
vertex_shader_declaration
|
||||
);
|
||||
}
|
||||
|
||||
void Shd7BumpDiffClass::Shutdown()
|
||||
{
|
||||
Pass_0_Vertex_Shader.Destroy();
|
||||
Pass_1_Vertex_Shader.Destroy();
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Apply shared states for 2 pass DX7 bump diffuse
|
||||
/*! 6/03/02 8:12a KJM Created
|
||||
*/
|
||||
void Shd7BumpDiffClass::Apply_Shared(int pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
// vertex processing behavior
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_SOFTWAREVERTEXPROCESSING,!Pass_0_Vertex_Shader.Is_Using_Hardware());
|
||||
|
||||
// fixed function uses pass through by default
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_PASSTHRU);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_PASSTHRU);
|
||||
|
||||
if (pass==0)
|
||||
{
|
||||
// set vertex shader
|
||||
DX8Wrapper::Set_Vertex_Shader(Pass_0_Vertex_Shader.Peek_Shader());
|
||||
|
||||
// set texture stage settings
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLOROP, D3DTOP_DOTPRODUCT3 );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_ALPHAARG1, D3DTA_CURRENT);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1 );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLORARG1, D3DTA_TEXTURE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLOROP, D3DTOP_MODULATE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLORARG2, D3DTA_SPECULAR );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAARG1, D3DTA_CURRENT);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAOP, D3DTOP_ADDSMOOTH );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAARG2, D3DTA_DIFFUSE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(2, D3DTSS_COLOROP, D3DTOP_DISABLE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(2, D3DTSS_ALPHAOP, D3DTOP_DISABLE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_ALPHABLENDENABLE, TRUE);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_DESTBLEND, D3DBLEND_ZERO);
|
||||
}
|
||||
else
|
||||
{
|
||||
// set vertex shader
|
||||
DX8Wrapper::Set_Vertex_Shader(Pass_1_Vertex_Shader.Peek_Shader());
|
||||
|
||||
// set texture stage settings
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLOROP, D3DTOP_DOTPRODUCT3 );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_ALPHAARG1, D3DTA_CURRENT);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1 );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLORARG1, D3DTA_TEXTURE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLOROP, D3DTOP_MODULATE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLORARG2, D3DTA_SPECULAR );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAARG1, D3DTA_CURRENT);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1 );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAARG2, D3DTA_DIFFUSE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(2, D3DTSS_COLOROP, D3DTOP_DISABLE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(2, D3DTSS_ALPHAOP, D3DTOP_DISABLE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_ALPHABLENDENABLE, TRUE);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_DESTBLEND, D3DBLEND_ONE);
|
||||
}
|
||||
|
||||
// set constants
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_CONST, D3DXVECTOR4(0.0f, 1.0f, 0.5f, 2.0f), 1);
|
||||
|
||||
// calculate shader view projection matrix
|
||||
Matrix4x4 view_matrix;
|
||||
DX8Wrapper::Get_Transform(D3DTS_VIEW, view_matrix);
|
||||
|
||||
Matrix4x4 proj_matrix;
|
||||
DX8Wrapper::Get_Transform(D3DTS_PROJECTION, proj_matrix);
|
||||
|
||||
Matrix4x4::Multiply(proj_matrix, view_matrix, &View_Projection_Matrix);
|
||||
}
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Apply per instance states for 2 pass DX7 bump diffuse
|
||||
/*! 6/03/02 8:12a KJM Created
|
||||
*/
|
||||
void Shd7BumpDiffClass::Apply_Instance(int cur_pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
DX8Wrapper::Set_Texture(0, NormalMap);
|
||||
DX8Wrapper::Set_Texture(1, Texture);
|
||||
|
||||
// set vertex shader constants
|
||||
Matrix4x4 world;
|
||||
DX8Wrapper::Get_Transform(D3DTS_WORLD, world);
|
||||
|
||||
Matrix4x4 world_view_proj_matrix;
|
||||
|
||||
Matrix4x4::Multiply(View_Projection_Matrix,world,&world_view_proj_matrix);
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_WORLD_VIEW_PROJECTION, &world_view_proj_matrix, 4);
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_WORLD, &world, 4);
|
||||
|
||||
ShdHWVertexShader::Light
|
||||
(
|
||||
rinfo,
|
||||
Ambient,
|
||||
Diffuse
|
||||
);
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_BUMPINESS, &Bumpiness, 1);
|
||||
}
|
||||
|
||||
unsigned Shd7BumpDiffClass::Get_Vertex_Stream_Count() const
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
unsigned Shd7BumpDiffClass::Get_Vertex_Size(unsigned stream) const
|
||||
{
|
||||
return sizeof(VertexFormatXYZNDUV1TG3);
|
||||
}
|
||||
|
||||
void Shd7BumpDiffClass::Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
)
|
||||
{
|
||||
VertexFormatXYZNDUV1TG3* verts=(VertexFormatXYZNDUV1TG3*)dest_buffer;
|
||||
|
||||
for (unsigned i=0; i<vertex_count; ++i)
|
||||
{
|
||||
if (vss.Locations)
|
||||
{
|
||||
verts[i].x=vss.Locations[i][0];
|
||||
verts[i].y=vss.Locations[i][1];
|
||||
verts[i].z=vss.Locations[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].x=0.0f;
|
||||
verts[i].y=0.0f;
|
||||
verts[i].z=0.0f;
|
||||
}
|
||||
|
||||
if (vss.DiffuseInt)
|
||||
{
|
||||
verts[i].diffuse=vss.DiffuseInt[i];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].diffuse=0xffffffff;
|
||||
}
|
||||
|
||||
if (vss.Normals)
|
||||
{
|
||||
verts[i].nx=vss.Normals[i][0];
|
||||
verts[i].ny=vss.Normals[i][1];
|
||||
verts[i].nz=vss.Normals[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].nx=0.0f;
|
||||
verts[i].ny=0.0f;
|
||||
verts[i].nz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.UV[0])
|
||||
{
|
||||
verts[i].u1=vss.UV[0][i].U;
|
||||
verts[i].v1=vss.UV[0][i].V;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].u1=0.0f;
|
||||
verts[i].v1=0.0f;
|
||||
}
|
||||
|
||||
if (vss.S)
|
||||
{
|
||||
verts[i].Sx=vss.S[i].X;
|
||||
verts[i].Sy=vss.S[i].Y;
|
||||
verts[i].Sz=vss.S[i].Z;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].Sx=0.0f;
|
||||
verts[i].Sy=0.0f;
|
||||
verts[i].Sz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.T)
|
||||
{
|
||||
verts[i].Tx=vss.T[i].X;
|
||||
verts[i].Ty=vss.T[i].Y;
|
||||
verts[i].Tz=vss.T[i].Z;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].Tx=0.0f;
|
||||
verts[i].Ty=0.0f;
|
||||
verts[i].Tz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.SxT)
|
||||
{
|
||||
verts[i].SxTx=vss.SxT[i].X;
|
||||
verts[i].SxTy=vss.SxT[i].Y;
|
||||
verts[i].SxTz=vss.SxT[i].Z;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].SxTx=0.0f;
|
||||
verts[i].SxTy=0.0f;
|
||||
verts[i].SxTz=0.0f;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,92 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WW3D *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/ww3d2/shd7bumpdiff.h $*
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 6/03/02 8:12a $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHD7BUMPDIFF_H
|
||||
#define SHD7BUMPDIFF_H
|
||||
|
||||
#ifndef SHDINTERFACE_H
|
||||
#include "shdinterface.h"
|
||||
#endif
|
||||
|
||||
#ifndef SHDHWSHADER_H
|
||||
#include "shdhwshader.h"
|
||||
#endif
|
||||
|
||||
|
||||
class Shd7BumpDiffClass : public ShdInterfaceClass
|
||||
{
|
||||
public:
|
||||
Shd7BumpDiffClass(const ShdDefClass* def);
|
||||
virtual ~Shd7BumpDiffClass();
|
||||
|
||||
static void Init();
|
||||
static void Shutdown();
|
||||
|
||||
virtual int Get_Pass_Count() { return 2; }
|
||||
|
||||
virtual int Get_Texture_Count() const { return 2; }
|
||||
virtual TextureClass* Peek_Texture(int idx) const { return idx==0 ? Texture : NormalMap; }
|
||||
|
||||
virtual void Apply_Shared(int cur_pass, RenderInfoClass& rinfo);
|
||||
virtual void Apply_Instance(int cur_pass, RenderInfoClass& rinfo);
|
||||
|
||||
virtual unsigned Get_Vertex_Stream_Count() const;
|
||||
virtual unsigned Get_Vertex_Size(unsigned stream) const;
|
||||
virtual bool Use_HW_Vertex_Processing() const { return Pass_0_Vertex_Shader.Is_Using_Hardware(); }
|
||||
virtual void Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
);
|
||||
|
||||
protected:
|
||||
|
||||
static ShdHWVertexShader Pass_0_Vertex_Shader;
|
||||
static ShdHWVertexShader Pass_1_Vertex_Shader;
|
||||
|
||||
static Matrix4x4 View_Projection_Matrix;
|
||||
|
||||
TextureClass* Texture;
|
||||
TextureClass* NormalMap;
|
||||
|
||||
Vector4 Ambient;
|
||||
Vector4 Diffuse;
|
||||
Vector4 Bumpiness;
|
||||
};
|
||||
|
||||
#endif // SHD7BUMPDIFF_H
|
||||
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
// bump diffuse map shader constants
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
#ifndef SHD7BUMPDIFF_CONSTANTS_H
|
||||
#define SHD7BUMPDIFF_CONSTANTS_H
|
||||
|
||||
// vertex shader macros
|
||||
|
||||
#define CV_WORLD_VIEW_PROJECTION 1
|
||||
|
||||
#define CV_WORLD_VIEW_PROJECTION_0 1
|
||||
#define CV_WORLD_VIEW_PROJECTION_1 2
|
||||
#define CV_WORLD_VIEW_PROJECTION_2 3
|
||||
#define CV_WORLD_VIEW_PROJECTION_3 4
|
||||
|
||||
// 5-11 world view & world view inverse transpose
|
||||
|
||||
#define CV_WORLD 12
|
||||
|
||||
#define CV_WORLD_0 12
|
||||
#define CV_WORLD_1 13
|
||||
#define CV_WORLD_2 14
|
||||
#define CV_WORLD_3 15
|
||||
|
||||
// 16-26 lighting constants
|
||||
|
||||
#define CV_BUMPINESS 27
|
||||
|
||||
#define CV_EYE_WORLD 28
|
||||
|
||||
|
||||
// inputs
|
||||
#define V_POSITION v0
|
||||
#define V_NORMAL v1
|
||||
#define V_DIFFUSE v2
|
||||
#define V_TEXTURE v3
|
||||
#define V_S v4
|
||||
#define V_T v5
|
||||
#define V_SxT v6
|
||||
|
||||
|
||||
// registers
|
||||
#define HALF_ANGLE r0
|
||||
#define S_WORLD r1
|
||||
#define T_WORLD r2
|
||||
#define SxT_WORLD r3
|
||||
#define LIGHT_LOCAL r4
|
||||
#define LIGHT_0 r5
|
||||
#define LIGHT_1 r6
|
||||
#define LIGHT_2 r7
|
||||
#define LIGHT_3 r8
|
||||
#define COL r9
|
||||
#define WORLD_VERTEX r10
|
||||
#define EYE_VECTOR r11
|
||||
|
||||
#define WORLD_NORMAL r1
|
||||
|
||||
|
||||
#define OUTPUT_REG r0
|
||||
|
||||
// texture stages
|
||||
#define TEX_CUBEMAP t0
|
||||
|
||||
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,120 @@
|
||||
//
|
||||
// Command & Conquer Generals Zero Hour(tm)
|
||||
// Copyright 2025 Electronic Arts Inc.
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
//
|
||||
|
||||
// DX7 bump diffuse vertex shader pass 0
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
vs.1.1
|
||||
|
||||
#include "shdhw_constants.h"
|
||||
|
||||
#include "shd7bumpdiff_constants.h"
|
||||
|
||||
// In:
|
||||
// v0 - object space vertex position
|
||||
// v1 - object space normal
|
||||
// v2 - color
|
||||
// v3 - texture coords
|
||||
// v4 - S basis
|
||||
// v5 - T basis
|
||||
// v6 - SxT
|
||||
|
||||
// object space vertex position -> screen (early as possible for view clipping)
|
||||
dp4 oPos.x, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_0]
|
||||
dp4 oPos.y, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_1]
|
||||
dp4 oPos.z, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_2]
|
||||
dp4 oPos.w, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_3]
|
||||
|
||||
// Transform basis vectors to world space
|
||||
dp3 S_WORLD.x, V_S, c[CV_WORLD_0]
|
||||
dp3 S_WORLD.y, V_S, c[CV_WORLD_1]
|
||||
dp3 S_WORLD.z, V_S, c[CV_WORLD_2]
|
||||
|
||||
dp3 T_WORLD.x, V_T, c[CV_WORLD_0]
|
||||
dp3 T_WORLD.y, V_T, c[CV_WORLD_1]
|
||||
dp3 T_WORLD.z, V_T, c[CV_WORLD_2]
|
||||
|
||||
dp3 SxT_WORLD.x, V_SxT, c[CV_WORLD_0]
|
||||
dp3 SxT_WORLD.y, V_SxT, c[CV_WORLD_1]
|
||||
dp3 SxT_WORLD.z, V_SxT, c[CV_WORLD_2]
|
||||
|
||||
// transform light 0 by basis vectors to put it into texture space
|
||||
dp3 LIGHT_LOCAL.x, S_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
dp3 LIGHT_LOCAL.y, T_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
dp3 LIGHT_LOCAL.z, SxT_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
|
||||
// Normalize the light vector
|
||||
dp3 LIGHT_LOCAL.w, LIGHT_LOCAL, LIGHT_LOCAL
|
||||
rsq LIGHT_LOCAL.w, LIGHT_LOCAL.w
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, LIGHT_LOCAL.w
|
||||
|
||||
dp3 WORLD_NORMAL.x, V_NORMAL, c[CV_WORLD_0]
|
||||
dp3 WORLD_NORMAL.y, V_NORMAL, c[CV_WORLD_1]
|
||||
dp3 WORLD_NORMAL.z, V_NORMAL, c[CV_WORLD_2]
|
||||
|
||||
// Normalize the world normal vector
|
||||
dp3 WORLD_NORMAL.w, WORLD_NORMAL, WORLD_NORMAL
|
||||
rsq WORLD_NORMAL.w, WORLD_NORMAL.w
|
||||
mul WORLD_NORMAL, WORLD_NORMAL, WORLD_NORMAL.w
|
||||
|
||||
// calculate light 0 factor
|
||||
dp3 LIGHT_0.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_0] // L.N
|
||||
max LIGHT_0.w, LIGHT_0.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_0.w, LIGHT_0.w, c[CV_LIGHT_COLOR_0].w // light attentuation factor
|
||||
|
||||
// calculate light 1 factor
|
||||
dp3 LIGHT_1.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_1] // L.N
|
||||
max LIGHT_1.w, LIGHT_1.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_1.w, LIGHT_1.w, c[CV_LIGHT_COLOR_1].w // light attentuation factor
|
||||
|
||||
// calculate light 2 factor
|
||||
dp3 LIGHT_2.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_2] // L.N
|
||||
max LIGHT_2.w, LIGHT_2.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_2.w, LIGHT_2.w, c[CV_LIGHT_COLOR_2].w // light attentuation factor
|
||||
|
||||
// calculate light 3 factor
|
||||
dp3 LIGHT_3.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_3] // L.N
|
||||
max LIGHT_3.w, LIGHT_3.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_3.w, LIGHT_3.w, c[CV_LIGHT_COLOR_3].w // light attentuation factor
|
||||
|
||||
// accumulate light colors
|
||||
mul COL, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
mad COL, c[CV_LIGHT_COLOR_1], LIGHT_1.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_2], LIGHT_2.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_3], LIGHT_3.w, COL
|
||||
|
||||
// apply vertex color and diffuse and ambient material terms
|
||||
mul COL, COL, V_DIFFUSE
|
||||
mul COL, COL, c[CV_DIFFUSE]
|
||||
add oD1, COL, c[CV_AMBIENT]
|
||||
|
||||
// Scale to 0-1
|
||||
add LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].yyy
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].zzz
|
||||
|
||||
// apply bump scale and bias controls
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_BUMPINESS].xxx
|
||||
add oD0, LIGHT_LOCAL, c[CV_BUMPINESS].yyy
|
||||
|
||||
// place negated bump light intensity in alpha channel
|
||||
add oD0.w, c[CV_CONST].y, -LIGHT_0.w
|
||||
|
||||
mov oT0, V_TEXTURE
|
||||
mov oT1, V_TEXTURE
|
||||
|
||||
|
||||
@@ -0,0 +1,120 @@
|
||||
//
|
||||
// Command & Conquer Generals Zero Hour(tm)
|
||||
// Copyright 2025 Electronic Arts Inc.
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
//
|
||||
|
||||
// DX7 bump diffuse vertex shader pass 1
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
vs.1.1
|
||||
|
||||
#include "shdhw_constants.h"
|
||||
|
||||
#include "shd7bumpdiff_constants.h"
|
||||
|
||||
// In:
|
||||
// v0 - object space vertex position
|
||||
// v1 - object space normal
|
||||
// v2 - color
|
||||
// v3 - texture coords
|
||||
// v4 - S basis
|
||||
// v5 - T basis
|
||||
// v6 - SxT
|
||||
|
||||
// object space vertex position -> screen (early as possible for view clipping)
|
||||
dp4 oPos.x, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_0]
|
||||
dp4 oPos.y, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_1]
|
||||
dp4 oPos.z, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_2]
|
||||
dp4 oPos.w, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_3]
|
||||
|
||||
// Transform basis vectors to world space
|
||||
dp3 S_WORLD.x, V_S, c[CV_WORLD_0]
|
||||
dp3 S_WORLD.y, V_S, c[CV_WORLD_1]
|
||||
dp3 S_WORLD.z, V_S, c[CV_WORLD_2]
|
||||
|
||||
dp3 T_WORLD.x, V_T, c[CV_WORLD_0]
|
||||
dp3 T_WORLD.y, V_T, c[CV_WORLD_1]
|
||||
dp3 T_WORLD.z, V_T, c[CV_WORLD_2]
|
||||
|
||||
dp3 SxT_WORLD.x, V_SxT, c[CV_WORLD_0]
|
||||
dp3 SxT_WORLD.y, V_SxT, c[CV_WORLD_1]
|
||||
dp3 SxT_WORLD.z, V_SxT, c[CV_WORLD_2]
|
||||
|
||||
// transform light 0 by basis vectors to put it into texture space
|
||||
dp3 LIGHT_LOCAL.x, S_WORLD.xyz, -c[CV_LIGHT_DIRECTION_0]
|
||||
dp3 LIGHT_LOCAL.y, T_WORLD.xyz, -c[CV_LIGHT_DIRECTION_0]
|
||||
dp3 LIGHT_LOCAL.z, SxT_WORLD.xyz, -c[CV_LIGHT_DIRECTION_0]
|
||||
|
||||
// Normalize the light vector
|
||||
dp3 LIGHT_LOCAL.w, LIGHT_LOCAL, LIGHT_LOCAL
|
||||
rsq LIGHT_LOCAL.w, LIGHT_LOCAL.w
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, LIGHT_LOCAL.w
|
||||
|
||||
dp3 WORLD_NORMAL.x, V_NORMAL, c[CV_WORLD_0]
|
||||
dp3 WORLD_NORMAL.y, V_NORMAL, c[CV_WORLD_1]
|
||||
dp3 WORLD_NORMAL.z, V_NORMAL, c[CV_WORLD_2]
|
||||
|
||||
// Normalize the world normal vector
|
||||
dp3 WORLD_NORMAL.w, WORLD_NORMAL, WORLD_NORMAL
|
||||
rsq WORLD_NORMAL.w, WORLD_NORMAL.w
|
||||
mul WORLD_NORMAL, WORLD_NORMAL, WORLD_NORMAL.w
|
||||
|
||||
// calculate light 0 factor
|
||||
dp3 LIGHT_0.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_0] // L.N
|
||||
max LIGHT_0.w, LIGHT_0.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_0.w, LIGHT_0.w, c[CV_LIGHT_COLOR_0].w // light attentuation factor
|
||||
|
||||
// calculate light 1 factor
|
||||
dp3 LIGHT_1.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_1] // L.N
|
||||
max LIGHT_1.w, LIGHT_1.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_1.w, LIGHT_1.w, c[CV_LIGHT_COLOR_1].w // light attentuation factor
|
||||
|
||||
// calculate light 2 factor
|
||||
dp3 LIGHT_2.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_2] // L.N
|
||||
max LIGHT_2.w, LIGHT_2.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_2.w, LIGHT_2.w, c[CV_LIGHT_COLOR_2].w // light attentuation factor
|
||||
|
||||
// calculate light 3 factor
|
||||
dp3 LIGHT_3.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_3] // L.N
|
||||
max LIGHT_3.w, LIGHT_3.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_3.w, LIGHT_3.w, c[CV_LIGHT_COLOR_3].w // light attentuation factor
|
||||
|
||||
// accumulate light colors
|
||||
mul COL, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
mad COL, c[CV_LIGHT_COLOR_1], LIGHT_1.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_2], LIGHT_2.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_3], LIGHT_3.w, COL
|
||||
|
||||
// apply vertex color and diffuse and ambient material terms
|
||||
mul COL, COL, V_DIFFUSE
|
||||
mul COL, COL, c[CV_DIFFUSE]
|
||||
add oD1, COL, c[CV_AMBIENT]
|
||||
|
||||
// Scale to 0-1
|
||||
add LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].yyy
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].zzz
|
||||
|
||||
// apply bump scale and bias controls
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_BUMPINESS].xxx
|
||||
add oD0, LIGHT_LOCAL, c[CV_BUMPINESS].yyy
|
||||
|
||||
// place negated bump light intensity in alpha channel
|
||||
add oD0.w, c[CV_CONST].y, -LIGHT_0.w
|
||||
|
||||
mov oT0, V_TEXTURE
|
||||
mov oT1, V_TEXTURE
|
||||
|
||||
|
||||
@@ -0,0 +1,374 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WW3D *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/ww3d2/shd7bumpspec.cpp $*
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 6/06/02 11:18p $*
|
||||
* *
|
||||
* $Revision:: 3 $*
|
||||
* *
|
||||
* 06/06/02 KM added software vertex shader fallback check
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include "dx8fvf.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "assetmgr.h"
|
||||
#include "rinfo.h"
|
||||
#include "camera.h"
|
||||
|
||||
#include "shdbumpspec.h"
|
||||
#include "shd7bumpspec.h"
|
||||
#include "shd7bumpspec_constants.h"
|
||||
#include "shdclassids.h"
|
||||
|
||||
// shader code declarations
|
||||
#include "shd7bumpspecpass0.vsh_code.h"
|
||||
#include "shd7bumpspecpass1.vsh_code.h"
|
||||
|
||||
ShdHWVertexShader Shd7BumpSpecClass::Pass_0_Vertex_Shader;
|
||||
ShdHWVertexShader Shd7BumpSpecClass::Pass_1_Vertex_Shader;
|
||||
Matrix4x4 Shd7BumpSpecClass::View_Projection_Matrix;
|
||||
|
||||
|
||||
Shd7BumpSpecClass::Shd7BumpSpecClass(const ShdDefClass* def)
|
||||
: ShdInterfaceClass(def,SHDDEF_CLASSID_BUMPSPEC),
|
||||
Texture(NULL),
|
||||
NormalMap(NULL)
|
||||
{
|
||||
ShdBumpSpecDefClass* Definition=(ShdBumpSpecDefClass*)def;
|
||||
|
||||
Texture=WW3DAssetManager::Get_Instance()->Get_Texture
|
||||
(
|
||||
Definition->Get_Texture_Name()
|
||||
);
|
||||
|
||||
NormalMap=WW3DAssetManager::Get_Instance()->Get_Texture
|
||||
(
|
||||
Definition->Get_Bump_Map_Name()
|
||||
);
|
||||
|
||||
const Vector3& a=Definition->Get_Ambient();
|
||||
Ambient.Set(a.X,a.Y,a.Z,1.0f);
|
||||
|
||||
const Vector3& d=Definition->Get_Diffuse();
|
||||
Diffuse.Set(d.X,d.Y,d.Z,1.0f);
|
||||
|
||||
const Vector3& s=Definition->Get_Specular();
|
||||
Specular.Set(s.X,s.Y,s.Z,1.0f);
|
||||
|
||||
const Vector2& db=Definition->Get_Diffuse_Bumpiness();
|
||||
const Vector2& ds=Definition->Get_Specular_Bumpiness();
|
||||
Bumpiness.Set(db.X,db.Y,ds.X,ds.Y);
|
||||
}
|
||||
|
||||
Shd7BumpSpecClass::~Shd7BumpSpecClass()
|
||||
{
|
||||
REF_PTR_RELEASE(Texture);
|
||||
REF_PTR_RELEASE(NormalMap);
|
||||
}
|
||||
|
||||
void Shd7BumpSpecClass::Init()
|
||||
{
|
||||
// Create vertex shader
|
||||
DWORD vertex_shader_declaration[]=
|
||||
{
|
||||
D3DVSD_STREAM(0),
|
||||
(D3DVSD_REG(0, D3DVSDT_FLOAT3)), // vertex position
|
||||
(D3DVSD_REG(1, D3DVSDT_FLOAT3)), // vertex normal
|
||||
(D3DVSD_REG(2, D3DVSDT_D3DCOLOR)), // vertex color
|
||||
(D3DVSD_REG(3, D3DVSDT_FLOAT2)), // vertex texture coords
|
||||
(D3DVSD_REG(4, D3DVSDT_FLOAT3)), // vertex S basis
|
||||
(D3DVSD_REG(5, D3DVSDT_FLOAT3)), // vertex T basis
|
||||
(D3DVSD_REG(6, D3DVSDT_FLOAT3)), // vertex SxT basis
|
||||
D3DVSD_END()
|
||||
};
|
||||
|
||||
Pass_0_Vertex_Shader.Create
|
||||
(
|
||||
shd7bumpspecpass0_vsh_code,
|
||||
vertex_shader_declaration
|
||||
);
|
||||
|
||||
Pass_1_Vertex_Shader.Create
|
||||
(
|
||||
shd7bumpspecpass1_vsh_code,
|
||||
vertex_shader_declaration
|
||||
);
|
||||
|
||||
}
|
||||
|
||||
void Shd7BumpSpecClass::Shutdown()
|
||||
{
|
||||
Pass_0_Vertex_Shader.Destroy();
|
||||
Pass_1_Vertex_Shader.Destroy();
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Apply shared states for 2 pass DX7 bump specular with gloss map
|
||||
/*! 5/27/02 5:39p KJM Created
|
||||
/*! 06/06/02 KM added software vertex shader fallback check
|
||||
*/
|
||||
void Shd7BumpSpecClass::Apply_Shared(int pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
// vertex processing behavior
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_SOFTWAREVERTEXPROCESSING,!Pass_0_Vertex_Shader.Is_Using_Hardware());
|
||||
|
||||
// fixed function uses pass through by default
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_PASSTHRU);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_PASSTHRU);
|
||||
|
||||
if (pass==0)
|
||||
{
|
||||
// set vertex shader
|
||||
DX8Wrapper::Set_Vertex_Shader(Pass_0_Vertex_Shader.Peek_Shader());
|
||||
|
||||
// set texture stage settings
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLOROP, D3DTOP_DOTPRODUCT3 );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_ALPHAARG1, D3DTA_CURRENT);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1 );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLORARG1, D3DTA_TEXTURE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLOROP, D3DTOP_MODULATE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLORARG2, D3DTA_SPECULAR );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAARG1, D3DTA_CURRENT);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAOP, D3DTOP_ADDSMOOTH );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAARG2, D3DTA_DIFFUSE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(2, D3DTSS_COLOROP, D3DTOP_DISABLE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(2, D3DTSS_ALPHAOP, D3DTOP_DISABLE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_ALPHABLENDENABLE, TRUE);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_DESTBLEND, D3DBLEND_ZERO);
|
||||
}
|
||||
else
|
||||
{
|
||||
// specular pass
|
||||
|
||||
// set vertex shader
|
||||
DX8Wrapper::Set_Vertex_Shader(Pass_1_Vertex_Shader.Peek_Shader());
|
||||
|
||||
const Matrix3D& cam=rinfo.Camera.Get_Transform();
|
||||
|
||||
// set constants
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant
|
||||
(
|
||||
CV_EYE_WORLD,
|
||||
D3DXVECTOR4
|
||||
(
|
||||
cam.Get_X_Translation(),
|
||||
cam.Get_Y_Translation(),
|
||||
cam.Get_Z_Translation(),
|
||||
1.0f
|
||||
),
|
||||
1
|
||||
);
|
||||
|
||||
// set texture stage settings
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG1, D3DTA_TEXTURE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLOROP, D3DTOP_DOTPRODUCT3 );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_ALPHAARG1, D3DTA_CURRENT);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_ALPHAOP, D3DTOP_MODULATE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_ALPHAARG2, D3DTA_CURRENT);
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLORARG1, D3DTA_CURRENT );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLOROP, D3DTOP_MODULATE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLORARG2, D3DTA_SPECULAR );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAARG1, D3DTA_TEXTURE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAOP, D3DTOP_MODULATE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAARG2, D3DTA_CURRENT );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(2, D3DTSS_COLOROP, D3DTOP_DISABLE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(2, D3DTSS_ALPHAOP, D3DTOP_DISABLE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_ALPHABLENDENABLE, TRUE);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_DESTBLEND, D3DBLEND_ONE);
|
||||
}
|
||||
|
||||
// set constants
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_CONST, D3DXVECTOR4(0.0f, 1.0f, 0.5f, 2.0f), 1);
|
||||
|
||||
// calculate shader view projection matrix
|
||||
Matrix4x4 view_matrix;
|
||||
DX8Wrapper::Get_Transform(D3DTS_VIEW, view_matrix);
|
||||
|
||||
Matrix4x4 proj_matrix;
|
||||
DX8Wrapper::Get_Transform(D3DTS_PROJECTION, proj_matrix);
|
||||
|
||||
Matrix4x4::Multiply(proj_matrix, view_matrix, &View_Projection_Matrix);
|
||||
}
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Apply per instance states for 2 pass DX7 bump specular with gloss map
|
||||
/*! 5/27/02 5:39p KJM Created
|
||||
*/
|
||||
void Shd7BumpSpecClass::Apply_Instance(int cur_pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
DX8Wrapper::Set_Texture(0, NormalMap);
|
||||
DX8Wrapper::Set_Texture(1, Texture);
|
||||
|
||||
// set vertex shader constants
|
||||
Matrix4x4 world;
|
||||
DX8Wrapper::Get_Transform(D3DTS_WORLD, world);
|
||||
|
||||
Matrix4x4 world_view_proj_matrix;
|
||||
|
||||
Matrix4x4::Multiply(View_Projection_Matrix,world,&world_view_proj_matrix);
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_WORLD_VIEW_PROJECTION, &world_view_proj_matrix, 4);
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_WORLD, &world, 4);
|
||||
|
||||
ShdHWVertexShader::Light
|
||||
(
|
||||
rinfo,
|
||||
Ambient,
|
||||
Diffuse,
|
||||
Specular
|
||||
);
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_BUMPINESS, &Bumpiness, 1);
|
||||
}
|
||||
|
||||
unsigned Shd7BumpSpecClass::Get_Vertex_Stream_Count() const
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
unsigned Shd7BumpSpecClass::Get_Vertex_Size(unsigned stream) const
|
||||
{
|
||||
return sizeof(VertexFormatXYZNDUV1TG3);
|
||||
}
|
||||
|
||||
void Shd7BumpSpecClass::Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
)
|
||||
{
|
||||
VertexFormatXYZNDUV1TG3* verts=(VertexFormatXYZNDUV1TG3*)dest_buffer;
|
||||
|
||||
for (unsigned i=0; i<vertex_count; ++i)
|
||||
{
|
||||
if (vss.Locations)
|
||||
{
|
||||
verts[i].x=vss.Locations[i][0];
|
||||
verts[i].y=vss.Locations[i][1];
|
||||
verts[i].z=vss.Locations[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].x=0.0f;
|
||||
verts[i].y=0.0f;
|
||||
verts[i].z=0.0f;
|
||||
}
|
||||
|
||||
if (vss.DiffuseInt)
|
||||
{
|
||||
verts[i].diffuse=vss.DiffuseInt[i];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].diffuse=0xffffffff;
|
||||
}
|
||||
|
||||
if (vss.Normals)
|
||||
{
|
||||
verts[i].nx=vss.Normals[i][0];
|
||||
verts[i].ny=vss.Normals[i][1];
|
||||
verts[i].nz=vss.Normals[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].nx=0.0f;
|
||||
verts[i].ny=0.0f;
|
||||
verts[i].nz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.UV[0])
|
||||
{
|
||||
verts[i].u1=vss.UV[0][i].U;
|
||||
verts[i].v1=vss.UV[0][i].V;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].u1=0.0f;
|
||||
verts[i].v1=0.0f;
|
||||
}
|
||||
|
||||
if (vss.S)
|
||||
{
|
||||
verts[i].Sx=vss.S[i].X;
|
||||
verts[i].Sy=vss.S[i].Y;
|
||||
verts[i].Sz=vss.S[i].Z;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].Sx=0.0f;
|
||||
verts[i].Sy=0.0f;
|
||||
verts[i].Sz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.T)
|
||||
{
|
||||
verts[i].Tx=vss.T[i].X;
|
||||
verts[i].Ty=vss.T[i].Y;
|
||||
verts[i].Tz=vss.T[i].Z;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].Tx=0.0f;
|
||||
verts[i].Ty=0.0f;
|
||||
verts[i].Tz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.SxT)
|
||||
{
|
||||
verts[i].SxTx=vss.SxT[i].X;
|
||||
verts[i].SxTy=vss.SxT[i].Y;
|
||||
verts[i].SxTz=vss.SxT[i].Z;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].SxTx=0.0f;
|
||||
verts[i].SxTy=0.0f;
|
||||
verts[i].SxTz=0.0f;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,93 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WW3D *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/ww3d2/shd7bumpspec.h $*
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 5/27/02 2:48p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHD7BUMPSPEC_H
|
||||
#define SHD7BUMPSPEC_H
|
||||
|
||||
#ifndef SHDINTERFACE_H
|
||||
#include "shdinterface.h"
|
||||
#endif
|
||||
|
||||
#ifndef SHDHWSHADER_H
|
||||
#include "shdhwshader.h"
|
||||
#endif
|
||||
|
||||
|
||||
class Shd7BumpSpecClass : public ShdInterfaceClass
|
||||
{
|
||||
public:
|
||||
Shd7BumpSpecClass(const ShdDefClass* def);
|
||||
virtual ~Shd7BumpSpecClass();
|
||||
|
||||
static void Init();
|
||||
static void Shutdown();
|
||||
|
||||
virtual int Get_Pass_Count() { return 2; }
|
||||
|
||||
virtual int Get_Texture_Count() const { return 2; }
|
||||
virtual TextureClass* Peek_Texture(int idx) const { return idx==0 ? Texture : NormalMap; }
|
||||
|
||||
virtual void Apply_Shared(int cur_pass, RenderInfoClass& rinfo);
|
||||
virtual void Apply_Instance(int cur_pass, RenderInfoClass& rinfo);
|
||||
|
||||
virtual unsigned Get_Vertex_Stream_Count() const;
|
||||
virtual unsigned Get_Vertex_Size(unsigned stream) const;
|
||||
virtual bool Use_HW_Vertex_Processing() const { return Pass_0_Vertex_Shader.Is_Using_Hardware(); }
|
||||
virtual void Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
);
|
||||
|
||||
protected:
|
||||
|
||||
static ShdHWVertexShader Pass_0_Vertex_Shader;
|
||||
static ShdHWVertexShader Pass_1_Vertex_Shader;
|
||||
|
||||
static Matrix4x4 View_Projection_Matrix;
|
||||
|
||||
TextureClass* Texture;
|
||||
TextureClass* NormalMap;
|
||||
|
||||
Vector4 Ambient;
|
||||
Vector4 Diffuse;
|
||||
Vector4 Specular;
|
||||
Vector4 Bumpiness;
|
||||
};
|
||||
|
||||
#endif // SHD7BUMPSPEC_H
|
||||
@@ -0,0 +1,100 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
// bump specular with gloss map shader constants
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
#ifndef SHD7BUMPSPEC_CONSTANTS_H
|
||||
#define SHD7BUMPSPEC_CONSTANTS_H
|
||||
|
||||
// vertex shader macros
|
||||
|
||||
|
||||
#define CV_WORLD_VIEW_PROJECTION 1
|
||||
|
||||
#define CV_WORLD_VIEW_PROJECTION_0 1
|
||||
#define CV_WORLD_VIEW_PROJECTION_1 2
|
||||
#define CV_WORLD_VIEW_PROJECTION_2 3
|
||||
#define CV_WORLD_VIEW_PROJECTION_3 4
|
||||
|
||||
|
||||
//#define CV_WORLD_VIEW 5
|
||||
|
||||
//#define CV_WORLD_VIEW_0 5
|
||||
//#define CV_WORLD_VIEW_1 6
|
||||
//#define CV_WORLD_VIEW_2 7
|
||||
//#define CV_WORLD_VIEW_3 8
|
||||
|
||||
|
||||
//#define CV_WORLD_VIEW_INVERSE_TRANSPOSE 9
|
||||
|
||||
//#define CV_WORLD_VIEW_INVERSE_TRANSPOSE_0 9
|
||||
//#define CV_WORLD_VIEW_INVERSE_TRANSPOSE_1 10
|
||||
//#define CV_WORLD_VIEW_INVERSE_TRANSPOSE_2 11
|
||||
|
||||
|
||||
|
||||
#define CV_WORLD 12
|
||||
|
||||
#define CV_WORLD_0 12
|
||||
#define CV_WORLD_1 13
|
||||
#define CV_WORLD_2 14
|
||||
#define CV_WORLD_3 15
|
||||
|
||||
// 16-26 lighting constants
|
||||
|
||||
#define CV_BUMPINESS 27
|
||||
|
||||
#define CV_EYE_WORLD 28
|
||||
|
||||
|
||||
// inputs
|
||||
#define V_POSITION v0
|
||||
#define V_NORMAL v1
|
||||
#define V_DIFFUSE v2
|
||||
#define V_TEXTURE v3
|
||||
#define V_S v4
|
||||
#define V_T v5
|
||||
#define V_SxT v6
|
||||
|
||||
|
||||
// registers
|
||||
#define HALF_ANGLE r0
|
||||
#define S_WORLD r1
|
||||
#define T_WORLD r2
|
||||
#define SxT_WORLD r3
|
||||
#define LIGHT_LOCAL r4
|
||||
#define LIGHT_0 r5
|
||||
#define LIGHT_1 r6
|
||||
#define LIGHT_2 r7
|
||||
#define LIGHT_3 r8
|
||||
#define COL r9
|
||||
#define WORLD_VERTEX r10
|
||||
#define EYE_VECTOR r11
|
||||
|
||||
#define WORLD_NORMAL r1
|
||||
|
||||
|
||||
#define OUTPUT_REG r0
|
||||
|
||||
// texture stages
|
||||
#define TEX_CUBEMAP t0
|
||||
|
||||
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,122 @@
|
||||
//
|
||||
// Command & Conquer Generals Zero Hour(tm)
|
||||
// Copyright 2025 Electronic Arts Inc.
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
//
|
||||
|
||||
// DX7 bump specular mask vertex shader pass 0
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
vs.1.1
|
||||
|
||||
#include "shdhw_constants.h"
|
||||
|
||||
#include "shd7bumpspec_constants.h"
|
||||
|
||||
// In:
|
||||
// v0 - object space vertex position
|
||||
// v1 - object space normal
|
||||
// v2 - color
|
||||
// v3 - texture coords
|
||||
// v4 - S basis
|
||||
// v5 - T basis
|
||||
// v6 - SxT
|
||||
|
||||
// object space vertex position -> screen (early as possible for view clipping)
|
||||
dp4 oPos.x, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_0]
|
||||
dp4 oPos.y, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_1]
|
||||
dp4 oPos.z, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_2]
|
||||
dp4 oPos.w, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_3]
|
||||
|
||||
// Transform basis vectors to world space
|
||||
dp3 S_WORLD.x, V_S, c[CV_WORLD_0]
|
||||
dp3 S_WORLD.y, V_S, c[CV_WORLD_1]
|
||||
dp3 S_WORLD.z, V_S, c[CV_WORLD_2]
|
||||
|
||||
dp3 T_WORLD.x, V_T, c[CV_WORLD_0]
|
||||
dp3 T_WORLD.y, V_T, c[CV_WORLD_1]
|
||||
dp3 T_WORLD.z, V_T, c[CV_WORLD_2]
|
||||
|
||||
dp3 SxT_WORLD.x, V_SxT, c[CV_WORLD_0]
|
||||
dp3 SxT_WORLD.y, V_SxT, c[CV_WORLD_1]
|
||||
dp3 SxT_WORLD.z, V_SxT, c[CV_WORLD_2]
|
||||
|
||||
// transform light 0 by basis vectors to put it into texture space
|
||||
dp3 LIGHT_LOCAL.x, S_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
dp3 LIGHT_LOCAL.y, T_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
dp3 LIGHT_LOCAL.z, SxT_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
|
||||
// Normalize the light vector
|
||||
dp3 LIGHT_LOCAL.w, LIGHT_LOCAL, LIGHT_LOCAL
|
||||
rsq LIGHT_LOCAL.w, LIGHT_LOCAL.w
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, LIGHT_LOCAL.w
|
||||
|
||||
dp3 WORLD_NORMAL.x, V_NORMAL, c[CV_WORLD_0]
|
||||
dp3 WORLD_NORMAL.y, V_NORMAL, c[CV_WORLD_1]
|
||||
dp3 WORLD_NORMAL.z, V_NORMAL, c[CV_WORLD_2]
|
||||
|
||||
// Normalize the world normal vector
|
||||
dp3 WORLD_NORMAL.w, WORLD_NORMAL, WORLD_NORMAL
|
||||
rsq WORLD_NORMAL.w, WORLD_NORMAL.w
|
||||
mul WORLD_NORMAL, WORLD_NORMAL, WORLD_NORMAL.w
|
||||
|
||||
// calculate light 0 factor
|
||||
dp3 LIGHT_0.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_0] // L.N
|
||||
max LIGHT_0.w, LIGHT_0.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_0.w, LIGHT_0.w, c[CV_LIGHT_COLOR_0].w // light attentuation factor
|
||||
|
||||
// calculate light 1 factor
|
||||
dp3 LIGHT_1.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_1] // L.N
|
||||
max LIGHT_1.w, LIGHT_1.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_1.w, LIGHT_1.w, c[CV_LIGHT_COLOR_1].w // light attentuation factor
|
||||
|
||||
// calculate light 2 factor
|
||||
dp3 LIGHT_2.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_2] // L.N
|
||||
max LIGHT_2.w, LIGHT_2.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_2.w, LIGHT_2.w, c[CV_LIGHT_COLOR_2].w // light attentuation factor
|
||||
|
||||
// calculate light 3 factor
|
||||
dp3 LIGHT_3.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_3] // L.N
|
||||
max LIGHT_3.w, LIGHT_3.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_3.w, LIGHT_3.w, c[CV_LIGHT_COLOR_3].w // light attentuation factor
|
||||
|
||||
// accumulate light colors
|
||||
mul COL, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
mad COL, c[CV_LIGHT_COLOR_1], LIGHT_1.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_2], LIGHT_2.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_3], LIGHT_3.w, COL
|
||||
|
||||
// apply vertex color and diffuse and ambient material terms
|
||||
mul COL, COL, V_DIFFUSE
|
||||
mul COL, COL, c[CV_DIFFUSE]
|
||||
add oD1, COL, c[CV_AMBIENT]
|
||||
|
||||
|
||||
// Scale to 0-1
|
||||
add LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].yyy
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].zzz
|
||||
|
||||
// apply bump scale and bias controls
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_BUMPINESS].xxx
|
||||
add oD0, LIGHT_LOCAL, c[CV_BUMPINESS].yyy
|
||||
|
||||
// place negated bump light intensity in alpha channel
|
||||
add oD0.w, c[CV_CONST].y, -LIGHT_0.w
|
||||
|
||||
|
||||
mov oT0, V_TEXTURE
|
||||
mov oT1, V_TEXTURE
|
||||
|
||||
|
||||
@@ -0,0 +1,159 @@
|
||||
//
|
||||
// Command & Conquer Generals Zero Hour(tm)
|
||||
// Copyright 2025 Electronic Arts Inc.
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
//
|
||||
|
||||
// DX7 bump specular with gloss map vertex shader pass 1
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
vs.1.1
|
||||
|
||||
#include "shdhw_constants.h"
|
||||
|
||||
#include "shd7bumpspec_constants.h"
|
||||
|
||||
// In:
|
||||
// v0 - object space vertex position
|
||||
// v1 - object space normal
|
||||
// v2 - color
|
||||
// v3 - texture coords
|
||||
// v4 - S basis
|
||||
// v5 - T basis
|
||||
// v6 - SxT
|
||||
|
||||
// object space vertex position -> screen (early as possible for view clipping)
|
||||
dp4 EYE_VECTOR.x, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_0]
|
||||
dp4 EYE_VECTOR.y, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_1]
|
||||
dp4 EYE_VECTOR.z, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_2]
|
||||
dp4 EYE_VECTOR.w, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_3]
|
||||
|
||||
mov oPos, EYE_VECTOR
|
||||
|
||||
// Set alpha to 1
|
||||
mov oD0.w, c[CV_CONST].y
|
||||
|
||||
mov oT0, V_TEXTURE
|
||||
mov oT1, V_TEXTURE
|
||||
|
||||
|
||||
// Transform basis vectors to world space
|
||||
dp3 S_WORLD.x, V_S, c[CV_WORLD_0]
|
||||
dp3 S_WORLD.y, V_S, c[CV_WORLD_1]
|
||||
dp3 S_WORLD.z, V_S, c[CV_WORLD_2]
|
||||
|
||||
dp3 T_WORLD.x, V_T, c[CV_WORLD_0]
|
||||
dp3 T_WORLD.y, V_T, c[CV_WORLD_1]
|
||||
dp3 T_WORLD.z, V_T, c[CV_WORLD_2]
|
||||
|
||||
dp3 SxT_WORLD.x, V_SxT, c[CV_WORLD_0]
|
||||
dp3 SxT_WORLD.y, V_SxT, c[CV_WORLD_1]
|
||||
dp3 SxT_WORLD.z, V_SxT, c[CV_WORLD_2]
|
||||
|
||||
|
||||
// calculate half angle
|
||||
// transform vertex position to world space
|
||||
// to calculate V, vector to viewer in world
|
||||
// space.
|
||||
dp4 WORLD_VERTEX.x, V_POSITION, c[CV_WORLD_0]
|
||||
dp4 WORLD_VERTEX.y, V_POSITION, c[CV_WORLD_1]
|
||||
dp4 WORLD_VERTEX.z, V_POSITION, c[CV_WORLD_2]
|
||||
//dp4 WORLD_VERTEX.w, V_POSITION, c[CV_WORLD_3]
|
||||
|
||||
// Half angle vector is (L+V)/||L+V|| or Normalize( L+V )
|
||||
// ||a|| is magnitude of a
|
||||
// L = vec to light from vertex point
|
||||
// V = vec to viewer from vertex point
|
||||
|
||||
// vertex position - eye position
|
||||
// eye position - vertex position
|
||||
add EYE_VECTOR, c[CV_EYE_WORLD], -WORLD_VERTEX.xyz
|
||||
|
||||
// Normalize the eye vector
|
||||
dp3 EYE_VECTOR.w, EYE_VECTOR, EYE_VECTOR
|
||||
rsq EYE_VECTOR.w, EYE_VECTOR.w
|
||||
mul EYE_VECTOR, EYE_VECTOR, EYE_VECTOR.w
|
||||
|
||||
// Add them to average & create half angle vector
|
||||
add HALF_ANGLE, c[CV_LIGHT_DIRECTION_0], EYE_VECTOR
|
||||
|
||||
|
||||
// Normalize the half angle vector
|
||||
dp3 HALF_ANGLE.w, HALF_ANGLE, HALF_ANGLE
|
||||
rsq HALF_ANGLE.w, HALF_ANGLE.w
|
||||
mul HALF_ANGLE, HALF_ANGLE, HALF_ANGLE.w
|
||||
|
||||
dp3 LIGHT_LOCAL.x, HALF_ANGLE, S_WORLD
|
||||
dp3 LIGHT_LOCAL.y, HALF_ANGLE, T_WORLD
|
||||
dp3 LIGHT_LOCAL.z, HALF_ANGLE, SxT_WORLD
|
||||
|
||||
// Normalize the half angle vector
|
||||
dp3 LIGHT_LOCAL.w, LIGHT_LOCAL, LIGHT_LOCAL
|
||||
rsq LIGHT_LOCAL.w, LIGHT_LOCAL.w
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, LIGHT_LOCAL.w
|
||||
|
||||
// calculate light 0 factor
|
||||
dp3 WORLD_NORMAL.x, V_NORMAL, c[CV_WORLD_0]
|
||||
dp3 WORLD_NORMAL.y, V_NORMAL, c[CV_WORLD_1]
|
||||
dp3 WORLD_NORMAL.z, V_NORMAL, c[CV_WORLD_2]
|
||||
|
||||
// Normalize the world normal vector
|
||||
dp3 WORLD_NORMAL.w, WORLD_NORMAL, WORLD_NORMAL
|
||||
rsq WORLD_NORMAL.w, WORLD_NORMAL.w
|
||||
mul WORLD_NORMAL, WORLD_NORMAL, WORLD_NORMAL.w
|
||||
|
||||
dp3 LIGHT_0.w, HALF_ANGLE, WORLD_NORMAL // N.H
|
||||
max LIGHT_0.w, LIGHT_0.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_0.w, LIGHT_0.w, c[CV_LIGHT_COLOR_0].w // light attentuation factor
|
||||
|
||||
mul LIGHT_0.w, LIGHT_0, LIGHT_0
|
||||
mul LIGHT_0.w, LIGHT_0, LIGHT_0
|
||||
mul LIGHT_0.w, LIGHT_0, LIGHT_0
|
||||
|
||||
// calculate light 1 factor
|
||||
//dp3 LIGHT_1.w, HALF_ANGLE, c[CV_LIGHT_DIRECTION_1] // L.H
|
||||
//max LIGHT_1.w, LIGHT_1.w, c[CV_CONST].x // clamp 0-1
|
||||
//mul LIGHT_1.w, LIGHT_1.w, c[CV_LIGHT_COLOR_1].w // light attentuation factor
|
||||
|
||||
//mul LIGHT_1.w, LIGHT_1, LIGHT_1
|
||||
//mul LIGHT_1.w, LIGHT_1, LIGHT_1
|
||||
//mul LIGHT_1.w, LIGHT_1, LIGHT_1
|
||||
|
||||
// calculate light 2 factor
|
||||
//dp3 LIGHT_2.w, HALF_ANGLE, c[CV_LIGHT_DIRECTION_2] // L.H
|
||||
//max LIGHT_2.w, LIGHT_2.w, c[CV_CONST].x // clamp 0-1
|
||||
//mul LIGHT_2.w, LIGHT_2.w, c[CV_LIGHT_COLOR_2].w // light attentuation factor
|
||||
|
||||
//mul LIGHT_2.w, LIGHT_2, LIGHT_2
|
||||
//mul LIGHT_2.w, LIGHT_2, LIGHT_2
|
||||
//mul LIGHT_2.w, LIGHT_2, LIGHT_2
|
||||
|
||||
|
||||
// accumulate light colors
|
||||
mul COL, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
//mad COL, c[CV_LIGHT_COLOR_1], LIGHT_1.w, COL
|
||||
//mad COL, c[CV_LIGHT_COLOR_2], LIGHT_2.w, COL
|
||||
|
||||
|
||||
mul oD1, COL, c[CV_SPECULAR]
|
||||
|
||||
// Scale to 0-1
|
||||
add LIGHT_LOCAL.xyz, LIGHT_LOCAL, c[CV_CONST].yyy
|
||||
mul LIGHT_LOCAL.xyz, LIGHT_LOCAL, c[CV_CONST].zzz
|
||||
|
||||
// apply bump scale and bias controls
|
||||
mul LIGHT_LOCAL.xyz, LIGHT_LOCAL, c[CV_BUMPINESS].zzz
|
||||
add oD0.xyz, LIGHT_LOCAL, c[CV_BUMPINESS].www
|
||||
|
||||
@@ -0,0 +1,382 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shd8bumpdiff.cpp $*
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 07/08/02 3:40p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include "dx8fvf.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "assetmgr.h"
|
||||
#include "rinfo.h"
|
||||
#include "camera.h"
|
||||
#include "shdmesh.h"
|
||||
#include "texproject.h"
|
||||
|
||||
#include "shdbumpdiff.h"
|
||||
#include "shd8bumpdiff.h"
|
||||
#include "shd8bumpdiff_constants.h"
|
||||
#include "shdclassids.h"
|
||||
|
||||
// shader code declarations
|
||||
#include "shd8bumpdiff.vsh_code.h"
|
||||
#include "shd8bumpdiff.psh_code.h"
|
||||
#include "shd8ssbumpdiff.vsh_code.h"
|
||||
#include "shd8ssbumpdiff.psh_code.h"
|
||||
|
||||
|
||||
ShdHWVertexShader Shd8BumpDiffClass::Vertex_Shader;
|
||||
ShdHWPixelShader Shd8BumpDiffClass::Pixel_Shader;
|
||||
ShdHWPixelShader Shd8BumpDiffClass::Self_Shadow_Pixel_Shader;
|
||||
ShdHWVertexShader Shd8BumpDiffClass::Self_Shadow_Vertex_Shader;
|
||||
Matrix4x4 Shd8BumpDiffClass::View_Projection_Matrix;
|
||||
|
||||
Shd8BumpDiffClass::Shd8BumpDiffClass(const ShdDefClass* def)
|
||||
: ShdInterfaceClass(def,SHDDEF_CLASSID_BUMPDIFF),
|
||||
Texture(NULL),
|
||||
NormalMap(NULL)
|
||||
{
|
||||
ShdBumpDiffDefClass* Definition=(ShdBumpDiffDefClass*)def;
|
||||
|
||||
Texture=WW3DAssetManager::Get_Instance()->Get_Texture
|
||||
(
|
||||
Definition->Get_Texture_Name()
|
||||
);
|
||||
|
||||
NormalMap=WW3DAssetManager::Get_Instance()->Get_Texture
|
||||
(
|
||||
Definition->Get_Bump_Map_Name()
|
||||
);
|
||||
|
||||
const Vector3& a=Definition->Get_Ambient();
|
||||
Ambient.Set(a.X,a.Y,a.Z,0.0f);
|
||||
|
||||
const Vector3& d=Definition->Get_Diffuse();
|
||||
Diffuse.Set(d.X,d.Y,d.Z,0.0f);
|
||||
|
||||
const Vector2& db=Definition->Get_Diffuse_Bumpiness();
|
||||
Bumpiness.Set(db.X,db.Y,0,0);
|
||||
}
|
||||
|
||||
Shd8BumpDiffClass::~Shd8BumpDiffClass(void)
|
||||
{
|
||||
REF_PTR_RELEASE(Texture);
|
||||
REF_PTR_RELEASE(NormalMap);
|
||||
}
|
||||
|
||||
void Shd8BumpDiffClass::Init(void)
|
||||
{
|
||||
// Create vertex shader
|
||||
DWORD vertex_shader_declaration[]=
|
||||
{
|
||||
D3DVSD_STREAM(0),
|
||||
(D3DVSD_REG(0, D3DVSDT_FLOAT3)), // vertex position
|
||||
(D3DVSD_REG(1, D3DVSDT_FLOAT3)), // vertex normal
|
||||
(D3DVSD_REG(2, D3DVSDT_D3DCOLOR)), // vertex color
|
||||
(D3DVSD_REG(3, D3DVSDT_FLOAT2)), // vertex texture coords
|
||||
(D3DVSD_REG(4, D3DVSDT_FLOAT3)), // vertex S basis
|
||||
(D3DVSD_REG(5, D3DVSDT_FLOAT3)), // vertex T basis
|
||||
(D3DVSD_REG(6, D3DVSDT_FLOAT3)), // vertex SxT basis
|
||||
D3DVSD_END()
|
||||
};
|
||||
|
||||
Pixel_Shader.Create(shd8bumpdiff_psh_code);
|
||||
|
||||
Vertex_Shader.Create
|
||||
(
|
||||
shd8bumpdiff_vsh_code,
|
||||
vertex_shader_declaration
|
||||
);
|
||||
|
||||
Self_Shadow_Pixel_Shader.Create(shd8ssbumpdiff_psh_code);
|
||||
Self_Shadow_Vertex_Shader.Create
|
||||
(
|
||||
shd8ssbumpdiff_vsh_code,
|
||||
vertex_shader_declaration
|
||||
);
|
||||
}
|
||||
|
||||
void Shd8BumpDiffClass::Shutdown(void)
|
||||
{
|
||||
Vertex_Shader.Destroy();
|
||||
Pixel_Shader.Destroy();
|
||||
Self_Shadow_Pixel_Shader.Destroy();
|
||||
Self_Shadow_Vertex_Shader.Destroy();
|
||||
}
|
||||
|
||||
void Shd8BumpDiffClass::Apply_Shared(int cur_pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
// set vertex shader
|
||||
if (cur_pass==0)
|
||||
{
|
||||
DX8Wrapper::Set_Vertex_Shader(Vertex_Shader.Peek_Shader());
|
||||
}
|
||||
else
|
||||
{
|
||||
DX8Wrapper::Set_Vertex_Shader(Self_Shadow_Vertex_Shader.Peek_Shader());
|
||||
}
|
||||
|
||||
// set vertex shader constants
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_CONST, D3DXVECTOR4(0.0f, 1.0f, 0.5f, 2.0f), 1);
|
||||
|
||||
// set pixel shader
|
||||
if (cur_pass==0)
|
||||
{
|
||||
DX8Wrapper::Set_Pixel_Shader(Pixel_Shader.Peek_Shader());
|
||||
}
|
||||
else
|
||||
{
|
||||
DX8Wrapper::Set_Pixel_Shader(Self_Shadow_Pixel_Shader.Peek_Shader());
|
||||
}
|
||||
|
||||
// set constants
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_CONST, D3DXVECTOR4(0.0f, 1.0f, 0.5f, 2.0f), 1);
|
||||
|
||||
// calculate shader view projection matrix
|
||||
Matrix4x4 view_matrix;
|
||||
DX8Wrapper::Get_Transform(D3DTS_VIEW, view_matrix);
|
||||
|
||||
Matrix4x4 proj_matrix;
|
||||
DX8Wrapper::Get_Transform(D3DTS_PROJECTION, proj_matrix);
|
||||
|
||||
Matrix4x4::Multiply(proj_matrix, view_matrix, &View_Projection_Matrix);
|
||||
}
|
||||
|
||||
void Shd8BumpDiffClass::Apply_Instance(int cur_pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
if (cur_pass==0)
|
||||
{
|
||||
DX8Wrapper::Set_Texture(0, NormalMap);
|
||||
DX8Wrapper::Set_Texture(1, Texture);
|
||||
}
|
||||
else
|
||||
{
|
||||
ZTextureClass* ztex=DX8Wrapper::Get_Shadow_Map(0);
|
||||
|
||||
|
||||
DX8Wrapper::Set_Texture(0, Texture);
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_TEXMAP,&Self_Shadow_Transform,4);
|
||||
}
|
||||
|
||||
// set vertex shader constants
|
||||
Matrix4x4 world;
|
||||
DX8Wrapper::Get_Transform(D3DTS_WORLD, world);
|
||||
|
||||
Matrix4x4 world_view_proj_matrix;
|
||||
|
||||
Matrix4x4::Multiply(View_Projection_Matrix,world,&world_view_proj_matrix);
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_WORLD_VIEW_PROJECTION, &world_view_proj_matrix, 4);
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_WORLD, &world, 4);
|
||||
|
||||
ShdHWVertexShader::Light
|
||||
(
|
||||
rinfo,
|
||||
Ambient,
|
||||
Diffuse
|
||||
);
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_BUMPINESS, &Bumpiness, 1);
|
||||
}
|
||||
|
||||
unsigned Shd8BumpDiffClass::Get_Vertex_Stream_Count() const
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
unsigned Shd8BumpDiffClass::Get_Vertex_Size(unsigned stream) const
|
||||
{
|
||||
return sizeof(VertexFormatXYZNDUV1TG3);
|
||||
}
|
||||
|
||||
void Shd8BumpDiffClass::Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
)
|
||||
{
|
||||
VertexFormatXYZNDUV1TG3* verts=(VertexFormatXYZNDUV1TG3*)dest_buffer;
|
||||
|
||||
for (unsigned i=0; i<vertex_count; ++i)
|
||||
{
|
||||
if (vss.Locations)
|
||||
{
|
||||
verts[i].x=vss.Locations[i][0];
|
||||
verts[i].y=vss.Locations[i][1];
|
||||
verts[i].z=vss.Locations[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].x=0.0f;
|
||||
verts[i].y=0.0f;
|
||||
verts[i].z=0.0f;
|
||||
}
|
||||
|
||||
if (vss.DiffuseInt)
|
||||
{
|
||||
verts[i].diffuse=vss.DiffuseInt[i];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].diffuse=0xffffffff;
|
||||
}
|
||||
|
||||
if (vss.Normals)
|
||||
{
|
||||
verts[i].nx=vss.Normals[i][0];
|
||||
verts[i].ny=vss.Normals[i][1];
|
||||
verts[i].nz=vss.Normals[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].nx=0.0f;
|
||||
verts[i].ny=0.0f;
|
||||
verts[i].nz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.UV[0])
|
||||
{
|
||||
verts[i].u1=vss.UV[0][i].U;
|
||||
verts[i].v1=vss.UV[0][i].V;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].u1=0.0f;
|
||||
verts[i].v1=0.0f;
|
||||
}
|
||||
|
||||
if (vss.S)
|
||||
{
|
||||
verts[i].Sx=vss.S[i].X;
|
||||
verts[i].Sy=vss.S[i].Y;
|
||||
verts[i].Sz=vss.S[i].Z;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].Sx=0.0f;
|
||||
verts[i].Sy=0.0f;
|
||||
verts[i].Sz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.T)
|
||||
{
|
||||
verts[i].Tx=vss.T[i].X;
|
||||
verts[i].Ty=vss.T[i].Y;
|
||||
verts[i].Tz=vss.T[i].Z;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].Tx=0.0f;
|
||||
verts[i].Ty=0.0f;
|
||||
verts[i].Tz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.SxT)
|
||||
{
|
||||
verts[i].SxTx=vss.SxT[i].X;
|
||||
verts[i].SxTy=vss.SxT[i].Y;
|
||||
verts[i].SxTz=vss.SxT[i].Z;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].SxTx=0.0f;
|
||||
verts[i].SxTy=0.0f;
|
||||
verts[i].SxTz=0.0f;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool Shd8BumpDiffClass::Pass_Selection
|
||||
(
|
||||
ShdMeshClass* mesh,
|
||||
RenderInfoClass* rinfo,
|
||||
int pass
|
||||
)
|
||||
{
|
||||
if (mesh->Is_Applying_Shadow_Map())
|
||||
{
|
||||
if (pass==1) // just do once
|
||||
{
|
||||
// is rendering self shadowed object
|
||||
Setup_Self_Shadow_Info(*mesh,*rinfo);
|
||||
}
|
||||
return (pass==1);
|
||||
}
|
||||
|
||||
return (pass==0);
|
||||
}
|
||||
|
||||
|
||||
/**********************************************************************************************
|
||||
//! Set up transform for shadow maps
|
||||
/*! 06/07/02 KM created
|
||||
*/
|
||||
void Shd8BumpDiffClass::Setup_Self_Shadow_Info(ShdMeshClass& mesh, RenderInfoClass& rinfo)
|
||||
{
|
||||
Matrix4x4 tex_mat=mesh.Peek_Texture_Projector()->Peek_Mapper()->Get_Texture_Transform();
|
||||
|
||||
//set special texture matrix for shadow mapping
|
||||
ZTextureClass* smap=DX8Wrapper::Get_Shadow_Map(0); // todo KJM assign shadow map from rinfo
|
||||
|
||||
if (!smap) return;
|
||||
|
||||
float off_x=0.5f+(0.5f/(float)smap->Get_Width());
|
||||
float off_y=0.5f+(0.5f/(float)smap->Get_Height());
|
||||
|
||||
unsigned int bits=Get_Num_Depth_Bits(smap->Get_Texture_Format());
|
||||
float range=(float)(0xFFFFFFFF>>(32-bits));
|
||||
float bias=0.0f;//-0.001f*range;
|
||||
Matrix4x4 sb_mat
|
||||
(
|
||||
Vector4(0.5f, 0.0f, 0.0f, 0.0f),
|
||||
Vector4(0.0f, -0.5f, 0.0f, 0.0f),
|
||||
Vector4(0.0f, 0.0f, range, 0.0f),
|
||||
Vector4(off_x, off_y, bias, 1.0f)
|
||||
);
|
||||
|
||||
Matrix4x4 view2tex;
|
||||
Matrix4x4::Multiply(sb_mat,tex_mat,&view2tex);
|
||||
|
||||
Matrix4x4 world;
|
||||
world.Init(mesh.Get_Transform());
|
||||
|
||||
Matrix4x4 view;
|
||||
view.Init(rinfo.Camera.Get_View_Matrix());
|
||||
|
||||
Matrix4x4 vw_mat;
|
||||
Matrix4x4::Multiply(world,view,&vw_mat);
|
||||
|
||||
Matrix4x4::Multiply(view2tex,vw_mat,&Self_Shadow_Transform);
|
||||
}
|
||||
@@ -0,0 +1,99 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/ww3d2/shd8bumpdiff.h $*
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 07/08/02 3:39p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHD8BUMPDIFF_H
|
||||
#define SHD8BUMPDIFF_H
|
||||
|
||||
#ifndef SHDINTERFACE_H
|
||||
#include "shdinterface.h"
|
||||
#endif
|
||||
|
||||
#ifndef SHDHWSHADER_H
|
||||
#include "shdhwshader.h"
|
||||
#endif
|
||||
|
||||
class Shd8BumpDiffClass : public ShdInterfaceClass
|
||||
{
|
||||
public:
|
||||
Shd8BumpDiffClass(const ShdDefClass* def);
|
||||
virtual ~Shd8BumpDiffClass();
|
||||
|
||||
static void Init();
|
||||
static void Shutdown();
|
||||
|
||||
virtual int Get_Pass_Count() { return 2; }
|
||||
virtual bool Pass_Selection(ShdMeshClass*, RenderInfoClass*,int);
|
||||
|
||||
virtual int Get_Texture_Count() const { return 2; }
|
||||
virtual TextureClass* Peek_Texture(int idx) const { return idx==0 ? Texture : NormalMap; }
|
||||
|
||||
virtual void Apply_Shared(int cur_pass, RenderInfoClass& rinfo);
|
||||
virtual void Apply_Instance(int cur_pass, RenderInfoClass& rinfo);
|
||||
|
||||
virtual unsigned Get_Vertex_Stream_Count() const;
|
||||
virtual unsigned Get_Vertex_Size(unsigned stream) const;
|
||||
virtual bool Use_HW_Vertex_Processing() const { return Vertex_Shader.Is_Using_Hardware(); }
|
||||
virtual void Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
);
|
||||
|
||||
protected:
|
||||
|
||||
void Setup_Self_Shadow_Info(ShdMeshClass& mesh, RenderInfoClass& rinfo);
|
||||
|
||||
static ShdHWVertexShader Vertex_Shader;
|
||||
static ShdHWPixelShader Pixel_Shader;
|
||||
|
||||
static Matrix4x4 View_Projection_Matrix;
|
||||
|
||||
TextureClass* Texture;
|
||||
TextureClass* NormalMap;
|
||||
|
||||
Vector4 Ambient;
|
||||
Vector4 Diffuse;
|
||||
Vector4 Bumpiness;
|
||||
|
||||
// self shadowing
|
||||
static ShdHWPixelShader Self_Shadow_Pixel_Shader;
|
||||
static ShdHWVertexShader Self_Shadow_Vertex_Shader;
|
||||
Matrix4x4 Self_Shadow_Transform;
|
||||
};
|
||||
|
||||
#endif // SHD8BUMPDIFF_H
|
||||
@@ -0,0 +1,46 @@
|
||||
//
|
||||
// Command & Conquer Generals Zero Hour(tm)
|
||||
// Copyright 2025 Electronic Arts Inc.
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
//
|
||||
|
||||
// DX8 bump diffuse shader
|
||||
// Kenny Mitchell
|
||||
|
||||
#include "shd8bumpdiff_constants.h"
|
||||
|
||||
// pixel shader version 1.1
|
||||
ps.1.1
|
||||
|
||||
tex TEX_NORMALMAP // normal map texture
|
||||
tex TEX_DECAL // decal texture
|
||||
|
||||
// bumped normal
|
||||
dp3 TEX_NORMALMAP, TEX_NORMALMAP_bx2, COL_LIGHT_bx2
|
||||
|
||||
// modulate texture and light color
|
||||
mul TEX_DECAL.rgb, COL_DIFFUSE, TEX_DECAL
|
||||
|
||||
// apply bump color in reverse direction with saturation
|
||||
mul_sat r1, TEX_DECAL, -TEX_NORMALMAP
|
||||
|
||||
// apply bump color in primary direction with saturation
|
||||
mul_sat r0, TEX_DECAL, TEX_NORMALMAP
|
||||
|
||||
// add bump light contribution
|
||||
add r0, r0, r1
|
||||
|
||||
// add key light contribution
|
||||
mad r0, TEX_DECAL, COL_LIGHT.a, r0
|
||||
@@ -0,0 +1,134 @@
|
||||
//
|
||||
// Command & Conquer Generals Zero Hour(tm)
|
||||
// Copyright 2025 Electronic Arts Inc.
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
//
|
||||
|
||||
// DX8 bump diffuse vertex shader
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
vs.1.1
|
||||
|
||||
#include "shdhw_constants.h"
|
||||
|
||||
#include "shd8bumpdiff_constants.h"
|
||||
|
||||
// In:
|
||||
// v0 - object space vertex position
|
||||
// v1 - object space normal
|
||||
// v2 - color
|
||||
// v3 - texture coords
|
||||
// v4 - S basis
|
||||
// v5 - T basis
|
||||
// v6 - SxT
|
||||
|
||||
// object space vertex position -> screen (early as possible for view clipping)
|
||||
dp4 EYE_VECTOR.x, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_0]
|
||||
dp4 EYE_VECTOR.y, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_1]
|
||||
dp4 EYE_VECTOR.z, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_2]
|
||||
dp4 EYE_VECTOR.w, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_3]
|
||||
|
||||
mov oPos, EYE_VECTOR
|
||||
|
||||
// Transform basis vectors to world space
|
||||
dp3 S_WORLD.x, V_S, c[CV_WORLD_0]
|
||||
dp3 S_WORLD.y, V_S, c[CV_WORLD_1]
|
||||
dp3 S_WORLD.z, V_S, c[CV_WORLD_2]
|
||||
|
||||
dp3 T_WORLD.x, V_T, c[CV_WORLD_0]
|
||||
dp3 T_WORLD.y, V_T, c[CV_WORLD_1]
|
||||
dp3 T_WORLD.z, V_T, c[CV_WORLD_2]
|
||||
|
||||
dp3 SxT_WORLD.x, V_SxT, c[CV_WORLD_0]
|
||||
dp3 SxT_WORLD.y, V_SxT, c[CV_WORLD_1]
|
||||
dp3 SxT_WORLD.z, V_SxT, c[CV_WORLD_2]
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
// transform light 0 by basis vectors to put it into texture space
|
||||
dp3 LIGHT_LOCAL.x, S_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
dp3 LIGHT_LOCAL.y, T_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
dp3 LIGHT_LOCAL.z, SxT_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
|
||||
// Normalize the light vector
|
||||
dp3 LIGHT_LOCAL.w, LIGHT_LOCAL, LIGHT_LOCAL
|
||||
rsq LIGHT_LOCAL.w, LIGHT_LOCAL.w
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, LIGHT_LOCAL.w
|
||||
|
||||
dp3 WORLD_NORMAL.x, V_NORMAL, c[CV_WORLD_0]
|
||||
dp3 WORLD_NORMAL.y, V_NORMAL, c[CV_WORLD_1]
|
||||
dp3 WORLD_NORMAL.z, V_NORMAL, c[CV_WORLD_2]
|
||||
|
||||
// Normalize the world normal vector
|
||||
dp3 WORLD_NORMAL.w, WORLD_NORMAL, WORLD_NORMAL
|
||||
rsq WORLD_NORMAL.w, WORLD_NORMAL.w
|
||||
mul WORLD_NORMAL, WORLD_NORMAL, WORLD_NORMAL.w
|
||||
|
||||
|
||||
// calculate light 0 factor
|
||||
dp3 LIGHT_0.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_0] // L.N
|
||||
max LIGHT_0.w, LIGHT_0.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_0.w, LIGHT_0.w, c[CV_LIGHT_COLOR_0].w // light attentuation factor
|
||||
|
||||
// calculate light 1 factor
|
||||
dp3 LIGHT_1.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_1] // L.N
|
||||
max LIGHT_1.w, LIGHT_1.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_1.w, LIGHT_1.w, c[CV_LIGHT_COLOR_1].w // light attentuation factor
|
||||
|
||||
// calculate light 2 factor
|
||||
dp3 LIGHT_2.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_2] // L.N
|
||||
max LIGHT_2.w, LIGHT_2.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_2.w, LIGHT_2.w, c[CV_LIGHT_COLOR_2].w // light attentuation factor
|
||||
|
||||
// calculate light 3 factor
|
||||
dp3 LIGHT_3.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_3] // L.N
|
||||
max LIGHT_3.w, LIGHT_3.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_3.w, LIGHT_3.w, c[CV_LIGHT_COLOR_3].w // light attentuation factor
|
||||
|
||||
// accumulate light colors
|
||||
mul COL, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
mad COL, c[CV_LIGHT_COLOR_1], LIGHT_1.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_2], LIGHT_2.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_3], LIGHT_3.w, COL
|
||||
|
||||
// apply vertex color and diffuse and ambient material terms
|
||||
mul COL, COL, V_DIFFUSE
|
||||
mul COL, COL, c[CV_DIFFUSE]
|
||||
add oD1, COL, c[CV_AMBIENT]
|
||||
|
||||
// Scale to 0-1
|
||||
add LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].yyy
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].zzz
|
||||
|
||||
// apply bump scale and bias controls
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_BUMPINESS].xxx
|
||||
add oD0, LIGHT_LOCAL, c[CV_BUMPINESS].yyy
|
||||
|
||||
|
||||
// calc light factor excluding bumped lights
|
||||
add LIGHT_0.w, c[CV_CONST].y, -LIGHT_0.w
|
||||
add LIGHT_1.w, c[CV_CONST].y, -LIGHT_1.w
|
||||
|
||||
mul LIGHT_0.w, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
mul LIGHT_1.w, c[CV_LIGHT_COLOR_1], LIGHT_1.w
|
||||
add oD0.w, LIGHT_0.w, LIGHT_1.w
|
||||
|
||||
mov oT0, V_TEXTURE
|
||||
mov oT1, V_TEXTURE
|
||||
|
||||
|
||||
@@ -0,0 +1,98 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
// DX8 bump diffuse shader constants
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
#ifndef SHD8BUMPDIFF_CONSTANTS_H
|
||||
#define SHD8BUMPDIFF_CONSTANTS_H
|
||||
|
||||
// vertex shader macros
|
||||
|
||||
|
||||
#define CV_WORLD_VIEW_PROJECTION 1
|
||||
|
||||
#define CV_WORLD_VIEW_PROJECTION_0 1
|
||||
#define CV_WORLD_VIEW_PROJECTION_1 2
|
||||
#define CV_WORLD_VIEW_PROJECTION_2 3
|
||||
#define CV_WORLD_VIEW_PROJECTION_3 4
|
||||
|
||||
|
||||
#define CV_WORLD 12
|
||||
|
||||
#define CV_WORLD_0 12
|
||||
#define CV_WORLD_1 13
|
||||
#define CV_WORLD_2 14
|
||||
#define CV_WORLD_3 15
|
||||
|
||||
// 16-26 lighting constants
|
||||
|
||||
#define CV_BUMPINESS 27
|
||||
|
||||
#define CV_EYE_WORLD 28
|
||||
|
||||
#define CV_TEXMAP 30
|
||||
|
||||
#define CV_TEXMAP_0 30
|
||||
#define CV_TEXMAP_1 31
|
||||
#define CV_TEXMAP_2 32
|
||||
#define CV_TEXMAP_3 33
|
||||
|
||||
// inputs
|
||||
#define V_POSITION v0
|
||||
#define V_NORMAL v1
|
||||
#define V_DIFFUSE v2
|
||||
#define V_TEXTURE v3
|
||||
#define V_S v4
|
||||
#define V_T v5
|
||||
#define V_SxT v6
|
||||
|
||||
|
||||
// registers
|
||||
#define HALF_ANGLE r0
|
||||
|
||||
#define S_WORLD r1
|
||||
|
||||
#define T_WORLD r2
|
||||
#define SxT_WORLD r3
|
||||
#define LIGHT_LOCAL r4
|
||||
#define LIGHT_0 r5
|
||||
#define LIGHT_1 r6
|
||||
#define LIGHT_2 r7
|
||||
#define LIGHT_3 r8
|
||||
#define COL r9
|
||||
#define WORLD_NORMAL r10
|
||||
|
||||
#define EYE_VECTOR r11
|
||||
#define WORLD_VERTEX r11
|
||||
|
||||
|
||||
// pixel shader constants
|
||||
|
||||
#define OUTPUT_REG r0
|
||||
|
||||
// texture stages
|
||||
#define TEX_NORMALMAP t0
|
||||
#define TEX_DECAL t1
|
||||
|
||||
#define COL_LIGHT v0
|
||||
#define COL_DIFFUSE v1
|
||||
|
||||
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,408 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shd8bumpspec.cpp $*
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 5/27/02 3:40p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include "dx8fvf.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "assetmgr.h"
|
||||
#include "rinfo.h"
|
||||
#include "camera.h"
|
||||
#include "shdmesh.h"
|
||||
#include "texproject.h"
|
||||
|
||||
#include "shdbumpspec.h"
|
||||
#include "shd8bumpspec.h"
|
||||
#include "shd8bumpspec_constants.h"
|
||||
#include "shdclassids.h"
|
||||
|
||||
// shader code declarations
|
||||
#include "shd8bumpspec.vsh_code.h"
|
||||
#include "shd8bumpspec.psh_code.h"
|
||||
#include "shd8ssbumpspec.vsh_code.h"
|
||||
#include "shd8ssbumpspec.psh_code.h"
|
||||
|
||||
|
||||
ShdHWVertexShader Shd8BumpSpecClass::Vertex_Shader;
|
||||
ShdHWPixelShader Shd8BumpSpecClass::Pixel_Shader;
|
||||
ShdHWPixelShader Shd8BumpSpecClass::Self_Shadow_Pixel_Shader;
|
||||
ShdHWVertexShader Shd8BumpSpecClass::Self_Shadow_Vertex_Shader;
|
||||
Matrix4x4 Shd8BumpSpecClass::View_Projection_Matrix;
|
||||
|
||||
Shd8BumpSpecClass::Shd8BumpSpecClass(const ShdDefClass* def)
|
||||
: ShdInterfaceClass(def,SHDDEF_CLASSID_BUMPSPEC),
|
||||
Texture(NULL),
|
||||
NormalMap(NULL)
|
||||
{
|
||||
ShdBumpSpecDefClass* Definition=(ShdBumpSpecDefClass*)def;
|
||||
|
||||
Texture=WW3DAssetManager::Get_Instance()->Get_Texture
|
||||
(
|
||||
Definition->Get_Texture_Name()
|
||||
);
|
||||
|
||||
NormalMap=WW3DAssetManager::Get_Instance()->Get_Texture
|
||||
(
|
||||
Definition->Get_Bump_Map_Name()
|
||||
);
|
||||
|
||||
const Vector3& a=Definition->Get_Ambient();
|
||||
Ambient.Set(a.X,a.Y,a.Z,0.0f);
|
||||
|
||||
const Vector3& d=Definition->Get_Diffuse();
|
||||
Diffuse.Set(d.X,d.Y,d.Z,0.0f);
|
||||
|
||||
const Vector3& s=Definition->Get_Specular();
|
||||
Specular.Set(s.X,s.Y,s.Z,0.0f);
|
||||
|
||||
const Vector2& db=Definition->Get_Diffuse_Bumpiness();
|
||||
const Vector2& ds=Definition->Get_Specular_Bumpiness();
|
||||
Bumpiness.Set(db.X,db.Y,ds.X,ds.Y);
|
||||
}
|
||||
|
||||
Shd8BumpSpecClass::~Shd8BumpSpecClass(void)
|
||||
{
|
||||
REF_PTR_RELEASE(Texture);
|
||||
REF_PTR_RELEASE(NormalMap);
|
||||
}
|
||||
|
||||
void Shd8BumpSpecClass::Init(void)
|
||||
{
|
||||
// Create vertex shader
|
||||
DWORD vertex_shader_declaration[]=
|
||||
{
|
||||
D3DVSD_STREAM(0),
|
||||
(D3DVSD_REG(0, D3DVSDT_FLOAT3)), // vertex position
|
||||
(D3DVSD_REG(1, D3DVSDT_FLOAT3)), // vertex normal
|
||||
(D3DVSD_REG(2, D3DVSDT_D3DCOLOR)), // vertex color
|
||||
(D3DVSD_REG(3, D3DVSDT_FLOAT2)), // vertex texture coords
|
||||
(D3DVSD_REG(4, D3DVSDT_FLOAT3)), // vertex S basis
|
||||
(D3DVSD_REG(5, D3DVSDT_FLOAT3)), // vertex T basis
|
||||
(D3DVSD_REG(6, D3DVSDT_FLOAT3)), // vertex SxT basis
|
||||
D3DVSD_END()
|
||||
};
|
||||
|
||||
Pixel_Shader.Create
|
||||
(
|
||||
shd8bumpspec_psh_code
|
||||
);
|
||||
Vertex_Shader.Create
|
||||
(
|
||||
shd8bumpspec_vsh_code,
|
||||
vertex_shader_declaration
|
||||
);
|
||||
|
||||
Self_Shadow_Pixel_Shader.Create
|
||||
(
|
||||
shd8ssbumpspec_psh_code
|
||||
);
|
||||
Self_Shadow_Vertex_Shader.Create
|
||||
(
|
||||
shd8ssbumpspec_vsh_code,
|
||||
vertex_shader_declaration
|
||||
);
|
||||
}
|
||||
|
||||
void Shd8BumpSpecClass::Shutdown(void)
|
||||
{
|
||||
Vertex_Shader.Destroy();
|
||||
Pixel_Shader.Destroy();
|
||||
Self_Shadow_Pixel_Shader.Destroy();
|
||||
Self_Shadow_Vertex_Shader.Destroy();
|
||||
}
|
||||
|
||||
void Shd8BumpSpecClass::Apply_Shared(int cur_pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
// set vertex shader
|
||||
if (cur_pass==0)
|
||||
{
|
||||
DX8Wrapper::Set_Vertex_Shader(Vertex_Shader.Peek_Shader());
|
||||
}
|
||||
else
|
||||
{
|
||||
DX8Wrapper::Set_Vertex_Shader(Self_Shadow_Vertex_Shader.Peek_Shader());
|
||||
}
|
||||
|
||||
// set vertex shader constants
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_CONST, D3DXVECTOR4(0.0f, 1.0f, 0.5f, 2.0f), 1);
|
||||
|
||||
const Matrix3D& cam=rinfo.Camera.Get_Transform();
|
||||
|
||||
// set constants
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant
|
||||
(
|
||||
CV_EYE_WORLD,
|
||||
D3DXVECTOR4
|
||||
(
|
||||
cam.Get_X_Translation(),
|
||||
cam.Get_Y_Translation(),
|
||||
cam.Get_Z_Translation(),
|
||||
1.0f
|
||||
),
|
||||
1
|
||||
);
|
||||
|
||||
// set pixel shader
|
||||
if (cur_pass==0)
|
||||
{
|
||||
DX8Wrapper::Set_Pixel_Shader(Pixel_Shader.Peek_Shader());
|
||||
}
|
||||
else
|
||||
{
|
||||
DX8Wrapper::Set_Pixel_Shader(Self_Shadow_Pixel_Shader.Peek_Shader());
|
||||
}
|
||||
|
||||
// set constants
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_CONST, D3DXVECTOR4(0.0f, 1.0f, 0.5f, 2.0f), 1);
|
||||
|
||||
// calculate shader view projection matrix
|
||||
Matrix4x4 view_matrix;
|
||||
DX8Wrapper::Get_Transform(D3DTS_VIEW, view_matrix);
|
||||
|
||||
Matrix4x4 proj_matrix;
|
||||
DX8Wrapper::Get_Transform(D3DTS_PROJECTION, proj_matrix);
|
||||
|
||||
Matrix4x4::Multiply(proj_matrix, view_matrix, &View_Projection_Matrix);
|
||||
}
|
||||
|
||||
void Shd8BumpSpecClass::Apply_Instance(int cur_pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
if (cur_pass==0)
|
||||
{
|
||||
DX8Wrapper::Set_Texture(0, NormalMap);
|
||||
DX8Wrapper::Set_Texture(1, Texture);
|
||||
}
|
||||
else
|
||||
{
|
||||
ZTextureClass* ztex=DX8Wrapper::Get_Shadow_Map(0);
|
||||
|
||||
|
||||
DX8Wrapper::Set_Texture(0, Texture);
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_TEXMAP,&Self_Shadow_Transform,4);
|
||||
}
|
||||
|
||||
// set vertex shader constants
|
||||
Matrix4x4 world;
|
||||
DX8Wrapper::Get_Transform(D3DTS_WORLD, world);
|
||||
|
||||
Matrix4x4 world_view_proj_matrix;
|
||||
|
||||
Matrix4x4::Multiply(View_Projection_Matrix,world,&world_view_proj_matrix);
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_WORLD_VIEW_PROJECTION, &world_view_proj_matrix, 4);
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_WORLD, &world, 4);
|
||||
|
||||
ShdHWVertexShader::Light
|
||||
(
|
||||
rinfo,
|
||||
Ambient,
|
||||
Diffuse,
|
||||
Specular
|
||||
);
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_BUMPINESS, &Bumpiness, 1);
|
||||
}
|
||||
|
||||
unsigned Shd8BumpSpecClass::Get_Vertex_Stream_Count() const
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
unsigned Shd8BumpSpecClass::Get_Vertex_Size(unsigned stream) const
|
||||
{
|
||||
return sizeof(VertexFormatXYZNDUV1TG3);
|
||||
}
|
||||
|
||||
void Shd8BumpSpecClass::Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
)
|
||||
{
|
||||
VertexFormatXYZNDUV1TG3* verts=(VertexFormatXYZNDUV1TG3*)dest_buffer;
|
||||
|
||||
for (unsigned i=0; i<vertex_count; ++i)
|
||||
{
|
||||
if (vss.Locations)
|
||||
{
|
||||
verts[i].x=vss.Locations[i][0];
|
||||
verts[i].y=vss.Locations[i][1];
|
||||
verts[i].z=vss.Locations[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].x=0.0f;
|
||||
verts[i].y=0.0f;
|
||||
verts[i].z=0.0f;
|
||||
}
|
||||
|
||||
if (vss.DiffuseInt)
|
||||
{
|
||||
verts[i].diffuse=vss.DiffuseInt[i];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].diffuse=0xffffffff;
|
||||
}
|
||||
|
||||
if (vss.Normals)
|
||||
{
|
||||
verts[i].nx=vss.Normals[i][0];
|
||||
verts[i].ny=vss.Normals[i][1];
|
||||
verts[i].nz=vss.Normals[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].nx=0.0f;
|
||||
verts[i].ny=0.0f;
|
||||
verts[i].nz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.UV[0])
|
||||
{
|
||||
verts[i].u1=vss.UV[0][i].U;
|
||||
verts[i].v1=vss.UV[0][i].V;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].u1=0.0f;
|
||||
verts[i].v1=0.0f;
|
||||
}
|
||||
|
||||
if (vss.S)
|
||||
{
|
||||
verts[i].Sx=vss.S[i].X;
|
||||
verts[i].Sy=vss.S[i].Y;
|
||||
verts[i].Sz=vss.S[i].Z;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].Sx=0.0f;
|
||||
verts[i].Sy=0.0f;
|
||||
verts[i].Sz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.T)
|
||||
{
|
||||
verts[i].Tx=vss.T[i].X;
|
||||
verts[i].Ty=vss.T[i].Y;
|
||||
verts[i].Tz=vss.T[i].Z;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].Tx=0.0f;
|
||||
verts[i].Ty=0.0f;
|
||||
verts[i].Tz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.SxT)
|
||||
{
|
||||
verts[i].SxTx=vss.SxT[i].X;
|
||||
verts[i].SxTy=vss.SxT[i].Y;
|
||||
verts[i].SxTz=vss.SxT[i].Z;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].SxTx=0.0f;
|
||||
verts[i].SxTy=0.0f;
|
||||
verts[i].SxTz=0.0f;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool Shd8BumpSpecClass::Pass_Selection
|
||||
(
|
||||
ShdMeshClass* mesh,
|
||||
RenderInfoClass* rinfo,
|
||||
int pass
|
||||
)
|
||||
{
|
||||
if (mesh->Is_Applying_Shadow_Map())
|
||||
{
|
||||
if (pass==1) // just do once
|
||||
{
|
||||
// is rendering self shadowed object
|
||||
Setup_Self_Shadow_Info(*mesh,*rinfo);
|
||||
}
|
||||
return (pass==1);
|
||||
}
|
||||
|
||||
return (pass==0);
|
||||
}
|
||||
|
||||
|
||||
/**********************************************************************************************
|
||||
//! Set up transform for shadow maps
|
||||
/*! 06/07/02 KM created
|
||||
*/
|
||||
void Shd8BumpSpecClass::Setup_Self_Shadow_Info(ShdMeshClass& mesh, RenderInfoClass& rinfo)
|
||||
{
|
||||
Matrix4x4 tex_mat=mesh.Peek_Texture_Projector()->Peek_Mapper()->Get_Texture_Transform();
|
||||
|
||||
//set special texture matrix for shadow mapping
|
||||
ZTextureClass* smap=DX8Wrapper::Get_Shadow_Map(0); // todo KJM assign shadow map from rinfo
|
||||
|
||||
if (!smap) return;
|
||||
|
||||
float off_x=0.5f+(0.5f/(float)smap->Get_Width());
|
||||
float off_y=0.5f+(0.5f/(float)smap->Get_Height());
|
||||
|
||||
unsigned int bits=Get_Num_Depth_Bits(smap->Get_Texture_Format());
|
||||
float range=(float)(0xFFFFFFFF>>(32-bits));
|
||||
float bias=0.0f;//-0.001f*range;
|
||||
Matrix4x4 sb_mat
|
||||
(
|
||||
Vector4(0.5f, 0.0f, 0.0f, 0.0f),
|
||||
Vector4(0.0f, -0.5f, 0.0f, 0.0f),
|
||||
Vector4(0.0f, 0.0f, range, 0.0f),
|
||||
Vector4(off_x, off_y, bias, 1.0f)
|
||||
);
|
||||
|
||||
Matrix4x4 view2tex;
|
||||
Matrix4x4::Multiply(sb_mat,tex_mat,&view2tex);
|
||||
|
||||
Matrix4x4 world;
|
||||
world.Init(mesh.Get_Transform());
|
||||
|
||||
Matrix4x4 view;
|
||||
view.Init(rinfo.Camera.Get_View_Matrix());
|
||||
|
||||
Matrix4x4 vw_mat;
|
||||
Matrix4x4::Multiply(world,view,&vw_mat);
|
||||
|
||||
Matrix4x4::Multiply(view2tex,vw_mat,&Self_Shadow_Transform);
|
||||
}
|
||||
100
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shd8bumpspec.h
Normal file
100
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shd8bumpspec.h
Normal file
@@ -0,0 +1,100 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WW3D *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/ww3d2/shd8bumpspec.h $*
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 5/27/02 3:39p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHD8BUMPSPEC_H
|
||||
#define SHD8BUMPSPEC_H
|
||||
|
||||
#ifndef SHDINTERFACE_H
|
||||
#include "shdinterface.h"
|
||||
#endif
|
||||
|
||||
#ifndef SHDHWSHADER_H
|
||||
#include "shdhwshader.h"
|
||||
#endif
|
||||
|
||||
class Shd8BumpSpecClass : public ShdInterfaceClass
|
||||
{
|
||||
public:
|
||||
Shd8BumpSpecClass(const ShdDefClass* def);
|
||||
virtual ~Shd8BumpSpecClass();
|
||||
|
||||
static void Init();
|
||||
static void Shutdown();
|
||||
|
||||
virtual int Get_Pass_Count() { return 2; }
|
||||
virtual bool Pass_Selection(ShdMeshClass*, RenderInfoClass*,int);
|
||||
|
||||
virtual int Get_Texture_Count() const { return 2; }
|
||||
virtual TextureClass* Peek_Texture(int idx) const { return idx==0 ? Texture : NormalMap; }
|
||||
|
||||
virtual void Apply_Shared(int cur_pass, RenderInfoClass& rinfo);
|
||||
virtual void Apply_Instance(int cur_pass, RenderInfoClass& rinfo);
|
||||
|
||||
virtual unsigned Get_Vertex_Stream_Count() const;
|
||||
virtual unsigned Get_Vertex_Size(unsigned stream) const;
|
||||
virtual bool Use_HW_Vertex_Processing() const { return Vertex_Shader.Is_Using_Hardware(); }
|
||||
virtual void Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
);
|
||||
|
||||
protected:
|
||||
|
||||
void Setup_Self_Shadow_Info(ShdMeshClass& mesh, RenderInfoClass& rinfo);
|
||||
|
||||
static ShdHWVertexShader Vertex_Shader;
|
||||
static ShdHWPixelShader Pixel_Shader;
|
||||
|
||||
static Matrix4x4 View_Projection_Matrix;
|
||||
|
||||
TextureClass* Texture;
|
||||
TextureClass* NormalMap;
|
||||
|
||||
Vector4 Ambient;
|
||||
Vector4 Diffuse;
|
||||
Vector4 Specular;
|
||||
Vector4 Bumpiness;
|
||||
|
||||
// self shadowing
|
||||
static ShdHWPixelShader Self_Shadow_Pixel_Shader;
|
||||
static ShdHWVertexShader Self_Shadow_Vertex_Shader;
|
||||
Matrix4x4 Self_Shadow_Transform;
|
||||
};
|
||||
|
||||
#endif // SHD8BUMPSPEC_H
|
||||
@@ -0,0 +1,57 @@
|
||||
//
|
||||
// Command & Conquer Generals Zero Hour(tm)
|
||||
// Copyright 2025 Electronic Arts Inc.
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
//
|
||||
|
||||
// DX8 bump specular with gloss shader
|
||||
// Kenny Mitchell
|
||||
|
||||
#include "shd8bumpspec_constants.h"
|
||||
|
||||
// pixel shader version 1.1
|
||||
ps.1.1
|
||||
|
||||
tex TEX_NORMALMAP // normal map texture
|
||||
tex TEX_DECAL // decal texture
|
||||
|
||||
texcoord TEX_SPECULAR // specular term
|
||||
|
||||
// bumped normal
|
||||
dp3 TEX_NORMALMAP, TEX_NORMALMAP_bx2, COL_LIGHT_bx2
|
||||
|
||||
// modulate texture and light color
|
||||
mul TEX_DECAL.rgb, COL_DIFFUSE, TEX_DECAL
|
||||
|
||||
// apply bump color in reverse direction with saturation
|
||||
mul_sat r1, TEX_DECAL, -TEX_NORMALMAP
|
||||
|
||||
// apply bump color in primary direction with saturation
|
||||
mul_sat r0, TEX_DECAL, TEX_NORMALMAP
|
||||
|
||||
// add bump light contribution
|
||||
add r0, r0, r1
|
||||
|
||||
// add key light contribution
|
||||
mad r0, TEX_DECAL, COL_LIGHT.a, r0
|
||||
|
||||
|
||||
// specular section
|
||||
// apply gloss map
|
||||
mul_sat r1, TEX_DECAL.a, TEX_NORMALMAP
|
||||
|
||||
// apply specular power
|
||||
mad r0, TEX_SPECULAR, r1, r0
|
||||
|
||||
@@ -0,0 +1,183 @@
|
||||
//
|
||||
// Command & Conquer Generals Zero Hour(tm)
|
||||
// Copyright 2025 Electronic Arts Inc.
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
//
|
||||
|
||||
// DX8 bump specularwith gloss map vertex shader
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
vs.1.1
|
||||
|
||||
#include "shdhw_constants.h"
|
||||
|
||||
#include "shd8bumpspec_constants.h"
|
||||
|
||||
// In:
|
||||
// v0 - object space vertex position
|
||||
// v1 - object space normal
|
||||
// v2 - color
|
||||
// v3 - texture coords
|
||||
// v4 - S basis
|
||||
// v5 - T basis
|
||||
// v6 - SxT
|
||||
|
||||
// object space vertex position -> screen (early as possible for view clipping)
|
||||
dp4 EYE_VECTOR.x, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_0]
|
||||
dp4 EYE_VECTOR.y, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_1]
|
||||
dp4 EYE_VECTOR.z, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_2]
|
||||
dp4 EYE_VECTOR.w, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_3]
|
||||
|
||||
mov oPos, EYE_VECTOR
|
||||
|
||||
// Transform basis vectors to world space
|
||||
dp3 S_WORLD.x, V_S, c[CV_WORLD_0]
|
||||
dp3 S_WORLD.y, V_S, c[CV_WORLD_1]
|
||||
dp3 S_WORLD.z, V_S, c[CV_WORLD_2]
|
||||
|
||||
dp3 T_WORLD.x, V_T, c[CV_WORLD_0]
|
||||
dp3 T_WORLD.y, V_T, c[CV_WORLD_1]
|
||||
dp3 T_WORLD.z, V_T, c[CV_WORLD_2]
|
||||
|
||||
dp3 SxT_WORLD.x, V_SxT, c[CV_WORLD_0]
|
||||
dp3 SxT_WORLD.y, V_SxT, c[CV_WORLD_1]
|
||||
dp3 SxT_WORLD.z, V_SxT, c[CV_WORLD_2]
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
// transform light 0 by basis vectors to put it into texture space
|
||||
dp3 LIGHT_LOCAL.x, S_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
dp3 LIGHT_LOCAL.y, T_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
dp3 LIGHT_LOCAL.z, SxT_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
|
||||
// Normalize the light vector
|
||||
dp3 LIGHT_LOCAL.w, LIGHT_LOCAL, LIGHT_LOCAL
|
||||
rsq LIGHT_LOCAL.w, LIGHT_LOCAL.w
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, LIGHT_LOCAL.w
|
||||
|
||||
dp3 WORLD_NORMAL.x, V_NORMAL, c[CV_WORLD_0]
|
||||
dp3 WORLD_NORMAL.y, V_NORMAL, c[CV_WORLD_1]
|
||||
dp3 WORLD_NORMAL.z, V_NORMAL, c[CV_WORLD_2]
|
||||
|
||||
// Normalize the world normal vector
|
||||
dp3 WORLD_NORMAL.w, WORLD_NORMAL, WORLD_NORMAL
|
||||
rsq WORLD_NORMAL.w, WORLD_NORMAL.w
|
||||
mul WORLD_NORMAL, WORLD_NORMAL, WORLD_NORMAL.w
|
||||
|
||||
|
||||
// calculate light 0 factor
|
||||
dp3 LIGHT_0.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_0] // L.N
|
||||
max LIGHT_0.w, LIGHT_0.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_0.w, LIGHT_0.w, c[CV_LIGHT_COLOR_0].w // light attentuation factor
|
||||
|
||||
// calculate light 1 factor
|
||||
dp3 LIGHT_1.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_1] // L.N
|
||||
max LIGHT_1.w, LIGHT_1.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_1.w, LIGHT_1.w, c[CV_LIGHT_COLOR_1].w // light attentuation factor
|
||||
|
||||
// calculate light 2 factor
|
||||
dp3 LIGHT_2.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_2] // L.N
|
||||
max LIGHT_2.w, LIGHT_2.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_2.w, LIGHT_2.w, c[CV_LIGHT_COLOR_2].w // light attentuation factor
|
||||
|
||||
// calculate light 3 factor
|
||||
dp3 LIGHT_3.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_3] // L.N
|
||||
max LIGHT_3.w, LIGHT_3.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_3.w, LIGHT_3.w, c[CV_LIGHT_COLOR_3].w // light attentuation factor
|
||||
|
||||
// accumulate light colors
|
||||
mul COL, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
mad COL, c[CV_LIGHT_COLOR_1], LIGHT_1.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_2], LIGHT_2.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_3], LIGHT_3.w, COL
|
||||
|
||||
// apply vertex color and diffuse and ambient material terms
|
||||
mul COL, COL, V_DIFFUSE
|
||||
mul COL, COL, c[CV_DIFFUSE]
|
||||
add oD1, COL, c[CV_AMBIENT]
|
||||
|
||||
// Scale to 0-1
|
||||
add LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].yyy
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].zzz
|
||||
|
||||
// apply bump scale and bias controls
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_BUMPINESS].xxx
|
||||
add oD0, LIGHT_LOCAL, c[CV_BUMPINESS].yyy
|
||||
|
||||
|
||||
// calc light factor excluding bumped lights
|
||||
add LIGHT_0.w, c[CV_CONST].y, -LIGHT_0.w
|
||||
add LIGHT_1.w, c[CV_CONST].y, -LIGHT_1.w
|
||||
|
||||
mul LIGHT_0.w, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
mul LIGHT_1.w, c[CV_LIGHT_COLOR_1], LIGHT_1.w
|
||||
add oD0.w, LIGHT_0.w, LIGHT_1.w
|
||||
|
||||
|
||||
// calculate specular term
|
||||
|
||||
// calculate half angle
|
||||
// transform vertex position to world space
|
||||
// to calculate V, vector to viewer in world
|
||||
// space.
|
||||
dp4 WORLD_VERTEX.x, V_POSITION, c[CV_WORLD_0]
|
||||
dp4 WORLD_VERTEX.y, V_POSITION, c[CV_WORLD_1]
|
||||
dp4 WORLD_VERTEX.z, V_POSITION, c[CV_WORLD_2]
|
||||
//dp4 WORLD_VERTEX.w, V_POSITION, c[CV_WORLD_3]
|
||||
|
||||
// Half angle vector is (L+V)/||L+V|| or Normalize( L+V )
|
||||
// ||a|| is magnitude of a
|
||||
// L = vec to light from vertex point
|
||||
// V = vec to viewer from vertex point
|
||||
|
||||
// vertex position - eye position
|
||||
// eye position - vertex position
|
||||
add EYE_VECTOR, c[CV_EYE_WORLD], -WORLD_VERTEX.xyz
|
||||
|
||||
// Normalize the eye vector
|
||||
dp3 EYE_VECTOR.w, EYE_VECTOR, EYE_VECTOR
|
||||
rsq EYE_VECTOR.w, EYE_VECTOR.w
|
||||
mul EYE_VECTOR, EYE_VECTOR, EYE_VECTOR.w
|
||||
|
||||
// Add them to average & create half angle vector
|
||||
add HALF_ANGLE, c[CV_LIGHT_DIRECTION_0], EYE_VECTOR
|
||||
|
||||
// Normalize the half angle vector
|
||||
dp3 HALF_ANGLE.w, HALF_ANGLE, HALF_ANGLE
|
||||
rsq HALF_ANGLE.w, HALF_ANGLE.w
|
||||
mul HALF_ANGLE, HALF_ANGLE, HALF_ANGLE.w
|
||||
|
||||
// calculate light 0 factor
|
||||
dp3 LIGHT_0.w, HALF_ANGLE, WORLD_NORMAL // N.H
|
||||
max LIGHT_0.w, LIGHT_0.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_0.w, LIGHT_0.w, c[CV_LIGHT_COLOR_0].w // light attentuation factor
|
||||
|
||||
mul LIGHT_0.w, LIGHT_0, LIGHT_0
|
||||
mul LIGHT_0.w, LIGHT_0, LIGHT_0
|
||||
mul LIGHT_0.w, LIGHT_0, LIGHT_0
|
||||
|
||||
// accumulate light colors
|
||||
mul COL, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
|
||||
// output per vertex specular color
|
||||
mul oT2, COL, c[CV_SPECULAR]
|
||||
|
||||
mov oT0, V_TEXTURE
|
||||
mov oT1, V_TEXTURE
|
||||
|
||||
|
||||
@@ -0,0 +1,99 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
// DX8 bump specular mask with gloss map shader constants
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
#ifndef SHD8BUMPSPEC_CONSTANTS_H
|
||||
#define SHD8BUMPSPEC_CONSTANTS_H
|
||||
|
||||
// vertex shader macros
|
||||
|
||||
|
||||
#define CV_WORLD_VIEW_PROJECTION 1
|
||||
|
||||
#define CV_WORLD_VIEW_PROJECTION_0 1
|
||||
#define CV_WORLD_VIEW_PROJECTION_1 2
|
||||
#define CV_WORLD_VIEW_PROJECTION_2 3
|
||||
#define CV_WORLD_VIEW_PROJECTION_3 4
|
||||
|
||||
|
||||
#define CV_WORLD 12
|
||||
|
||||
#define CV_WORLD_0 12
|
||||
#define CV_WORLD_1 13
|
||||
#define CV_WORLD_2 14
|
||||
#define CV_WORLD_3 15
|
||||
|
||||
// 16-26 lighting constants
|
||||
|
||||
#define CV_BUMPINESS 27
|
||||
|
||||
#define CV_EYE_WORLD 28
|
||||
|
||||
#define CV_TEXMAP 30
|
||||
|
||||
#define CV_TEXMAP_0 30
|
||||
#define CV_TEXMAP_1 31
|
||||
#define CV_TEXMAP_2 32
|
||||
#define CV_TEXMAP_3 33
|
||||
|
||||
// inputs
|
||||
#define V_POSITION v0
|
||||
#define V_NORMAL v1
|
||||
#define V_DIFFUSE v2
|
||||
#define V_TEXTURE v3
|
||||
#define V_S v4
|
||||
#define V_T v5
|
||||
#define V_SxT v6
|
||||
|
||||
|
||||
// registers
|
||||
#define HALF_ANGLE r0
|
||||
|
||||
#define S_WORLD r1
|
||||
|
||||
#define T_WORLD r2
|
||||
#define SxT_WORLD r3
|
||||
#define LIGHT_LOCAL r4
|
||||
#define LIGHT_0 r5
|
||||
#define LIGHT_1 r6
|
||||
#define LIGHT_2 r7
|
||||
#define LIGHT_3 r8
|
||||
#define COL r9
|
||||
#define WORLD_NORMAL r10
|
||||
|
||||
#define EYE_VECTOR r11
|
||||
#define WORLD_VERTEX r11
|
||||
|
||||
|
||||
// pixel shader constants
|
||||
|
||||
#define OUTPUT_REG r0
|
||||
|
||||
// texture stages
|
||||
#define TEX_NORMALMAP t0
|
||||
#define TEX_DECAL t1
|
||||
#define TEX_SPECULAR t2
|
||||
|
||||
#define COL_LIGHT v0
|
||||
#define COL_DIFFUSE v1
|
||||
|
||||
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,57 @@
|
||||
//
|
||||
// Command & Conquer Generals Zero Hour(tm)
|
||||
// Copyright 2025 Electronic Arts Inc.
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
//
|
||||
|
||||
// DX8 self shadowed bump specular with gloss shader
|
||||
// Kenny Mitchell
|
||||
|
||||
#include "shd8bumpspec_constants.h"
|
||||
|
||||
// pixel shader version 1.1
|
||||
ps.1.1
|
||||
|
||||
tex TEX_NORMALMAP // normal map texture
|
||||
//tex TEX_DECAL // decal texture
|
||||
|
||||
mov r0,TEX_NORMALMAP
|
||||
|
||||
//texcoord TEX_SPECULAR // specular term
|
||||
//texcoord t3
|
||||
|
||||
// bumped normal
|
||||
//dp3_sat r1, TEX_NORMALMAP_bx2, COL_LIGHT_bx2
|
||||
|
||||
// fill light normal
|
||||
//add r1, COL_LIGHT.a, r1
|
||||
|
||||
// modulate texture and light color
|
||||
//mul r0, COL_DIFFUSE, TEX_DECAL
|
||||
|
||||
// apply light intensity
|
||||
//mul r0, r0, r1
|
||||
|
||||
// specular section
|
||||
//dp3_sat r1, TEX_NORMALMAP_bx2, t3_bx2
|
||||
|
||||
//mul r1, r1, r1
|
||||
//mul r1, r1, r1
|
||||
|
||||
// apply gloss map
|
||||
//mul r1, TEX_DECAL.a, r1
|
||||
|
||||
//mad r0, TEX_SPECULAR, r1, r0
|
||||
|
||||
@@ -0,0 +1,221 @@
|
||||
//
|
||||
// Command & Conquer Generals Zero Hour(tm)
|
||||
// Copyright 2025 Electronic Arts Inc.
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
//
|
||||
|
||||
// DX8 self shadowed bump specular with gloss map vertex shader
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
vs.1.1
|
||||
|
||||
#include "shdhw_constants.h"
|
||||
|
||||
#include "shd8bumpspec_constants.h"
|
||||
|
||||
// In:
|
||||
// v0 - object space vertex position
|
||||
// v1 - object space normal
|
||||
// v2 - color
|
||||
// v3 - texture coords
|
||||
// v4 - S basis
|
||||
// v5 - T basis
|
||||
// v6 - SxT
|
||||
|
||||
// object space vertex position -> screen (early as possible for view clipping)
|
||||
dp4 EYE_VECTOR.x, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_0]
|
||||
dp4 EYE_VECTOR.y, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_1]
|
||||
dp4 EYE_VECTOR.z, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_2]
|
||||
dp4 EYE_VECTOR.w, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_3]
|
||||
|
||||
mov oPos, EYE_VECTOR
|
||||
|
||||
dp4 oT0.x, V_POSITION, c[CV_TEXMAP_0]
|
||||
dp4 oT0.y, V_POSITION, c[CV_TEXMAP_1]
|
||||
dp4 oT0.z, V_POSITION, c[CV_TEXMAP_2]
|
||||
dp4 oT0.w, V_POSITION, c[CV_TEXMAP_3]
|
||||
|
||||
|
||||
// Transform basis vectors to world space
|
||||
dp3 S_WORLD.x, V_S, c[CV_WORLD_0]
|
||||
dp3 S_WORLD.y, V_S, c[CV_WORLD_1]
|
||||
dp3 S_WORLD.z, V_S, c[CV_WORLD_2]
|
||||
|
||||
dp3 T_WORLD.x, V_T, c[CV_WORLD_0]
|
||||
dp3 T_WORLD.y, V_T, c[CV_WORLD_1]
|
||||
dp3 T_WORLD.z, V_T, c[CV_WORLD_2]
|
||||
|
||||
dp3 SxT_WORLD.x, V_SxT, c[CV_WORLD_0]
|
||||
dp3 SxT_WORLD.y, V_SxT, c[CV_WORLD_1]
|
||||
dp3 SxT_WORLD.z, V_SxT, c[CV_WORLD_2]
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
// transform light 0 by basis vectors to put it into texture space
|
||||
dp3 LIGHT_LOCAL.x, S_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
dp3 LIGHT_LOCAL.y, T_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
dp3 LIGHT_LOCAL.z, SxT_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
|
||||
// Normalize the light vector
|
||||
dp3 LIGHT_LOCAL.w, LIGHT_LOCAL, LIGHT_LOCAL
|
||||
rsq LIGHT_LOCAL.w, LIGHT_LOCAL.w
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, LIGHT_LOCAL.w
|
||||
|
||||
dp3 WORLD_NORMAL.x, V_NORMAL, c[CV_WORLD_0]
|
||||
dp3 WORLD_NORMAL.y, V_NORMAL, c[CV_WORLD_1]
|
||||
dp3 WORLD_NORMAL.z, V_NORMAL, c[CV_WORLD_2]
|
||||
|
||||
// Normalize the world normal vector
|
||||
dp3 WORLD_NORMAL.w, WORLD_NORMAL, WORLD_NORMAL
|
||||
rsq WORLD_NORMAL.w, WORLD_NORMAL.w
|
||||
mul WORLD_NORMAL, WORLD_NORMAL, WORLD_NORMAL.w
|
||||
|
||||
|
||||
// calculate light 0 factor
|
||||
dp3 LIGHT_0.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_0] // L.N
|
||||
max LIGHT_0.w, LIGHT_0.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_0.w, LIGHT_0.w, c[CV_LIGHT_COLOR_0].w // light attentuation factor
|
||||
|
||||
// calculate light 1 factor
|
||||
dp3 LIGHT_1.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_1] // L.N
|
||||
max LIGHT_1.w, LIGHT_1.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_1.w, LIGHT_1.w, c[CV_LIGHT_COLOR_1].w // light attentuation factor
|
||||
|
||||
// calculate light 2 factor
|
||||
dp3 LIGHT_2.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_2] // L.N
|
||||
max LIGHT_2.w, LIGHT_2.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_2.w, LIGHT_2.w, c[CV_LIGHT_COLOR_2].w // light attentuation factor
|
||||
|
||||
// calculate light 3 factor
|
||||
dp3 LIGHT_3.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_3] // L.N
|
||||
max LIGHT_3.w, LIGHT_3.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_3.w, LIGHT_3.w, c[CV_LIGHT_COLOR_3].w // light attentuation factor
|
||||
|
||||
// accumulate light colors
|
||||
mul COL, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
mad COL, c[CV_LIGHT_COLOR_1], LIGHT_1.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_2], LIGHT_2.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_3], LIGHT_3.w, COL
|
||||
|
||||
// apply vertex color and diffuse and ambient material terms
|
||||
mul COL, COL, V_DIFFUSE
|
||||
mul COL, COL, c[CV_DIFFUSE]
|
||||
add oD1, COL, c[CV_AMBIENT]
|
||||
|
||||
// Scale to 0-1
|
||||
add LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].yyy
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].zzz
|
||||
|
||||
// apply bump scale and bias controls
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_BUMPINESS].xxx
|
||||
add oD0, LIGHT_LOCAL, c[CV_BUMPINESS].yyy
|
||||
|
||||
// set compliment of diffuse light factor
|
||||
add oD0.w, c[CV_CONST].y, -LIGHT_0.w
|
||||
|
||||
|
||||
|
||||
// calculate specular term
|
||||
|
||||
// calculate half angle
|
||||
// transform vertex position to world space
|
||||
// to calculate V, vector to viewer in world
|
||||
// space.
|
||||
dp4 WORLD_VERTEX.x, V_POSITION, c[CV_WORLD_0]
|
||||
dp4 WORLD_VERTEX.y, V_POSITION, c[CV_WORLD_1]
|
||||
dp4 WORLD_VERTEX.z, V_POSITION, c[CV_WORLD_2]
|
||||
//dp4 WORLD_VERTEX.w, V_POSITION, c[CV_WORLD_3]
|
||||
|
||||
// Half angle vector is (L+V)/||L+V|| or Normalize( L+V )
|
||||
// ||a|| is magnitude of a
|
||||
// L = vec to light from vertex point
|
||||
// V = vec to viewer from vertex point
|
||||
|
||||
// vertex position - eye position
|
||||
// eye position - vertex position
|
||||
add EYE_VECTOR, c[CV_EYE_WORLD], -WORLD_VERTEX.xyz
|
||||
|
||||
// Normalize the eye vector
|
||||
dp3 EYE_VECTOR.w, EYE_VECTOR, EYE_VECTOR
|
||||
rsq EYE_VECTOR.w, EYE_VECTOR.w
|
||||
mul EYE_VECTOR, EYE_VECTOR, EYE_VECTOR.w
|
||||
|
||||
// Add them to average & create half angle vector
|
||||
add HALF_ANGLE, c[CV_LIGHT_DIRECTION_0], EYE_VECTOR
|
||||
|
||||
|
||||
// Normalize the half angle vector
|
||||
dp3 HALF_ANGLE.w, HALF_ANGLE, HALF_ANGLE
|
||||
rsq HALF_ANGLE.w, HALF_ANGLE.w
|
||||
mul HALF_ANGLE, HALF_ANGLE, HALF_ANGLE.w
|
||||
|
||||
|
||||
dp3 LIGHT_LOCAL.x, S_WORLD.xyz, HALF_ANGLE
|
||||
dp3 LIGHT_LOCAL.y, T_WORLD.xyz, HALF_ANGLE
|
||||
dp3 LIGHT_LOCAL.z, SxT_WORLD.xyz, HALF_ANGLE
|
||||
|
||||
// Normalize the half angle vector
|
||||
dp3 LIGHT_LOCAL.w, LIGHT_LOCAL, LIGHT_LOCAL
|
||||
rsq LIGHT_LOCAL.w, LIGHT_LOCAL.w
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, LIGHT_LOCAL.w
|
||||
|
||||
// Scale to 0-1
|
||||
//add LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].yyy
|
||||
//mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].zzz
|
||||
|
||||
// apply bump scale and bias controls
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_BUMPINESS].zzz
|
||||
//add oT3, LIGHT_LOCAL, c[CV_BUMPINESS].www
|
||||
|
||||
|
||||
|
||||
// calculate light 0 factor
|
||||
dp3 LIGHT_0.w, HALF_ANGLE, WORLD_NORMAL // N.H
|
||||
max LIGHT_0.w, LIGHT_0.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_0.w, LIGHT_0.w, c[CV_LIGHT_COLOR_0].w // light attentuation factor
|
||||
|
||||
mul LIGHT_0.w, LIGHT_0, LIGHT_0
|
||||
mul LIGHT_0.w, LIGHT_0, LIGHT_0
|
||||
mul LIGHT_0.w, LIGHT_0, LIGHT_0
|
||||
|
||||
// calculate light 1 factor
|
||||
//dp3 LIGHT_1.w, HALF_ANGLE, c[CV_LIGHT_DIRECTION_1] // L.H
|
||||
//max LIGHT_1.w, LIGHT_1.w, c[CV_CONST].x // clamp 0-1
|
||||
//mul LIGHT_1.w, LIGHT_1.w, c[CV_LIGHT_COLOR_1].w // light attentuation factor
|
||||
|
||||
// calculate light 2 factor
|
||||
//dp3 LIGHT_2.w, HALF_ANGLE, c[CV_LIGHT_DIRECTION_2] // L.H
|
||||
//max LIGHT_2.w, LIGHT_2.w, c[CV_CONST].x // clamp 0-1
|
||||
//mul LIGHT_2.w, LIGHT_2.w, c[CV_LIGHT_COLOR_2].w // light attentuation factor
|
||||
|
||||
// accumulate light colors
|
||||
mul COL, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
//mad COL, c[CV_LIGHT_COLOR_1], LIGHT_1.w, COL
|
||||
//mad COL, c[CV_LIGHT_COLOR_2], LIGHT_2.w, COL
|
||||
|
||||
|
||||
//mul oT2, COL, c[CV_SPECULAR]
|
||||
|
||||
// Set alpha to 1
|
||||
//add oT3.w, c[CV_CONST].y, -LIGHT_0.w
|
||||
|
||||
|
||||
//mov oT0, V_TEXTURE
|
||||
//mov oT1, V_TEXTURE
|
||||
|
||||
|
||||
@@ -0,0 +1,57 @@
|
||||
//
|
||||
// Command & Conquer Generals Zero Hour(tm)
|
||||
// Copyright 2025 Electronic Arts Inc.
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
//
|
||||
|
||||
// DX8 self shadowed bump specular with gloss shader
|
||||
// Kenny Mitchell
|
||||
|
||||
#include "shd8bumpspec_constants.h"
|
||||
|
||||
// pixel shader version 1.1
|
||||
ps.1.1
|
||||
|
||||
tex TEX_NORMALMAP // normal map texture
|
||||
//tex TEX_DECAL // decal texture
|
||||
|
||||
mov r0,TEX_NORMALMAP
|
||||
|
||||
//texcoord TEX_SPECULAR // specular term
|
||||
//texcoord t3
|
||||
|
||||
// bumped normal
|
||||
//dp3_sat r1, TEX_NORMALMAP_bx2, COL_LIGHT_bx2
|
||||
|
||||
// fill light normal
|
||||
//add r1, COL_LIGHT.a, r1
|
||||
|
||||
// modulate texture and light color
|
||||
//mul r0, COL_DIFFUSE, TEX_DECAL
|
||||
|
||||
// apply light intensity
|
||||
//mul r0, r0, r1
|
||||
|
||||
// specular section
|
||||
//dp3_sat r1, TEX_NORMALMAP_bx2, t3_bx2
|
||||
|
||||
//mul r1, r1, r1
|
||||
//mul r1, r1, r1
|
||||
|
||||
// apply gloss map
|
||||
//mul r1, TEX_DECAL.a, r1
|
||||
|
||||
//mad r0, TEX_SPECULAR, r1, r0
|
||||
|
||||
@@ -0,0 +1,221 @@
|
||||
//
|
||||
// Command & Conquer Generals Zero Hour(tm)
|
||||
// Copyright 2025 Electronic Arts Inc.
|
||||
//
|
||||
// This program is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
//
|
||||
|
||||
// DX8 self shadowed bump specular with gloss map vertex shader
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
vs.1.1
|
||||
|
||||
#include "shdhw_constants.h"
|
||||
|
||||
#include "shd8bumpspec_constants.h"
|
||||
|
||||
// In:
|
||||
// v0 - object space vertex position
|
||||
// v1 - object space normal
|
||||
// v2 - color
|
||||
// v3 - texture coords
|
||||
// v4 - S basis
|
||||
// v5 - T basis
|
||||
// v6 - SxT
|
||||
|
||||
// object space vertex position -> screen (early as possible for view clipping)
|
||||
dp4 EYE_VECTOR.x, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_0]
|
||||
dp4 EYE_VECTOR.y, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_1]
|
||||
dp4 EYE_VECTOR.z, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_2]
|
||||
dp4 EYE_VECTOR.w, V_POSITION, c[CV_WORLD_VIEW_PROJECTION_3]
|
||||
|
||||
mov oPos, EYE_VECTOR
|
||||
|
||||
dp4 oT0.x, V_POSITION, c[CV_TEXMAP_0]
|
||||
dp4 oT0.y, V_POSITION, c[CV_TEXMAP_1]
|
||||
dp4 oT0.z, V_POSITION, c[CV_TEXMAP_2]
|
||||
dp4 oT0.w, V_POSITION, c[CV_TEXMAP_3]
|
||||
|
||||
|
||||
// Transform basis vectors to world space
|
||||
dp3 S_WORLD.x, V_S, c[CV_WORLD_0]
|
||||
dp3 S_WORLD.y, V_S, c[CV_WORLD_1]
|
||||
dp3 S_WORLD.z, V_S, c[CV_WORLD_2]
|
||||
|
||||
dp3 T_WORLD.x, V_T, c[CV_WORLD_0]
|
||||
dp3 T_WORLD.y, V_T, c[CV_WORLD_1]
|
||||
dp3 T_WORLD.z, V_T, c[CV_WORLD_2]
|
||||
|
||||
dp3 SxT_WORLD.x, V_SxT, c[CV_WORLD_0]
|
||||
dp3 SxT_WORLD.y, V_SxT, c[CV_WORLD_1]
|
||||
dp3 SxT_WORLD.z, V_SxT, c[CV_WORLD_2]
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
// transform light 0 by basis vectors to put it into texture space
|
||||
dp3 LIGHT_LOCAL.x, S_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
dp3 LIGHT_LOCAL.y, T_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
dp3 LIGHT_LOCAL.z, SxT_WORLD.xyz, c[CV_LIGHT_DIRECTION_0]
|
||||
|
||||
// Normalize the light vector
|
||||
dp3 LIGHT_LOCAL.w, LIGHT_LOCAL, LIGHT_LOCAL
|
||||
rsq LIGHT_LOCAL.w, LIGHT_LOCAL.w
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, LIGHT_LOCAL.w
|
||||
|
||||
dp3 WORLD_NORMAL.x, V_NORMAL, c[CV_WORLD_0]
|
||||
dp3 WORLD_NORMAL.y, V_NORMAL, c[CV_WORLD_1]
|
||||
dp3 WORLD_NORMAL.z, V_NORMAL, c[CV_WORLD_2]
|
||||
|
||||
// Normalize the world normal vector
|
||||
dp3 WORLD_NORMAL.w, WORLD_NORMAL, WORLD_NORMAL
|
||||
rsq WORLD_NORMAL.w, WORLD_NORMAL.w
|
||||
mul WORLD_NORMAL, WORLD_NORMAL, WORLD_NORMAL.w
|
||||
|
||||
|
||||
// calculate light 0 factor
|
||||
dp3 LIGHT_0.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_0] // L.N
|
||||
max LIGHT_0.w, LIGHT_0.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_0.w, LIGHT_0.w, c[CV_LIGHT_COLOR_0].w // light attentuation factor
|
||||
|
||||
// calculate light 1 factor
|
||||
dp3 LIGHT_1.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_1] // L.N
|
||||
max LIGHT_1.w, LIGHT_1.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_1.w, LIGHT_1.w, c[CV_LIGHT_COLOR_1].w // light attentuation factor
|
||||
|
||||
// calculate light 2 factor
|
||||
dp3 LIGHT_2.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_2] // L.N
|
||||
max LIGHT_2.w, LIGHT_2.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_2.w, LIGHT_2.w, c[CV_LIGHT_COLOR_2].w // light attentuation factor
|
||||
|
||||
// calculate light 3 factor
|
||||
dp3 LIGHT_3.w, WORLD_NORMAL, c[CV_LIGHT_DIRECTION_3] // L.N
|
||||
max LIGHT_3.w, LIGHT_3.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_3.w, LIGHT_3.w, c[CV_LIGHT_COLOR_3].w // light attentuation factor
|
||||
|
||||
// accumulate light colors
|
||||
mul COL, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
mad COL, c[CV_LIGHT_COLOR_1], LIGHT_1.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_2], LIGHT_2.w, COL
|
||||
mad COL, c[CV_LIGHT_COLOR_3], LIGHT_3.w, COL
|
||||
|
||||
// apply vertex color and diffuse and ambient material terms
|
||||
mul COL, COL, V_DIFFUSE
|
||||
mul COL, COL, c[CV_DIFFUSE]
|
||||
add oD1, COL, c[CV_AMBIENT]
|
||||
|
||||
// Scale to 0-1
|
||||
add LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].yyy
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].zzz
|
||||
|
||||
// apply bump scale and bias controls
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_BUMPINESS].xxx
|
||||
add oD0, LIGHT_LOCAL, c[CV_BUMPINESS].yyy
|
||||
|
||||
// set compliment of diffuse light factor
|
||||
add oD0.w, c[CV_CONST].y, -LIGHT_0.w
|
||||
|
||||
|
||||
|
||||
// calculate specular term
|
||||
|
||||
// calculate half angle
|
||||
// transform vertex position to world space
|
||||
// to calculate V, vector to viewer in world
|
||||
// space.
|
||||
dp4 WORLD_VERTEX.x, V_POSITION, c[CV_WORLD_0]
|
||||
dp4 WORLD_VERTEX.y, V_POSITION, c[CV_WORLD_1]
|
||||
dp4 WORLD_VERTEX.z, V_POSITION, c[CV_WORLD_2]
|
||||
//dp4 WORLD_VERTEX.w, V_POSITION, c[CV_WORLD_3]
|
||||
|
||||
// Half angle vector is (L+V)/||L+V|| or Normalize( L+V )
|
||||
// ||a|| is magnitude of a
|
||||
// L = vec to light from vertex point
|
||||
// V = vec to viewer from vertex point
|
||||
|
||||
// vertex position - eye position
|
||||
// eye position - vertex position
|
||||
add EYE_VECTOR, c[CV_EYE_WORLD], -WORLD_VERTEX.xyz
|
||||
|
||||
// Normalize the eye vector
|
||||
dp3 EYE_VECTOR.w, EYE_VECTOR, EYE_VECTOR
|
||||
rsq EYE_VECTOR.w, EYE_VECTOR.w
|
||||
mul EYE_VECTOR, EYE_VECTOR, EYE_VECTOR.w
|
||||
|
||||
// Add them to average & create half angle vector
|
||||
add HALF_ANGLE, c[CV_LIGHT_DIRECTION_0], EYE_VECTOR
|
||||
|
||||
|
||||
// Normalize the half angle vector
|
||||
dp3 HALF_ANGLE.w, HALF_ANGLE, HALF_ANGLE
|
||||
rsq HALF_ANGLE.w, HALF_ANGLE.w
|
||||
mul HALF_ANGLE, HALF_ANGLE, HALF_ANGLE.w
|
||||
|
||||
|
||||
dp3 LIGHT_LOCAL.x, S_WORLD.xyz, HALF_ANGLE
|
||||
dp3 LIGHT_LOCAL.y, T_WORLD.xyz, HALF_ANGLE
|
||||
dp3 LIGHT_LOCAL.z, SxT_WORLD.xyz, HALF_ANGLE
|
||||
|
||||
// Normalize the half angle vector
|
||||
dp3 LIGHT_LOCAL.w, LIGHT_LOCAL, LIGHT_LOCAL
|
||||
rsq LIGHT_LOCAL.w, LIGHT_LOCAL.w
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, LIGHT_LOCAL.w
|
||||
|
||||
// Scale to 0-1
|
||||
//add LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].yyy
|
||||
//mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_CONST].zzz
|
||||
|
||||
// apply bump scale and bias controls
|
||||
mul LIGHT_LOCAL, LIGHT_LOCAL, c[CV_BUMPINESS].zzz
|
||||
//add oT3, LIGHT_LOCAL, c[CV_BUMPINESS].www
|
||||
|
||||
|
||||
|
||||
// calculate light 0 factor
|
||||
dp3 LIGHT_0.w, HALF_ANGLE, WORLD_NORMAL // N.H
|
||||
max LIGHT_0.w, LIGHT_0.w, c[CV_CONST].x // clamp 0-1
|
||||
mul LIGHT_0.w, LIGHT_0.w, c[CV_LIGHT_COLOR_0].w // light attentuation factor
|
||||
|
||||
mul LIGHT_0.w, LIGHT_0, LIGHT_0
|
||||
mul LIGHT_0.w, LIGHT_0, LIGHT_0
|
||||
mul LIGHT_0.w, LIGHT_0, LIGHT_0
|
||||
|
||||
// calculate light 1 factor
|
||||
//dp3 LIGHT_1.w, HALF_ANGLE, c[CV_LIGHT_DIRECTION_1] // L.H
|
||||
//max LIGHT_1.w, LIGHT_1.w, c[CV_CONST].x // clamp 0-1
|
||||
//mul LIGHT_1.w, LIGHT_1.w, c[CV_LIGHT_COLOR_1].w // light attentuation factor
|
||||
|
||||
// calculate light 2 factor
|
||||
//dp3 LIGHT_2.w, HALF_ANGLE, c[CV_LIGHT_DIRECTION_2] // L.H
|
||||
//max LIGHT_2.w, LIGHT_2.w, c[CV_CONST].x // clamp 0-1
|
||||
//mul LIGHT_2.w, LIGHT_2.w, c[CV_LIGHT_COLOR_2].w // light attentuation factor
|
||||
|
||||
// accumulate light colors
|
||||
mul COL, c[CV_LIGHT_COLOR_0], LIGHT_0.w
|
||||
//mad COL, c[CV_LIGHT_COLOR_1], LIGHT_1.w, COL
|
||||
//mad COL, c[CV_LIGHT_COLOR_2], LIGHT_2.w, COL
|
||||
|
||||
|
||||
//mul oT2, COL, c[CV_SPECULAR]
|
||||
|
||||
// Set alpha to 1
|
||||
//add oT3.w, c[CV_CONST].y, -LIGHT_0.w
|
||||
|
||||
|
||||
//mov oT0, V_TEXTURE
|
||||
//mov oT1, V_TEXTURE
|
||||
|
||||
|
||||
224
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdbumpdiff.cpp
Normal file
224
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdbumpdiff.cpp
Normal file
@@ -0,0 +1,224 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WW3D *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/ww3d2/shdbumpdiff.cpp $*
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 6/03/02 8:12a $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include "dx8fvf.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "assetmgr.h"
|
||||
|
||||
#include "shdbumpdiff.h"
|
||||
#include "shd6bumpdiff.h"
|
||||
#include "shd7bumpdiff.h"
|
||||
#include "shd8bumpdiff.h"
|
||||
|
||||
#include "editable.h"
|
||||
#include "shdclassids.h"
|
||||
#include "shddeffactory.h"
|
||||
#include "shdinterface.h"
|
||||
|
||||
#include "persistfactory.h"
|
||||
#include "wwhack.h"
|
||||
|
||||
DECLARE_FORCE_LINK(BumpDiffShader);
|
||||
REGISTER_SHDDEF(ShdBumpDiffDefClass,SHDDEF_CLASSID_BUMPDIFF,"Bump Diffuse");
|
||||
|
||||
// static member
|
||||
ShdVersion ShdBumpDiffDefClass::Version;
|
||||
|
||||
|
||||
// Save-Load methods for ShdDefClass
|
||||
enum
|
||||
{
|
||||
CHUNKID_VARIABLES = 0x16490450,
|
||||
|
||||
VARID_TEXTURE_NAME = 0x00,
|
||||
VARID_BUMP_MAP_NAME,
|
||||
|
||||
VARID_AMBIENT_COLOR,
|
||||
VARID_DIFFUSE_COLOR,
|
||||
VARID_DIFFUSE_BUMPINESS,
|
||||
};
|
||||
|
||||
ShdBumpDiffDefClass::ShdBumpDiffDefClass()
|
||||
: ShdDefClass(SHDDEF_CLASSID_BUMPDIFF),
|
||||
Ambient(1,1,1),
|
||||
Diffuse(1,1,1),
|
||||
Diffuse_Bumpiness(1,0)
|
||||
{
|
||||
NAMED_TEXTURE_FILENAME_PARAM(ShdBumpDiffDefClass, TextureName, "Base Map", "Targa Files", ".tga");
|
||||
NAMED_TEXTURE_FILENAME_PARAM(ShdBumpDiffDefClass, BumpMapName, "Bump Map", "Targa Files", ".tga");
|
||||
|
||||
NAMED_EDITABLE_PARAM(ShdBumpDiffDefClass, ParameterClass::TYPE_COLOR, Ambient, "Ambient");
|
||||
NAMED_EDITABLE_PARAM(ShdBumpDiffDefClass, ParameterClass::TYPE_COLOR, Diffuse, "Diffuse");
|
||||
|
||||
NAMED_EDITABLE_PARAM(ShdBumpDiffDefClass, ParameterClass::TYPE_FLOAT, Diffuse_Bumpiness.X, "Diffuse Bump Scale");
|
||||
NAMED_EDITABLE_PARAM(ShdBumpDiffDefClass, ParameterClass::TYPE_FLOAT, Diffuse_Bumpiness.Y, "Diffuse Bump Bias");
|
||||
}
|
||||
|
||||
ShdBumpDiffDefClass::ShdBumpDiffDefClass(const ShdBumpDiffDefClass& that)
|
||||
: ShdDefClass(that),
|
||||
Ambient(that.Ambient),
|
||||
Diffuse(that.Diffuse),
|
||||
Diffuse_Bumpiness(that.Diffuse_Bumpiness)
|
||||
{
|
||||
TextureName=that.TextureName;
|
||||
BumpMapName=that.BumpMapName;
|
||||
}
|
||||
|
||||
ShdBumpDiffDefClass::~ShdBumpDiffDefClass()
|
||||
{
|
||||
}
|
||||
|
||||
bool ShdBumpDiffDefClass::Is_Valid_Config(StringClass &message)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ShdBumpDiffDefClass::Save(ChunkSaveClass &csave)
|
||||
{
|
||||
ShdDefClass::Save(csave);
|
||||
|
||||
csave.Begin_Chunk(CHUNKID_VARIABLES);
|
||||
|
||||
bool retval = true;
|
||||
|
||||
// only save the file name
|
||||
char fname[_MAX_PATH];
|
||||
|
||||
_splitpath(TextureName,NULL,NULL,fname,NULL);
|
||||
strcat(fname,".tga");
|
||||
TextureName=fname;
|
||||
|
||||
WRITE_MICRO_CHUNK_WWSTRING(csave, VARID_TEXTURE_NAME, TextureName);
|
||||
|
||||
_splitpath(BumpMapName,NULL,NULL,fname,NULL);
|
||||
strcat(fname,".tga");
|
||||
BumpMapName=fname;
|
||||
|
||||
WRITE_MICRO_CHUNK_WWSTRING(csave, VARID_BUMP_MAP_NAME, BumpMapName);
|
||||
|
||||
WRITE_MICRO_CHUNK(csave, VARID_AMBIENT_COLOR, Ambient);
|
||||
WRITE_MICRO_CHUNK(csave, VARID_DIFFUSE_COLOR, Diffuse);
|
||||
|
||||
WRITE_MICRO_CHUNK(csave, VARID_DIFFUSE_BUMPINESS, Diffuse_Bumpiness);
|
||||
|
||||
csave.End_Chunk();
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
||||
bool ShdBumpDiffDefClass::Load(ChunkLoadClass &cload)
|
||||
{
|
||||
ShdDefClass::Load(cload);
|
||||
|
||||
// Loop through all the microchunks that define the variables
|
||||
while (cload.Open_Chunk()) {
|
||||
switch (cload.Cur_Chunk_ID())
|
||||
{
|
||||
case CHUNKID_VARIABLES:
|
||||
while (cload.Open_Micro_Chunk())
|
||||
{
|
||||
switch (cload.Cur_Micro_Chunk_ID())
|
||||
{
|
||||
READ_MICRO_CHUNK_WWSTRING(cload, VARID_TEXTURE_NAME, TextureName);
|
||||
READ_MICRO_CHUNK_WWSTRING(cload, VARID_BUMP_MAP_NAME, BumpMapName);
|
||||
|
||||
READ_MICRO_CHUNK(cload, VARID_AMBIENT_COLOR, Ambient);
|
||||
READ_MICRO_CHUNK(cload, VARID_DIFFUSE_COLOR, Diffuse);
|
||||
|
||||
READ_MICRO_CHUNK(cload, VARID_DIFFUSE_BUMPINESS, Diffuse_Bumpiness);
|
||||
}
|
||||
|
||||
cload.Close_Micro_Chunk();
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
cload.Close_Chunk();
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
void ShdBumpDiffDefClass::Init()
|
||||
{
|
||||
// select shader version
|
||||
if ((DX8Wrapper::Get_Current_Caps()->Get_Pixel_Shader_Major_Version())==1 &&
|
||||
(DX8Wrapper::Get_Current_Caps()->Get_Pixel_Shader_Minor_Version())>=1)
|
||||
{
|
||||
Version.Set(SHDVER_8);
|
||||
}
|
||||
else if (DX8Wrapper::Get_Current_Caps()->Support_Dot3())
|
||||
{
|
||||
Version.Set(SHDVER_7);
|
||||
}
|
||||
else
|
||||
{
|
||||
Version.Set(SHDVER_6);
|
||||
}
|
||||
|
||||
switch (Version.Get())
|
||||
{
|
||||
case SHDVER_8 : Shd8BumpDiffClass::Init(); break;
|
||||
case SHDVER_7 : Shd7BumpDiffClass::Init(); break;
|
||||
case SHDVER_6 : Shd6BumpDiffClass::Init(); break;
|
||||
}
|
||||
}
|
||||
|
||||
void ShdBumpDiffDefClass::Shutdown()
|
||||
{
|
||||
switch (Version.Get())
|
||||
{
|
||||
case SHDVER_8 : Shd8BumpDiffClass::Shutdown(); break;
|
||||
case SHDVER_7 : Shd7BumpDiffClass::Shutdown(); break;
|
||||
case SHDVER_6 : Shd6BumpDiffClass::Shutdown(); break;
|
||||
}
|
||||
}
|
||||
|
||||
ShdInterfaceClass* ShdBumpDiffDefClass::Create() const
|
||||
{
|
||||
switch (Version.Get())
|
||||
{
|
||||
case SHDVER_8 : return new Shd8BumpDiffClass(this); break;
|
||||
case SHDVER_7 : return new Shd7BumpDiffClass(this); break;
|
||||
case SHDVER_6 : return new Shd6BumpDiffClass(this); break;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
109
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdbumpdiff.h
Normal file
109
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdbumpdiff.h
Normal file
@@ -0,0 +1,109 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WW3D *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/ww3d2/shdbumpdiff.h $*
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 6/03/02 8:12a $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHDBUMPDIFF_H
|
||||
#define SHDBUMPDIFF_H
|
||||
|
||||
#include "shddef.h"
|
||||
#include "saveload.h"
|
||||
#include "shader.h"
|
||||
|
||||
class ShdBumpDiffDefClass : public ShdDefClass
|
||||
{
|
||||
public:
|
||||
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
// Editable interface requirements
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
DECLARE_EDITABLE(ShdBumpDiffDefClass, ShdDefClass);
|
||||
|
||||
ShdBumpDiffDefClass();
|
||||
ShdBumpDiffDefClass(const ShdBumpDiffDefClass& that);
|
||||
virtual ~ShdBumpDiffDefClass();
|
||||
|
||||
virtual ShdDefClass* Clone() const { return new ShdBumpDiffDefClass(*this); }
|
||||
|
||||
// Shader Creation (should create a shader compatible with the current hardware/API)
|
||||
virtual void Init();
|
||||
virtual void Shutdown();
|
||||
virtual ShdInterfaceClass* Create() const;
|
||||
|
||||
// Validation methods
|
||||
virtual bool Is_Valid_Config(StringClass &message);
|
||||
|
||||
// Requirements
|
||||
virtual bool Requires_Normals() const { return true; }
|
||||
virtual bool Requires_Tangent_Space_Vectors() const { return true; }
|
||||
virtual bool Requires_Sorting() const { return false; }
|
||||
virtual int Static_Sort_Index() const { return 0; }
|
||||
|
||||
// From PersistClass
|
||||
virtual bool Save(ChunkSaveClass &csave);
|
||||
virtual bool Load(ChunkLoadClass &cload);
|
||||
|
||||
void Set_Texture_Name(const StringClass& name) { TextureName=name; }
|
||||
const StringClass& Get_Texture_Name() const { return TextureName; }
|
||||
|
||||
void Set_Bump_Map_Name(const StringClass& name) { BumpMapName=name; }
|
||||
const StringClass& Get_Bump_Map_Name() const { return BumpMapName; }
|
||||
|
||||
void Set_Ambient(const Vector3& ambient) { Ambient=ambient; }
|
||||
const Vector3& Get_Ambient() const { return Ambient; }
|
||||
|
||||
void Set_Diffuse(const Vector3& diffuse) { Diffuse=diffuse; }
|
||||
const Vector3& Get_Diffuse() const { return Diffuse; }
|
||||
|
||||
void Set_Diffuse_Bumpiness(const Vector2& diffuse_bumpiness) { Diffuse_Bumpiness=diffuse_bumpiness; }
|
||||
const Vector2& Get_Diffuse_Bumpiness() const { return Diffuse_Bumpiness; }
|
||||
|
||||
private:
|
||||
|
||||
static ShdVersion Version;
|
||||
|
||||
bool Save_Variables(ChunkSaveClass &csave);
|
||||
bool Load_Variables(ChunkLoadClass &cload);
|
||||
|
||||
StringClass TextureName;
|
||||
StringClass BumpMapName;
|
||||
|
||||
Vector3 Ambient;
|
||||
Vector3 Diffuse;
|
||||
|
||||
Vector2 Diffuse_Bumpiness;
|
||||
};
|
||||
|
||||
|
||||
#endif //SHDBUMPDIFF_H
|
||||
236
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdbumpspec.cpp
Normal file
236
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdbumpspec.cpp
Normal file
@@ -0,0 +1,236 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WW3D *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/ww3d2/shdbumpspec.cpp $*
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 5/27/02 2:21p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include "dx8fvf.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "assetmgr.h"
|
||||
|
||||
#include "shdbumpspec.h"
|
||||
#include "shd6bumpspec.h"
|
||||
#include "shd7bumpspec.h"
|
||||
#include "shd8bumpspec.h"
|
||||
|
||||
#include "editable.h"
|
||||
#include "shdclassids.h"
|
||||
#include "shddeffactory.h"
|
||||
#include "shdinterface.h"
|
||||
|
||||
#include "persistfactory.h"
|
||||
#include "wwhack.h"
|
||||
|
||||
DECLARE_FORCE_LINK(BumpSpecShader);
|
||||
REGISTER_SHDDEF(ShdBumpSpecDefClass,SHDDEF_CLASSID_BUMPSPEC,"Bump Specular");
|
||||
|
||||
// static member
|
||||
ShdVersion ShdBumpSpecDefClass::Version;
|
||||
|
||||
// Save-Load methods for ShdDefClass
|
||||
enum
|
||||
{
|
||||
CHUNKID_VARIABLES = 0x16490450,
|
||||
|
||||
VARID_TEXTURE_NAME = 0x00,
|
||||
VARID_BUMP_MAP_NAME,
|
||||
|
||||
VARID_AMBIENT_COLOR,
|
||||
VARID_DIFFUSE_COLOR,
|
||||
VARID_SPECULAR_COLOR,
|
||||
VARID_DIFFUSE_BUMPINESS,
|
||||
VARID_SPECULAR_BUMPINESS
|
||||
};
|
||||
|
||||
ShdBumpSpecDefClass::ShdBumpSpecDefClass()
|
||||
: ShdDefClass(SHDDEF_CLASSID_BUMPSPEC),
|
||||
Ambient(1,1,1),
|
||||
Diffuse(1,1,1),
|
||||
Specular(1,1,1),
|
||||
Diffuse_Bumpiness(1,0),
|
||||
Specular_Bumpiness(1,0)
|
||||
{
|
||||
NAMED_TEXTURE_FILENAME_PARAM(ShdBumpSpecDefClass, TextureName, "Base and Alpha Gloss Map", "Targa Files", ".tga");
|
||||
NAMED_TEXTURE_FILENAME_PARAM(ShdBumpSpecDefClass, BumpMapName, "Bump Map", "Targa Files", ".tga");
|
||||
|
||||
NAMED_EDITABLE_PARAM(ShdBumpSpecDefClass, ParameterClass::TYPE_COLOR, Ambient, "Ambient");
|
||||
NAMED_EDITABLE_PARAM(ShdBumpSpecDefClass, ParameterClass::TYPE_COLOR, Diffuse, "Diffuse");
|
||||
NAMED_EDITABLE_PARAM(ShdBumpSpecDefClass, ParameterClass::TYPE_COLOR, Specular, "Specular");
|
||||
|
||||
NAMED_EDITABLE_PARAM(ShdBumpSpecDefClass, ParameterClass::TYPE_FLOAT, Diffuse_Bumpiness.X, "Diffuse Bump Scale");
|
||||
NAMED_EDITABLE_PARAM(ShdBumpSpecDefClass, ParameterClass::TYPE_FLOAT, Diffuse_Bumpiness.Y, "Diffuse Bump Bias");
|
||||
NAMED_EDITABLE_PARAM(ShdBumpSpecDefClass, ParameterClass::TYPE_FLOAT, Specular_Bumpiness.X, "Specular Bump Scale");
|
||||
NAMED_EDITABLE_PARAM(ShdBumpSpecDefClass, ParameterClass::TYPE_FLOAT, Specular_Bumpiness.Y, "Specular Bump Bias");
|
||||
}
|
||||
|
||||
ShdBumpSpecDefClass::ShdBumpSpecDefClass(const ShdBumpSpecDefClass& that)
|
||||
: ShdDefClass(that),
|
||||
Ambient(that.Ambient),
|
||||
Diffuse(that.Diffuse),
|
||||
Specular(that.Specular),
|
||||
Diffuse_Bumpiness(that.Diffuse_Bumpiness),
|
||||
Specular_Bumpiness(that.Specular_Bumpiness)
|
||||
{
|
||||
TextureName=that.TextureName;
|
||||
BumpMapName=that.BumpMapName;
|
||||
}
|
||||
|
||||
ShdBumpSpecDefClass::~ShdBumpSpecDefClass()
|
||||
{
|
||||
}
|
||||
|
||||
bool ShdBumpSpecDefClass::Is_Valid_Config(StringClass &message)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ShdBumpSpecDefClass::Save(ChunkSaveClass &csave)
|
||||
{
|
||||
ShdDefClass::Save(csave);
|
||||
|
||||
csave.Begin_Chunk(CHUNKID_VARIABLES);
|
||||
|
||||
bool retval = true;
|
||||
|
||||
// only save the file name
|
||||
char fname[_MAX_PATH];
|
||||
|
||||
_splitpath(TextureName,NULL,NULL,fname,NULL);
|
||||
strcat(fname,".tga");
|
||||
TextureName=fname;
|
||||
|
||||
WRITE_MICRO_CHUNK_WWSTRING(csave, VARID_TEXTURE_NAME, TextureName);
|
||||
|
||||
_splitpath(BumpMapName,NULL,NULL,fname,NULL);
|
||||
strcat(fname,".tga");
|
||||
BumpMapName=fname;
|
||||
|
||||
WRITE_MICRO_CHUNK_WWSTRING(csave, VARID_BUMP_MAP_NAME, BumpMapName);
|
||||
|
||||
WRITE_MICRO_CHUNK(csave, VARID_AMBIENT_COLOR, Ambient);
|
||||
WRITE_MICRO_CHUNK(csave, VARID_DIFFUSE_COLOR, Diffuse);
|
||||
WRITE_MICRO_CHUNK(csave, VARID_SPECULAR_COLOR, Specular);
|
||||
|
||||
WRITE_MICRO_CHUNK(csave, VARID_DIFFUSE_BUMPINESS, Diffuse_Bumpiness);
|
||||
WRITE_MICRO_CHUNK(csave, VARID_SPECULAR_BUMPINESS, Specular_Bumpiness);
|
||||
|
||||
csave.End_Chunk();
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
||||
bool ShdBumpSpecDefClass::Load(ChunkLoadClass &cload)
|
||||
{
|
||||
ShdDefClass::Load(cload);
|
||||
|
||||
// Loop through all the microchunks that define the variables
|
||||
while (cload.Open_Chunk()) {
|
||||
switch (cload.Cur_Chunk_ID())
|
||||
{
|
||||
case CHUNKID_VARIABLES:
|
||||
while (cload.Open_Micro_Chunk())
|
||||
{
|
||||
switch (cload.Cur_Micro_Chunk_ID())
|
||||
{
|
||||
READ_MICRO_CHUNK_WWSTRING(cload, VARID_TEXTURE_NAME, TextureName);
|
||||
READ_MICRO_CHUNK_WWSTRING(cload, VARID_BUMP_MAP_NAME, BumpMapName);
|
||||
|
||||
READ_MICRO_CHUNK(cload, VARID_AMBIENT_COLOR, Ambient);
|
||||
READ_MICRO_CHUNK(cload, VARID_DIFFUSE_COLOR, Diffuse);
|
||||
READ_MICRO_CHUNK(cload, VARID_SPECULAR_COLOR, Specular);
|
||||
|
||||
READ_MICRO_CHUNK(cload, VARID_DIFFUSE_BUMPINESS, Diffuse_Bumpiness);
|
||||
READ_MICRO_CHUNK(cload, VARID_SPECULAR_BUMPINESS, Specular_Bumpiness);
|
||||
}
|
||||
|
||||
cload.Close_Micro_Chunk();
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
cload.Close_Chunk();
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
void ShdBumpSpecDefClass::Init()
|
||||
{
|
||||
// select shader version
|
||||
if ((DX8Wrapper::Get_Current_Caps()->Get_Pixel_Shader_Major_Version())==1 &&
|
||||
(DX8Wrapper::Get_Current_Caps()->Get_Pixel_Shader_Minor_Version())>=1)
|
||||
{
|
||||
Version.Set(SHDVER_8);
|
||||
}
|
||||
else if (DX8Wrapper::Get_Current_Caps()->Support_Dot3())
|
||||
{
|
||||
Version.Set(SHDVER_7);
|
||||
}
|
||||
else
|
||||
{
|
||||
Version.Set(SHDVER_6);
|
||||
}
|
||||
|
||||
switch (Version.Get())
|
||||
{
|
||||
case SHDVER_8 : Shd8BumpSpecClass::Init(); break;
|
||||
case SHDVER_7 : Shd7BumpSpecClass::Init(); break;
|
||||
case SHDVER_6 : Shd6BumpSpecClass::Init(); break;
|
||||
}
|
||||
}
|
||||
|
||||
void ShdBumpSpecDefClass::Shutdown()
|
||||
{
|
||||
switch (Version.Get())
|
||||
{
|
||||
case SHDVER_8 : Shd8BumpSpecClass::Shutdown(); break;
|
||||
case SHDVER_7 : Shd7BumpSpecClass::Shutdown(); break;
|
||||
case SHDVER_6 : Shd6BumpSpecClass::Shutdown(); break;
|
||||
}
|
||||
}
|
||||
|
||||
ShdInterfaceClass* ShdBumpSpecDefClass::Create() const
|
||||
{
|
||||
switch (Version.Get())
|
||||
{
|
||||
case SHDVER_8 : return new Shd8BumpSpecClass(this); break;
|
||||
case SHDVER_7 : return new Shd7BumpSpecClass(this); break;
|
||||
case SHDVER_6 : return new Shd6BumpSpecClass(this); break;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
116
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdbumpspec.h
Normal file
116
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdbumpspec.h
Normal file
@@ -0,0 +1,116 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WW3D *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/ww3d2/shdbumpspec.h $*
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 5/27/02 2:21p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHDBUMPSPEC_H
|
||||
#define SHDBUMPSPEC_H
|
||||
|
||||
#include "shddef.h"
|
||||
#include "saveload.h"
|
||||
|
||||
class ShdBumpSpecDefClass : public ShdDefClass
|
||||
{
|
||||
public:
|
||||
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
// Editable interface requirements
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
DECLARE_EDITABLE(ShdBumpSpecDefClass, ShdDefClass);
|
||||
|
||||
ShdBumpSpecDefClass();
|
||||
ShdBumpSpecDefClass(const ShdBumpSpecDefClass& that);
|
||||
virtual ~ShdBumpSpecDefClass();
|
||||
|
||||
virtual ShdDefClass* Clone() const { return new ShdBumpSpecDefClass(*this); }
|
||||
|
||||
// Shader Creation (should create a shader compatible with the current hardware/API)
|
||||
virtual void Init();
|
||||
virtual void Shutdown();
|
||||
virtual ShdInterfaceClass* Create() const;
|
||||
|
||||
// Validation methods
|
||||
virtual bool Is_Valid_Config(StringClass &message);
|
||||
|
||||
// Requirements
|
||||
virtual bool Requires_Normals() const { return true; }
|
||||
virtual bool Requires_Tangent_Space_Vectors() const { return true; }
|
||||
virtual bool Requires_Sorting() const { return false; }
|
||||
virtual int Static_Sort_Index() const { return 0; }
|
||||
|
||||
// From PersistClass
|
||||
virtual bool Save(ChunkSaveClass &csave);
|
||||
virtual bool Load(ChunkLoadClass &cload);
|
||||
|
||||
void Set_Texture_Name(const StringClass& name) { TextureName=name; }
|
||||
const StringClass& Get_Texture_Name() const { return TextureName; }
|
||||
|
||||
void Set_Bump_Map_Name(const StringClass& name) { BumpMapName=name; }
|
||||
const StringClass& Get_Bump_Map_Name() const { return BumpMapName; }
|
||||
|
||||
void Set_Ambient(const Vector3& ambient) { Ambient=ambient; }
|
||||
const Vector3& Get_Ambient() const { return Ambient; }
|
||||
|
||||
void Set_Diffuse(const Vector3& diffuse) { Diffuse=diffuse; }
|
||||
const Vector3& Get_Diffuse() const { return Diffuse; }
|
||||
|
||||
void Set_Specular(const Vector3& specular) { Specular=specular; }
|
||||
const Vector3& Get_Specular() const { return Specular; }
|
||||
|
||||
void Set_Diffuse_Bumpiness(const Vector2& diffuse_bumpiness) { Diffuse_Bumpiness=diffuse_bumpiness; }
|
||||
const Vector2& Get_Diffuse_Bumpiness() const { return Diffuse_Bumpiness; }
|
||||
|
||||
void Set_Specular_Bumpiness(const Vector2& specular_bumpiness) { Specular_Bumpiness=specular_bumpiness; }
|
||||
const Vector2& Get_Specular_Bumpiness() const { return Specular_Bumpiness; }
|
||||
|
||||
private:
|
||||
|
||||
static ShdVersion Version;
|
||||
|
||||
bool Save_Variables(ChunkSaveClass &csave);
|
||||
bool Load_Variables(ChunkLoadClass &cload);
|
||||
|
||||
StringClass TextureName;
|
||||
StringClass BumpMapName;
|
||||
|
||||
Vector3 Ambient;
|
||||
Vector3 Diffuse;
|
||||
Vector3 Specular;
|
||||
|
||||
Vector2 Diffuse_Bumpiness;
|
||||
Vector2 Specular_Bumpiness;
|
||||
};
|
||||
|
||||
|
||||
#endif //SHDBUMPSPEC_H
|
||||
@@ -0,0 +1,70 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shdclassids.h $*
|
||||
* *
|
||||
* $Org Author:: Jani_p
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 8/01/02 3:12p $*
|
||||
* *
|
||||
* $Revision:: 4 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHDCLASSIDS_H
|
||||
#define SHDCLASSIDS_H
|
||||
|
||||
|
||||
/*
|
||||
** ClassID's for Shader Definitions
|
||||
*/
|
||||
enum
|
||||
{
|
||||
SHDDEF_CLASSID_DUMMY = 0,
|
||||
SHDDEF_CLASSID_SIMPLE,
|
||||
SHDDEF_CLASSID_GLOSSMASK,
|
||||
SHDDEF_CLASSID_BUMPSPEC,
|
||||
SHDDEF_CLASSID_BUMPDIFF,
|
||||
SHDDEF_CLASSID_CUBEMAP,
|
||||
SHDDEF_CLASSID_LEGACYW3D,
|
||||
SHDDEF_CLASSID_LAST,
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
** ClassID's for actual Shader Implementations (typically there will be several for each "type", one
|
||||
** for each hardware configuration...)
|
||||
*/
|
||||
enum
|
||||
{
|
||||
SHD_CLASSID_DUMMY = 0,
|
||||
SHD_CLASSID_LAST,
|
||||
};
|
||||
|
||||
|
||||
#endif //SHDCLASSIDS_H
|
||||
328
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdcubemap.cpp
Normal file
328
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdcubemap.cpp
Normal file
@@ -0,0 +1,328 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shdcubemap.cpp $*
|
||||
* *
|
||||
* $Org Author:: Kenny_m
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 8/01/02 3:12p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* Currently unsupported due to cube map texture management needed by W3D
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include <d3dx8math.h>
|
||||
#include "dx8fvf.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "assetmgr.h"
|
||||
|
||||
#include "shdcubemap.h"
|
||||
|
||||
#include "editable.h"
|
||||
#include "shdclassids.h"
|
||||
#include "shddeffactory.h"
|
||||
#include "shdinterface.h"
|
||||
#include "shdhwshader.h"
|
||||
|
||||
#include "persistfactory.h"
|
||||
#include "wwhack.h"
|
||||
|
||||
DECLARE_FORCE_LINK(CubeMapShader);
|
||||
REGISTER_SHDDEF(ShdCubeMapDefClass,SHDDEF_CLASSID_CUBEMAP,"Cube Map");
|
||||
|
||||
|
||||
// Save-Load methods for ShdDefClass
|
||||
enum
|
||||
{
|
||||
CHUNKID_VARIABLES = 0x16490470,
|
||||
|
||||
VARID_TEXTURE_NAME = 0x00,
|
||||
|
||||
VARID_AMBIENT_COLOR,
|
||||
VARID_DIFFUSE_COLOR,
|
||||
VARID_SPECULAR_COLOR
|
||||
};
|
||||
|
||||
ShdCubeMapDefClass::ShdCubeMapDefClass()
|
||||
: ShdDefClass(SHDDEF_CLASSID_CUBEMAP),
|
||||
Ambient(1,1,1),
|
||||
Diffuse(1,1,1),
|
||||
Specular(0,0,0)
|
||||
{
|
||||
NAMED_TEXTURE_FILENAME_PARAM(ShdCubeMapDefClass, TextureName, "Texture Name", "Targa Files", ".tga");
|
||||
|
||||
NAMED_EDITABLE_PARAM(ShdCubeMapDefClass, ParameterClass::TYPE_COLOR, Ambient, "Ambient");
|
||||
NAMED_EDITABLE_PARAM(ShdCubeMapDefClass, ParameterClass::TYPE_COLOR, Diffuse, "Diffuse");
|
||||
NAMED_EDITABLE_PARAM(ShdCubeMapDefClass, ParameterClass::TYPE_COLOR, Specular, "Specular");
|
||||
}
|
||||
|
||||
ShdCubeMapDefClass::ShdCubeMapDefClass(const ShdCubeMapDefClass& that)
|
||||
: ShdDefClass(that),
|
||||
Ambient(that.Ambient),
|
||||
Diffuse(that.Diffuse),
|
||||
Specular(that.Specular)
|
||||
{
|
||||
TextureName=that.TextureName;
|
||||
}
|
||||
|
||||
ShdCubeMapDefClass::~ShdCubeMapDefClass()
|
||||
{
|
||||
}
|
||||
|
||||
bool ShdCubeMapDefClass::Is_Valid_Config(StringClass &message)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ShdCubeMapDefClass::Save(ChunkSaveClass &csave)
|
||||
{
|
||||
ShdDefClass::Save(csave);
|
||||
|
||||
csave.Begin_Chunk(CHUNKID_VARIABLES);
|
||||
|
||||
bool retval = true;
|
||||
|
||||
// only save the file name
|
||||
char fname[_MAX_PATH];
|
||||
|
||||
_splitpath(TextureName,NULL,NULL,fname,NULL);
|
||||
strcat(fname,".dds");
|
||||
TextureName=fname;
|
||||
|
||||
WRITE_MICRO_CHUNK_WWSTRING(csave, VARID_TEXTURE_NAME, TextureName);
|
||||
|
||||
WRITE_MICRO_CHUNK(csave, VARID_AMBIENT_COLOR, Ambient);
|
||||
WRITE_MICRO_CHUNK(csave, VARID_DIFFUSE_COLOR, Diffuse);
|
||||
WRITE_MICRO_CHUNK(csave, VARID_SPECULAR_COLOR, Specular);
|
||||
|
||||
csave.End_Chunk();
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
||||
bool ShdCubeMapDefClass::Load(ChunkLoadClass &cload)
|
||||
{
|
||||
ShdDefClass::Load(cload);
|
||||
|
||||
// Loop through all the microchunks that define the variables
|
||||
while (cload.Open_Chunk()) {
|
||||
switch (cload.Cur_Chunk_ID())
|
||||
{
|
||||
case CHUNKID_VARIABLES:
|
||||
while (cload.Open_Micro_Chunk())
|
||||
{
|
||||
switch (cload.Cur_Micro_Chunk_ID())
|
||||
{
|
||||
READ_MICRO_CHUNK_WWSTRING(cload, VARID_TEXTURE_NAME, TextureName);
|
||||
|
||||
READ_MICRO_CHUNK(cload, VARID_AMBIENT_COLOR, Ambient);
|
||||
READ_MICRO_CHUNK(cload, VARID_DIFFUSE_COLOR, Diffuse);
|
||||
READ_MICRO_CHUNK(cload, VARID_SPECULAR_COLOR, Specular);
|
||||
}
|
||||
|
||||
cload.Close_Micro_Chunk();
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
cload.Close_Chunk();
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
void ShdCubeMapDefClass::Init()
|
||||
{
|
||||
Shd6CubeMapClass::Init();
|
||||
}
|
||||
|
||||
void ShdCubeMapDefClass::Shutdown()
|
||||
{
|
||||
Shd6CubeMapClass::Shutdown();
|
||||
}
|
||||
|
||||
ShdInterfaceClass* ShdCubeMapDefClass::Create() const
|
||||
{
|
||||
return new Shd6CubeMapClass(this);
|
||||
}
|
||||
|
||||
|
||||
|
||||
Matrix4x4 Shd6CubeMapClass::View_Projection_Matrix;
|
||||
|
||||
Shd6CubeMapClass::Shd6CubeMapClass(const ShdDefClass* def)
|
||||
: ShdInterfaceClass(def,SHDDEF_CLASSID_CUBEMAP),
|
||||
Texture(NULL)
|
||||
{
|
||||
ShdCubeMapDefClass* Definition=(ShdCubeMapDefClass*)def;
|
||||
|
||||
Texture=WW3DAssetManager::Get_Instance()->Get_Texture
|
||||
(
|
||||
Definition->Get_Texture_Name(),
|
||||
MIP_LEVELS_ALL,
|
||||
WW3D_FORMAT_UNKNOWN,
|
||||
true,
|
||||
TextureBaseClass::TEX_CUBEMAP
|
||||
);
|
||||
|
||||
const Vector3& a=Definition->Get_Ambient();
|
||||
Ambient.Set(a.X,a.Y,a.Z,1.0f);
|
||||
|
||||
const Vector3& d=Definition->Get_Diffuse();
|
||||
Diffuse.Set(d.X,d.Y,d.Z,1.0f);
|
||||
|
||||
const Vector3& s=Definition->Get_Specular();
|
||||
Specular.Set(s.X,s.Y,s.Z,1.0f);
|
||||
|
||||
Material=new D3DMATERIAL8;
|
||||
memset(Material,0,sizeof(D3DMATERIAL8));
|
||||
Material->Ambient.r=a.X; Material->Ambient.g=a.Y; Material->Ambient.b=a.Z;
|
||||
Material->Diffuse.r=d.X; Material->Diffuse.g=d.Y; Material->Diffuse.b=d.Z;
|
||||
Material->Specular.r=s.X; Material->Specular.g=s.Y; Material->Specular.b=s.Z;
|
||||
Material->Power=20;
|
||||
}
|
||||
|
||||
Shd6CubeMapClass::~Shd6CubeMapClass()
|
||||
{
|
||||
REF_PTR_RELEASE(Texture);
|
||||
}
|
||||
|
||||
void Shd6CubeMapClass::Init()
|
||||
{
|
||||
}
|
||||
|
||||
void Shd6CubeMapClass::Shutdown()
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
/**********************************************************************************************
|
||||
//! Apply shared states for 1 pass DX6
|
||||
/*! 7/12/02 3:39p KJM Created
|
||||
*/
|
||||
void Shd6CubeMapClass::Apply_Shared(int pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
// fixed function uses pass through by default
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_CAMERASPACEREFLECTIONVECTOR);
|
||||
|
||||
// set vertex shader
|
||||
DX8Wrapper::Set_Vertex_Shader(DX8_FVF_XYZNDCUBEMAP);
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLOROP, D3DTOP_MODULATE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_ALPHAOP, D3DTOP_MODULATE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLOROP, D3DTOP_DISABLE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAOP, D3DTOP_DISABLE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_LIGHTING, TRUE);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_SPECULARENABLE, TRUE);
|
||||
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_AMBIENTMATERIALSOURCE,D3DMCS_MATERIAL);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_DIFFUSEMATERIALSOURCE,D3DMCS_MATERIAL);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_SPECULARMATERIALSOURCE,D3DMCS_MATERIAL);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_EMISSIVEMATERIALSOURCE,D3DMCS_MATERIAL);
|
||||
|
||||
DX8Wrapper::Set_DX8_Material(Material);
|
||||
}
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Apply per instance states for 1 pass DX6
|
||||
/*! 7/10/02 5:39p KJM Created
|
||||
*/
|
||||
void Shd6CubeMapClass::Apply_Instance(int cur_pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
DX8Wrapper::Set_Texture(0, Texture);
|
||||
}
|
||||
|
||||
unsigned Shd6CubeMapClass::Get_Vertex_Stream_Count() const
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
unsigned Shd6CubeMapClass::Get_Vertex_Size(unsigned stream) const
|
||||
{
|
||||
return sizeof(VertexFormatXYZNDCUBEMAP);
|
||||
}
|
||||
|
||||
void Shd6CubeMapClass::Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
)
|
||||
{
|
||||
VertexFormatXYZNDCUBEMAP* verts=(VertexFormatXYZNDCUBEMAP*)dest_buffer;
|
||||
|
||||
for (unsigned i=0; i<vertex_count; ++i)
|
||||
{
|
||||
if (vss.Locations)
|
||||
{
|
||||
verts[i].x=vss.Locations[i][0];
|
||||
verts[i].y=vss.Locations[i][1];
|
||||
verts[i].z=vss.Locations[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].x=0.0f;
|
||||
verts[i].y=0.0f;
|
||||
verts[i].z=0.0f;
|
||||
}
|
||||
|
||||
if (vss.DiffuseInt)
|
||||
{
|
||||
verts[i].diffuse=vss.DiffuseInt[i];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].diffuse=0xffffffff;
|
||||
}
|
||||
|
||||
if (vss.Normals)
|
||||
{
|
||||
verts[i].nx=vss.Normals[i][0];
|
||||
verts[i].ny=vss.Normals[i][1];
|
||||
verts[i].nz=vss.Normals[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].nx=0.0f;
|
||||
verts[i].ny=0.0f;
|
||||
verts[i].nz=0.0f;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
152
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdcubemap.h
Normal file
152
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdcubemap.h
Normal file
@@ -0,0 +1,152 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shdcubemap.cpp $*
|
||||
* *
|
||||
* $Org Author:: Kenny_m
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 8/01/02 3:12p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHDCUBEMAP_H
|
||||
#define SHDCUBEMAP_H
|
||||
|
||||
#ifndef SHDINTERFACE_H
|
||||
#include "shdinterface.h"
|
||||
#endif
|
||||
|
||||
#include "shddef.h"
|
||||
#include "saveload.h"
|
||||
#include "shader.h"
|
||||
|
||||
class ShdCubeMapDefClass : public ShdDefClass
|
||||
{
|
||||
public:
|
||||
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
// Editable interface requirements
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
DECLARE_EDITABLE(ShdCubeMapDefClass, ShdDefClass);
|
||||
|
||||
ShdCubeMapDefClass();
|
||||
ShdCubeMapDefClass(const ShdCubeMapDefClass& that);
|
||||
virtual ~ShdCubeMapDefClass();
|
||||
|
||||
virtual ShdDefClass* Clone() const { return new ShdCubeMapDefClass(*this); }
|
||||
|
||||
// Shader Creation (should create a shader compatible with the current hardware/API)
|
||||
virtual void Init();
|
||||
virtual void Shutdown();
|
||||
virtual ShdInterfaceClass* Create() const;
|
||||
|
||||
// Validation methods
|
||||
virtual bool Is_Valid_Config(StringClass &message);
|
||||
|
||||
// Requirements
|
||||
virtual bool Requires_Normals() const { return true; }
|
||||
virtual bool Requires_Tangent_Space_Vectors() const { return false; }
|
||||
virtual bool Requires_Sorting() const { return false; }
|
||||
virtual int Static_Sort_Index() const { return 0; }
|
||||
|
||||
// From PersistClass
|
||||
virtual bool Save(ChunkSaveClass &csave);
|
||||
virtual bool Load(ChunkLoadClass &cload);
|
||||
|
||||
void Set_Texture_Name(const StringClass& name) { TextureName=name; }
|
||||
const StringClass& Get_Texture_Name() const { return TextureName; }
|
||||
|
||||
void Set_Ambient(const Vector3& ambient) { Ambient=ambient; }
|
||||
const Vector3& Get_Ambient() const { return Ambient; }
|
||||
|
||||
void Set_Diffuse(const Vector3& diffuse) { Diffuse=diffuse; }
|
||||
const Vector3& Get_Diffuse() const { return Diffuse; }
|
||||
|
||||
void Set_Specular(const Vector3& specular) { Specular=specular; }
|
||||
const Vector3& Get_Specular() const { return Specular; }
|
||||
|
||||
private:
|
||||
|
||||
bool Save_Variables(ChunkSaveClass &csave);
|
||||
bool Load_Variables(ChunkLoadClass &cload);
|
||||
|
||||
StringClass TextureName;
|
||||
|
||||
Vector3 Ambient;
|
||||
Vector3 Diffuse;
|
||||
Vector3 Specular;
|
||||
};
|
||||
|
||||
|
||||
|
||||
class Shd6CubeMapClass : public ShdInterfaceClass
|
||||
{
|
||||
public:
|
||||
Shd6CubeMapClass(const ShdDefClass* def);
|
||||
virtual ~Shd6CubeMapClass();
|
||||
|
||||
static void Init();
|
||||
static void Shutdown();
|
||||
|
||||
virtual int Get_Pass_Count() { return 1; }
|
||||
|
||||
virtual int Get_Texture_Count() const { return 1; }
|
||||
virtual TextureClass* Peek_Texture(int idx) const { return NULL; }
|
||||
|
||||
virtual void Apply_Shared(int cur_pass, RenderInfoClass& rinfo);
|
||||
virtual void Apply_Instance(int cur_pass, RenderInfoClass& rinfo);
|
||||
|
||||
virtual unsigned Get_Vertex_Stream_Count() const;
|
||||
virtual unsigned Get_Vertex_Size(unsigned stream) const;
|
||||
virtual bool Use_HW_Vertex_Processing() const { return true; }
|
||||
|
||||
virtual void Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
);
|
||||
|
||||
protected:
|
||||
|
||||
static Matrix4x4 View_Projection_Matrix;
|
||||
|
||||
D3DMATERIAL8* Material;
|
||||
|
||||
TextureClass* Texture;
|
||||
|
||||
Vector4 Ambient;
|
||||
Vector4 Diffuse;
|
||||
Vector4 Specular;
|
||||
};
|
||||
|
||||
|
||||
#endif //SHDCUBEMAP_H
|
||||
216
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shddef.cpp
Normal file
216
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shddef.cpp
Normal file
@@ -0,0 +1,216 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shddef.cpp $*
|
||||
* *
|
||||
* $Org Author:: Jani_p
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 6/07/02 3:12p $*
|
||||
* *
|
||||
* $Revision:: 2 $*
|
||||
* *
|
||||
* 6/07/02 KJM : Added validation enum
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include "shddef.h"
|
||||
#include "chunkio.h"
|
||||
#include "w3d_file.h"
|
||||
|
||||
|
||||
ShdDefClass::ShdDefClass(uint32 classid) :
|
||||
ClassID(classid),
|
||||
Name("UnNamed"),
|
||||
SurfaceType(0)
|
||||
{
|
||||
|
||||
ENUM_PARAM (
|
||||
ShdDefClass, SurfaceType,
|
||||
(
|
||||
"Light Metal", SURFACE_TYPE_LIGHT_METAL,
|
||||
"Heavy Metal", SURFACE_TYPE_HEAVY_METAL,
|
||||
"Water", SURFACE_TYPE_WATER,
|
||||
"Sand", SURFACE_TYPE_SAND,
|
||||
"Dirt", SURFACE_TYPE_DIRT,
|
||||
"Mud", SURFACE_TYPE_MUD,
|
||||
"Grass", SURFACE_TYPE_GRASS,
|
||||
"Wood", SURFACE_TYPE_WOOD,
|
||||
"Concrete", SURFACE_TYPE_CONCRETE,
|
||||
"Flesh", SURFACE_TYPE_FLESH,
|
||||
"Rock", SURFACE_TYPE_ROCK,
|
||||
"Snow", SURFACE_TYPE_SNOW,
|
||||
"Ice", SURFACE_TYPE_ICE,
|
||||
"Default", SURFACE_TYPE_DEFAULT,
|
||||
"Glass", SURFACE_TYPE_GLASS,
|
||||
"Cloth", SURFACE_TYPE_CLOTH,
|
||||
"Tiberium Field", SURFACE_TYPE_TIBERIUM_FIELD,
|
||||
"Foliage Permeable", SURFACE_TYPE_FOLIAGE_PERMEABLE,
|
||||
"Glass Permeable", SURFACE_TYPE_GLASS_PERMEABLE,
|
||||
"Ice Permeable", SURFACE_TYPE_ICE_PERMEABLE,
|
||||
"Cloth Permeable", SURFACE_TYPE_CLOTH_PERMEABLE,
|
||||
"Electrical", SURFACE_TYPE_ELECTRICAL,
|
||||
"Electrical Permeable", SURFACE_TYPE_ELECTRICAL_PERMEABLE,
|
||||
"Flammable", SURFACE_TYPE_FLAMMABLE,
|
||||
"Flammable Permeable", SURFACE_TYPE_FLAMMABLE_PERMEABLE ,
|
||||
"Steam", SURFACE_TYPE_STEAM,
|
||||
"Steam Permeable", SURFACE_TYPE_STEAM_PERMEABLE,
|
||||
"Water Permeable", SURFACE_TYPE_WATER_PERMEABLE,
|
||||
"Tiberium Water", SURFACE_TYPE_TIBERIUM_WATER,
|
||||
"Tiberium Water Permeable", SURFACE_TYPE_TIBERIUM_WATER_PERMEABLE,
|
||||
"Underwater Dirt", SURFACE_TYPE_UNDERWATER_DIRT,
|
||||
"Underwater Tiberium Dirt", SURFACE_TYPE_UNDERWATER_TIBERIUM_DIRT,
|
||||
NULL
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
ShdDefClass::ShdDefClass(const ShdDefClass & that):
|
||||
ClassID(that.ClassID),
|
||||
Name(that.Name),
|
||||
SurfaceType(that.SurfaceType)
|
||||
{
|
||||
}
|
||||
|
||||
ShdDefClass::~ShdDefClass(void)
|
||||
{
|
||||
}
|
||||
|
||||
const char * ShdDefClass::Get_Name (void) const
|
||||
{
|
||||
return Name;
|
||||
}
|
||||
|
||||
void ShdDefClass::Set_Name (const char *new_name)
|
||||
{
|
||||
Name = new_name;
|
||||
}
|
||||
|
||||
void ShdDefClass::Reset(void)
|
||||
{
|
||||
SurfaceType = 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
**
|
||||
** Save-Load methods for ShdDefClass
|
||||
**
|
||||
*******************************************************************************/
|
||||
enum
|
||||
{
|
||||
CHUNKID_VARIABLES = 0x16490430,
|
||||
|
||||
VARID_NAME = 0x00,
|
||||
VARID_SURFACETYPE,
|
||||
};
|
||||
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Serialize this ShdDef into a chunk saver
|
||||
/*!
|
||||
@param csave - ChunkSave object to write into
|
||||
*/
|
||||
bool ShdDefClass::Save (ChunkSaveClass &csave)
|
||||
{
|
||||
bool retval=true;
|
||||
|
||||
csave.Begin_Chunk(CHUNKID_VARIABLES);
|
||||
|
||||
retval=Save_Variables(csave);
|
||||
|
||||
csave.End_Chunk ();
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Load this ShdDef from a chunk loader
|
||||
/*!
|
||||
@param cload - ChunkLoad object to read from
|
||||
*/
|
||||
bool ShdDefClass::Load (ChunkLoadClass &cload)
|
||||
{
|
||||
bool retval = true;
|
||||
|
||||
cload.Open_Chunk();
|
||||
|
||||
retval=cload.Cur_Chunk_ID()==CHUNKID_VARIABLES;
|
||||
Load_Variables(cload);
|
||||
|
||||
cload.Close_Chunk();
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Save the variables for this object
|
||||
/*!
|
||||
Each variable is stored in its own "micro-chunk" for flexibility.
|
||||
|
||||
@param csave - chunk saver to write to.
|
||||
*/
|
||||
bool ShdDefClass::Save_Variables (ChunkSaveClass &csave)
|
||||
{
|
||||
bool retval = true;
|
||||
WRITE_MICRO_CHUNK_WWSTRING (csave, VARID_NAME, Name);
|
||||
WRITE_MICRO_CHUNK (csave, VARID_SURFACETYPE, SurfaceType);
|
||||
return retval;
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Load the variables for this object from a chunk
|
||||
/*!
|
||||
@param cload - chunk loader to read from
|
||||
*/
|
||||
bool ShdDefClass::Load_Variables (ChunkLoadClass &cload)
|
||||
{
|
||||
bool retval = true;
|
||||
|
||||
//
|
||||
// Loop through all the microchunks that define the variables
|
||||
//
|
||||
while (cload.Open_Micro_Chunk ())
|
||||
{
|
||||
switch (cload.Cur_Micro_Chunk_ID ())
|
||||
{
|
||||
READ_MICRO_CHUNK_WWSTRING (cload, VARID_NAME, Name);
|
||||
READ_MICRO_CHUNK (cload, VARID_SURFACETYPE, SurfaceType);
|
||||
}
|
||||
|
||||
cload.Close_Micro_Chunk();
|
||||
}
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
||||
140
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shddef.h
Normal file
140
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shddef.h
Normal file
@@ -0,0 +1,140 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shddef.h $*
|
||||
* *
|
||||
* $Org Author:: Jani_p
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 6/07/02 3:12p $*
|
||||
* *
|
||||
* $Revision:: 2 $*
|
||||
* *
|
||||
* 6/07/02 KJM : Added validation enum
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHDDEF_H
|
||||
#define SHDDEF_H
|
||||
|
||||
#include "always.h"
|
||||
#include "editable.h"
|
||||
#include "refcount.h"
|
||||
|
||||
class ShdInterfaceClass;
|
||||
|
||||
enum SHDVER
|
||||
{
|
||||
SHDVER_UNDEFINED=0,
|
||||
SHDVER_6,
|
||||
SHDVER_7,
|
||||
SHDVER_8
|
||||
};
|
||||
|
||||
class ShdVersion
|
||||
{
|
||||
public:
|
||||
ShdVersion() : Version(SHDVER_UNDEFINED) {}
|
||||
|
||||
void Set(const SHDVER ver) { Version=ver; }
|
||||
SHDVER Get() const { return Version; }
|
||||
|
||||
private:
|
||||
|
||||
SHDVER Version;
|
||||
};
|
||||
|
||||
|
||||
|
||||
/**
|
||||
** ShdDefClass - This class is the base class for all shader "definition" objects.
|
||||
**
|
||||
** A shader definition object has two responsibilities.
|
||||
**
|
||||
** - It contains a "generic" description (chars, ints, floats, etc) of all of the user-settable parameters used
|
||||
** by an instance of this type of shader (e.g. what textures it uses, colors, etc).
|
||||
**
|
||||
** - It contains a virtual "Create" function which can create an actual shader for you. This function is an
|
||||
** abstract factory which creates a shader implementation compatible with the current hardware the application
|
||||
** is running on.
|
||||
*/
|
||||
class ShdDefClass : public EditableClass, public RefCountClass
|
||||
{
|
||||
public:
|
||||
DECLARE_EDITABLE(ShdDefClass, EditableClass);
|
||||
|
||||
ShdDefClass(uint32 class_id);
|
||||
ShdDefClass(const ShdDefClass & that);
|
||||
virtual ~ShdDefClass(void);
|
||||
|
||||
virtual ShdDefClass * Clone(void) const = 0;
|
||||
virtual void Reset(void);
|
||||
|
||||
// Run-Time Type identification (ID's defined in "shdclassids.h")
|
||||
WWINLINE uint32 Get_Class_ID (void) const { return ClassID; }
|
||||
|
||||
// Shader Management & Creation (should create a shader compatible with the current hardware/API)
|
||||
virtual void Init()=0;
|
||||
virtual void Shutdown()=0;
|
||||
virtual ShdInterfaceClass * Create (void) const = 0;
|
||||
|
||||
// Name methods
|
||||
const char * Get_Name (void) const;
|
||||
void Set_Name (const char *new_name);
|
||||
|
||||
// Surface type, used for decal, sound, and emitter creation
|
||||
int Get_Surface_Type(void) const { return SurfaceType; }
|
||||
void Set_Surface_Type(int t) { SurfaceType = t; }
|
||||
|
||||
// Validation methods
|
||||
virtual bool Is_Valid_Config (StringClass &message) { return true; }
|
||||
|
||||
// Requirements PRELIMINARY, NEED TO VALIDATE THIS PART OF THE INTERFACE!!!
|
||||
virtual bool Uses_Vertex_Alpha(void) const { return false; }
|
||||
virtual bool Uses_UV_Channel(int i) const { return (i==0); }
|
||||
virtual bool Uses_Vertex_Colors(void) const { return false; }
|
||||
virtual bool Requires_Normals(void) const { return false; }
|
||||
virtual bool Requires_Tangent_Space_Vectors(void) const { return false; }
|
||||
virtual bool Requires_Sorting(void) const { return false; }
|
||||
virtual int Static_Sort_Index(void) const { return 0; }
|
||||
|
||||
// From PersistClass
|
||||
virtual bool Save (ChunkSaveClass &csave);
|
||||
virtual bool Load (ChunkLoadClass &cload);
|
||||
|
||||
private:
|
||||
|
||||
bool Save_Variables (ChunkSaveClass &csave);
|
||||
bool Load_Variables (ChunkLoadClass &cload);
|
||||
|
||||
uint32 ClassID;
|
||||
StringClass Name;
|
||||
int SurfaceType;
|
||||
};
|
||||
|
||||
|
||||
|
||||
#endif //SHDDEF_H
|
||||
@@ -0,0 +1,74 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shddeffactory.cpp $*
|
||||
* *
|
||||
* $Org Author:: Jani_p
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 6/01/02 3:12p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
|
||||
#include "shddeffactory.h"
|
||||
#include "shddefmanager.h"
|
||||
|
||||
|
||||
/*
|
||||
**
|
||||
** ShdDefFactory Implementation
|
||||
**
|
||||
*/
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Constructor for ShdDefFactoryClass
|
||||
/*!
|
||||
Automatically registers this instance of the ShdDefFactory with the manager.
|
||||
*/
|
||||
ShdDefFactoryClass::ShdDefFactoryClass (void) :
|
||||
NextFactory(NULL),
|
||||
PrevFactory(NULL)
|
||||
{
|
||||
ShdDefManagerClass::Register_Factory (this);
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Destructor for ShdDefFactoryClass
|
||||
/*!
|
||||
Automatically un-registers this instance of a ShdDefFactory from the manager.
|
||||
*/
|
||||
ShdDefFactoryClass::~ShdDefFactoryClass (void)
|
||||
{
|
||||
ShdDefManagerClass::Unregister_Factory (this);
|
||||
}
|
||||
|
||||
|
||||
|
||||
115
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shddeffactory.h
Normal file
115
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shddeffactory.h
Normal file
@@ -0,0 +1,115 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shddeffactory.h $*
|
||||
* *
|
||||
* $Org Author:: Jani_p
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 6/01/02 3:12p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHDDEFFACTORY_H
|
||||
#define SHDDEFFACTORY_H
|
||||
|
||||
#include "always.h"
|
||||
#include "bittype.h"
|
||||
|
||||
class ShdDefClass;
|
||||
|
||||
/*
|
||||
** NOTE: For most users, the only thing you need from this module is the REGISTER_SHDDEF(T,ID,NAME) macro
|
||||
*/
|
||||
|
||||
|
||||
/**
|
||||
** ShdDefFactoryClass - An instance of this class is used to automatically register
|
||||
** each unique type of ShdDefClass with the system. This object is responsible for
|
||||
** creating shader definitions. All existing 'DefFactories' can be iterated over
|
||||
** and presented to the user in a menu.
|
||||
*/
|
||||
class ShdDefFactoryClass
|
||||
{
|
||||
public:
|
||||
ShdDefFactoryClass (void);
|
||||
virtual ~ShdDefFactoryClass (void);
|
||||
|
||||
//////////////////////////////////////////////////////////////
|
||||
// Public methods
|
||||
//////////////////////////////////////////////////////////////
|
||||
virtual ShdDefClass * Create (void) const = 0;
|
||||
virtual const char * Get_Name (void) const = 0;
|
||||
virtual uint32 Get_Class_ID (void) const = 0;
|
||||
|
||||
protected:
|
||||
|
||||
//////////////////////////////////////////////////////////////
|
||||
// Protected member data
|
||||
//////////////////////////////////////////////////////////////
|
||||
ShdDefFactoryClass * NextFactory;
|
||||
ShdDefFactoryClass * PrevFactory;
|
||||
|
||||
friend class ShdDefManagerClass;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
** SimpleShdDefFactoryClass - This template automates the process of creating a ShdDefFactory.
|
||||
** For complete ease of use, the associated REGISTER_SHDDEF macro can be used in the cpp file
|
||||
** of your shader definition.
|
||||
** Macro useage example (in the cpp file for your shader definition):
|
||||
** REGISTER_SHDDEF(MyShdDefClass, MYSHDDEF_CLASSID, "Greg's super-fancy shader");
|
||||
*/
|
||||
template<class T, int class_id, char *name> class SimpleShdDefFactoryClass : public ShdDefFactoryClass
|
||||
{
|
||||
public:
|
||||
SimpleShdDefFactoryClass (void) { }
|
||||
virtual ~SimpleShdDefFactoryClass (void) { }
|
||||
|
||||
//////////////////////////////////////////////////////////////
|
||||
// Public methods
|
||||
//////////////////////////////////////////////////////////////
|
||||
virtual ShdDefClass * Create (void) const { return new T; }
|
||||
virtual const char * Get_Name (void) const { return name; }
|
||||
virtual uint32 Get_Class_ID (void) const { return class_id; }
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
** Use this macro in the .CPP file for your shader definition to automatically link it
|
||||
** into the shader editing system.
|
||||
*/
|
||||
#define REGISTER_SHDDEF(T,ID,NAME) \
|
||||
char T ## Name[] = NAME; \
|
||||
SimpleShdDefFactoryClass<T,ID,T ## Name> T ## Factory \
|
||||
|
||||
|
||||
|
||||
#endif //SHDDEFFACTORY_H
|
||||
@@ -0,0 +1,250 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shddefmanager.cpp $*
|
||||
* *
|
||||
* $Org Author:: Jani_p
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 5/20/02 3:12p $*
|
||||
* *
|
||||
* $Revision:: 2 $*
|
||||
* *
|
||||
* 5/20/02 KM Added save load behavior
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include "w3d_file.h"
|
||||
#include "chunkio.h"
|
||||
#include "shddef.h"
|
||||
#include "shddefmanager.h"
|
||||
#include "shddeffactory.h"
|
||||
#include "wwdebug.h"
|
||||
#include "string.h"
|
||||
|
||||
|
||||
/*
|
||||
** Static head of the factory list
|
||||
*/
|
||||
ShdDefFactoryClass *ShdDefManagerClass::_FactoryListHead = NULL;
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Used to look up the ShdDefFactory for a given class id
|
||||
/*!
|
||||
@param class_id - class id to look up the factory for
|
||||
@returns the factory if it is found or NULL
|
||||
*/
|
||||
ShdDefFactoryClass *
|
||||
ShdDefManagerClass::Find_Factory (uint32 class_id)
|
||||
{
|
||||
ShdDefFactoryClass *factory = 0;
|
||||
|
||||
//
|
||||
// Loop through all the factories and see if we can
|
||||
// find the one who owns the corresponding class-id.
|
||||
//
|
||||
for ( ShdDefFactoryClass *curr_factory = _FactoryListHead;
|
||||
(factory == 0) && (curr_factory != 0);
|
||||
curr_factory = curr_factory->NextFactory)
|
||||
{
|
||||
//
|
||||
// Is this the factory we were looking for?
|
||||
//
|
||||
if (curr_factory->Get_Class_ID () == class_id) {
|
||||
factory = curr_factory;
|
||||
}
|
||||
}
|
||||
|
||||
return factory;
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Used to look up the ShdDefFactory for a given named shader def
|
||||
/*!
|
||||
@param name - name of the desired shader def
|
||||
@returns the factory if it is found or NULL if not
|
||||
*/
|
||||
ShdDefFactoryClass * ShdDefManagerClass::Find_Factory (const char *name)
|
||||
{
|
||||
ShdDefFactoryClass * factory = 0;
|
||||
|
||||
//
|
||||
// Loop through all the factories and see if we can
|
||||
// find the one who owns the corresponding class-id.
|
||||
//
|
||||
for ( ShdDefFactoryClass *curr_factory = _FactoryListHead;
|
||||
(factory == 0) && (curr_factory != 0);
|
||||
curr_factory = curr_factory->NextFactory) {
|
||||
|
||||
//
|
||||
// Is this the factory we were looking for?
|
||||
//
|
||||
if (::stricmp (curr_factory->Get_Name (), name) == 0) {
|
||||
factory = curr_factory;
|
||||
}
|
||||
}
|
||||
|
||||
return factory;
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Registers a factory with the system
|
||||
/*!
|
||||
@param factory - the factory to register
|
||||
*/
|
||||
void ShdDefManagerClass::Register_Factory (ShdDefFactoryClass *factory)
|
||||
{
|
||||
WWASSERT (factory->NextFactory == 0);
|
||||
WWASSERT (factory->PrevFactory == 0);
|
||||
Link_Factory (factory);
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! removes a factory from the system
|
||||
/*!
|
||||
@param factory - the factory to unregister
|
||||
*/
|
||||
void ShdDefManagerClass::Unregister_Factory (ShdDefFactoryClass *factory)
|
||||
{
|
||||
WWASSERT (factory != 0);
|
||||
Unlink_Factory (factory);
|
||||
return ;
|
||||
}
|
||||
|
||||
|
||||
ShdDefFactoryClass * ShdDefManagerClass::Get_First (void)
|
||||
{
|
||||
return _FactoryListHead;
|
||||
}
|
||||
|
||||
ShdDefFactoryClass * ShdDefManagerClass::Get_Next (ShdDefFactoryClass *current)
|
||||
{
|
||||
//
|
||||
// Simply return the next factory in the chain
|
||||
//
|
||||
if (current != NULL) {
|
||||
return current->NextFactory;
|
||||
}
|
||||
|
||||
return _FactoryListHead;
|
||||
}
|
||||
|
||||
void ShdDefManagerClass::Link_Factory (ShdDefFactoryClass *factory)
|
||||
{
|
||||
WWASSERT (factory->NextFactory == 0);
|
||||
WWASSERT (factory->PrevFactory == 0);
|
||||
|
||||
// Adding this factory in front of the current head of the list
|
||||
factory->NextFactory = _FactoryListHead;
|
||||
|
||||
// If the list wasn't empty, link the next factory back to this factory
|
||||
if (factory->NextFactory != 0) {
|
||||
factory->NextFactory->PrevFactory = factory;
|
||||
}
|
||||
|
||||
// Point the head of the list at this factory now
|
||||
_FactoryListHead = factory;
|
||||
return ;
|
||||
}
|
||||
|
||||
void ShdDefManagerClass::Unlink_Factory (ShdDefFactoryClass *factory)
|
||||
{
|
||||
WWASSERT(factory != 0);
|
||||
|
||||
// Handle the factory's prev pointer:
|
||||
if (factory->PrevFactory == 0) {
|
||||
|
||||
// this factory is the head
|
||||
WWASSERT (_FactoryListHead == factory);
|
||||
_FactoryListHead = factory->NextFactory;
|
||||
|
||||
} else {
|
||||
|
||||
// link it's prev with it's next
|
||||
factory->PrevFactory->NextFactory = factory->NextFactory;
|
||||
|
||||
}
|
||||
|
||||
// Handle the factory's next pointer if its not at the end of the list:
|
||||
if (factory->NextFactory != 0) {
|
||||
|
||||
factory->NextFactory->PrevFactory = factory->PrevFactory;
|
||||
|
||||
}
|
||||
|
||||
// factory is now un-linked
|
||||
factory->NextFactory = 0;
|
||||
factory->PrevFactory = 0;
|
||||
return ;
|
||||
}
|
||||
|
||||
ShdDefClass* ShdDefManagerClass::Create_ShdDefClass_Instance(uint32 class_id)
|
||||
{
|
||||
// first look up the factory for this classid
|
||||
ShdDefFactoryClass * factory = Find_Factory (class_id);
|
||||
|
||||
if (factory != NULL)
|
||||
{
|
||||
return factory->Create();
|
||||
}
|
||||
else
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
void ShdDefManagerClass::Save_Shader(ChunkSaveClass& csave, ShdDefClass* shddef)
|
||||
{
|
||||
csave.Begin_Chunk(W3D_CHUNK_SHDSUBMESH_SHADER_CLASSID);
|
||||
uint32 id=shddef->Get_Class_ID();
|
||||
csave.Write(&id,sizeof(uint32));
|
||||
csave.End_Chunk();
|
||||
|
||||
csave.Begin_Chunk(W3D_CHUNK_SHDSUBMESH_SHADER_DEF);
|
||||
shddef->Save(csave);
|
||||
csave.End_Chunk();
|
||||
|
||||
}
|
||||
|
||||
void ShdDefManagerClass::Load_Shader(ChunkLoadClass& cload, ShdDefClass** shddef)
|
||||
{
|
||||
uint32 id;
|
||||
|
||||
cload.Open_Chunk();
|
||||
cload.Read(&id,sizeof(uint32));
|
||||
cload.Close_Chunk();
|
||||
|
||||
*shddef=Create_ShdDefClass_Instance(id);
|
||||
|
||||
cload.Open_Chunk();
|
||||
(*shddef)->Load(cload);
|
||||
cload.Close_Chunk();
|
||||
}
|
||||
|
||||
@@ -0,0 +1,91 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shddefmanager.h $*
|
||||
* *
|
||||
* $Org Author:: Jani_p
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 5/20/02 3:12p $*
|
||||
* *
|
||||
* $Revision:: 2 $*
|
||||
* *
|
||||
* 5/20/02 KM Added save load behavior
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHDDEFMANAGER_H
|
||||
#define SHDDEFMANAGER_H
|
||||
|
||||
#include "always.h"
|
||||
#include "bittype.h"
|
||||
|
||||
class ShdDefClass;
|
||||
class ShdDefFactoryClass;
|
||||
class ChunkSaveClass;
|
||||
class ChunkLoadClass;
|
||||
|
||||
|
||||
/**
|
||||
** ShdDefManagerClass - This class contains a list of all constructed ShdDefFactories.
|
||||
** This class is used to iterate through the shader definition factories in the material
|
||||
** editor for example.
|
||||
*/
|
||||
class ShdDefManagerClass
|
||||
{
|
||||
public:
|
||||
|
||||
static ShdDefFactoryClass * Find_Factory (uint32 class_id);
|
||||
static ShdDefFactoryClass * Find_Factory (const char *name);
|
||||
static void Register_Factory (ShdDefFactoryClass *factory);
|
||||
static void Unregister_Factory (ShdDefFactoryClass *factory);
|
||||
|
||||
// Class enumeration
|
||||
static ShdDefFactoryClass * Get_First (uint32 superclass_id);
|
||||
static ShdDefFactoryClass * Get_Next (ShdDefFactoryClass *current, uint32 superclass_id);
|
||||
|
||||
// Factory enumeration
|
||||
static ShdDefFactoryClass * Get_First (void);
|
||||
static ShdDefFactoryClass * Get_Next (ShdDefFactoryClass *current);
|
||||
|
||||
// Construction
|
||||
static ShdDefClass * Create_ShdDefClass_Instance(uint32 class_id);
|
||||
|
||||
// save/load
|
||||
static void Save_Shader(ChunkSaveClass& csave, ShdDefClass* shddef);
|
||||
static void Load_Shader(ChunkLoadClass& cload, ShdDefClass** shddef);
|
||||
|
||||
private:
|
||||
|
||||
static void Link_Factory (ShdDefFactoryClass *factory);
|
||||
static void Unlink_Factory (ShdDefFactoryClass *factory);
|
||||
|
||||
static ShdDefFactoryClass * _FactoryListHead;
|
||||
};
|
||||
|
||||
|
||||
|
||||
#endif SHDDEFMANAGER_H
|
||||
70
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shddump.h
Normal file
70
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shddump.h
Normal file
@@ -0,0 +1,70 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shddump.h $*
|
||||
* *
|
||||
* $Org Author:: Kenny_m
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 8/05/02 3:12p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
// header file for use in wdump util only
|
||||
|
||||
#ifndef SHDDUMP_H
|
||||
#define SHDDUMP_H
|
||||
|
||||
#ifndef SHDCLASSIDS_H
|
||||
#include "shdclassids.h"
|
||||
#endif
|
||||
|
||||
const char* Shader_ClassIDs[SHDDEF_CLASSID_LAST]=
|
||||
{
|
||||
"SHDDEF_CLASSID_DUMMY",
|
||||
"SHDDEF_CLASSID_SIMPLE",
|
||||
"SHDDEF_CLASSID_GLOSSMASK",
|
||||
"SHDDEF_CLASSID_BUMPSPEC",
|
||||
"SHDDEF_CLASSID_BUMPDIFF",
|
||||
"SHDDEF_CLASSID_CUBEMAP"
|
||||
};
|
||||
|
||||
struct ShdDef_ChunkStruct
|
||||
{
|
||||
DWORD DefChunkId;
|
||||
char Pad0[6];
|
||||
char DefName[8];
|
||||
char Pad1[2];
|
||||
int SurfaceType;
|
||||
DWORD ShdChunkId;
|
||||
char Pad2[6];
|
||||
char TexName[];
|
||||
};
|
||||
|
||||
|
||||
#endif //SHDDUMP_H
|
||||
@@ -0,0 +1,62 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : wwshade *
|
||||
* *
|
||||
* $Archive:: \code\wwshade\shdforcelinks.cpp $*
|
||||
* *
|
||||
* Org Author:: Patrick Smith *
|
||||
* *
|
||||
* Author:: Kenny Mitchell *
|
||||
* *
|
||||
* $Modtime:: 6/27/2002 4:28p $*
|
||||
* *
|
||||
* $Revision:: 3 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include "shdforcelinks.h"
|
||||
#include "wwhack.h"
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// SHD_Force_Links
|
||||
//
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
void SHD_Force_Links ()
|
||||
{
|
||||
//
|
||||
// Force-link those modules that would be "linked-out" of the static lib
|
||||
// because they are not directly referenced.
|
||||
//
|
||||
FORCE_LINK (SimpleShader);
|
||||
FORCE_LINK (GlossMaskShader);
|
||||
FORCE_LINK (BumpSpecShader);
|
||||
FORCE_LINK (BumpDiffShader);
|
||||
FORCE_LINK (CubeMapShader);
|
||||
FORCE_LINK (LegacyW3DShader);
|
||||
|
||||
return ;
|
||||
}
|
||||
@@ -0,0 +1,53 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : wwshade *
|
||||
* *
|
||||
* $Archive:: \code\wwshade\shdforcelinks.h $*
|
||||
* *
|
||||
* Org Author:: Patrick Smith *
|
||||
* *
|
||||
* Author:: Kenny Mitchell *
|
||||
* *
|
||||
* $Modtime:: 6/27/2002 4:28p $*
|
||||
* *
|
||||
* $Revision:: 2 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#ifndef __SHDFORCELINKS_H
|
||||
#define __SHDFORCELINKS_H
|
||||
|
||||
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
// Function prototypes
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
void SHD_Force_Links();
|
||||
|
||||
|
||||
#endif //__SHDFORCELINKS_H
|
||||
@@ -0,0 +1,363 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shdglossmask.cpp $*
|
||||
* *
|
||||
* $Org Author:: Kenny_m
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 8/01/02 11:39a $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include <d3dx8math.h>
|
||||
#include "dx8fvf.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "assetmgr.h"
|
||||
|
||||
#include "shdglossmask.h"
|
||||
|
||||
#include "editable.h"
|
||||
#include "shdclassids.h"
|
||||
#include "shddeffactory.h"
|
||||
#include "shdinterface.h"
|
||||
#include "shdhwshader.h"
|
||||
|
||||
#include "persistfactory.h"
|
||||
#include "wwhack.h"
|
||||
|
||||
DECLARE_FORCE_LINK(GlossMaskShader);
|
||||
REGISTER_SHDDEF(ShdGlossMaskDefClass,SHDDEF_CLASSID_GLOSSMASK,"Gloss Mask");
|
||||
|
||||
|
||||
// Save-Load methods for ShdDefClass
|
||||
enum
|
||||
{
|
||||
CHUNKID_VARIABLES = 0x16490460,
|
||||
|
||||
VARID_TEXTURE_NAME = 0x00,
|
||||
|
||||
VARID_AMBIENT_COLOR,
|
||||
VARID_DIFFUSE_COLOR,
|
||||
VARID_SPECULAR_COLOR
|
||||
};
|
||||
|
||||
ShdGlossMaskDefClass::ShdGlossMaskDefClass()
|
||||
: ShdDefClass(SHDDEF_CLASSID_GLOSSMASK),
|
||||
Ambient(1,1,1),
|
||||
Diffuse(1,1,1),
|
||||
Specular(1,1,1)
|
||||
{
|
||||
NAMED_TEXTURE_FILENAME_PARAM(ShdGlossMaskDefClass, TextureName, "Texture Name", "Targa Files", ".tga");
|
||||
|
||||
NAMED_EDITABLE_PARAM(ShdGlossMaskDefClass, ParameterClass::TYPE_COLOR, Ambient, "Ambient");
|
||||
NAMED_EDITABLE_PARAM(ShdGlossMaskDefClass, ParameterClass::TYPE_COLOR, Diffuse, "Diffuse");
|
||||
NAMED_EDITABLE_PARAM(ShdGlossMaskDefClass, ParameterClass::TYPE_COLOR, Specular, "Specular");
|
||||
}
|
||||
|
||||
ShdGlossMaskDefClass::ShdGlossMaskDefClass(const ShdGlossMaskDefClass& that)
|
||||
: ShdDefClass(that),
|
||||
Ambient(that.Ambient),
|
||||
Diffuse(that.Diffuse),
|
||||
Specular(that.Specular)
|
||||
{
|
||||
TextureName=that.TextureName;
|
||||
}
|
||||
|
||||
ShdGlossMaskDefClass::~ShdGlossMaskDefClass()
|
||||
{
|
||||
}
|
||||
|
||||
bool ShdGlossMaskDefClass::Is_Valid_Config(StringClass &message)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ShdGlossMaskDefClass::Save(ChunkSaveClass &csave)
|
||||
{
|
||||
ShdDefClass::Save(csave);
|
||||
|
||||
csave.Begin_Chunk(CHUNKID_VARIABLES);
|
||||
|
||||
bool retval = true;
|
||||
|
||||
// only save the file name
|
||||
char fname[_MAX_PATH];
|
||||
|
||||
_splitpath(TextureName,NULL,NULL,fname,NULL);
|
||||
strcat(fname,".tga");
|
||||
TextureName=fname;
|
||||
|
||||
WRITE_MICRO_CHUNK_WWSTRING(csave, VARID_TEXTURE_NAME, TextureName);
|
||||
|
||||
WRITE_MICRO_CHUNK(csave, VARID_AMBIENT_COLOR, Ambient);
|
||||
WRITE_MICRO_CHUNK(csave, VARID_DIFFUSE_COLOR, Diffuse);
|
||||
WRITE_MICRO_CHUNK(csave, VARID_SPECULAR_COLOR, Specular);
|
||||
|
||||
csave.End_Chunk();
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
||||
bool ShdGlossMaskDefClass::Load(ChunkLoadClass &cload)
|
||||
{
|
||||
ShdDefClass::Load(cload);
|
||||
|
||||
// Loop through all the microchunks that define the variables
|
||||
while (cload.Open_Chunk()) {
|
||||
switch (cload.Cur_Chunk_ID())
|
||||
{
|
||||
case CHUNKID_VARIABLES:
|
||||
while (cload.Open_Micro_Chunk())
|
||||
{
|
||||
switch (cload.Cur_Micro_Chunk_ID())
|
||||
{
|
||||
READ_MICRO_CHUNK_WWSTRING(cload, VARID_TEXTURE_NAME, TextureName);
|
||||
|
||||
READ_MICRO_CHUNK(cload, VARID_AMBIENT_COLOR, Ambient);
|
||||
READ_MICRO_CHUNK(cload, VARID_DIFFUSE_COLOR, Diffuse);
|
||||
READ_MICRO_CHUNK(cload, VARID_SPECULAR_COLOR, Specular);
|
||||
}
|
||||
|
||||
cload.Close_Micro_Chunk();
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
cload.Close_Chunk();
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
void ShdGlossMaskDefClass::Init()
|
||||
{
|
||||
Shd6GlossMaskClass::Init();
|
||||
}
|
||||
|
||||
void ShdGlossMaskDefClass::Shutdown()
|
||||
{
|
||||
Shd6GlossMaskClass::Shutdown();
|
||||
}
|
||||
|
||||
ShdInterfaceClass* ShdGlossMaskDefClass::Create() const
|
||||
{
|
||||
return new Shd6GlossMaskClass(this);
|
||||
}
|
||||
|
||||
|
||||
|
||||
Matrix4x4 Shd6GlossMaskClass::View_Projection_Matrix;
|
||||
|
||||
Shd6GlossMaskClass::Shd6GlossMaskClass(const ShdDefClass* def)
|
||||
: ShdInterfaceClass(def,SHDDEF_CLASSID_GLOSSMASK),
|
||||
Texture(NULL)
|
||||
{
|
||||
ShdGlossMaskDefClass* Definition=(ShdGlossMaskDefClass*)def;
|
||||
|
||||
Texture=WW3DAssetManager::Get_Instance()->Get_Texture
|
||||
(
|
||||
Definition->Get_Texture_Name()
|
||||
);
|
||||
|
||||
const Vector3& a=Definition->Get_Ambient();
|
||||
Ambient.Set(a.X,a.Y,a.Z,1.0f);
|
||||
|
||||
const Vector3& d=Definition->Get_Diffuse();
|
||||
Diffuse.Set(d.X,d.Y,d.Z,1.0f);
|
||||
|
||||
const Vector3& s=Definition->Get_Specular();
|
||||
Specular.Set(s.X,s.Y,s.Z,1.0f);
|
||||
|
||||
Material=new D3DMATERIAL8;
|
||||
memset(Material,0,sizeof(D3DMATERIAL8));
|
||||
Material->Ambient.r=a.X; Material->Ambient.g=a.Y; Material->Ambient.b=a.Z;
|
||||
Material->Diffuse.r=d.X; Material->Diffuse.g=d.Y; Material->Diffuse.b=d.Z;
|
||||
Material->Specular.r=s.X; Material->Specular.g=s.Y; Material->Specular.b=s.Z;
|
||||
Material->Power=20;
|
||||
}
|
||||
|
||||
Shd6GlossMaskClass::~Shd6GlossMaskClass()
|
||||
{
|
||||
REF_PTR_RELEASE(Texture);
|
||||
}
|
||||
|
||||
void Shd6GlossMaskClass::Init()
|
||||
{
|
||||
}
|
||||
|
||||
void Shd6GlossMaskClass::Shutdown()
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
/**********************************************************************************************
|
||||
//! Apply shared states for 1 pass DX6
|
||||
/*! 7/12/02 3:39p KJM Created
|
||||
*/
|
||||
void Shd6GlossMaskClass::Apply_Shared(int pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
// fixed function uses pass through by default
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_PASSTHRU);
|
||||
|
||||
// set vertex shader
|
||||
DX8Wrapper::Set_Vertex_Shader(DX8_FVF_XYZNDUV1);
|
||||
|
||||
// set texture stage settings
|
||||
if (DX8Wrapper::Get_Current_Caps()->Support_ModAlphaAddClr())
|
||||
{
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLOROP, D3DTOP_MODULATE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_ALPHAARG1, D3DTA_TEXTURE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1 );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLORARG1, D3DTA_CURRENT );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLOROP, D3DTOP_MODULATEALPHA_ADDCOLOR);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLORARG2, D3DTA_SPECULAR );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAARG1, D3DTA_CURRENT);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1 );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(2, D3DTSS_COLOROP, D3DTOP_DISABLE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(2, D3DTSS_ALPHAOP, D3DTOP_DISABLE );
|
||||
}
|
||||
else
|
||||
{
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLOROP, D3DTOP_MODULATE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLOROP, D3DTOP_DISABLE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAOP, D3DTOP_DISABLE );
|
||||
}
|
||||
|
||||
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_LIGHTING, TRUE);
|
||||
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_AMBIENTMATERIALSOURCE,D3DMCS_MATERIAL);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_DIFFUSEMATERIALSOURCE,D3DMCS_MATERIAL);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_SPECULARMATERIALSOURCE,D3DMCS_MATERIAL);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_EMISSIVEMATERIALSOURCE,D3DMCS_MATERIAL);
|
||||
|
||||
DX8Wrapper::Set_DX8_Material(Material);
|
||||
|
||||
}
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Apply per instance states for 1 pass DX6
|
||||
/*! 7/10/02 5:39p KJM Created
|
||||
*/
|
||||
void Shd6GlossMaskClass::Apply_Instance(int cur_pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
DX8Wrapper::Set_Texture(0, Texture);
|
||||
|
||||
if (DX8Wrapper::Get_Current_Caps()->Support_ModAlphaAddClr())
|
||||
{
|
||||
DX8Wrapper::Set_Texture(1, Texture);
|
||||
}
|
||||
|
||||
DX8Wrapper::Set_DX8_Material(Material);
|
||||
}
|
||||
|
||||
unsigned Shd6GlossMaskClass::Get_Vertex_Stream_Count() const
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
unsigned Shd6GlossMaskClass::Get_Vertex_Size(unsigned stream) const
|
||||
{
|
||||
return sizeof(VertexFormatXYZNDUV1);
|
||||
}
|
||||
|
||||
void Shd6GlossMaskClass::Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
)
|
||||
{
|
||||
VertexFormatXYZNDUV1* verts=(VertexFormatXYZNDUV1*)dest_buffer;
|
||||
|
||||
for (unsigned i=0; i<vertex_count; ++i)
|
||||
{
|
||||
if (vss.Locations)
|
||||
{
|
||||
verts[i].x=vss.Locations[i][0];
|
||||
verts[i].y=vss.Locations[i][1];
|
||||
verts[i].z=vss.Locations[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].x=0.0f;
|
||||
verts[i].y=0.0f;
|
||||
verts[i].z=0.0f;
|
||||
}
|
||||
|
||||
if (vss.DiffuseInt)
|
||||
{
|
||||
verts[i].diffuse=vss.DiffuseInt[i];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].diffuse=0xffffffff;
|
||||
}
|
||||
|
||||
if (vss.Normals)
|
||||
{
|
||||
verts[i].nx=vss.Normals[i][0];
|
||||
verts[i].ny=vss.Normals[i][1];
|
||||
verts[i].nz=vss.Normals[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].nx=0.0f;
|
||||
verts[i].ny=0.0f;
|
||||
verts[i].nz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.UV[0])
|
||||
{
|
||||
verts[i].u1=vss.UV[0][i].U;
|
||||
verts[i].v1=vss.UV[0][i].V;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].u1=0.0f;
|
||||
verts[i].v1=0.0f;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
152
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdglossmask.h
Normal file
152
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdglossmask.h
Normal file
@@ -0,0 +1,152 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shdglossmask.cpp $*
|
||||
* *
|
||||
* $Org Author:: Kenny_m
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 8/01/02 11:39a $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHDGLOSSMASK_H
|
||||
#define SHDGLOSSMASK_H
|
||||
|
||||
#ifndef SHDINTERFACE_H
|
||||
#include "shdinterface.h"
|
||||
#endif
|
||||
|
||||
#include "shddef.h"
|
||||
#include "saveload.h"
|
||||
#include "shader.h"
|
||||
|
||||
class ShdGlossMaskDefClass : public ShdDefClass
|
||||
{
|
||||
public:
|
||||
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
// Editable interface requirements
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
DECLARE_EDITABLE(ShdGlossMaskDefClass, ShdDefClass);
|
||||
|
||||
ShdGlossMaskDefClass();
|
||||
ShdGlossMaskDefClass(const ShdGlossMaskDefClass& that);
|
||||
virtual ~ShdGlossMaskDefClass();
|
||||
|
||||
virtual ShdDefClass* Clone() const { return new ShdGlossMaskDefClass(*this); }
|
||||
|
||||
// Shader Creation (should create a shader compatible with the current hardware/API)
|
||||
virtual void Init();
|
||||
virtual void Shutdown();
|
||||
virtual ShdInterfaceClass* Create() const;
|
||||
|
||||
// Validation methods
|
||||
virtual bool Is_Valid_Config(StringClass &message);
|
||||
|
||||
// Requirements
|
||||
virtual bool Requires_Normals() const { return true; }
|
||||
virtual bool Requires_Tangent_Space_Vectors() const { return false; }
|
||||
virtual bool Requires_Sorting() const { return false; }
|
||||
virtual int Static_Sort_Index() const { return 0; }
|
||||
|
||||
// From PersistClass
|
||||
virtual bool Save(ChunkSaveClass &csave);
|
||||
virtual bool Load(ChunkLoadClass &cload);
|
||||
|
||||
void Set_Texture_Name(const StringClass& name) { TextureName=name; }
|
||||
const StringClass& Get_Texture_Name() const { return TextureName; }
|
||||
|
||||
void Set_Ambient(const Vector3& ambient) { Ambient=ambient; }
|
||||
const Vector3& Get_Ambient() const { return Ambient; }
|
||||
|
||||
void Set_Diffuse(const Vector3& diffuse) { Diffuse=diffuse; }
|
||||
const Vector3& Get_Diffuse() const { return Diffuse; }
|
||||
|
||||
void Set_Specular(const Vector3& specular) { Specular=specular; }
|
||||
const Vector3& Get_Specular() const { return Specular; }
|
||||
|
||||
private:
|
||||
|
||||
bool Save_Variables(ChunkSaveClass &csave);
|
||||
bool Load_Variables(ChunkLoadClass &cload);
|
||||
|
||||
StringClass TextureName;
|
||||
|
||||
Vector3 Ambient;
|
||||
Vector3 Diffuse;
|
||||
Vector3 Specular;
|
||||
};
|
||||
|
||||
|
||||
|
||||
class Shd6GlossMaskClass : public ShdInterfaceClass
|
||||
{
|
||||
public:
|
||||
Shd6GlossMaskClass(const ShdDefClass* def);
|
||||
virtual ~Shd6GlossMaskClass();
|
||||
|
||||
static void Init();
|
||||
static void Shutdown();
|
||||
|
||||
virtual int Get_Pass_Count() { return 1; }
|
||||
|
||||
virtual int Get_Texture_Count() const { return 1; }
|
||||
virtual TextureClass* Peek_Texture(int idx) const { return Texture; }
|
||||
|
||||
virtual void Apply_Shared(int cur_pass, RenderInfoClass& rinfo);
|
||||
virtual void Apply_Instance(int cur_pass, RenderInfoClass& rinfo);
|
||||
|
||||
virtual unsigned Get_Vertex_Stream_Count() const;
|
||||
virtual unsigned Get_Vertex_Size(unsigned stream) const;
|
||||
virtual bool Use_HW_Vertex_Processing() const { return true; }
|
||||
|
||||
virtual void Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
);
|
||||
|
||||
protected:
|
||||
|
||||
static Matrix4x4 View_Projection_Matrix;
|
||||
|
||||
D3DMATERIAL8* Material;
|
||||
|
||||
TextureClass* Texture;
|
||||
|
||||
Vector4 Ambient;
|
||||
Vector4 Diffuse;
|
||||
Vector4 Specular;
|
||||
};
|
||||
|
||||
|
||||
#endif //SHDGLOSSMASK_H
|
||||
@@ -0,0 +1,43 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
// generic shaders constants
|
||||
// Kenny Mitchell - Westwood Studios EA 2002
|
||||
|
||||
#ifndef SHDHW_CONSTANTS_H
|
||||
#define SHDHW_CONSTANTS_H
|
||||
|
||||
// constants (0,1,0.5,2.0)
|
||||
#define CV_CONST 0
|
||||
|
||||
// lighting constants
|
||||
#define CV_LIGHT_DIRECTION_0 16
|
||||
#define CV_LIGHT_DIRECTION_1 17
|
||||
#define CV_LIGHT_DIRECTION_2 18
|
||||
#define CV_LIGHT_DIRECTION_3 19
|
||||
|
||||
#define CV_LIGHT_COLOR_0 20
|
||||
#define CV_LIGHT_COLOR_1 21
|
||||
#define CV_LIGHT_COLOR_2 22
|
||||
#define CV_LIGHT_COLOR_3 23
|
||||
|
||||
#define CV_AMBIENT 24
|
||||
#define CV_DIFFUSE 25
|
||||
#define CV_SPECULAR 26
|
||||
|
||||
#endif
|
||||
510
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdhwshader.cpp
Normal file
510
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdhwshader.cpp
Normal file
@@ -0,0 +1,510 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WW3D *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/ww3d2/shdhwshader.cpp $*
|
||||
* *
|
||||
* $Org Author:: Kenny_m
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 07/07/02 12:18p $*
|
||||
* *
|
||||
* $Revision:: 3 $*
|
||||
* *
|
||||
* 06/06/02 KM added software vertex shader fallback check
|
||||
* 07/07/02 KM Generic shader functions for factoring HW shader code
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include <stdio.h>
|
||||
#include "shdhwshader.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "rinfo.h"
|
||||
#include "shdhw_constants.h"
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Execute and wait for a hidden shell command
|
||||
/*! 5/27/02 5:39p KJM Created
|
||||
*/
|
||||
void ShdHWShader::Shell_Run(char* cmd)
|
||||
{
|
||||
int result;
|
||||
|
||||
#ifdef WIN32
|
||||
STARTUPINFO si;
|
||||
PROCESS_INFORMATION pi;
|
||||
memset(&pi, 0, sizeof(pi));
|
||||
memset(&si, 0, sizeof(si));
|
||||
si.cb = sizeof(si);
|
||||
si.dwFlags=STARTF_USESHOWWINDOW;
|
||||
si.wShowWindow=SW_HIDE;
|
||||
|
||||
static bool found=false;
|
||||
static char work_dir[_MAX_PATH];
|
||||
|
||||
if (!found)
|
||||
{
|
||||
char* shader_path="\\shaders\\";
|
||||
|
||||
::GetCurrentDirectory(_MAX_PATH,work_dir);
|
||||
strcat(work_dir,shader_path);
|
||||
}
|
||||
|
||||
result=CreateProcess(0,cmd,0,0,0,0,0,work_dir,&si,&pi);
|
||||
|
||||
if (result)
|
||||
{
|
||||
WaitForSingleObject(pi.hThread, INFINITE);
|
||||
|
||||
// Close process and thread handles.
|
||||
CloseHandle(pi.hProcess);
|
||||
CloseHandle(pi.hThread);
|
||||
|
||||
found=true;
|
||||
}
|
||||
else
|
||||
{
|
||||
int err=GetLastError();
|
||||
MessageBox
|
||||
(
|
||||
NULL,
|
||||
"Failed to execute preprocessor on shader\n"
|
||||
"Ensure shaders folder is in application subdirectory\n",
|
||||
"Shader Asset Error",
|
||||
MB_OK
|
||||
);
|
||||
WWASSERT_PRINT(result,"Failed to execute preprocessor on shader (ensure shaders folder is in application subdirectory)");
|
||||
}
|
||||
#else
|
||||
result=system(cmd);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Preprocess and assemble a HW shader from file
|
||||
/*! 5/27/02 5:39p KJM Created
|
||||
*/
|
||||
void ShdHWShader::Preprocess_And_Assemble_Shader_From_File
|
||||
(
|
||||
char* file_name,
|
||||
LPD3DXBUFFER* constants,
|
||||
LPD3DXBUFFER* shader_code
|
||||
)
|
||||
{
|
||||
char shell_command[_MAX_PATH];
|
||||
char temp_path[_MAX_PATH];
|
||||
char temp_file[_MAX_PATH];
|
||||
|
||||
|
||||
GetTempPath(_MAX_PATH, temp_path);
|
||||
GetTempFileName(temp_path,"shd",1,temp_file);
|
||||
|
||||
_snprintf
|
||||
(
|
||||
shell_command,
|
||||
sizeof(shell_command),
|
||||
"shaders\\rspp %s %s",
|
||||
file_name,
|
||||
temp_file
|
||||
);
|
||||
|
||||
LPD3DXBUFFER* errors=NULL;
|
||||
|
||||
Shell_Run(shell_command);
|
||||
|
||||
HRESULT result=D3DXAssembleShaderFromFile
|
||||
(
|
||||
temp_file,
|
||||
NULL,
|
||||
constants,
|
||||
shader_code,
|
||||
errors
|
||||
);
|
||||
WWASSERT_PRINT(result==D3D_OK,"Failed to assemble shader from file");
|
||||
}
|
||||
|
||||
// 06/06/02 KM added software vertex shader fallback check
|
||||
bool ShdHWVertexShader::Using_Hardware=true;
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Destruct this vertex shader
|
||||
/*! 5/27/02 5:39p KJM Created
|
||||
*/
|
||||
ShdHWVertexShader::~ShdHWVertexShader()
|
||||
{
|
||||
Destroy();
|
||||
}
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Destroy this vertex shader
|
||||
/*! 5/27/02 5:39p KJM Created
|
||||
*/
|
||||
void ShdHWVertexShader::Destroy()
|
||||
{
|
||||
if (Shader)
|
||||
{
|
||||
DX8Wrapper::_Get_D3D_Device8()->SetVertexShader(D3DFVF_XYZ|D3DFVF_DIFFUSE);
|
||||
DX8Wrapper::_Get_D3D_Device8()->DeleteVertexShader(Shader);
|
||||
Shader=0;
|
||||
}
|
||||
}
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Create Vertex Shader from a file and vertex stream declaration
|
||||
/*! 05/27/02 5:39p KJM Created
|
||||
/*! 06/06/02 KM added software vertex shader fallback check
|
||||
*/
|
||||
DWORD ShdHWVertexShader::Create
|
||||
(
|
||||
char* file_name,
|
||||
DWORD* vertex_shader_declaration
|
||||
)
|
||||
{
|
||||
// Create vertex shader
|
||||
LPD3DXBUFFER shader_code=NULL;
|
||||
|
||||
Preprocess_And_Assemble_Shader_From_File
|
||||
(
|
||||
file_name,
|
||||
NULL,
|
||||
&shader_code
|
||||
);
|
||||
|
||||
// try hardware first
|
||||
Using_Hardware=true;
|
||||
HRESULT result=DX8Wrapper::_Get_D3D_Device8()->CreateVertexShader
|
||||
(
|
||||
(DWORD*)vertex_shader_declaration,
|
||||
(DWORD*)shader_code->GetBufferPointer(),
|
||||
(DWORD*)&Shader,
|
||||
0
|
||||
);
|
||||
if (result!=D3D_OK)
|
||||
{
|
||||
// try software
|
||||
Using_Hardware=false;
|
||||
result=DX8Wrapper::_Get_D3D_Device8()->CreateVertexShader
|
||||
(
|
||||
(DWORD*)vertex_shader_declaration,
|
||||
(DWORD*)shader_code->GetBufferPointer(),
|
||||
(DWORD*)&Shader,
|
||||
D3DUSAGE_SOFTWAREPROCESSING
|
||||
);
|
||||
WWASSERT_PRINT(result==D3D_OK,"Failed to create vertex shader");
|
||||
}
|
||||
|
||||
if (shader_code) shader_code->Release();
|
||||
|
||||
return Shader;
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Create Vertex Shader from a dword constant and vertex stream declaration
|
||||
/*! 07/19/02 3:39p KJM Created
|
||||
*/
|
||||
DWORD ShdHWVertexShader::Create
|
||||
(
|
||||
DWORD* shader_code_str,
|
||||
DWORD* vertex_shader_declaration
|
||||
)
|
||||
{
|
||||
HRESULT result;
|
||||
LPD3DXBUFFER shader_code=NULL;
|
||||
LPD3DXBUFFER errors=NULL;
|
||||
|
||||
result=D3DXAssembleShader
|
||||
(
|
||||
shader_code_str,
|
||||
strlen((char*)shader_code_str),
|
||||
NULL,//D3DXASM_DEBUG,
|
||||
NULL,
|
||||
&shader_code,
|
||||
&errors
|
||||
);
|
||||
if (result!=D3D_OK)
|
||||
{
|
||||
OutputDebugString((char*)errors->GetBufferPointer());
|
||||
WWASSERT_PRINT(result==D3D_OK,"Failed to assemble shader");
|
||||
}
|
||||
|
||||
// try hardware first
|
||||
Using_Hardware=true;
|
||||
result=DX8Wrapper::_Get_D3D_Device8()->CreateVertexShader
|
||||
(
|
||||
(DWORD*)vertex_shader_declaration,
|
||||
(DWORD*)shader_code->GetBufferPointer(),
|
||||
(DWORD*)&Shader,
|
||||
0
|
||||
);
|
||||
if (result!=D3D_OK)
|
||||
{
|
||||
// try software
|
||||
Using_Hardware=false;
|
||||
result=DX8Wrapper::_Get_D3D_Device8()->CreateVertexShader
|
||||
(
|
||||
(DWORD*)vertex_shader_declaration,
|
||||
(DWORD*)shader_code->GetBufferPointer(),
|
||||
(DWORD*)&Shader,
|
||||
D3DUSAGE_SOFTWAREPROCESSING
|
||||
);
|
||||
WWASSERT_PRINT(result==D3D_OK,"Failed to create vertex shader");
|
||||
if (result!=D3D_OK)
|
||||
{
|
||||
OutputDebugString((char*)shader_code_str);
|
||||
}
|
||||
}
|
||||
|
||||
return Shader;
|
||||
}
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Destruct this pixel shader
|
||||
/*! 5/27/02 5:39p KJM Created
|
||||
*/
|
||||
ShdHWPixelShader::~ShdHWPixelShader()
|
||||
{
|
||||
Destroy();
|
||||
}
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Destroy this pixel shader
|
||||
/*! 5/27/02 5:39p KJM Created
|
||||
*/
|
||||
void ShdHWPixelShader::Destroy()
|
||||
{
|
||||
if (Shader)
|
||||
{
|
||||
DX8Wrapper::_Get_D3D_Device8()->SetPixelShader(0);
|
||||
DX8Wrapper::_Get_D3D_Device8()->DeletePixelShader(Shader);
|
||||
Shader=0;
|
||||
}
|
||||
}
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Create Pixel Shader from a file
|
||||
/*! 5/27/02 5:39p KJM Created
|
||||
*/
|
||||
DWORD ShdHWPixelShader::Create(char* file_name)
|
||||
{
|
||||
// Create pixel shader
|
||||
LPD3DXBUFFER shader_code=NULL;
|
||||
|
||||
Preprocess_And_Assemble_Shader_From_File
|
||||
(
|
||||
file_name,
|
||||
NULL,
|
||||
&shader_code
|
||||
);
|
||||
|
||||
HRESULT result=DX8Wrapper::_Get_D3D_Device8()->CreatePixelShader
|
||||
(
|
||||
(DWORD*)shader_code->GetBufferPointer(),
|
||||
(DWORD*)&Shader
|
||||
);
|
||||
WWASSERT_PRINT(result==D3D_OK,"Failed to create pixel shader");
|
||||
|
||||
return Shader;
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Create Pixel Shader from a dword constant
|
||||
/*! 07/19/02 3:39p KJM Created
|
||||
*/
|
||||
DWORD ShdHWPixelShader::Create(DWORD* shader_code_str)
|
||||
{
|
||||
HRESULT result;
|
||||
LPD3DXBUFFER shader_code=NULL;
|
||||
LPD3DXBUFFER errors;
|
||||
|
||||
result=D3DXAssembleShader
|
||||
(
|
||||
shader_code_str,
|
||||
strlen((char*)shader_code_str),
|
||||
NULL,
|
||||
NULL,
|
||||
&shader_code,
|
||||
&errors
|
||||
);
|
||||
if (result!=D3D_OK)
|
||||
{
|
||||
OutputDebugString((char*)errors->GetBufferPointer());
|
||||
WWASSERT_PRINT(result==D3D_OK,"Failed to assemble shader");
|
||||
}
|
||||
|
||||
result=DX8Wrapper::_Get_D3D_Device8()->CreatePixelShader
|
||||
(
|
||||
(DWORD*)shader_code->GetBufferPointer(),
|
||||
(DWORD*)&Shader
|
||||
);
|
||||
WWASSERT_PRINT(result==D3D_OK,"Failed to create pixel shader");
|
||||
|
||||
return Shader;
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Apply generic lighting
|
||||
/*! 07/07/02 12:23p KJM Created
|
||||
*/
|
||||
void ShdHWVertexShader::Light
|
||||
(
|
||||
RenderInfoClass& rinfo,
|
||||
Vector4& ambient,
|
||||
Vector4& diffuse,
|
||||
Vector4& specular
|
||||
)
|
||||
{
|
||||
LightEnvironmentClass* lenv=rinfo.light_environment;
|
||||
|
||||
Vector4 light_ambient(1,1,1,1);
|
||||
|
||||
if (lenv)
|
||||
{
|
||||
int num_lights=lenv->Get_Light_Count();
|
||||
|
||||
// most cases set up and use the light environment
|
||||
if (num_lights)
|
||||
{
|
||||
const Vector3& amb=lenv->Get_Equivalent_Ambient();
|
||||
light_ambient.Set
|
||||
(
|
||||
amb.X,
|
||||
amb.Y,
|
||||
amb.Z,
|
||||
0
|
||||
);
|
||||
int i;
|
||||
|
||||
int max=LightEnvironmentClass::Get_Max_Lights();
|
||||
|
||||
if (num_lights>max) num_lights=max;
|
||||
|
||||
Vector4 cdir, ccol;
|
||||
for (i=0;i<max;i++)
|
||||
{
|
||||
if (i<num_lights)
|
||||
{
|
||||
Vector3 rot;
|
||||
const Vector3& dir=lenv->Get_Light_Direction(i);
|
||||
const Vector3& col=lenv->Get_Light_Diffuse(i);
|
||||
|
||||
cdir.Set(dir.X,dir.Y,dir.Z,1.0f);
|
||||
ccol.Set(col.X,col.Y,col.Z,1.0f);
|
||||
}
|
||||
else
|
||||
{
|
||||
// if no light just set color to zero
|
||||
ccol.Set(0,0,0,0);
|
||||
}
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_LIGHT_DIRECTION_0+i, &cdir, 1);
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_LIGHT_COLOR_0+i, &ccol, 1);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
const Vector3& amb_col=DX8Wrapper::Get_Ambient();
|
||||
|
||||
light_ambient.X=amb_col.X;
|
||||
light_ambient.Y=amb_col.Y;
|
||||
light_ambient.Z=amb_col.Z;
|
||||
|
||||
// otherwise have to extract light from render state
|
||||
int max=LightEnvironmentClass::Get_Max_Lights();
|
||||
int i;
|
||||
|
||||
RenderStateStruct state;
|
||||
DX8Wrapper::Get_Render_State(state);
|
||||
Vector4 cdir, ccol;
|
||||
|
||||
for (i=0;i<max;i++)
|
||||
{
|
||||
if (state.LightEnable[i])
|
||||
{
|
||||
D3DLIGHT8& light=state.Lights[i];
|
||||
|
||||
// handle directional and positional lights
|
||||
if (light.Type==D3DLIGHT_DIRECTIONAL)
|
||||
{
|
||||
const D3DXVECTOR3& dir=state.Lights[i].Direction;
|
||||
|
||||
cdir.Set(-dir.x,-dir.y,-dir.z,0.0f);
|
||||
}
|
||||
else
|
||||
{
|
||||
const D3DXVECTOR3& pos=state.Lights[i].Position;
|
||||
|
||||
// just normalise the light position for now (as only appears to be used in w3dview)
|
||||
cdir.Set(pos.x,pos.y,pos.z,0.0f);
|
||||
}
|
||||
|
||||
cdir.Normalize();
|
||||
ccol.Set
|
||||
(
|
||||
state.Lights[i].Diffuse.r,
|
||||
state.Lights[i].Diffuse.g,
|
||||
state.Lights[i].Diffuse.b,
|
||||
1.0f
|
||||
);
|
||||
}
|
||||
else
|
||||
{
|
||||
// if no light just set color to zero
|
||||
ccol.Set(0,0,0,0);
|
||||
}
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_LIGHT_DIRECTION_0+i, &cdir, 1);
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_LIGHT_COLOR_0+i, &ccol, 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
light_ambient.X*=ambient.X;
|
||||
light_ambient.Y*=ambient.Y;
|
||||
light_ambient.Z*=ambient.Z;
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_AMBIENT, &light_ambient, 1);
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_DIFFUSE, &diffuse, 1);
|
||||
DX8Wrapper::Set_Vertex_Shader_Constant(CV_SPECULAR, &specular, 1);
|
||||
}
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Apply generic lighting (no specular supplied)
|
||||
/*! 07/07/02 12:23p KJM Created
|
||||
*/
|
||||
void ShdHWVertexShader::Light
|
||||
(
|
||||
RenderInfoClass& rinfo,
|
||||
Vector4& ambient,
|
||||
Vector4& diffuse
|
||||
)
|
||||
{
|
||||
Vector4 specular(0,0,0,0);
|
||||
Light(rinfo,ambient,diffuse,specular);
|
||||
}
|
||||
|
||||
133
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdhwshader.h
Normal file
133
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdhwshader.h
Normal file
@@ -0,0 +1,133 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WW3D *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/ww3d2/shdhwshader.h $*
|
||||
* *
|
||||
* $Org Author:: Kenny_m
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 07/07/02 11:18p $*
|
||||
* *
|
||||
* $Revision:: 3 $*
|
||||
* *
|
||||
* 06/06/02 KM added software vertex shader fallback check
|
||||
* 07/07/02 KM Generic shader functions for factoring HW shader code
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHDHWSHADER_H
|
||||
#define SHDHWSHADER_H
|
||||
|
||||
#ifndef _D3D8_H_
|
||||
#include <d3d8.h>
|
||||
#endif
|
||||
|
||||
#ifndef __D3DX8_H__
|
||||
#include <d3dx8.h>
|
||||
#endif
|
||||
|
||||
#ifndef SHDHW_CONSTANTS_H
|
||||
#include "shdhw_constants.h"
|
||||
#endif
|
||||
|
||||
|
||||
class RenderInfoClass;
|
||||
class Vector4;
|
||||
|
||||
class ShdHWShader
|
||||
{
|
||||
public:
|
||||
ShdHWShader() : Shader(0) {}
|
||||
virtual ~ShdHWShader() {}
|
||||
|
||||
DWORD Peek_Shader() const { return Shader; }
|
||||
|
||||
protected:
|
||||
|
||||
void Shell_Run(char* cmd);
|
||||
|
||||
void Preprocess_And_Assemble_Shader_From_File
|
||||
(
|
||||
char* file_name,
|
||||
LPD3DXBUFFER* constants,
|
||||
LPD3DXBUFFER* shader_code
|
||||
);
|
||||
|
||||
DWORD Shader;
|
||||
};
|
||||
|
||||
class ShdHWVertexShader : public ShdHWShader
|
||||
{
|
||||
public:
|
||||
virtual ~ShdHWVertexShader();
|
||||
|
||||
DWORD Create
|
||||
(
|
||||
char* file_name,
|
||||
DWORD* vertex_shader_declaration
|
||||
);
|
||||
|
||||
DWORD Create
|
||||
(
|
||||
DWORD* shader_code,
|
||||
DWORD* vertex_shader_declaration
|
||||
);
|
||||
|
||||
void Destroy();
|
||||
|
||||
static bool Is_Using_Hardware() { return Using_Hardware; }
|
||||
|
||||
static void Light
|
||||
(
|
||||
RenderInfoClass& rinfo,
|
||||
Vector4& ambient,
|
||||
Vector4& diffuse,
|
||||
Vector4& specular
|
||||
);
|
||||
|
||||
static void Light
|
||||
(
|
||||
RenderInfoClass& rinfo,
|
||||
Vector4& ambient,
|
||||
Vector4& diffuse
|
||||
);
|
||||
|
||||
private:
|
||||
static bool Using_Hardware;
|
||||
};
|
||||
|
||||
class ShdHWPixelShader : public ShdHWShader
|
||||
{
|
||||
public:
|
||||
virtual ~ShdHWPixelShader();
|
||||
|
||||
DWORD Create(char* file_name);
|
||||
DWORD Create(DWORD* shader_code);
|
||||
|
||||
void Destroy();
|
||||
};
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,78 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shdinterface.cpp $*
|
||||
* *
|
||||
* $Org Author:: Jani_p
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 6/05/02 3:12p $*
|
||||
* *
|
||||
* $Revision:: 2 $*
|
||||
* *
|
||||
* 6/05/02 KJM : Added texture info functions
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include "shdinterface.h"
|
||||
#include "shddef.h"
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Constructor
|
||||
/*!
|
||||
Base class constructor for shaders. Saves a pointer to the definition for this shader.
|
||||
|
||||
@param
|
||||
*/
|
||||
ShdInterfaceClass::ShdInterfaceClass(const ShdDefClass * def, int class_id) :
|
||||
Definition(NULL),
|
||||
ClassID(class_id)
|
||||
{
|
||||
REF_PTR_SET(Definition,def);
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Destructor
|
||||
/*!
|
||||
Destructor for ShdInterfaceClass, releases the definition.
|
||||
*/
|
||||
ShdInterfaceClass::~ShdInterfaceClass(void)
|
||||
{
|
||||
REF_PTR_RELEASE(Definition);
|
||||
}
|
||||
|
||||
|
||||
//**********************************************************************************************
|
||||
//! returns a pointer to the definition for this shader
|
||||
/*!
|
||||
@returns
|
||||
*/
|
||||
const ShdDefClass * ShdInterfaceClass::Peek_Definition(void)
|
||||
{
|
||||
return Definition;
|
||||
}
|
||||
142
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdinterface.h
Normal file
142
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdinterface.h
Normal file
@@ -0,0 +1,142 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shdinterface.h $*
|
||||
* *
|
||||
* $Org Author:: Jani_p
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 6/05/02 3:12p $*
|
||||
* *
|
||||
* $Revision:: 2 $*
|
||||
* *
|
||||
* 6/05/02 KJM : Added texture info functions
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHDINTERFACE_H
|
||||
#define SHDINTERFACE_H
|
||||
|
||||
#include "always.h"
|
||||
#include "refcount.h"
|
||||
#include "dx8wrapper.h"
|
||||
|
||||
class ShdDefClass;
|
||||
class ShdMeshClass;
|
||||
class RenderInfoClass;
|
||||
class TextureClass;
|
||||
|
||||
/*
|
||||
** Maximum passes allowed for any shader implementation!
|
||||
*/
|
||||
const int SHD_MAX_PASSES = 4;
|
||||
|
||||
/**
|
||||
** Utility structure for passing in streams to the shader. Those streams that are not available will be NULL,
|
||||
** and the shader should ASSERT that it is passed everything it needs in its Copy_Vertex_Stream() function.
|
||||
** The caller of the Copy_Vertex_Stream() should use query functions (such as Requires_Normals()) in the definition
|
||||
** to determine which streams the shader needs.
|
||||
*/
|
||||
struct VertexStreamStruct
|
||||
{
|
||||
VertexStreamStruct()
|
||||
: Locations(0),
|
||||
Normals(0),
|
||||
DiffuseInt(0),
|
||||
DiffuseFloat(0)
|
||||
{
|
||||
for (int i=0;i<MAX_TEXTURE_STAGES;++i)
|
||||
{
|
||||
UV[i]=0;
|
||||
}
|
||||
}
|
||||
|
||||
const Vector3* Locations;
|
||||
const Vector3* Normals;
|
||||
const Vector2* UV[MAX_TEXTURE_STAGES];
|
||||
const unsigned* DiffuseInt;
|
||||
const Vector4* DiffuseFloat;
|
||||
const Vector3* S;
|
||||
const Vector3* T;
|
||||
const Vector3* SxT;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
** ShdInterfaceClass - This class is the virtual interface for all shaders. A derived shader's job is to
|
||||
** set up the D3D render states for a particular rendering operation. Instances of shaders are
|
||||
** are created by an associated ShdDefClass.
|
||||
*/
|
||||
class ShdInterfaceClass : public RefCountClass
|
||||
{
|
||||
public:
|
||||
ShdInterfaceClass(const ShdDefClass * def,int class_id);
|
||||
virtual ~ShdInterfaceClass(void);
|
||||
|
||||
const ShdDefClass * Peek_Definition(void);
|
||||
|
||||
WWINLINE int Get_Class_ID() const { return ClassID; }
|
||||
|
||||
// For rendering efficiency, all shaders should implement comparison operator that the renderer
|
||||
// can use to sort the meshes.
|
||||
virtual bool Greater_Than (const ShdInterfaceClass& s,int pass) const { return true; }
|
||||
virtual bool Similar_Enough (const ShdInterfaceClass& s,int pass) const { return true; }
|
||||
|
||||
virtual int Get_Pass_Count(void) = 0;
|
||||
virtual bool Pass_Selection(ShdMeshClass*, RenderInfoClass*,int) { return true; }
|
||||
|
||||
virtual void Apply_Shared(int cur_pass, RenderInfoClass& rinfo) = 0;
|
||||
virtual void Apply_Instance(int cur_pass, RenderInfoClass& rinfo) = 0;
|
||||
|
||||
// The shader needs to tell how many vertex streams it needs and what are the sizes of vertices
|
||||
// in each stream.
|
||||
virtual unsigned Get_Vertex_Stream_Count() const = 0;
|
||||
virtual unsigned Get_Vertex_Size(unsigned stream) const = 0;
|
||||
|
||||
virtual bool Use_HW_Vertex_Processing() const = 0;
|
||||
|
||||
virtual int Get_Texture_Count() const = 0;
|
||||
virtual TextureClass* Peek_Texture(int idx) const = 0;
|
||||
|
||||
// The shader needs to construct each vertex stream as requested. The data comes in a standard
|
||||
// VertexStreamStruct, and the shader can format it as it wishes (nothing else will be using
|
||||
// the buffer than the shader itself.
|
||||
virtual void Copy_Vertex_Stream(unsigned stream, void* dest_buffer, const VertexStreamStruct& vss, unsigned vertex_count) = 0;
|
||||
|
||||
// Return whether this shader is opaque. This property is used to determine whether
|
||||
// geometric shadows should be cast from an object for example. Alpha-Test shaders should
|
||||
// return false to Is_Opaque.
|
||||
virtual bool Is_Opaque(void) const { return true; }
|
||||
|
||||
protected:
|
||||
|
||||
const ShdDefClass * Definition;
|
||||
int ClassID;
|
||||
|
||||
};
|
||||
|
||||
|
||||
#endif //SHDINTERFACE_H
|
||||
@@ -0,0 +1,615 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shdlegacyw3d.cpp $*
|
||||
* *
|
||||
* $Org Author:: Jani_p
|
||||
*
|
||||
* $Author:: Jani_p
|
||||
*
|
||||
* $Modtime:: 7/12/02 3:12p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include <d3dx8math.h>
|
||||
#include "dx8fvf.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "assetmgr.h"
|
||||
|
||||
#include "shdlegacyw3d.h"
|
||||
|
||||
#include "editable.h"
|
||||
#include "chunkio.h"
|
||||
#include "w3d_util.h"
|
||||
#include "persistfactory.h"
|
||||
#include "wwhack.h"
|
||||
|
||||
#include "shdclassids.h"
|
||||
#include "shddeffactory.h"
|
||||
#include "shdinterface.h"
|
||||
#include "shdhwshader.h"
|
||||
|
||||
|
||||
DECLARE_FORCE_LINK(LegacyW3DShader);
|
||||
REGISTER_SHDDEF(ShdLegacyW3DDefClass,SHDDEF_CLASSID_LEGACYW3D,"LegacyW3D");
|
||||
|
||||
|
||||
// Save-Load methods for ShdDefClass
|
||||
enum
|
||||
{
|
||||
SHDLEGACY_CHUNKID_VARIABLES = 0x11070958,
|
||||
|
||||
SHDLEGACY_CHUNKID_TEXTURE_NAME00,
|
||||
SHDLEGACY_CHUNKID_TEXTURE_NAME01,
|
||||
SHDLEGACY_CHUNKID_TEXTURE_NAME10,
|
||||
SHDLEGACY_CHUNKID_TEXTURE_NAME11,
|
||||
SHDLEGACY_CHUNKID_TEXTURE_NAME20,
|
||||
SHDLEGACY_CHUNKID_TEXTURE_NAME21,
|
||||
SHDLEGACY_CHUNKID_TEXTURE_NAME30,
|
||||
SHDLEGACY_CHUNKID_TEXTURE_NAME31,
|
||||
|
||||
SHDLEGACY_CHUNKID_MAPPERARGS00,
|
||||
SHDLEGACY_CHUNKID_MAPPERARGS01,
|
||||
SHDLEGACY_CHUNKID_MAPPERARGS10,
|
||||
SHDLEGACY_CHUNKID_MAPPERARGS11,
|
||||
SHDLEGACY_CHUNKID_MAPPERARGS20,
|
||||
SHDLEGACY_CHUNKID_MAPPERARGS21,
|
||||
SHDLEGACY_CHUNKID_MAPPERARGS30,
|
||||
SHDLEGACY_CHUNKID_MAPPERARGS31,
|
||||
|
||||
VARID_PASS_COUNT = 0x00,
|
||||
|
||||
VARID_SHADER0,
|
||||
VARID_SHADER1,
|
||||
VARID_SHADER2,
|
||||
VARID_SHADER3,
|
||||
|
||||
VARID_MATERIAL0,
|
||||
VARID_MATERIAL1,
|
||||
VARID_MATERIAL2,
|
||||
VARID_MATERIAL3,
|
||||
|
||||
VARID_TEXTURE_ATTRIBUTES00,
|
||||
VARID_TEXTURE_ATTRIBUTES01,
|
||||
VARID_TEXTURE_ATTRIBUTES10,
|
||||
VARID_TEXTURE_ATTRIBUTES11,
|
||||
VARID_TEXTURE_ATTRIBUTES20,
|
||||
VARID_TEXTURE_ATTRIBUTES21,
|
||||
VARID_TEXTURE_ATTRIBUTES30,
|
||||
VARID_TEXTURE_ATTRIBUTES31,
|
||||
|
||||
VARID_MAPCHANNEL00,
|
||||
VARID_MAPCHANNEL01,
|
||||
VARID_MAPCHANNEL10,
|
||||
VARID_MAPCHANNEL11,
|
||||
VARID_MAPCHANNEL20,
|
||||
VARID_MAPCHANNEL21,
|
||||
VARID_MAPCHANNEL30,
|
||||
VARID_MAPCHANNEL31,
|
||||
|
||||
VARID_AMBIENT_COLOR,
|
||||
VARID_DIFFUSE_COLOR
|
||||
};
|
||||
|
||||
|
||||
ShdLegacyW3DDefClass::ShdLegacyW3DDefClass()
|
||||
: ShdDefClass(SHDDEF_CLASSID_LEGACYW3D),
|
||||
PassCount(0)
|
||||
{
|
||||
// init defaults
|
||||
for (int pass_index=0; pass_index < MeshMatDescClass::MAX_PASSES; pass_index++) {
|
||||
memset(&(Shaders[pass_index]),0,sizeof(W3dShaderStruct));
|
||||
memset(&(Materials[pass_index]),0,sizeof(W3dVertexMaterialStruct));
|
||||
|
||||
for (int stage_index=0; stage_index < MeshMatDescClass::MAX_TEX_STAGES; stage_index++) {
|
||||
TextureAttributes[pass_index][stage_index] = 0;
|
||||
MapChannel[pass_index][stage_index] = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ShdLegacyW3DDefClass::ShdLegacyW3DDefClass(const ShdLegacyW3DDefClass& that)
|
||||
: ShdDefClass(that),
|
||||
PassCount(that.PassCount)
|
||||
{
|
||||
// init defaults
|
||||
for (int pass_index=0; pass_index < MeshMatDescClass::MAX_PASSES; pass_index++) {
|
||||
memset(&(Shaders[pass_index]),0,sizeof(W3dShaderStruct));
|
||||
memset(&(Materials[pass_index]),0,sizeof(W3dVertexMaterialStruct));
|
||||
|
||||
for (int stage_index=0; stage_index < MeshMatDescClass::MAX_TEX_STAGES; stage_index++) {
|
||||
TextureAttributes[pass_index][stage_index] = 0;
|
||||
MapChannel[pass_index][stage_index] = 0;
|
||||
}
|
||||
}
|
||||
|
||||
for (int pass=0;pass<PassCount;++pass) {
|
||||
for (int stage=0;stage<MeshMatDescClass::MAX_TEX_STAGES;++stage) {
|
||||
TextureNames[pass][stage]=that.TextureNames[pass][stage];
|
||||
}
|
||||
// Shaders[pass]=that.Shaders[pass];
|
||||
// Materials[pass]=that.Materials[pass];
|
||||
}
|
||||
}
|
||||
|
||||
ShdLegacyW3DDefClass::~ShdLegacyW3DDefClass()
|
||||
{
|
||||
}
|
||||
|
||||
bool ShdLegacyW3DDefClass::Is_Valid_Config(StringClass &message)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ShdLegacyW3DDefClass::Uses_UV_Channel(int i) const
|
||||
{
|
||||
for (int pass=0; pass<PassCount; pass++) {
|
||||
for (int stage=0; stage<MeshMatDescClass::MAX_TEX_STAGES; stage++) {
|
||||
if (MapChannel[pass][stage] == i) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool ShdLegacyW3DDefClass::Save(ChunkSaveClass &csave)
|
||||
{
|
||||
// Call parent class
|
||||
ShdDefClass::Save(csave);
|
||||
|
||||
// Save our variables
|
||||
csave.Begin_Chunk(SHDLEGACY_CHUNKID_VARIABLES);
|
||||
Save_Variables(csave);
|
||||
csave.End_Chunk();
|
||||
|
||||
// Save any mapper args and texture names present
|
||||
for (int pass_index=0; pass_index<PassCount; pass_index++) {
|
||||
for (int stage_index=0; stage_index<2; stage_index++) {
|
||||
|
||||
// Write the texture name
|
||||
if (!TextureNames[pass_index][stage_index].Is_Empty()) {
|
||||
|
||||
/* (gth) need to save entire path for Max to work properly right???
|
||||
char fname[_MAX_PATH];
|
||||
char extension[_MAX_PATH];
|
||||
_splitpath(TextureNames[pass_index][stage_index].Peek_Buffer(),NULL,NULL,fname,extension);
|
||||
strcat(fname,extension);
|
||||
*/
|
||||
int chunk_id = SHDLEGACY_CHUNKID_TEXTURE_NAME00 + pass_index * 2 + stage_index;
|
||||
WRITE_WWSTRING_CHUNK(csave,chunk_id,TextureNames[pass_index][stage_index]);
|
||||
}
|
||||
|
||||
// Write the mapper args
|
||||
if (!MapperArgs[pass_index][stage_index].Is_Empty()) {
|
||||
int chunk_id = SHDLEGACY_CHUNKID_MAPPERARGS00 + pass_index * 2 + stage_index;
|
||||
WRITE_WWSTRING_CHUNK(csave,chunk_id,MapperArgs[pass_index][stage_index])
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool ShdLegacyW3DDefClass::Load(ChunkLoadClass &cload)
|
||||
{
|
||||
int offset = 0;
|
||||
int pass = 0;
|
||||
int stage = 0;
|
||||
|
||||
// Call parent class
|
||||
ShdDefClass::Load(cload);
|
||||
|
||||
// Read in the chunks
|
||||
while (cload.Open_Chunk()) {
|
||||
switch (cload.Cur_Chunk_ID())
|
||||
{
|
||||
case SHDLEGACY_CHUNKID_VARIABLES:
|
||||
Load_Variables(cload);
|
||||
break;
|
||||
|
||||
case SHDLEGACY_CHUNKID_TEXTURE_NAME00:
|
||||
case SHDLEGACY_CHUNKID_TEXTURE_NAME01:
|
||||
case SHDLEGACY_CHUNKID_TEXTURE_NAME10:
|
||||
case SHDLEGACY_CHUNKID_TEXTURE_NAME11:
|
||||
case SHDLEGACY_CHUNKID_TEXTURE_NAME20:
|
||||
case SHDLEGACY_CHUNKID_TEXTURE_NAME21:
|
||||
case SHDLEGACY_CHUNKID_TEXTURE_NAME30:
|
||||
case SHDLEGACY_CHUNKID_TEXTURE_NAME31:
|
||||
offset = cload.Cur_Chunk_ID() - SHDLEGACY_CHUNKID_TEXTURE_NAME00;
|
||||
pass = offset / 2;
|
||||
stage = offset % 2;
|
||||
cload.Read(TextureNames[pass][stage].Get_Buffer(cload.Cur_Chunk_Length()),cload.Cur_Chunk_Length());
|
||||
break;
|
||||
|
||||
case SHDLEGACY_CHUNKID_MAPPERARGS00:
|
||||
case SHDLEGACY_CHUNKID_MAPPERARGS01:
|
||||
case SHDLEGACY_CHUNKID_MAPPERARGS10:
|
||||
case SHDLEGACY_CHUNKID_MAPPERARGS11:
|
||||
case SHDLEGACY_CHUNKID_MAPPERARGS20:
|
||||
case SHDLEGACY_CHUNKID_MAPPERARGS21:
|
||||
case SHDLEGACY_CHUNKID_MAPPERARGS30:
|
||||
case SHDLEGACY_CHUNKID_MAPPERARGS31:
|
||||
offset = cload.Cur_Chunk_ID() - SHDLEGACY_CHUNKID_MAPPERARGS00;
|
||||
pass = offset / 2;
|
||||
stage = offset % 2;
|
||||
cload.Read(MapperArgs[pass][stage].Get_Buffer(cload.Cur_Chunk_Length()),cload.Cur_Chunk_Length());
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
cload.Close_Chunk();
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ShdLegacyW3DDefClass::Save_Variables(ChunkSaveClass &csave)
|
||||
{
|
||||
WRITE_MICRO_CHUNK(csave, VARID_PASS_COUNT, PassCount);
|
||||
|
||||
for (int pass_index=0; pass_index<PassCount; pass_index++) {
|
||||
|
||||
// Write the shader and vertex material
|
||||
WRITE_MICRO_CHUNK(csave, VARID_SHADER0 + pass_index, Shaders[pass_index]);
|
||||
WRITE_MICRO_CHUNK(csave, VARID_MATERIAL0 + pass_index, Materials[pass_index]);
|
||||
|
||||
for (int stage_index=0; stage_index<2; stage_index++) {
|
||||
|
||||
// Write the texture attributes
|
||||
if (TextureAttributes[pass_index][stage_index] != 0) {
|
||||
WRITE_MICRO_CHUNK(csave, VARID_TEXTURE_ATTRIBUTES00 + pass_index*2 + stage_index, TextureAttributes[pass_index][stage_index]);
|
||||
}
|
||||
|
||||
// Write the map channels
|
||||
if (MapChannel[pass_index][stage_index] != 0) {
|
||||
WRITE_MICRO_CHUNK(csave, VARID_MAPCHANNEL00 + pass_index*2 + stage_index, MapChannel[pass_index][stage_index]);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ShdLegacyW3DDefClass::Load_Variables(ChunkLoadClass &cload)
|
||||
{
|
||||
int offset = 0;
|
||||
int pass = 0;
|
||||
int stage = 0;
|
||||
|
||||
while (cload.Open_Micro_Chunk())
|
||||
{
|
||||
switch (cload.Cur_Micro_Chunk_ID())
|
||||
{
|
||||
READ_MICRO_CHUNK(cload, VARID_PASS_COUNT, PassCount);
|
||||
|
||||
case VARID_SHADER0:
|
||||
case VARID_SHADER1:
|
||||
case VARID_SHADER2:
|
||||
case VARID_SHADER3:
|
||||
pass = cload.Cur_Micro_Chunk_ID() - VARID_SHADER0;
|
||||
cload.Read(&Shaders[pass],sizeof(Shaders[pass]));
|
||||
break;
|
||||
|
||||
case VARID_MATERIAL0:
|
||||
case VARID_MATERIAL1:
|
||||
case VARID_MATERIAL2:
|
||||
case VARID_MATERIAL3:
|
||||
pass = cload.Cur_Micro_Chunk_ID() - VARID_MATERIAL0;
|
||||
cload.Read(&Materials[pass],sizeof(Materials[pass]));
|
||||
break;
|
||||
|
||||
case VARID_TEXTURE_ATTRIBUTES00:
|
||||
case VARID_TEXTURE_ATTRIBUTES01:
|
||||
case VARID_TEXTURE_ATTRIBUTES10:
|
||||
case VARID_TEXTURE_ATTRIBUTES11:
|
||||
case VARID_TEXTURE_ATTRIBUTES20:
|
||||
case VARID_TEXTURE_ATTRIBUTES21:
|
||||
case VARID_TEXTURE_ATTRIBUTES30:
|
||||
case VARID_TEXTURE_ATTRIBUTES31:
|
||||
offset = cload.Cur_Micro_Chunk_ID() - VARID_TEXTURE_ATTRIBUTES00;
|
||||
pass = offset / 2;
|
||||
stage = offset % 2;
|
||||
cload.Read(&TextureAttributes[pass][stage],sizeof(TextureAttributes[pass][stage]));
|
||||
break;
|
||||
|
||||
case VARID_MAPCHANNEL00:
|
||||
case VARID_MAPCHANNEL01:
|
||||
case VARID_MAPCHANNEL10:
|
||||
case VARID_MAPCHANNEL11:
|
||||
case VARID_MAPCHANNEL20:
|
||||
case VARID_MAPCHANNEL21:
|
||||
case VARID_MAPCHANNEL30:
|
||||
case VARID_MAPCHANNEL31:
|
||||
offset = cload.Cur_Micro_Chunk_ID() - VARID_MAPCHANNEL00;
|
||||
pass = offset / 2;
|
||||
stage = offset % 2;
|
||||
cload.Read(&MapChannel[pass][stage],sizeof(MapChannel[pass][stage]));
|
||||
break;
|
||||
}
|
||||
|
||||
cload.Close_Micro_Chunk();
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
void ShdLegacyW3DDefClass::Init()
|
||||
{
|
||||
Shd6LegacyW3DClass::Init();
|
||||
}
|
||||
|
||||
void ShdLegacyW3DDefClass::Shutdown()
|
||||
{
|
||||
Shd6LegacyW3DClass::Shutdown();
|
||||
}
|
||||
|
||||
ShdInterfaceClass* ShdLegacyW3DDefClass::Create() const
|
||||
{
|
||||
return NEW_REF(Shd6LegacyW3DClass,(this));
|
||||
}
|
||||
|
||||
Shd6LegacyW3DClass::Shd6LegacyW3DClass(const ShdDefClass* def)
|
||||
: ShdInterfaceClass(def,SHDDEF_CLASSID_LEGACYW3D),
|
||||
PassCount(0)
|
||||
{
|
||||
int pass;
|
||||
int stage;
|
||||
for (pass=0;pass<MeshMatDescClass::MAX_PASSES;++pass) {
|
||||
Materials[pass]=NULL;
|
||||
for (int stage=0;stage<MeshMatDescClass::MAX_TEX_STAGES;++stage) {
|
||||
Textures[pass][stage]=NULL;
|
||||
}
|
||||
}
|
||||
|
||||
ShdLegacyW3DDefClass* Definition=(ShdLegacyW3DDefClass*)def;
|
||||
PassCount=Definition->Get_Pass_Count();
|
||||
|
||||
for (pass=0;pass<PassCount;++pass) {
|
||||
|
||||
// Set up the shaders
|
||||
W3dUtilityClass::Convert_Shader(Definition->Get_Shader(pass),&(Shaders[pass]));
|
||||
|
||||
// Set up the vertex materials
|
||||
VertexMaterialClass * vmat = NEW_REF(VertexMaterialClass,());
|
||||
vmat->Parse_W3dVertexMaterialStruct(Definition->Get_Material(pass));
|
||||
|
||||
char * map0_args = NULL;
|
||||
char * map1_args = NULL;
|
||||
if (!Definition->Get_Mapper_Args(pass,0).Is_Empty()) {
|
||||
map0_args = Definition->Get_Mapper_Args(pass,0).Peek_Buffer();
|
||||
}
|
||||
if (!Definition->Get_Mapper_Args(pass,1).Is_Empty()) {
|
||||
map1_args = Definition->Get_Mapper_Args(pass,1).Peek_Buffer();
|
||||
}
|
||||
vmat->Parse_Mapping_Args(Definition->Get_Material(pass),map0_args,map1_args);
|
||||
vmat->Set_UV_Source(0,Definition->Get_Map_Channel(pass,0));
|
||||
vmat->Set_UV_Source(1,Definition->Get_Map_Channel(pass,1));
|
||||
vmat->Set_Lighting(true);
|
||||
REF_PTR_SET(Materials[pass],vmat);
|
||||
REF_PTR_RELEASE(vmat);
|
||||
|
||||
// Set up the textures
|
||||
for (stage=0;stage<MeshMatDescClass::MAX_TEX_STAGES;++stage) {
|
||||
StringClass tex_name=Definition->Get_Texture_Name(pass,stage);
|
||||
if (tex_name!="") {
|
||||
Textures[pass][stage]=WW3DAssetManager::Get_Instance()->Get_Texture(tex_name);
|
||||
}
|
||||
else {
|
||||
Textures[pass][stage]=NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Shd6LegacyW3DClass::~Shd6LegacyW3DClass()
|
||||
{
|
||||
for (int pass=0;pass<PassCount;++pass) {
|
||||
for (int stage=0;stage<MeshMatDescClass::MAX_TEX_STAGES;++stage) {
|
||||
REF_PTR_RELEASE(Textures[pass][stage]);
|
||||
}
|
||||
REF_PTR_RELEASE(Materials[pass]);
|
||||
}
|
||||
}
|
||||
|
||||
void Shd6LegacyW3DClass::Init()
|
||||
{
|
||||
}
|
||||
|
||||
void Shd6LegacyW3DClass::Shutdown()
|
||||
{
|
||||
}
|
||||
|
||||
bool Shd6LegacyW3DClass::Greater_Than(const ShdInterfaceClass& s,int pass) const
|
||||
{
|
||||
// By class
|
||||
if (s.Get_Class_ID()!=Get_Class_ID()) {
|
||||
return s.Get_Class_ID()>Get_Class_ID();
|
||||
}
|
||||
|
||||
const Shd6LegacyW3DClass* src=static_cast<const Shd6LegacyW3DClass*>(&s);
|
||||
|
||||
// If same class, sort by textures
|
||||
if (src->Textures[pass][0]!=Textures[pass][0]) {
|
||||
return src->Textures[pass][0]>Textures[pass][0];
|
||||
}
|
||||
|
||||
// If same texture, sort by materials
|
||||
if (src->Materials[pass]!=Materials[pass]) {
|
||||
return src->Materials[pass]>Materials[pass];
|
||||
}
|
||||
|
||||
// If same material, sort by shaders
|
||||
if (src->Shaders[pass].Get_Bits()!=(unsigned)Shaders[pass].Get_Bits()) {
|
||||
return src->Shaders[pass].Get_Bits()>Shaders[pass].Get_Bits();
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/**********************************************************************************************
|
||||
//! Apply shared states for 1 pass DX6
|
||||
/*! 7/12/02 3:39p KJM Created
|
||||
*/
|
||||
void Shd6LegacyW3DClass::Apply_Shared(int pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
SNAPSHOT_SAY(("Shd6LegacyW3DClass::Apply_Shared(pass: %d)\n",pass));
|
||||
// fixed function uses pass through by default
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_PASSTHRU);
|
||||
}
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Apply per instance states for 1 pass DX6
|
||||
/*! 7/10/02 5:39p KJM Created
|
||||
*/
|
||||
void Shd6LegacyW3DClass::Apply_Instance(int cur_pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
SNAPSHOT_SAY(("Shd6LegacyW3DClass::Apply_Instance(pass: %d)\n",cur_pass));
|
||||
|
||||
// set vertex shader
|
||||
StringClass str;
|
||||
SNAPSHOT_SAY(("legacyshader:DX8Wrapper::Set_Shader(%s)\n",Shaders[cur_pass].Get_Description(str)));
|
||||
DX8Wrapper::Set_Shader(Shaders[cur_pass]);
|
||||
|
||||
DX8Wrapper::Set_Vertex_Shader(FVF);
|
||||
|
||||
SNAPSHOT_SAY(("legacyshader:DX8Wrapper::Set_Material(%s)\n",Materials[cur_pass] ? Materials[cur_pass]->Get_Name() : "NULL"));
|
||||
DX8Wrapper::Set_Material(Materials[cur_pass]);
|
||||
|
||||
for (int stage=0;stage<MeshMatDescClass::MAX_TEX_STAGES;++stage) {
|
||||
SNAPSHOT_SAY(("legacyshader:DX8Wrapper::Set_Texture(%d,%s)\n",stage,Textures[cur_pass][stage] ? Textures[cur_pass][stage]->Get_Full_Path() : "NULL"));
|
||||
DX8Wrapper::Set_Texture(stage, Textures[cur_pass][stage]);
|
||||
}
|
||||
}
|
||||
|
||||
unsigned Shd6LegacyW3DClass::Get_Vertex_Stream_Count() const
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
unsigned Shd6LegacyW3DClass::Get_Vertex_Size(unsigned stream) const
|
||||
{
|
||||
FVFInfoClass fvf_info(FVF);
|
||||
return fvf_info.Get_FVF_Size();
|
||||
}
|
||||
|
||||
void Shd6LegacyW3DClass::Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
)
|
||||
{
|
||||
FVFInfoClass fi(FVF);
|
||||
|
||||
/*
|
||||
** Append the UV coordinates to the vertex buffer
|
||||
*/
|
||||
int uvcount = 0;
|
||||
if ((FVF&D3DFVF_TEX1) == D3DFVF_TEX1) {
|
||||
uvcount = 1;
|
||||
}
|
||||
if ((FVF&D3DFVF_TEX2) == D3DFVF_TEX2) {
|
||||
uvcount = 2;
|
||||
}
|
||||
if ((FVF&D3DFVF_TEX3) == D3DFVF_TEX3) {
|
||||
uvcount = 3;
|
||||
}
|
||||
if ((FVF&D3DFVF_TEX4) == D3DFVF_TEX4) {
|
||||
uvcount = 4;
|
||||
}
|
||||
if ((FVF&D3DFVF_TEX5) == D3DFVF_TEX5) {
|
||||
uvcount = 5;
|
||||
}
|
||||
if ((FVF&D3DFVF_TEX6) == D3DFVF_TEX6) {
|
||||
uvcount = 6;
|
||||
}
|
||||
if ((FVF&D3DFVF_TEX7) == D3DFVF_TEX7) {
|
||||
uvcount = 7;
|
||||
}
|
||||
if ((FVF&D3DFVF_TEX8) == D3DFVF_TEX8) {
|
||||
uvcount = 8;
|
||||
}
|
||||
|
||||
unsigned char* vb=(unsigned char*)dest_buffer;
|
||||
|
||||
for (unsigned i=0; i<vertex_count; ++i)
|
||||
{
|
||||
if ((FVF&D3DFVF_XYZ)==D3DFVF_XYZ) {
|
||||
if (vss.Locations)
|
||||
{
|
||||
*(Vector3*)(vb+fi.Get_Location_Offset())=vss.Locations[i];
|
||||
}
|
||||
else
|
||||
{
|
||||
*(Vector3*)(vb+fi.Get_Location_Offset())=Vector3(0.0f,0.0f,0.0f);
|
||||
}
|
||||
}
|
||||
|
||||
if ((FVF&D3DFVF_DIFFUSE)==D3DFVF_DIFFUSE) {
|
||||
if (vss.DiffuseInt)
|
||||
{
|
||||
*(unsigned int*)(vb+fi.Get_Diffuse_Offset())=vss.DiffuseInt[i];
|
||||
}
|
||||
else
|
||||
{
|
||||
*(unsigned int*)(vb+fi.Get_Diffuse_Offset())=0xffffffff;
|
||||
}
|
||||
}
|
||||
|
||||
if ((FVF&D3DFVF_NORMAL)==D3DFVF_NORMAL) {
|
||||
if (vss.Normals)
|
||||
{
|
||||
*(Vector3*)(vb+fi.Get_Normal_Offset())=vss.Normals[i];
|
||||
}
|
||||
else
|
||||
{
|
||||
*(Vector3*)(vb+fi.Get_Normal_Offset())=Vector3(0.0f,0.0f,0.0f);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
for (int j=0; j<uvcount; j++) {
|
||||
const Vector2*uvs=vss.UV[j];
|
||||
if (uvs) {
|
||||
*(Vector2*)(vb+fi.Get_Tex_Offset(j))=uvs[i];
|
||||
}
|
||||
else {
|
||||
*(Vector2*)(vb+fi.Get_Tex_Offset(j))=Vector2(0.0f,0.0f);
|
||||
}
|
||||
}
|
||||
|
||||
vb+=fi.Get_FVF_Size();
|
||||
}
|
||||
}
|
||||
|
||||
160
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdlegacyw3d.h
Normal file
160
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdlegacyw3d.h
Normal file
@@ -0,0 +1,160 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
|
||||
|
||||
#ifndef SHDLEGACYW3D_H
|
||||
#define SHDLEGACYW3D_H
|
||||
|
||||
#include "shdinterface.h"
|
||||
#include "shddef.h"
|
||||
#include "meshmatdesc.h"
|
||||
|
||||
/**
|
||||
** ShdLegacyW3DDefClass - This ShaderDef's sole purpose for existance is to let us make the
|
||||
** transition to using shaders for all of our materials. This shader will wrap the old
|
||||
** material system completely. The plan is to eventually have a full set of "real" shaders and
|
||||
** not need to use this at all.
|
||||
*/
|
||||
class ShdLegacyW3DDefClass : public ShdDefClass
|
||||
{
|
||||
public:
|
||||
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
// Editable interface requirements
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
DECLARE_EDITABLE(ShdLegacyW3DDefClass, ShdDefClass);
|
||||
|
||||
ShdLegacyW3DDefClass();
|
||||
ShdLegacyW3DDefClass(const ShdLegacyW3DDefClass& that);
|
||||
virtual ~ShdLegacyW3DDefClass();
|
||||
|
||||
virtual ShdDefClass* Clone() const { return new ShdLegacyW3DDefClass(*this); }
|
||||
|
||||
// Shader Creation (should create a shader compatible with the current hardware/API)
|
||||
virtual void Init();
|
||||
virtual void Shutdown();
|
||||
virtual ShdInterfaceClass* Create() const;
|
||||
|
||||
// Validation methods
|
||||
virtual bool Is_Valid_Config(StringClass &message);
|
||||
|
||||
// Requirements
|
||||
virtual bool Requires_Normals() const { return true; }
|
||||
virtual bool Requires_Tangent_Space_Vectors() const { return false; }
|
||||
virtual bool Requires_Sorting() const { return false; }
|
||||
virtual int Static_Sort_Index() const { return 0; }
|
||||
virtual bool Uses_UV_Channel(int i) const;
|
||||
|
||||
// From PersistClass
|
||||
virtual bool Save(ChunkSaveClass &csave);
|
||||
virtual bool Load(ChunkLoadClass &cload);
|
||||
|
||||
// Accessors
|
||||
int Get_Pass_Count() { return PassCount; }
|
||||
const StringClass& Get_Texture_Name(int pass, int stage) { return TextureNames[pass][stage]; }
|
||||
int Get_Texture_Attributes(int pass,int stage) { return TextureAttributes[pass][stage]; }
|
||||
const W3dShaderStruct& Get_Shader(int pass) { return Shaders[pass]; }
|
||||
const W3dVertexMaterialStruct & Get_Material(int pass) { return Materials[pass]; }
|
||||
StringClass & Get_Mapper_Args(int pass,int stage) { return MapperArgs[pass][stage]; }
|
||||
int Get_Map_Channel(int pass,int stage) { return MapChannel[pass][stage]; }
|
||||
|
||||
void Set_Pass_Count(int passes) { PassCount=passes; }
|
||||
void Set_Texture_Name(int pass, int stage, const StringClass& name) { TextureNames[pass][stage]=name; }
|
||||
void Set_Texture_Attributes(int pass, int stage, unsigned int attributes) { TextureAttributes[pass][stage] = attributes; }
|
||||
void Set_Shader(int pass, const W3dShaderStruct& shader) { Shaders[pass] = shader; }
|
||||
void Set_Material(int pass, const W3dVertexMaterialStruct& mat) { Materials[pass] = mat; }
|
||||
void Set_Mapper_Args(int pass, int stage,const char * args) { MapperArgs[pass][stage] = args; }
|
||||
void Set_Map_Channel(int pass, int stage, int channel) { MapChannel[pass][stage] = channel; }
|
||||
|
||||
private:
|
||||
|
||||
bool Save_Variables(ChunkSaveClass &csave);
|
||||
bool Load_Variables(ChunkLoadClass &cload);
|
||||
|
||||
int PassCount;
|
||||
|
||||
// Textures
|
||||
StringClass TextureNames[MeshMatDescClass::MAX_PASSES][MeshMatDescClass::MAX_TEX_STAGES];
|
||||
unsigned int TextureAttributes[MeshMatDescClass::MAX_PASSES][MeshMatDescClass::MAX_TEX_STAGES];
|
||||
|
||||
// Shaders
|
||||
W3dShaderStruct Shaders[MeshMatDescClass::MAX_PASSES];
|
||||
|
||||
// Materials
|
||||
W3dVertexMaterialStruct Materials[MeshMatDescClass::MAX_PASSES];
|
||||
StringClass MapperArgs[MeshMatDescClass::MAX_PASSES][MeshMatDescClass::MAX_TEX_STAGES];
|
||||
int MapChannel[MeshMatDescClass::MAX_PASSES][MeshMatDescClass::MAX_TEX_STAGES];
|
||||
|
||||
};
|
||||
|
||||
|
||||
|
||||
class Shd6LegacyW3DClass : public ShdInterfaceClass
|
||||
{
|
||||
public:
|
||||
Shd6LegacyW3DClass(const ShdDefClass* def);
|
||||
virtual ~Shd6LegacyW3DClass();
|
||||
|
||||
static void Init();
|
||||
static void Shutdown();
|
||||
|
||||
virtual bool Greater_Than(const ShdInterfaceClass& s,int pass) const;
|
||||
|
||||
virtual int Get_Pass_Count() { return PassCount; }
|
||||
void Set_Pass_Count(int pass_count) { PassCount=pass_count; }
|
||||
|
||||
virtual int Get_Texture_Count() const { return 0; }
|
||||
virtual TextureClass* Peek_Texture(int idx) const { return NULL; }
|
||||
|
||||
virtual void Apply_Shared(int cur_pass, RenderInfoClass& rinfo);
|
||||
virtual void Apply_Instance(int cur_pass, RenderInfoClass& rinfo);
|
||||
|
||||
virtual unsigned Get_Vertex_Stream_Count() const;
|
||||
virtual unsigned Get_Vertex_Size(unsigned stream) const;
|
||||
virtual bool Use_HW_Vertex_Processing() const { return true; }
|
||||
|
||||
virtual void Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
);
|
||||
|
||||
virtual bool Is_Opaque(void) const { return (Shaders[0].Get_Dst_Blend_Func() == ShaderClass::DSTBLEND_ZERO); }
|
||||
|
||||
// Shd6LegacyW3DClass Accessors
|
||||
VertexMaterialClass* Get_Material(int pass) { if (Materials[pass]) Materials[pass]->Add_Ref(); return Materials[pass]; }
|
||||
void Set_Material(int pass,VertexMaterialClass* mat) { REF_PTR_SET(Materials[pass],mat); }
|
||||
const ShaderClass& Get_Shader(int pass) { return Shaders[pass]; }
|
||||
void Set_Shader(int pass,const ShaderClass& shader) { Shaders[pass]=shader; }
|
||||
void Set_Texture(int pass,int stage,TextureClass* texture) { REF_PTR_SET(Textures[pass][stage],texture); }
|
||||
void Set_FVF(unsigned fvf) { FVF=fvf; }
|
||||
|
||||
protected:
|
||||
|
||||
unsigned FVF;
|
||||
int PassCount;
|
||||
TextureClass* Textures[MeshMatDescClass::MAX_PASSES][MeshMatDescClass::MAX_TEX_STAGES];
|
||||
ShaderClass Shaders[MeshMatDescClass::MAX_PASSES];
|
||||
VertexMaterialClass* Materials[MeshMatDescClass::MAX_PASSES];
|
||||
|
||||
};
|
||||
|
||||
#endif //SHDLEGACYW3D_H
|
||||
75
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdlib.cpp
Normal file
75
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdlib.cpp
Normal file
@@ -0,0 +1,75 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWShade *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/wwshade/shdlib.cpp $*
|
||||
* *
|
||||
* Org Author:: Kenny Mitchell *
|
||||
* *
|
||||
* Author : Kenny Mitchell *
|
||||
* *
|
||||
* $Modtime:: 07/01/02 10:31a $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* WWShade.lib library interface *
|
||||
*---------------------------------------------------------------------------------------------*/
|
||||
|
||||
|
||||
#include "shdlib.h"
|
||||
#include "assetmgr.h"
|
||||
#include "shdloader.h"
|
||||
#include "shdrenderer.h"
|
||||
|
||||
void SHD_Init()
|
||||
{
|
||||
ShdRendererClass::Peek_Instance()->Init();
|
||||
}
|
||||
|
||||
void SHD_Shutdown()
|
||||
{
|
||||
ShdRendererClass::Peek_Instance()->Shutdown();
|
||||
}
|
||||
|
||||
void SHD_Init_Shaders()
|
||||
{
|
||||
ShdRendererClass::Init_Shaders();
|
||||
}
|
||||
|
||||
void SHD_Shutdown_Shaders()
|
||||
{
|
||||
ShdRendererClass::Shutdown_Shaders();
|
||||
}
|
||||
|
||||
void SHD_Flush()
|
||||
{
|
||||
ShdRendererClass::Peek_Instance()->Flush();
|
||||
}
|
||||
|
||||
void SHD_Register_Loader()
|
||||
{
|
||||
WW3DAssetManager::Get_Instance()->Register_Prototype_Loader(&_ShdMeshLoader);
|
||||
// WW3DAssetManager::Get_Instance()->Register_Prototype_Loader(&_ShdMeshLegacyLoader);
|
||||
WW3DAssetManager::Get_Instance()->Register_Prototype_Loader(&_MeshLoader);
|
||||
}
|
||||
108
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdloader.cpp
Normal file
108
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdloader.cpp
Normal file
@@ -0,0 +1,108 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWShade *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/wwshade/shdloader.cpp $*
|
||||
* *
|
||||
* Org Author:: Kenny Mitchell *
|
||||
* *
|
||||
* Author : Kenny Mitchell *
|
||||
* *
|
||||
* $Modtime:: 06/27/02 3:51p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
* 06/26/02 KM Abstracting shader system
|
||||
*---------------------------------------------------------------------------------------------*/
|
||||
|
||||
#include "shdloader.h"
|
||||
#include "shdmesh.h"
|
||||
#include "mesh.h"
|
||||
|
||||
ShdMeshLoaderClass _ShdMeshLoader;
|
||||
ShdMeshLegacyLoaderClass _ShdMeshLegacyLoader;
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdMeshLoaderClass::Load -- reads in a shader mesh and creates a prototype for it *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 5/21/02 KJM : Created. *
|
||||
*=============================================================================================*/
|
||||
PrototypeClass* ShdMeshLoaderClass::Load_W3D(ChunkLoadClass& cload)
|
||||
{
|
||||
ShdMeshClass* mesh=NEW_REF(ShdMeshClass, ());
|
||||
|
||||
if (mesh==NULL)
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (mesh->Load_W3D(cload)!=WW3D_ERROR_OK)
|
||||
{
|
||||
// if the load failed, delete the mesh
|
||||
assert(mesh->Num_Refs() == 1);
|
||||
mesh->Release_Ref();
|
||||
return NULL;
|
||||
|
||||
}
|
||||
|
||||
// create the prototype and add it to the lists
|
||||
PrimitivePrototypeClass * newproto = new PrimitivePrototypeClass(mesh);
|
||||
mesh->Release_Ref();
|
||||
return newproto;
|
||||
}
|
||||
|
||||
|
||||
PrototypeClass * ShdMeshLegacyLoaderClass::Load_W3D(ChunkLoadClass & cload)
|
||||
{
|
||||
MeshClass * mesh = NEW_REF( MeshClass, () );
|
||||
|
||||
if (mesh == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (mesh->Load_W3D(cload) != WW3D_ERROR_OK) {
|
||||
|
||||
// if the load failed, delete the mesh
|
||||
assert(mesh->Num_Refs() == 1);
|
||||
mesh->Release_Ref();
|
||||
return NULL;
|
||||
|
||||
} else {
|
||||
ShdMeshClass* shdmesh=NEW_REF( ShdMeshClass, () );
|
||||
shdmesh->Init_From_Legacy_Mesh(mesh);
|
||||
mesh->Release_Ref();
|
||||
|
||||
// create the prototype and add it to the lists
|
||||
PrimitivePrototypeClass * newproto = W3DNEW PrimitivePrototypeClass(shdmesh);
|
||||
shdmesh->Release_Ref();
|
||||
return newproto;
|
||||
|
||||
}
|
||||
}
|
||||
68
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdloader.h
Normal file
68
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdloader.h
Normal file
@@ -0,0 +1,68 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWShade *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/wwshade/shdloader.h $*
|
||||
* *
|
||||
* Org Author:: Kenny Mitchell *
|
||||
* *
|
||||
* Author : Kenny Mitchell *
|
||||
* *
|
||||
* $Modtime:: 06/27/02 3:51p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
* 06/26/02 KM Integrating shader system
|
||||
*---------------------------------------------------------------------------------------------*/
|
||||
|
||||
#ifndef SHDLOADER_H
|
||||
#define SHDLOADER_H
|
||||
|
||||
#ifndef PROTO_H
|
||||
#include "proto.h"
|
||||
#endif
|
||||
|
||||
class ShdMeshLoaderClass : public PrototypeLoaderClass
|
||||
{
|
||||
public:
|
||||
|
||||
virtual int Chunk_Type(void) { return W3D_CHUNK_SHDMESH; }
|
||||
virtual PrototypeClass* Load_W3D(ChunkLoadClass& cload);
|
||||
};
|
||||
|
||||
/*
|
||||
** Prototype loader that converts legacy meshes into Shader meshes
|
||||
*/
|
||||
class ShdMeshLegacyLoaderClass : public PrototypeLoaderClass
|
||||
{
|
||||
public:
|
||||
|
||||
virtual int Chunk_Type(void) { return W3D_CHUNK_MESH; }
|
||||
virtual PrototypeClass * Load_W3D(ChunkLoadClass & cload);
|
||||
};
|
||||
|
||||
|
||||
extern ShdMeshLoaderClass _ShdMeshLoader;
|
||||
extern ShdMeshLegacyLoaderClass _ShdMeshLegacyLoader;
|
||||
|
||||
#endif
|
||||
681
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdmesh.cpp
Normal file
681
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdmesh.cpp
Normal file
@@ -0,0 +1,681 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWShade *
|
||||
* *
|
||||
* $Archive:: wwshade/shdmesh.cpp $*
|
||||
* *
|
||||
* Org Author:: Jani P *
|
||||
* *
|
||||
* Author : Kenny Mitchell *
|
||||
* *
|
||||
* $Modtime:: 07/12/02 10:31a $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
*---------------------------------------------------------------------------------------------*/
|
||||
|
||||
#include "shdmesh.h"
|
||||
#include "shdsubmesh.h"
|
||||
#include "shdrenderer.h"
|
||||
#include "rinfo.h"
|
||||
#include "camera.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "wwdebug.h"
|
||||
#include "wwprofile.h"
|
||||
#include "mesh.h"
|
||||
#include "meshmdl.h"
|
||||
|
||||
ShdMeshClass::ShdMeshClass()
|
||||
: Name("UnNamed"),
|
||||
LightEnvironment(NULL),
|
||||
Applying_Shadow_Map(false)
|
||||
{
|
||||
}
|
||||
|
||||
ShdMeshClass::ShdMeshClass(const ShdMeshClass & src)
|
||||
: RenderObjClass(src),
|
||||
Name(src.Name),
|
||||
LightEnvironment(NULL),
|
||||
Applying_Shadow_Map(false)
|
||||
{
|
||||
Free();
|
||||
SubMeshes.Resize(src.SubMeshes.Length());
|
||||
for (int i=0;i<SubMeshes.Length();++i)
|
||||
{
|
||||
SubMeshes[i].Mesh=NULL;
|
||||
SubMeshes[i].Renderer=NULL;
|
||||
REF_PTR_SET(SubMeshes[i].Mesh,src.SubMeshes[i].Mesh);
|
||||
}
|
||||
}
|
||||
|
||||
ShdMeshClass::~ShdMeshClass()
|
||||
{
|
||||
Free();
|
||||
// TODO TODO TODO!!!!!
|
||||
}
|
||||
|
||||
RenderObjClass * ShdMeshClass::Clone() const
|
||||
{
|
||||
return new ShdMeshClass(*this);
|
||||
}
|
||||
|
||||
const char * ShdMeshClass::Get_Name() const
|
||||
{
|
||||
return Name;
|
||||
}
|
||||
|
||||
void ShdMeshClass::Set_Name(const char * name)
|
||||
{
|
||||
Name = name;
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdMeshClass::Free -- Releases all memory/assets in use by this mesh *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 1/6/98 GTH : Created. *
|
||||
*=============================================================================================*/
|
||||
void ShdMeshClass::Free()
|
||||
{
|
||||
for (int i=0;i<SubMeshes.Length();++i)
|
||||
{
|
||||
REF_PTR_RELEASE(SubMeshes[i].Mesh);
|
||||
if (SubMeshes[i].Renderer)
|
||||
{
|
||||
delete SubMeshes[i].Renderer;
|
||||
SubMeshes[i].Renderer=NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int ShdMeshClass::Get_Num_Polys() const
|
||||
{
|
||||
int count = 0;
|
||||
for (int i=0; i<SubMeshes.Length(); i++)
|
||||
{
|
||||
count+= SubMeshes[i].Mesh->Get_Polygon_Count();
|
||||
}
|
||||
return count;
|
||||
}
|
||||
|
||||
int ShdMeshClass::Get_Num_Vertices(void) const
|
||||
{
|
||||
int count = 0;
|
||||
for (int i=0; i<SubMeshes.Length(); i++)
|
||||
{
|
||||
count+= SubMeshes[i].Mesh->Get_Vertex_Count();
|
||||
}
|
||||
return count;
|
||||
}
|
||||
|
||||
|
||||
void ShdMeshClass::Render(RenderInfoClass& rinfo)
|
||||
{
|
||||
WWPROFILE("ShdMeshClass::Render");
|
||||
if (Is_Not_Hidden_At_All() == false)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
// DX8_RECORD_MESH_RENDER();
|
||||
|
||||
// TODO: Static sort lists
|
||||
Set_Lighting_Environment(rinfo.light_environment);
|
||||
const FrustumClass & frustum=rinfo.Camera.Get_Frustum();
|
||||
|
||||
// if rendering shadow remember camera info
|
||||
if ((rinfo.Current_Override_Flags()&RenderInfoClass::RINFO_OVERRIDE_SHADOW_RENDERING))
|
||||
{
|
||||
// is generating shadow map
|
||||
Set_Is_Self_Shadowed();
|
||||
|
||||
// set texture projector
|
||||
Texture_Projector=rinfo.Texture_Projector;
|
||||
|
||||
Unset_Is_Applying_Shadow_Map();
|
||||
}
|
||||
else if (Is_Self_Shadowed())
|
||||
{
|
||||
// is applying shadow map
|
||||
Set_Is_Applying_Shadow_Map();
|
||||
Unset_Is_Self_Shadowed();
|
||||
}
|
||||
else
|
||||
{
|
||||
Unset_Is_Applying_Shadow_Map();
|
||||
}
|
||||
|
||||
|
||||
// TODO: What to do with SKINS?
|
||||
if (1)//CollisionMath::Overlap_Test(frustum,Get_Bounding_Box())!=CollisionMath::OUTSIDE )
|
||||
{
|
||||
// bool rendered_something = false;
|
||||
|
||||
// TODO: Override flags, decals and material passes (probably in the submesh rendering)
|
||||
for (int i=0;i<SubMeshes.Length();++i)
|
||||
{
|
||||
if (!SubMeshes[i].Renderer)
|
||||
{
|
||||
SubMeshes[i].Renderer=ShdRendererClass::Peek_Instance()->Register_Mesh(this,SubMeshes[i].Mesh);
|
||||
}
|
||||
|
||||
SubMeshes[i].Renderer->Render(rinfo);
|
||||
}
|
||||
|
||||
// TODO: RendererDebugger
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
//void ShdMeshClass::Render_Material_Pass(MaterialPassClass * pass,IndexBufferClass * ib)
|
||||
//{
|
||||
//
|
||||
//}
|
||||
|
||||
void ShdMeshClass::Special_Render(SpecialRenderInfoClass & rinfo)
|
||||
{
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdMeshClass::Cast_Ray -- compute a ray intersection with this mesh *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 6/17/98 GTH : Created. *
|
||||
*=============================================================================================*/
|
||||
bool ShdMeshClass::Cast_Ray(RayCollisionTestClass & raytest)
|
||||
{
|
||||
if ((Get_Collision_Type() & raytest.CollisionType) == 0) return false;
|
||||
if ((Is_Translucent()!=0) && (!raytest.CheckTranslucent)) return false;
|
||||
if (Is_Animation_Hidden()) return false;
|
||||
if (raytest.Result->StartBad) return false;
|
||||
|
||||
Matrix3D world_to_obj;
|
||||
Matrix3D world=Get_Transform();
|
||||
|
||||
// if aligned or oriented rotate the mesh so that it's aligned to the ray
|
||||
/* if (Model->Get_Flag(MeshModelClass::ALIGNED)) {
|
||||
Vector3 mesh_position;
|
||||
world.Get_Translation(&mesh_position);
|
||||
world.Obj_Look_At(mesh_position,mesh_position - raytest.Ray.Get_Dir(),0.0f);
|
||||
} else if (Model->Get_Flag(MeshModelClass::ORIENTED)) {
|
||||
Vector3 mesh_position;
|
||||
world.Get_Translation(&mesh_position);
|
||||
world.Obj_Look_At(mesh_position,raytest.Ray.Get_P0(),0.0f);
|
||||
}
|
||||
*/
|
||||
world.Get_Orthogonal_Inverse(world_to_obj);
|
||||
RayCollisionTestClass objray(raytest,world_to_obj);
|
||||
|
||||
for (int i=0;i<SubMeshes.Length();++i) {
|
||||
if (SubMeshes[i].Mesh->Cast_Ray(objray)) {
|
||||
// transform result back into original coordinate system
|
||||
raytest.CollidedRenderObj = this;
|
||||
Matrix3D::Rotate_Vector(world,raytest.Result->Normal, &(raytest.Result->Normal));
|
||||
if (raytest.Result->ComputeContactPoint) {
|
||||
Matrix3D::Transform_Vector(world,raytest.Result->ContactPoint, &(raytest.Result->ContactPoint));
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdMeshClass::Cast_AABox -- cast an AABox against this mesh *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 6/17/98 GTH : Created. *
|
||||
*=============================================================================================*/
|
||||
bool ShdMeshClass::Cast_AABox(AABoxCollisionTestClass & boxtest)
|
||||
{
|
||||
if ((Get_Collision_Type() & boxtest.CollisionType) == 0) return false;
|
||||
if (boxtest.Result->StartBad) return false;
|
||||
|
||||
for (int i=0;i<SubMeshes.Length();++i) {
|
||||
// This function analyses the tranform to call optimized functions in certain cases
|
||||
if (SubMeshes[i].Mesh->Cast_World_Space_AABox(boxtest, Get_Transform())) {
|
||||
boxtest.CollidedRenderObj = this;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* Cast_OBBox -- Cast an obbox against this mesh *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 6/17/98 GTH : Created. *
|
||||
*=============================================================================================*/
|
||||
bool ShdMeshClass::Cast_OBBox(OBBoxCollisionTestClass & boxtest)
|
||||
{
|
||||
if ((Get_Collision_Type() & boxtest.CollisionType) == 0) return false;
|
||||
if (boxtest.Result->StartBad) return false;
|
||||
|
||||
/*
|
||||
** transform into the local coordinate system of the mesh.
|
||||
*/
|
||||
const Matrix3D & tm = Get_Transform();
|
||||
Matrix3D world_to_obj;
|
||||
tm.Get_Orthogonal_Inverse(world_to_obj);
|
||||
OBBoxCollisionTestClass localtest(boxtest,world_to_obj);
|
||||
|
||||
for (int i=0;i<SubMeshes.Length();++i) {
|
||||
if (SubMeshes[i].Mesh->Cast_OBBox(localtest)) {
|
||||
|
||||
/*
|
||||
** If we hit, transform the result of the test back to the original coordinate system.
|
||||
*/
|
||||
boxtest.CollidedRenderObj = this;
|
||||
Matrix3D::Rotate_Vector(tm,boxtest.Result->Normal, &(boxtest.Result->Normal));
|
||||
if (boxtest.Result->ComputeContactPoint) {
|
||||
Matrix3D::Transform_Vector(tm,boxtest.Result->ContactPoint, &(boxtest.Result->ContactPoint));
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdMeshClass::Intersect_AABox -- test for intersection with given AABox *
|
||||
* *
|
||||
* The AAbox given is assumed to be in world space. Since meshes aren't generally in world *
|
||||
* space, the test must be transformed into our local coordinate system (which turns it into *
|
||||
* an OBBox...) *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 1/19/00 gth : Created. *
|
||||
*=============================================================================================*/
|
||||
bool ShdMeshClass::Intersect_AABox(AABoxIntersectionTestClass & boxtest)
|
||||
{
|
||||
if ((Get_Collision_Type() & boxtest.CollisionType) == 0) return false;
|
||||
|
||||
Matrix3D inv_tm;
|
||||
Get_Transform().Get_Orthogonal_Inverse(inv_tm);
|
||||
OBBoxIntersectionTestClass local_test(boxtest,inv_tm);
|
||||
|
||||
for (int i=0;i<SubMeshes.Length();++i) {
|
||||
if (SubMeshes[i].Mesh->Intersect_OBBox(local_test)) return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdMeshClass::Intersect_OBBox -- test for intersection with the given OBBox *
|
||||
* *
|
||||
* The given OBBox is assumed to be in world space so we need to transform it into the mesh's *
|
||||
* local coordinate system. *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 1/19/00 gth : Created. *
|
||||
*=============================================================================================*/
|
||||
bool ShdMeshClass::Intersect_OBBox(OBBoxIntersectionTestClass & boxtest)
|
||||
{
|
||||
if ((Get_Collision_Type() & boxtest.CollisionType) == 0) return false;
|
||||
|
||||
Matrix3D inv_tm;
|
||||
Get_Transform().Get_Orthogonal_Inverse(inv_tm);
|
||||
OBBoxIntersectionTestClass local_test(boxtest,inv_tm);
|
||||
|
||||
for (int i=0;i<SubMeshes.Length();++i) {
|
||||
if (SubMeshes[i].Mesh->Intersect_OBBox(local_test)) return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdMeshClass::Add_Dependencies_To_List -- Add dependent files to the list. *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 3/18/99 PDS : Created. *
|
||||
* 6/05/02 KJM : Added dependency calculation for shader system
|
||||
*=============================================================================================*/
|
||||
void ShdMeshClass::Add_Dependencies_To_List
|
||||
(
|
||||
DynamicVectorClass<StringClass> &file_list,
|
||||
bool textures_only
|
||||
)
|
||||
{
|
||||
// loop through sub meshes
|
||||
for (int i=0;i<SubMeshes.Length();i++)
|
||||
{
|
||||
ShdInterfaceClass* shd=SubMeshes[i].Mesh->Peek_Shader();
|
||||
|
||||
for (int tidx=0;tidx<shd->Get_Texture_Count();tidx++)
|
||||
{
|
||||
TextureClass* texture=shd->Peek_Texture(tidx);
|
||||
if (texture)
|
||||
{
|
||||
file_list.Add(texture->Get_Full_Path());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
RenderObjClass::Add_Dependencies_To_List (file_list, textures_only);
|
||||
return ;
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdMeshClass::Update_Cached_Bounding_Volumes -- default collision sphere. *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 5/14/2001 NH : Created. *
|
||||
*=============================================================================================*/
|
||||
void ShdMeshClass::Update_Cached_Bounding_Volumes(void) const
|
||||
{
|
||||
Get_Obj_Space_Bounding_Sphere(CachedBoundingSphere);
|
||||
|
||||
Matrix3D::Transform_Vector(Get_Transform(),CachedBoundingSphere.Center,&CachedBoundingSphere.Center);
|
||||
|
||||
// If we are camera-aligned or -oriented, we don't know which way we are facing at this point,
|
||||
// so the box we return needs to contain the sphere. Otherewise do the normal computation.
|
||||
/* if (Model->Get_Flag(MeshModelClass::ALIGNED) || Model->Get_Flag(MeshModelClass::ORIENTED)) {
|
||||
CachedBoundingBox.Center = CachedBoundingSphere.Center;
|
||||
CachedBoundingBox.Extent.Set(CachedBoundingSphere.Radius, CachedBoundingSphere.Radius, CachedBoundingSphere.Radius);
|
||||
} else {
|
||||
*/ Get_Obj_Space_Bounding_Box(CachedBoundingBox);
|
||||
CachedBoundingBox.Transform(Get_Transform());
|
||||
// }
|
||||
|
||||
Validate_Cached_Bounding_Volumes();
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdMeshClass::Get_Obj_Space_Bounding_Sphere -- returns obj-space bounding sphere *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 1/19/00 gth : Created. *
|
||||
*=============================================================================================*/
|
||||
void ShdMeshClass::Get_Obj_Space_Bounding_Sphere(SphereClass & sphere) const
|
||||
{
|
||||
if (SubMeshes.Length()) {
|
||||
SubMeshes[0].Mesh->Get_Bounding_Sphere(&sphere);
|
||||
// If there are more than one submesh, merge all bounding spheres
|
||||
for (int i=1;i<SubMeshes.Length();++i) {
|
||||
SphereClass tmp_s;
|
||||
SubMeshes[i].Mesh->Get_Bounding_Sphere(&tmp_s);
|
||||
sphere+=tmp_s;
|
||||
}
|
||||
}
|
||||
else {
|
||||
sphere.Center.Set(0,0,0);
|
||||
sphere.Radius = 1.0f;
|
||||
}
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdMeshClass::Get_Obj_Space_Bounding_Box -- returns the obj-space bounding box *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 1/19/00 gth : Created. *
|
||||
*=============================================================================================*/
|
||||
void ShdMeshClass::Get_Obj_Space_Bounding_Box(AABoxClass & box) const
|
||||
{
|
||||
if (SubMeshes.Length()) {
|
||||
SubMeshes[0].Mesh->Get_Bounding_Box(&box);
|
||||
// If there are more than one submesh, merge all bounding boxes
|
||||
for (int i=1;i<SubMeshes.Length();++i) {
|
||||
AABoxClass tmp_b;
|
||||
SubMeshes[i].Mesh->Get_Bounding_Box(&tmp_b);
|
||||
|
||||
box.Add_Box(tmp_b);
|
||||
}
|
||||
}
|
||||
else {
|
||||
box.Init(Vector3(0,0,0),Vector3(1,1,1));
|
||||
}
|
||||
}
|
||||
|
||||
void ShdMeshClass::Init_From_Legacy_Mesh(MeshClass* mesh)
|
||||
{
|
||||
Set_Name(mesh->Get_Name());
|
||||
MeshModelClass* model=mesh->Peek_Model();
|
||||
if (model)
|
||||
{
|
||||
int first_poly=0;
|
||||
int sub_mesh_count=0;
|
||||
while (first_poly<model->Get_Polygon_Count()) {
|
||||
sub_mesh_count++;
|
||||
ShdSubMeshClass * sub_mesh = NEW_REF( ShdSubMeshClass, () );
|
||||
sub_mesh->Init_From_Legacy_Mesh_Model(model,first_poly);
|
||||
SubMeshes.Resize(sub_mesh_count);
|
||||
SubMeshes[sub_mesh_count-1].Mesh=sub_mesh;
|
||||
SubMeshes[sub_mesh_count-1].Renderer=NULL;
|
||||
if (sub_mesh->Get_Visible_Polygon_Count()==0) break;
|
||||
first_poly+=sub_mesh->Get_Visible_Polygon_Count();
|
||||
}
|
||||
}
|
||||
|
||||
// Pull interesting stuff out of the w3d attributes bits
|
||||
Set_Collision_Type(mesh->Get_Collision_Type());
|
||||
Set_Hidden(mesh->Is_Hidden());
|
||||
Set_Translucent(mesh->Is_Translucent());
|
||||
}
|
||||
|
||||
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdMeshClass::Load -- creates a shader mesh out of a shader mesh chunk in a .w3d file *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 05/21/2002 KM : Created. *
|
||||
*=============================================================================================*/
|
||||
WW3DErrorType ShdMeshClass::Load_W3D(ChunkLoadClass& cload)
|
||||
{
|
||||
// Open the first chunk, it should be the shader mesh name
|
||||
cload.Open_Chunk();
|
||||
|
||||
if (cload.Cur_Chunk_ID()!=W3D_CHUNK_SHDMESH_NAME)
|
||||
{
|
||||
WWDEBUG_SAY(("Invalid format shader mesh.\n"));
|
||||
return WW3D_ERROR_LOAD_FAILED;
|
||||
}
|
||||
|
||||
// read name
|
||||
char buf[MAX_PATH];
|
||||
cload.Read(buf,cload.Cur_Chunk_Length());
|
||||
cload.Close_Chunk();
|
||||
Set_Name(buf);
|
||||
|
||||
// open header
|
||||
W3dShdMeshHeaderStruct hdr;
|
||||
cload.Open_Chunk();
|
||||
if
|
||||
(
|
||||
cload.Read
|
||||
(
|
||||
&hdr,
|
||||
sizeof(W3dShdMeshHeaderStruct)
|
||||
)!=sizeof(W3dShdMeshHeaderStruct)
|
||||
)
|
||||
{
|
||||
return WW3D_ERROR_LOAD_FAILED;
|
||||
}
|
||||
cload.Close_Chunk();
|
||||
|
||||
// Process the header
|
||||
|
||||
// Set Bounding Info
|
||||
Vector3 min(hdr.BoxMin.X,hdr.BoxMin.Y,hdr.BoxMin.Z);
|
||||
Vector3 max(hdr.BoxMax.X,hdr.BoxMax.Y,hdr.BoxMax.Z);
|
||||
|
||||
CachedBoundingBox.Init_Min_Max(min,max);
|
||||
|
||||
Vector3 cntr(hdr.SphCenter.X,hdr.SphCenter.Y,hdr.SphCenter.Z);
|
||||
CachedBoundingSphere.Init(cntr,hdr.SphRadius);
|
||||
|
||||
// Flags (todo)
|
||||
|
||||
// user text
|
||||
|
||||
|
||||
// next are the sub meshes
|
||||
Free();
|
||||
SubMeshes.Resize(hdr.NumSubMeshes);
|
||||
for (int i=0;i<SubMeshes.Length(); )
|
||||
{
|
||||
cload.Open_Chunk();
|
||||
|
||||
if (cload.Cur_Chunk_ID()==W3D_CHUNK_SHDMESH_USER_TEXT)
|
||||
{
|
||||
// todo
|
||||
cload.Read(buf,cload.Cur_Chunk_Length());
|
||||
}
|
||||
else
|
||||
{
|
||||
ShdSubMeshClass* ssmesh=NEW_REF(ShdSubMeshClass,());
|
||||
if (ssmesh==NULL)
|
||||
{
|
||||
WWDEBUG_SAY(("ShdMeshClass::Load_W3D - Failed to allocate sub mesh\r\n"));
|
||||
return WW3D_ERROR_LOAD_FAILED;
|
||||
}
|
||||
|
||||
SubMeshes[i].Mesh=ssmesh;
|
||||
SubMeshes[i].Renderer=NULL;
|
||||
REF_PTR_SET(SubMeshes[i].Mesh,SubMeshes[i].Mesh);
|
||||
|
||||
ssmesh->Load_W3D(cload);
|
||||
|
||||
// assign each sub-mesh with a name in the format: <parentmesh>.<index>
|
||||
StringClass tmp;
|
||||
tmp.Format("%s.%d",Name,i);
|
||||
ssmesh->Set_Name(tmp);
|
||||
|
||||
i++;
|
||||
}
|
||||
|
||||
cload.Close_Chunk();
|
||||
}
|
||||
|
||||
// Pull interesting stuff out of the w3d attributes bits
|
||||
int col_bits = (hdr.Attributes & W3D_MESH_FLAG_COLLISION_TYPE_MASK) >> W3D_MESH_FLAG_COLLISION_TYPE_SHIFT;
|
||||
Set_Collision_Type( col_bits << 1 );
|
||||
Set_Hidden(hdr.Attributes & W3D_MESH_FLAG_HIDDEN);
|
||||
|
||||
for (i=0;i<SubMeshes.Length(); i++) {
|
||||
bool shadow = (hdr.Attributes & W3D_MESH_FLAG_CAST_SHADOW) == W3D_MESH_FLAG_CAST_SHADOW;
|
||||
SubMeshes[i].Mesh->Set_Flag(MeshGeometryClass::CAST_SHADOW,shadow);
|
||||
}
|
||||
|
||||
// Indicate whether this mesh is translucent. The mesh is considered translucent
|
||||
// if sorting has been enabled (alpha blending on pass 0) or if pass0 contains alpha-test.
|
||||
// This flag is used to determine if the mesh can cast a geometric shadow.
|
||||
bool is_translucent = false;
|
||||
for (i=0;i<SubMeshes.Length(); i++) {
|
||||
if (SubMeshes[i].Mesh) {
|
||||
if (SubMeshes[i].Mesh->Is_Sorting()) {
|
||||
Set_Translucent(true);
|
||||
}
|
||||
ShdInterfaceClass * shader = SubMeshes[i].Mesh->Peek_Shader();
|
||||
if ((shader) && (!shader->Is_Opaque())) {
|
||||
Set_Translucent(true);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return WW3D_ERROR_OK;
|
||||
}
|
||||
|
||||
|
||||
int ShdMeshClass::Get_Sub_Mesh_Count(void) const
|
||||
{
|
||||
return SubMeshes.Length();
|
||||
}
|
||||
|
||||
ShdSubMeshClass * ShdMeshClass::Peek_Sub_Mesh(int i) const
|
||||
{
|
||||
return SubMeshes[i].Mesh;
|
||||
}
|
||||
|
||||
186
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdmesh.h
Normal file
186
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdmesh.h
Normal file
@@ -0,0 +1,186 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWShade *
|
||||
* *
|
||||
* $Archive:: wwshade/shdmesh.h $*
|
||||
* *
|
||||
* Org Author:: Jani P *
|
||||
* *
|
||||
* Author : Kenny Mitchell *
|
||||
* *
|
||||
* $Modtime:: 07/12/02 10:31a $*
|
||||
* *
|
||||
* $Revision:: 2 $*
|
||||
* *
|
||||
* 07/12/02 KM Removed legacy mesh conversion *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
*---------------------------------------------------------------------------------------------*/
|
||||
|
||||
#ifndef SHDMESH_H
|
||||
#define SHDMESH_H
|
||||
|
||||
#include "rendobj.h"
|
||||
#include "wwstring.h"
|
||||
#include "simplevec.h"
|
||||
#include "w3derr.h"
|
||||
#include "matrix4.h"
|
||||
|
||||
class ChunkLoadClass;
|
||||
class LightEnvironmentClass;
|
||||
class MaterialPassClass;
|
||||
class ShdSubMeshClass;
|
||||
class ShdRendererNodeClass;
|
||||
class MeshClass;
|
||||
class TexProjectClass;
|
||||
|
||||
struct ShdSubMeshStruct
|
||||
{
|
||||
ShdSubMeshClass* Mesh;
|
||||
ShdRendererNodeClass* Renderer;
|
||||
};
|
||||
|
||||
/**
|
||||
** ShdMeshClass - Mesh which uses the new shader system. This is a render object which
|
||||
** has the following characteristics:
|
||||
** - It uses the new shader system
|
||||
** - It contains one or more sub-meshes which each use only a single shader (unlike the old mesh system)
|
||||
*/
|
||||
class ShdMeshClass : public RenderObjClass
|
||||
{
|
||||
public:
|
||||
ShdMeshClass(void);
|
||||
ShdMeshClass(const ShdMeshClass & src);
|
||||
virtual ~ShdMeshClass(void);
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// Render Object Interface
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
virtual RenderObjClass * Clone(void) const;
|
||||
virtual int Class_ID(void) const { return CLASSID_SHDMESH; }
|
||||
virtual const char * Get_Name(void) const;
|
||||
virtual void Set_Name(const char * name);
|
||||
virtual int Get_Num_Polys(void) const;
|
||||
int Get_Num_Vertices(void) const;
|
||||
virtual void Render(RenderInfoClass & rinfo);
|
||||
// void Render_Material_Pass(MaterialPassClass * pass,IndexBufferClass * ib);
|
||||
virtual void Special_Render(SpecialRenderInfoClass & rinfo);
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// Render Object Interface - Collision Detection
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
virtual bool Cast_Ray(RayCollisionTestClass & raytest);
|
||||
virtual bool Cast_AABox(AABoxCollisionTestClass & boxtest);
|
||||
virtual bool Cast_OBBox(OBBoxCollisionTestClass & boxtest);
|
||||
virtual bool Intersect_AABox(AABoxIntersectionTestClass & boxtest);
|
||||
virtual bool Intersect_OBBox(OBBoxIntersectionTestClass & boxtest);
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// Render Object Interface - Bounding Volumes
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
virtual void Get_Obj_Space_Bounding_Sphere(SphereClass & sphere) const;
|
||||
virtual void Get_Obj_Space_Bounding_Box(AABoxClass & box) const;
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// Render Object Interface - Attributes, Options, Properties, etc
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// virtual int Get_Sort_Level(void) const;
|
||||
// virtual void Set_Sort_Level(int level);
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// Render Object Interface - Decals
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// virtual void Create_Decal(DecalGeneratorClass * generator);
|
||||
// virtual void Delete_Decal(uint32 decal_id);
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// MeshClass Interface
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
void Init_From_Legacy_Mesh(MeshClass* mesh);
|
||||
// WW3DErrorType Init(const MeshBuilderClass & builder,MaterialInfoClass * matinfo,const char * name,const char * hmodelname);
|
||||
WW3DErrorType Load_W3D(ChunkLoadClass & cload);
|
||||
void Generate_Culling_Tree(void);
|
||||
// MeshModelClass * Get_Model(void);
|
||||
// MeshModelClass * Peek_Model(void);
|
||||
uint32 Get_W3D_Flags(void);
|
||||
const char * Get_User_Text(void) const;
|
||||
|
||||
bool Contains(const Vector3 &point);
|
||||
|
||||
void Get_Deformed_Vertices(Vector3 *dst_vert, Vector3 *dst_norm);
|
||||
void Get_Deformed_Vertices(Vector3 *dst_vert);
|
||||
|
||||
void Set_Lighting_Environment(LightEnvironmentClass * light_env) { LightEnvironment = light_env; }
|
||||
LightEnvironmentClass * Get_Lighting_Environment(void) { return LightEnvironment; }
|
||||
|
||||
// void Set_Next_Visible_Skin(MeshClass * next_visible) { NextVisibleSkin = next_visible; }
|
||||
// MeshClass * Peek_Next_Visible_Skin(void) { return NextVisibleSkin; }
|
||||
//
|
||||
// void Set_Base_Vertex_Offset(int base) { BaseVertexOffset = base; }
|
||||
// int Get_Base_Vertex_Offset(void) { return BaseVertexOffset; }
|
||||
|
||||
// Do old .w3d mesh files get fog turned on or off?
|
||||
static bool Legacy_Meshes_Fogged;
|
||||
|
||||
// void Replace_Texture(TextureClass* texture,TextureClass* new_texture);
|
||||
// void Replace_VertexMaterial(VertexMaterialClass* vmat,VertexMaterialClass* new_vmat);
|
||||
|
||||
void Make_Unique();
|
||||
// unsigned Get_Debug_Id() const { return MeshDebugId; }
|
||||
//
|
||||
// void Set_Debugger_Disable(bool b) { IsDisabledByDebugger=b; }
|
||||
// bool Is_Disabled_By_Debugger() const { return IsDisabledByDebugger; }
|
||||
|
||||
/*
|
||||
** User Lighting feature, meshes can have a user lighting array.
|
||||
*/
|
||||
// void Install_User_Lighting_Array(Vector4 * lighting);
|
||||
// unsigned int * Get_User_Lighting_Array(bool alloc = false);
|
||||
//
|
||||
// virtual void Save_User_Lighting (ChunkSaveClass & csave);
|
||||
// virtual void Load_User_Lighting (ChunkLoadClass & cload);
|
||||
|
||||
void Set_Is_Applying_Shadow_Map() { Applying_Shadow_Map=true; }
|
||||
void Unset_Is_Applying_Shadow_Map() { Applying_Shadow_Map=false; }
|
||||
bool Is_Applying_Shadow_Map() const { return Applying_Shadow_Map; }
|
||||
|
||||
TexProjectClass* Peek_Texture_Projector() const { return Texture_Projector; }
|
||||
|
||||
// ShdMesh Accessors
|
||||
int Get_Sub_Mesh_Count(void) const;
|
||||
ShdSubMeshClass * Peek_Sub_Mesh(int i) const;
|
||||
|
||||
protected:
|
||||
|
||||
void Free(void);
|
||||
|
||||
virtual void Add_Dependencies_To_List (DynamicVectorClass<StringClass> &file_list, bool textures_only = false);
|
||||
virtual void Update_Cached_Bounding_Volumes(void) const;
|
||||
|
||||
StringClass Name;
|
||||
SimpleVecClass<ShdSubMeshStruct> SubMeshes;
|
||||
LightEnvironmentClass * LightEnvironment; // cached pointer to the light environment for this mesh
|
||||
bool Applying_Shadow_Map;
|
||||
TexProjectClass* Texture_Projector;
|
||||
};
|
||||
|
||||
#endif //SHDMESH_H
|
||||
BIN
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdpp.exe
Normal file
BIN
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdpp.exe
Normal file
Binary file not shown.
708
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdrenderer.cpp
Normal file
708
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdrenderer.cpp
Normal file
@@ -0,0 +1,708 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WW3D *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/ww3d2/shdrenderer.cpp $*
|
||||
*
|
||||
* Org Author:: Jani_p
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 7/29/02 1:50p $*
|
||||
* *
|
||||
* $Revision:: 3 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* 6/02/02 5:59p KM Added render info and light environment support $*
|
||||
* 7/29/02 1:50p KM Added VB and IB usage flags for software vertex shaders
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include "shdrenderer.h"
|
||||
#include "shdforcelinks.h"
|
||||
#include "shdmesh.h"
|
||||
#include "shdsubmesh.h"
|
||||
#include "shddef.h"
|
||||
#include "shddefmanager.h"
|
||||
#include "shdclassids.h"
|
||||
#include "wwdebug.h"
|
||||
#include "dx8vertexbuffer.h"
|
||||
#include "dx8indexbuffer.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "rinfo.h"
|
||||
#include "camera.h"
|
||||
#include "texture.h"
|
||||
#include "ww3dformat.h"
|
||||
#include "wwprofile.h"
|
||||
#include "sortingrenderer.h"
|
||||
#include "meshmatdesc.h"
|
||||
|
||||
static DynamicVectorClass<Vector3> _TempVertexBuffer;
|
||||
static DynamicVectorClass<Vector3> _TempNormalBuffer;
|
||||
|
||||
ShdRendererClass* ShdRendererClass::ShdRenderer=NULL;
|
||||
|
||||
ShdRendererClass::ShdRendererClass()
|
||||
{
|
||||
}
|
||||
|
||||
ShdRendererClass::~ShdRendererClass()
|
||||
{
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// Initialize the rendering system. This is the place to create different versions
|
||||
// (such as DX8, DX9, OGL) of the rendering system, if needed.
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
void ShdRendererClass::Init()
|
||||
{
|
||||
SHD_Force_Links();
|
||||
|
||||
WWASSERT(!ShdRenderer);
|
||||
|
||||
ShdRenderer=new ShdDX8RendererClass();
|
||||
|
||||
Init_Shaders();
|
||||
}
|
||||
|
||||
void ShdRendererClass::Init_Shaders()
|
||||
{
|
||||
ShdDefClass* def;
|
||||
for (int i=SHDDEF_CLASSID_DUMMY+1; i<SHDDEF_CLASSID_LAST; i++)
|
||||
{
|
||||
def=ShdDefManagerClass::Create_ShdDefClass_Instance(i);
|
||||
if (def != NULL) {
|
||||
def->Init();
|
||||
REF_PTR_RELEASE(def);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// Release the renderer system. At this point, all the meshes must have been
|
||||
// unregistered.
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
void ShdRendererClass::Shutdown()
|
||||
{
|
||||
Shutdown_Shaders();
|
||||
|
||||
WWASSERT(ShdRenderer);
|
||||
|
||||
delete ShdRenderer;
|
||||
ShdRenderer=0;
|
||||
}
|
||||
|
||||
void ShdRendererClass::Shutdown_Shaders()
|
||||
{
|
||||
ShdDefClass* def;
|
||||
for (int i=SHDDEF_CLASSID_DUMMY+1; i<SHDDEF_CLASSID_LAST; i++)
|
||||
{
|
||||
def=ShdDefManagerClass::Create_ShdDefClass_Instance(i);
|
||||
if (def) {
|
||||
def->Shutdown();
|
||||
REF_PTR_RELEASE(def);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// DirectX8 renderer utility class declaration
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
RendererListContainerClass::RendererListContainerClass(int pass) : Pass(pass)
|
||||
{
|
||||
}
|
||||
|
||||
RendererListContainerClass::~RendererListContainerClass()
|
||||
{
|
||||
Unregister_All();
|
||||
}
|
||||
|
||||
void RendererListContainerClass::Register_Renderer(ShdRendererNodeClass* node)
|
||||
{
|
||||
WWASSERT(node);
|
||||
node->Add_Ref();
|
||||
node->Set_Renderer_List_Container(this,Pass);
|
||||
LinkedNodes.Add_Tail(node);
|
||||
}
|
||||
|
||||
void RendererListContainerClass::Unregister_All()
|
||||
{
|
||||
while (!LinkedNodes.Is_Empty()) {
|
||||
ShdRendererNodeClass* node=LinkedNodes.Remove_Head();
|
||||
// REF_PTR_RELEASE(node);
|
||||
delete node;
|
||||
}
|
||||
}
|
||||
|
||||
void RendererListContainerClass::Flush()
|
||||
{
|
||||
ShdRendererNodeClass* prev_node=NULL;
|
||||
while (!VisibleNodes.Is_Empty())
|
||||
{
|
||||
ShdRendererNodeClass* node=VisibleNodes.Remove_Head();
|
||||
node->Apply_Shared_Shader_Settings(prev_node,Pass);
|
||||
node->Flush(Pass);
|
||||
prev_node=node;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
class ShdDX8RendererClass::MeshContainerClass : public RefCountClass
|
||||
{
|
||||
public:
|
||||
MeshContainerClass();
|
||||
virtual ~MeshContainerClass();
|
||||
|
||||
ShdRendererNodeClass* Register_Mesh(ShdMeshClass* mesh,ShdSubMeshClass* sub_mesh);
|
||||
// void Add_Visible_Node(ShdRendererNodeClass* node,int pass);
|
||||
void Flush();
|
||||
|
||||
private:
|
||||
|
||||
// ShdRendererNodeList VisibleNodeList[SHD_MAX_PASSES];
|
||||
RendererListContainerList RendererListContainers[SHD_MAX_PASSES];
|
||||
};
|
||||
|
||||
/**
|
||||
** ShdDX8RendererNode
|
||||
*/
|
||||
class ShdDX8RendererNodeClass : public ShdRendererNodeClass
|
||||
{
|
||||
public:
|
||||
ShdDX8RendererNodeClass(ShdDX8RendererClass::MeshContainerClass* container, ShdMeshClass* mesh,ShdSubMeshClass* sub_mesh);
|
||||
virtual ~ShdDX8RendererNodeClass();
|
||||
|
||||
virtual void Render(RenderInfoClass& rinfo);
|
||||
virtual void Flush(int pass);
|
||||
virtual void Apply_Shared_Shader_Settings(ShdRendererNodeClass* prev,int pass);
|
||||
|
||||
virtual bool Greater_Than(const ShdRendererNodeClass&, int pass) const;
|
||||
virtual bool Similar_Enough(const ShdRendererNodeClass&, int pass) const;
|
||||
|
||||
private:
|
||||
|
||||
ShdDX8RendererClass::MeshContainerClass* Container;
|
||||
ShdMeshClass* Mesh;
|
||||
ShdSubMeshClass* SubMesh;
|
||||
VertexBufferClass** VertexBuffers;
|
||||
IndexBufferClass* IndexBuffer;
|
||||
LightEnvironmentClass LightEnvironment; // todo KJM optimize for output lights
|
||||
RenderInfoClass* RenderInfo;
|
||||
};
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// DirectX8 renderer implementation
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
ShdDX8RendererClass::ShdDX8RendererClass()
|
||||
{
|
||||
MeshCategories=new MeshContainerClass*[SHDDEF_CLASSID_LAST];
|
||||
for (int i=0;i<SHDDEF_CLASSID_LAST;++i)
|
||||
{
|
||||
MeshCategories[i]=0;
|
||||
}
|
||||
}
|
||||
|
||||
ShdDX8RendererClass::~ShdDX8RendererClass()
|
||||
{
|
||||
for (int i=0;i<SHDDEF_CLASSID_LAST;++i)
|
||||
{
|
||||
if (MeshCategories[i])
|
||||
{
|
||||
REF_PTR_RELEASE(MeshCategories[i]);
|
||||
delete MeshCategories[i];
|
||||
MeshCategories[i]=0;
|
||||
}
|
||||
}
|
||||
delete[] MeshCategories;
|
||||
MeshCategories=0;
|
||||
}
|
||||
|
||||
bool ShdDX8RendererNodeClass::Greater_Than(const ShdRendererNodeClass& s, int pass) const
|
||||
{
|
||||
// Danger! Assuming ShdDX8RendererNodeClass!
|
||||
const ShdDX8RendererNodeClass* src=static_cast<const ShdDX8RendererNodeClass*>(&s);
|
||||
|
||||
WWASSERT(SubMesh && src->SubMesh);
|
||||
return SubMesh->Peek_Shader()->Greater_Than(*src->SubMesh->Peek_Shader(),pass);
|
||||
}
|
||||
|
||||
bool ShdDX8RendererNodeClass::Similar_Enough(const ShdRendererNodeClass& s, int pass) const
|
||||
{
|
||||
// Danger! Assuming ShdDX8RendererNodeClass!
|
||||
const ShdDX8RendererNodeClass* src=static_cast<const ShdDX8RendererNodeClass*>(&s);
|
||||
|
||||
WWASSERT(SubMesh && src->SubMesh);
|
||||
return SubMesh->Peek_Shader()->Similar_Enough(*src->SubMesh->Peek_Shader(),pass);
|
||||
}
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// Register mesh to the rendering system
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
ShdRendererNodeClass* ShdDX8RendererClass::Register_Mesh
|
||||
(
|
||||
ShdMeshClass* mesh,
|
||||
ShdSubMeshClass* sub_mesh
|
||||
)
|
||||
{
|
||||
ShdInterfaceClass* shd=sub_mesh->Peek_Shader();
|
||||
const ShdDefClass* def=shd->Peek_Definition();
|
||||
uint32 class_id=def->Get_Class_ID();
|
||||
WWASSERT(class_id<SHDDEF_CLASSID_LAST);
|
||||
if (!MeshCategories[class_id])
|
||||
{
|
||||
MeshCategories[class_id]=new MeshContainerClass();
|
||||
}
|
||||
return MeshCategories[class_id]->Register_Mesh(mesh,sub_mesh);
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// Flush the list of visible meshes
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
void ShdDX8RendererClass::Flush()
|
||||
{
|
||||
WWPROFILE("ShdDX8RendererClass::Flush");
|
||||
|
||||
DX8Wrapper::Apply_Render_State_Changes();
|
||||
DX8Wrapper::Invalidate_Cached_Render_States();
|
||||
DX8Wrapper::Apply_Default_State();
|
||||
|
||||
SNAPSHOT_SAY(("ShdDX8RendererClass::Flush()\n"));
|
||||
for (int i=0;i<SHDDEF_CLASSID_LAST;++i)
|
||||
{
|
||||
if (MeshCategories[i])
|
||||
{
|
||||
MeshCategories[i]->Flush();
|
||||
}
|
||||
}
|
||||
DX8Wrapper::Invalidate_Cached_Render_States();
|
||||
DX8Wrapper::Apply_Default_State();
|
||||
}
|
||||
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// MeshContiner is used for each shader type. Meshes are assigned to a container
|
||||
// when they're first rendered and they link themselves to container's visible list
|
||||
// each frame they're visible.
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
ShdDX8RendererClass::MeshContainerClass::MeshContainerClass()
|
||||
{
|
||||
}
|
||||
|
||||
ShdDX8RendererClass::MeshContainerClass::~MeshContainerClass()
|
||||
{
|
||||
for (int pass=0; pass<SHD_MAX_PASSES; pass++)
|
||||
{
|
||||
while (!RendererListContainers[pass].Is_Empty()) {
|
||||
RendererListContainerClass* cont=RendererListContainers[pass].Remove_Head();
|
||||
cont->Unregister_All();
|
||||
REF_PTR_RELEASE(cont);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// RendererNodeClass acts as a link between ShdMeshClass, ShdSubMeshClass and the
|
||||
// rendering system.
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
ShdRendererNodeClass* ShdDX8RendererClass::MeshContainerClass::Register_Mesh
|
||||
(
|
||||
ShdMeshClass* mesh,
|
||||
ShdSubMeshClass* sub_mesh
|
||||
)
|
||||
{
|
||||
ShdDX8RendererNodeClass* node=new ShdDX8RendererNodeClass(this,mesh,sub_mesh);
|
||||
ShdInterfaceClass* shdi=sub_mesh->Peek_Shader();
|
||||
WWASSERT(shdi);
|
||||
for (int pass=0; pass<shdi->Get_Pass_Count(); pass++)
|
||||
{
|
||||
RendererListContainerIterator ite(&RendererListContainers[pass]);
|
||||
ite.Last();
|
||||
while (!ite.Is_Done()) {
|
||||
RendererListContainerClass* cont=ite.Peek_Obj();
|
||||
if (cont) {
|
||||
ShdRendererNodeListIterator ite2(&cont->Peek_Linked_Nodes());
|
||||
ite2.First();
|
||||
// Container should delete itself when the last node is removed, so we must
|
||||
// never have an empty node.
|
||||
WWASSERT(!ite2.Is_Done());
|
||||
|
||||
ShdRendererNodeClass* obj=ite2.Peek_Obj();
|
||||
if (obj) {
|
||||
if (node->Greater_Than(*obj,pass)) {
|
||||
// If similar enough, add to the same renderer container, otherwise create a new one
|
||||
if (node->Similar_Enough(*obj,pass)) {
|
||||
cont->Register_Renderer(node);
|
||||
}
|
||||
else {
|
||||
RendererListContainerClass* new_cont=new RendererListContainerClass(pass);
|
||||
new_cont->Register_Renderer(node);
|
||||
RendererListContainers[pass].Add_After(new_cont,new_cont);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
ite.Prev();
|
||||
}
|
||||
if (ite.Is_Done()) {
|
||||
RendererListContainerClass* new_cont=new RendererListContainerClass(pass);
|
||||
new_cont->Register_Renderer(node);
|
||||
RendererListContainers[pass].Add(new_cont);
|
||||
}
|
||||
}
|
||||
|
||||
return node;
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// Render all visible nodes and clear the visible list.
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
void ShdDX8RendererClass::MeshContainerClass::Flush()
|
||||
{
|
||||
SNAPSHOT_SAY(("ShdDX8RendererClass::MeshContainerClass::Flush()\n"));
|
||||
|
||||
for (int pass=0; pass<SHD_MAX_PASSES; pass++)
|
||||
{
|
||||
RendererListContainerIterator ite(&RendererListContainers[pass]);
|
||||
ite.First();
|
||||
while (!ite.Is_Done()) {
|
||||
RendererListContainerClass* cont=ite.Peek_Obj();
|
||||
cont->Flush();
|
||||
ite.Next();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdDX8RendererNodeClass::ShdDX8RendererNodeClass --
|
||||
* Init the mesh for rendering... this node is used for all subsequent rendering of
|
||||
* the particular mesh.
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 4/20/2002 jp : Created
|
||||
* 5/26/2002 kjm : Updated stream handling for per-pixel shaders *
|
||||
* 6/02/2002 kjm : Added light environment handling
|
||||
* 7/29/2002 kjm : Added VB and IB usage flags for software vertex shaders
|
||||
*=============================================================================================*/
|
||||
ShdDX8RendererNodeClass::ShdDX8RendererNodeClass
|
||||
(
|
||||
ShdDX8RendererClass::MeshContainerClass* container,
|
||||
ShdMeshClass* mesh,
|
||||
ShdSubMeshClass* sub_mesh
|
||||
)
|
||||
: Container(container),
|
||||
Mesh(NULL),
|
||||
SubMesh(NULL),
|
||||
VertexBuffers(NULL),
|
||||
IndexBuffer(NULL)
|
||||
{
|
||||
REF_PTR_SET(Container,container);
|
||||
REF_PTR_SET(Mesh,mesh);
|
||||
REF_PTR_SET(SubMesh,sub_mesh);
|
||||
|
||||
// create usage depending on associated shader's processing behaviour KM
|
||||
DX8IndexBufferClass::UsageType ib_usage=DX8IndexBufferClass::USAGE_DEFAULT;
|
||||
|
||||
if (!SubMesh->Peek_Shader()->Use_HW_Vertex_Processing())
|
||||
{
|
||||
ib_usage=DX8IndexBufferClass::USAGE_SOFTWAREPROCESSING;
|
||||
}
|
||||
|
||||
int count=SubMesh->Get_Visible_Polygon_Count();
|
||||
if (!count) count=SubMesh->Get_Polygon_Count();
|
||||
unsigned index_count=count*3;
|
||||
if (SubMesh->Is_Sorting()) {
|
||||
IndexBuffer=new SortingIndexBufferClass(index_count);
|
||||
}
|
||||
else {
|
||||
IndexBuffer=new DX8IndexBufferClass(index_count,ib_usage);
|
||||
}
|
||||
IndexBufferClass::WriteLockClass ilock(IndexBuffer);
|
||||
const TriIndex* indices=SubMesh->Get_Polygon_Array();
|
||||
int i;
|
||||
int j=0;
|
||||
for (i=SubMesh->Get_First_Visible_Polygon();i<count+SubMesh->Get_First_Visible_Polygon();++i)
|
||||
{
|
||||
ilock.Get_Index_Array()[j++]=indices[i][0];
|
||||
ilock.Get_Index_Array()[j++]=indices[i][1];
|
||||
ilock.Get_Index_Array()[j++]=indices[i][2];
|
||||
}
|
||||
|
||||
// Don't use static vertex buffers if skin
|
||||
if (SubMesh->Get_Flag(MeshGeometryClass::SKIN)) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Compose the vertex and index buffers
|
||||
VertexStreamStruct vss;
|
||||
vss.Locations=SubMesh->Get_Vertex_Array();
|
||||
vss.Normals=SubMesh->Get_Vertex_Normal_Array();
|
||||
for (unsigned stage=0;stage<MAX_TEXTURE_STAGES;++stage)
|
||||
{
|
||||
vss.UV[stage]=SubMesh->Get_UV_Array(stage);
|
||||
}
|
||||
vss.DiffuseInt=SubMesh->Get_Diffuse_Array();
|
||||
vss.S=SubMesh->Get_Tangent_Basis_S_Array();
|
||||
vss.T=SubMesh->Get_Tangent_Basis_T_Array();
|
||||
vss.SxT=SubMesh->Get_Tangent_Basis_SxT_Array();
|
||||
|
||||
unsigned vertex_count=SubMesh->Get_Vertex_Count();
|
||||
unsigned stream_count=SubMesh->Peek_Shader()->Get_Vertex_Stream_Count();
|
||||
WWASSERT(stream_count>0);
|
||||
|
||||
// create usage depending on associated shader's processing behaviour KM
|
||||
DX8VertexBufferClass::UsageType vb_usage=DX8VertexBufferClass::USAGE_DEFAULT;
|
||||
|
||||
if (!SubMesh->Peek_Shader()->Use_HW_Vertex_Processing())
|
||||
{
|
||||
vb_usage=DX8VertexBufferClass::USAGE_SOFTWAREPROCESSING;
|
||||
}
|
||||
|
||||
VertexBuffers=new VertexBufferClass*[stream_count];
|
||||
unsigned n;
|
||||
for (n=0;n<stream_count;++n)
|
||||
{
|
||||
unsigned vertex_size=SubMesh->Peek_Shader()->Get_Vertex_Size(n);
|
||||
|
||||
if (SubMesh->Is_Sorting()) {
|
||||
VertexBuffers[n]=
|
||||
new SortingVertexBufferClass(vertex_count);
|
||||
}
|
||||
else {
|
||||
VertexBuffers[n]=
|
||||
new DX8VertexBufferClass
|
||||
(
|
||||
0,
|
||||
vertex_count,
|
||||
vb_usage,
|
||||
vertex_size
|
||||
);
|
||||
}
|
||||
|
||||
VertexBufferClass::WriteLockClass vlock(VertexBuffers[n]);
|
||||
SubMesh->Peek_Shader()->Copy_Vertex_Stream
|
||||
(
|
||||
n,
|
||||
vlock.Get_Vertex_Array(),
|
||||
vss,
|
||||
SubMesh->Get_Vertex_Count()
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
ShdDX8RendererNodeClass::~ShdDX8RendererNodeClass()
|
||||
{
|
||||
unsigned stream_count=SubMesh->Peek_Shader()->Get_Vertex_Stream_Count();
|
||||
unsigned n;
|
||||
for (n=0;n<stream_count;++n)
|
||||
{
|
||||
REF_PTR_RELEASE(VertexBuffers[n]);
|
||||
}
|
||||
delete[] VertexBuffers;
|
||||
VertexBuffers=NULL;
|
||||
|
||||
REF_PTR_RELEASE(IndexBuffer);
|
||||
REF_PTR_RELEASE(Mesh);
|
||||
REF_PTR_RELEASE(SubMesh);
|
||||
REF_PTR_RELEASE(Container);
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdDX8RendererNodeClass::Render -- Render node
|
||||
*
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 4/20/2002 jp : Created
|
||||
* 6/02/2002 kjm : Added light environment handling
|
||||
*=============================================================================================*/
|
||||
void ShdDX8RendererNodeClass::Render(RenderInfoClass& rinfo)
|
||||
{
|
||||
RenderInfo=&rinfo;
|
||||
if (rinfo.light_environment)
|
||||
{
|
||||
memcpy(&LightEnvironment,rinfo.light_environment,sizeof(LightEnvironmentClass));
|
||||
}
|
||||
else {
|
||||
LightEnvironment.Reset(Vector3(0.0f,0.0f,0.0f),Vector3(0.0f,0.0f,0.0f));
|
||||
}
|
||||
|
||||
Connect();
|
||||
}
|
||||
|
||||
bool enable_rnd=true;
|
||||
void ShdDX8RendererNodeClass::Flush(int cur_pass)
|
||||
{
|
||||
WWASSERT(RenderInfo);
|
||||
|
||||
// pass selection for this instance
|
||||
if (!SubMesh->Peek_Shader()->Pass_Selection(Mesh,RenderInfo,cur_pass))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
SNAPSHOT_SAY(("ShdDX8RendererNodeClass::Flush(%d) - %s\n",cur_pass,SubMesh->Get_Name()));
|
||||
|
||||
// BEGIN OF SKIN CODE
|
||||
if (SubMesh->Get_Flag(MeshGeometryClass::SKIN)) {
|
||||
DX8Wrapper::Set_Vertex_Buffer(NULL); // Free up the reference to the current vertex buffer
|
||||
// (in case it is the dynamic, which may have to be resized)
|
||||
|
||||
unsigned vertex_count=SubMesh->Get_Vertex_Count();
|
||||
unsigned stream_count=SubMesh->Peek_Shader()->Get_Vertex_Stream_Count();
|
||||
WWASSERT(stream_count>0);
|
||||
|
||||
// For now there are restrictions in vertex buffer format with skinning
|
||||
FVFInfoClass fi(dynamic_fvf_type);
|
||||
WWASSERT(SubMesh->Peek_Shader()->Get_Vertex_Size(0)==fi.Get_FVF_Size());
|
||||
|
||||
DynamicVBAccessClass vb(
|
||||
SubMesh->Is_Sorting() ? BUFFER_TYPE_DYNAMIC_SORTING : BUFFER_TYPE_DYNAMIC_DX8,
|
||||
dynamic_fvf_type,
|
||||
vertex_count);
|
||||
SNAPSHOT_SAY(("DynamicVBAccess - %s - %d vertices\n",SubMesh->Is_Sorting() ? "sorting" : "non-sorting",vertex_count));
|
||||
|
||||
if (_TempVertexBuffer.Length() < (int)vertex_count) _TempVertexBuffer.Resize(vertex_count);
|
||||
if (_TempNormalBuffer.Length() < (int)vertex_count) _TempNormalBuffer.Resize(vertex_count);
|
||||
Vector3* loc=&(_TempVertexBuffer[0]);
|
||||
Vector3* norm=&(_TempNormalBuffer[0]);
|
||||
WWASSERT(Mesh->Get_Container());
|
||||
SubMesh->Get_Deformed_Vertices(loc,norm,Mesh->Get_Container()->Get_HTree());
|
||||
|
||||
// Compose the vertex and index buffers
|
||||
VertexStreamStruct vss;
|
||||
vss.Locations=loc;
|
||||
vss.Normals=norm;
|
||||
for (unsigned stage=0;stage<MAX_TEXTURE_STAGES;++stage)
|
||||
{
|
||||
vss.UV[stage]=SubMesh->Get_UV_Array(stage);
|
||||
}
|
||||
vss.DiffuseInt=SubMesh->Get_Diffuse_Array();
|
||||
vss.S=SubMesh->Get_Tangent_Basis_S_Array();
|
||||
vss.T=SubMesh->Get_Tangent_Basis_T_Array();
|
||||
vss.SxT=SubMesh->Get_Tangent_Basis_SxT_Array();
|
||||
|
||||
WWASSERT(stream_count==1);
|
||||
{
|
||||
DynamicVBAccessClass::WriteLockClass vlock(&vb);
|
||||
SubMesh->Peek_Shader()->Copy_Vertex_Stream
|
||||
(
|
||||
0,//stream
|
||||
vlock.Get_Formatted_Vertex_Array(),
|
||||
vss,
|
||||
SubMesh->Get_Vertex_Count()
|
||||
);
|
||||
}
|
||||
DX8Wrapper::Set_Vertex_Buffer(vb);//stream 0
|
||||
|
||||
DX8Wrapper::Set_Index_Buffer(IndexBuffer,0);
|
||||
DX8Wrapper::Set_Transform(D3DTS_WORLD,Matrix3D(true));//Mesh->Get_Transform());
|
||||
|
||||
DX8Wrapper::Set_Light_Environment(&LightEnvironment);
|
||||
SubMesh->Peek_Shader()->Apply_Instance(cur_pass, *RenderInfo);
|
||||
|
||||
if (SubMesh->Is_Sorting()) {
|
||||
SortingRendererClass::Insert_Triangles
|
||||
(
|
||||
0,
|
||||
SubMesh->Get_Visible_Polygon_Count() ? SubMesh->Get_Visible_Polygon_Count() : SubMesh->Get_Polygon_Count(),
|
||||
0,
|
||||
SubMesh->Get_Vertex_Count()
|
||||
);
|
||||
}
|
||||
else {
|
||||
DX8Wrapper::Draw_Triangles
|
||||
(
|
||||
0,
|
||||
SubMesh->Get_Visible_Polygon_Count() ? SubMesh->Get_Visible_Polygon_Count() : SubMesh->Get_Polygon_Count(),
|
||||
0,
|
||||
SubMesh->Get_Vertex_Count()
|
||||
);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
// END OF SKIN CODE
|
||||
|
||||
|
||||
for (unsigned n=0;n<SubMesh->Peek_Shader()->Get_Vertex_Stream_Count();++n)
|
||||
{
|
||||
DX8Wrapper::Set_Vertex_Buffer(VertexBuffers[n],n);
|
||||
}
|
||||
|
||||
DX8Wrapper::Set_Index_Buffer(IndexBuffer,0);
|
||||
DX8Wrapper::Set_Transform(D3DTS_WORLD,Mesh->Get_Transform());
|
||||
|
||||
DX8Wrapper::Set_Light_Environment(&LightEnvironment);
|
||||
SubMesh->Peek_Shader()->Apply_Instance(cur_pass, *RenderInfo);
|
||||
|
||||
if (SubMesh->Is_Sorting()) {
|
||||
SortingRendererClass::Insert_Triangles
|
||||
(
|
||||
0,
|
||||
SubMesh->Get_Visible_Polygon_Count() ? SubMesh->Get_Visible_Polygon_Count() : SubMesh->Get_Polygon_Count(),
|
||||
0,
|
||||
SubMesh->Get_Vertex_Count()
|
||||
);
|
||||
}
|
||||
else {
|
||||
DX8Wrapper::Draw_Triangles
|
||||
(
|
||||
0,
|
||||
SubMesh->Get_Visible_Polygon_Count() ? SubMesh->Get_Visible_Polygon_Count() : SubMesh->Get_Polygon_Count(),
|
||||
0,
|
||||
SubMesh->Get_Vertex_Count()
|
||||
);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
void ShdDX8RendererNodeClass::Apply_Shared_Shader_Settings(ShdRendererNodeClass* prev_node, int pass)
|
||||
{
|
||||
// If the previously set shader is not the same type as this, we need to set
|
||||
// all render states to default state.
|
||||
if (prev_node) {
|
||||
ShdDX8RendererNodeClass* prev_dx8_node=static_cast<ShdDX8RendererNodeClass*>(prev_node); // Illegal to pass another type!
|
||||
ShdInterfaceClass* shd=prev_dx8_node->SubMesh->Peek_Shader();
|
||||
if (shd->Get_Class_ID()!=SubMesh->Peek_Shader()->Get_Class_ID()) {
|
||||
DX8Wrapper::Apply_Default_State();
|
||||
}
|
||||
}
|
||||
SubMesh->Peek_Shader()->Apply_Shared(pass, *RenderInfo);
|
||||
}
|
||||
|
||||
191
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdrenderer.h
Normal file
191
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdrenderer.h
Normal file
@@ -0,0 +1,191 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WW3D *
|
||||
* *
|
||||
* $Archive:: /Commando/Code/ww3d2/shdrenderer.h $*
|
||||
*
|
||||
* Org Author:: Jani_p
|
||||
* *
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 6/06/02 3:04p $*
|
||||
* *
|
||||
* $Revision:: 3 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* 6/02/02 5:59p KM Added render info and light environment support $*
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHDRENDERER_H
|
||||
#define SHDRENDERER_H
|
||||
|
||||
#include "multilist.h"
|
||||
#include "refcount.h"
|
||||
#include "shdinterface.h"
|
||||
|
||||
class ShdSubMeshClass;
|
||||
class ShdMeshClass;
|
||||
class RenderInfoClass;
|
||||
|
||||
class ShdRendererNodeClass;
|
||||
class RendererListContainerClass;
|
||||
|
||||
typedef MultiListClass<ShdRendererNodeClass> ShdRendererNodeList;
|
||||
typedef MultiListIterator<ShdRendererNodeClass> ShdRendererNodeListIterator;
|
||||
typedef MultiListClass<RendererListContainerClass> RendererListContainerList;
|
||||
typedef MultiListIterator<RendererListContainerClass> RendererListContainerIterator;
|
||||
|
||||
class RendererListContainerClass : public MultiListObjectClass, public RefCountClass
|
||||
{
|
||||
int Pass;
|
||||
ShdRendererNodeList LinkedNodes;
|
||||
ShdRendererNodeList VisibleNodes;
|
||||
public:
|
||||
RendererListContainerClass(int pass);
|
||||
virtual ~RendererListContainerClass();
|
||||
|
||||
void Add_Visible_Node(ShdRendererNodeClass* node) {
|
||||
VisibleNodes.Add_Tail(node);
|
||||
}
|
||||
|
||||
ShdRendererNodeList& Peek_Linked_Nodes() { return LinkedNodes; }
|
||||
|
||||
void Flush();
|
||||
|
||||
void Register_Renderer(ShdRendererNodeClass* node);
|
||||
void Unregister_All();
|
||||
|
||||
};
|
||||
|
||||
/**
|
||||
** ShdRendererNode
|
||||
** RendererNodeClass acts as a link between ShdMeshClass, ShdSubMeshClass and the
|
||||
** rendering system. Rendering API specific implementations are expected.
|
||||
*/
|
||||
class ShdRendererNodeClass : public MultiListObjectClass, public RefCountClass
|
||||
{
|
||||
RendererListContainerClass* RendererListContainer[SHD_MAX_PASSES];
|
||||
int MaxPass;
|
||||
public:
|
||||
ShdRendererNodeClass() : MaxPass(0)
|
||||
{
|
||||
for (int a=0;a<SHD_MAX_PASSES;++a) {
|
||||
RendererListContainer[a]=0;
|
||||
}
|
||||
}
|
||||
virtual ~ShdRendererNodeClass()
|
||||
{
|
||||
for (int a=0;a<SHD_MAX_PASSES;++a) {
|
||||
REF_PTR_RELEASE(RendererListContainer[a]);
|
||||
}
|
||||
}
|
||||
|
||||
virtual void Render(RenderInfoClass& rinfo)=0;
|
||||
virtual void Flush(int pass)=0;
|
||||
virtual void Apply_Shared_Shader_Settings(ShdRendererNodeClass* prev_node, int pass)=0;
|
||||
|
||||
virtual bool Greater_Than(const ShdRendererNodeClass&, int pass) const =0;
|
||||
|
||||
void Connect()
|
||||
{
|
||||
for (int pass=0;pass<=MaxPass;++pass) {
|
||||
WWASSERT(RendererListContainer[pass]);
|
||||
if (RendererListContainer[pass]) RendererListContainer[pass]->Add_Visible_Node(this);
|
||||
}
|
||||
}
|
||||
|
||||
void Set_Renderer_List_Container(RendererListContainerClass* cont,int pass)
|
||||
{
|
||||
REF_PTR_SET(RendererListContainer[pass],cont);
|
||||
if (cont) MaxPass=max(MaxPass,pass);
|
||||
}
|
||||
RendererListContainerClass* Peek_Renderer_List_Container(int pass) { return RendererListContainer[pass]; }
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
** ShdRenderer
|
||||
*/
|
||||
class ShdRendererClass
|
||||
{
|
||||
static ShdRendererClass* ShdRenderer;
|
||||
|
||||
protected:
|
||||
ShdRendererClass();
|
||||
virtual ~ShdRendererClass();
|
||||
public:
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// Init must be called before any objects can be rendered and Release() must be called
|
||||
// at the end to release all references to the rendering API. Working through a static
|
||||
// pointer instead of calling static functions will later allow us to switch to another
|
||||
// rendering API implementation of the renderer.
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
static void Init();
|
||||
static void Shutdown();
|
||||
|
||||
static void Init_Shaders();
|
||||
static void Shutdown_Shaders();
|
||||
|
||||
static ShdRendererClass* Peek_Instance() { return ShdRenderer; }
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// Register initialized a mesh for rendering.
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
virtual ShdRendererNodeClass* Register_Mesh(ShdMeshClass* mesh,ShdSubMeshClass* sub_mesh)=0;
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// Flush all linked meshes to the rendering system
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
virtual void Flush()=0;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
** ShdDX8Renderer
|
||||
*/
|
||||
class ShdDX8RendererClass : public ShdRendererClass
|
||||
{
|
||||
public:
|
||||
ShdDX8RendererClass();
|
||||
virtual ~ShdDX8RendererClass();
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// Register initialized a mesh for rendering. Note, these will need to be virtual
|
||||
// if new types of renderers are created.
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
virtual ShdRendererNodeClass* Register_Mesh(ShdMeshClass* mesh,ShdSubMeshClass* sub_mesh);
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// Flush all linked meshes to the rendering system
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
virtual void Flush();
|
||||
|
||||
class MeshContainerClass;
|
||||
private:
|
||||
MeshContainerClass** MeshCategories;
|
||||
|
||||
};
|
||||
|
||||
#endif //SHDRENDERER_H
|
||||
325
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdsimple.cpp
Normal file
325
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdsimple.cpp
Normal file
@@ -0,0 +1,325 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shdsimple.cpp $*
|
||||
* *
|
||||
* $Org Author:: Kenny_m
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 7/12/02 3:12p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#include <d3dx8math.h>
|
||||
#include "dx8fvf.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "assetmgr.h"
|
||||
|
||||
#include "shdsimple.h"
|
||||
|
||||
#include "editable.h"
|
||||
#include "shdclassids.h"
|
||||
#include "shddeffactory.h"
|
||||
#include "shdinterface.h"
|
||||
#include "shdhwshader.h"
|
||||
|
||||
#include "persistfactory.h"
|
||||
#include "wwhack.h"
|
||||
|
||||
DECLARE_FORCE_LINK(SimpleShader);
|
||||
REGISTER_SHDDEF(ShdSimpleDefClass,SHDDEF_CLASSID_SIMPLE,"Simple");
|
||||
|
||||
|
||||
// Save-Load methods for ShdDefClass
|
||||
enum
|
||||
{
|
||||
CHUNKID_VARIABLES = 0x16490450,
|
||||
|
||||
VARID_TEXTURE_NAME = 0x00,
|
||||
|
||||
VARID_AMBIENT_COLOR,
|
||||
VARID_DIFFUSE_COLOR
|
||||
};
|
||||
|
||||
ShdSimpleDefClass::ShdSimpleDefClass()
|
||||
: ShdDefClass(SHDDEF_CLASSID_SIMPLE),
|
||||
Ambient(1,1,1),
|
||||
Diffuse(1,1,1)
|
||||
{
|
||||
NAMED_TEXTURE_FILENAME_PARAM(ShdSimpleDefClass, TextureName, "Texture Name", "Targa Files", ".tga");
|
||||
|
||||
NAMED_EDITABLE_PARAM(ShdSimpleDefClass, ParameterClass::TYPE_COLOR, Ambient, "Ambient");
|
||||
NAMED_EDITABLE_PARAM(ShdSimpleDefClass, ParameterClass::TYPE_COLOR, Diffuse, "Diffuse");
|
||||
}
|
||||
|
||||
ShdSimpleDefClass::ShdSimpleDefClass(const ShdSimpleDefClass& that)
|
||||
: ShdDefClass(that),
|
||||
Ambient(0,0,0),
|
||||
Diffuse(1,1,1)
|
||||
{
|
||||
TextureName=that.TextureName;
|
||||
|
||||
Ambient=that.Ambient;
|
||||
Diffuse=that.Diffuse;
|
||||
}
|
||||
|
||||
ShdSimpleDefClass::~ShdSimpleDefClass()
|
||||
{
|
||||
}
|
||||
|
||||
bool ShdSimpleDefClass::Is_Valid_Config(StringClass &message)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ShdSimpleDefClass::Save(ChunkSaveClass &csave)
|
||||
{
|
||||
ShdDefClass::Save(csave);
|
||||
|
||||
csave.Begin_Chunk(CHUNKID_VARIABLES);
|
||||
|
||||
bool retval = true;
|
||||
|
||||
// only save the file name
|
||||
char fname[_MAX_PATH];
|
||||
|
||||
_splitpath(TextureName,NULL,NULL,fname,NULL);
|
||||
strcat(fname,".tga");
|
||||
TextureName=fname;
|
||||
|
||||
WRITE_MICRO_CHUNK_WWSTRING(csave, VARID_TEXTURE_NAME, TextureName);
|
||||
|
||||
WRITE_MICRO_CHUNK(csave, VARID_AMBIENT_COLOR, Ambient);
|
||||
WRITE_MICRO_CHUNK(csave, VARID_DIFFUSE_COLOR, Diffuse);
|
||||
|
||||
csave.End_Chunk();
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
||||
bool ShdSimpleDefClass::Load(ChunkLoadClass &cload)
|
||||
{
|
||||
ShdDefClass::Load(cload);
|
||||
|
||||
// Loop through all the microchunks that define the variables
|
||||
while (cload.Open_Chunk()) {
|
||||
switch (cload.Cur_Chunk_ID())
|
||||
{
|
||||
case CHUNKID_VARIABLES:
|
||||
while (cload.Open_Micro_Chunk())
|
||||
{
|
||||
switch (cload.Cur_Micro_Chunk_ID())
|
||||
{
|
||||
READ_MICRO_CHUNK_WWSTRING(cload, VARID_TEXTURE_NAME, TextureName);
|
||||
|
||||
READ_MICRO_CHUNK(cload, VARID_AMBIENT_COLOR, Ambient);
|
||||
READ_MICRO_CHUNK(cload, VARID_DIFFUSE_COLOR, Diffuse);
|
||||
}
|
||||
|
||||
cload.Close_Micro_Chunk();
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
cload.Close_Chunk();
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
void ShdSimpleDefClass::Init()
|
||||
{
|
||||
Shd6SimpleClass::Init();
|
||||
}
|
||||
|
||||
void ShdSimpleDefClass::Shutdown()
|
||||
{
|
||||
Shd6SimpleClass::Shutdown();
|
||||
}
|
||||
|
||||
ShdInterfaceClass* ShdSimpleDefClass::Create() const
|
||||
{
|
||||
return new Shd6SimpleClass(this);
|
||||
}
|
||||
|
||||
|
||||
|
||||
Matrix4x4 Shd6SimpleClass::View_Projection_Matrix;
|
||||
|
||||
Shd6SimpleClass::Shd6SimpleClass(const ShdDefClass* def)
|
||||
: ShdInterfaceClass(def,SHDDEF_CLASSID_SIMPLE),
|
||||
Texture(NULL)
|
||||
{
|
||||
ShdSimpleDefClass* Definition=(ShdSimpleDefClass*)def;
|
||||
|
||||
Texture=WW3DAssetManager::Get_Instance()->Get_Texture
|
||||
(
|
||||
Definition->Get_Texture_Name()
|
||||
);
|
||||
|
||||
const Vector3& a=Definition->Get_Ambient();
|
||||
Ambient.Set(a.X,a.Y,a.Z,1.0f);
|
||||
|
||||
const Vector3& d=Definition->Get_Diffuse();
|
||||
Diffuse.Set(d.X,d.Y,d.Z,1.0f);
|
||||
|
||||
Material=new D3DMATERIAL8;
|
||||
memset(Material,0,sizeof(D3DMATERIAL8));
|
||||
Material->Ambient.r=a.X; Material->Ambient.g=a.Y; Material->Ambient.b=a.Z;
|
||||
Material->Diffuse.r=d.X; Material->Diffuse.g=d.Y; Material->Diffuse.b=d.Z;
|
||||
}
|
||||
|
||||
Shd6SimpleClass::~Shd6SimpleClass()
|
||||
{
|
||||
REF_PTR_RELEASE(Texture);
|
||||
}
|
||||
|
||||
void Shd6SimpleClass::Init()
|
||||
{
|
||||
}
|
||||
|
||||
void Shd6SimpleClass::Shutdown()
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
/**********************************************************************************************
|
||||
//! Apply shared states for 1 pass DX6
|
||||
/*! 7/12/02 3:39p KJM Created
|
||||
*/
|
||||
void Shd6SimpleClass::Apply_Shared(int pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
// fixed function uses pass through by default
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_PASSTHRU);
|
||||
|
||||
// set vertex shader
|
||||
DX8Wrapper::Set_Vertex_Shader(DX8_FVF_XYZNDUV1);
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLOROP, D3DTOP_MODULATE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(0, D3DTSS_ALPHAOP, D3DTOP_MODULATE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_COLOROP, D3DTOP_DISABLE );
|
||||
DX8Wrapper::Set_DX8_Texture_Stage_State(1, D3DTSS_ALPHAOP, D3DTOP_DISABLE );
|
||||
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_LIGHTING, TRUE);
|
||||
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_AMBIENTMATERIALSOURCE,D3DMCS_MATERIAL);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_DIFFUSEMATERIALSOURCE,D3DMCS_MATERIAL);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_SPECULARMATERIALSOURCE,D3DMCS_MATERIAL);
|
||||
DX8Wrapper::Set_DX8_Render_State(D3DRS_EMISSIVEMATERIALSOURCE,D3DMCS_MATERIAL);
|
||||
|
||||
}
|
||||
|
||||
//**********************************************************************************************
|
||||
//! Apply per instance states for 1 pass DX6
|
||||
/*! 7/10/02 5:39p KJM Created
|
||||
*/
|
||||
void Shd6SimpleClass::Apply_Instance(int cur_pass, RenderInfoClass& rinfo)
|
||||
{
|
||||
DX8Wrapper::Set_DX8_Material(Material);
|
||||
DX8Wrapper::Set_Texture(0, Texture);
|
||||
}
|
||||
|
||||
unsigned Shd6SimpleClass::Get_Vertex_Stream_Count() const
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
unsigned Shd6SimpleClass::Get_Vertex_Size(unsigned stream) const
|
||||
{
|
||||
return sizeof(VertexFormatXYZNDUV1);
|
||||
}
|
||||
|
||||
void Shd6SimpleClass::Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
)
|
||||
{
|
||||
VertexFormatXYZNDUV1* verts=(VertexFormatXYZNDUV1*)dest_buffer;
|
||||
|
||||
for (unsigned i=0; i<vertex_count; ++i)
|
||||
{
|
||||
if (vss.Locations)
|
||||
{
|
||||
verts[i].x=vss.Locations[i][0];
|
||||
verts[i].y=vss.Locations[i][1];
|
||||
verts[i].z=vss.Locations[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].x=0.0f;
|
||||
verts[i].y=0.0f;
|
||||
verts[i].z=0.0f;
|
||||
}
|
||||
|
||||
if (vss.DiffuseInt)
|
||||
{
|
||||
verts[i].diffuse=vss.DiffuseInt[i];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].diffuse=0xffffffff;
|
||||
}
|
||||
|
||||
if (vss.Normals)
|
||||
{
|
||||
verts[i].nx=vss.Normals[i][0];
|
||||
verts[i].ny=vss.Normals[i][1];
|
||||
verts[i].nz=vss.Normals[i][2];
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].nx=0.0f;
|
||||
verts[i].ny=0.0f;
|
||||
verts[i].nz=0.0f;
|
||||
}
|
||||
|
||||
if (vss.UV[0])
|
||||
{
|
||||
verts[i].u1=vss.UV[0][i].U;
|
||||
verts[i].v1=vss.UV[0][i].V;
|
||||
}
|
||||
else
|
||||
{
|
||||
verts[i].u1=0.0f;
|
||||
verts[i].v1=0.0f;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
146
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdsimple.h
Normal file
146
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdsimple.h
Normal file
@@ -0,0 +1,146 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWSHADE *
|
||||
* *
|
||||
* $Archive:: wwshade/shdsimple.cpp $*
|
||||
* *
|
||||
* $Org Author:: Kenny_m
|
||||
*
|
||||
* $Author:: Kenny_m
|
||||
*
|
||||
* $Modtime:: 7/12/02 3:12p $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
* Functions: *
|
||||
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
||||
|
||||
#ifndef SHDSIMPLE_H
|
||||
#define SHDSIMPLE_H
|
||||
|
||||
#ifndef SHDINTERFACE_H
|
||||
#include "shdinterface.h"
|
||||
#endif
|
||||
|
||||
#include "shddef.h"
|
||||
|
||||
|
||||
class ShdSimpleDefClass : public ShdDefClass
|
||||
{
|
||||
public:
|
||||
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
// Editable interface requirements
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
DECLARE_EDITABLE(ShdSimpleDefClass, ShdDefClass);
|
||||
|
||||
ShdSimpleDefClass();
|
||||
ShdSimpleDefClass(const ShdSimpleDefClass& that);
|
||||
virtual ~ShdSimpleDefClass();
|
||||
|
||||
virtual ShdDefClass* Clone() const { return new ShdSimpleDefClass(*this); }
|
||||
|
||||
// Shader Creation (should create a shader compatible with the current hardware/API)
|
||||
virtual void Init();
|
||||
virtual void Shutdown();
|
||||
virtual ShdInterfaceClass* Create() const;
|
||||
|
||||
// Validation methods
|
||||
virtual bool Is_Valid_Config(StringClass &message);
|
||||
|
||||
// Requirements
|
||||
virtual bool Requires_Normals() const { return true; }
|
||||
virtual bool Requires_Tangent_Space_Vectors() const { return false; }
|
||||
virtual bool Requires_Sorting() const { return false; }
|
||||
virtual int Static_Sort_Index() const { return 0; }
|
||||
|
||||
// From PersistClass
|
||||
virtual bool Save(ChunkSaveClass &csave);
|
||||
virtual bool Load(ChunkLoadClass &cload);
|
||||
|
||||
void Set_Texture_Name(const StringClass& name) { TextureName=name; }
|
||||
const StringClass& Get_Texture_Name() const { return TextureName; }
|
||||
|
||||
void Set_Ambient(const Vector3& ambient) { Ambient=ambient; }
|
||||
const Vector3& Get_Ambient() const { return Ambient; }
|
||||
|
||||
void Set_Diffuse(const Vector3& diffuse) { Diffuse=diffuse; }
|
||||
const Vector3& Get_Diffuse() const { return Diffuse; }
|
||||
|
||||
private:
|
||||
|
||||
bool Save_Variables(ChunkSaveClass &csave);
|
||||
bool Load_Variables(ChunkLoadClass &cload);
|
||||
|
||||
StringClass TextureName;
|
||||
|
||||
Vector3 Ambient;
|
||||
Vector3 Diffuse;
|
||||
};
|
||||
|
||||
|
||||
|
||||
class Shd6SimpleClass : public ShdInterfaceClass
|
||||
{
|
||||
public:
|
||||
Shd6SimpleClass(const ShdDefClass* def);
|
||||
virtual ~Shd6SimpleClass();
|
||||
|
||||
static void Init();
|
||||
static void Shutdown();
|
||||
|
||||
virtual int Get_Pass_Count() { return 1; }
|
||||
|
||||
virtual int Get_Texture_Count() const { return 1; }
|
||||
virtual TextureClass* Peek_Texture(int idx) const { return Texture; }
|
||||
|
||||
virtual void Apply_Shared(int cur_pass, RenderInfoClass& rinfo);
|
||||
virtual void Apply_Instance(int cur_pass, RenderInfoClass& rinfo);
|
||||
|
||||
virtual unsigned Get_Vertex_Stream_Count() const;
|
||||
virtual unsigned Get_Vertex_Size(unsigned stream) const;
|
||||
virtual bool Use_HW_Vertex_Processing() const { return true; }
|
||||
|
||||
virtual void Copy_Vertex_Stream
|
||||
(
|
||||
unsigned stream,
|
||||
void* dest_buffer,
|
||||
const VertexStreamStruct& vss,
|
||||
unsigned vertex_count
|
||||
);
|
||||
|
||||
protected:
|
||||
|
||||
static Matrix4x4 View_Projection_Matrix;
|
||||
|
||||
D3DMATERIAL8* Material;
|
||||
|
||||
TextureClass* Texture;
|
||||
|
||||
Vector4 Ambient;
|
||||
Vector4 Diffuse;
|
||||
};
|
||||
|
||||
|
||||
#endif //SHDSIMPLE_H
|
||||
917
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdsubmesh.cpp
Normal file
917
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdsubmesh.cpp
Normal file
@@ -0,0 +1,917 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWShade *
|
||||
* *
|
||||
* $Archive:: wwshade/shdsubmesh.cpp $*
|
||||
* *
|
||||
* Org Author:: Jani P *
|
||||
* *
|
||||
* Author : Kenny Mitchell *
|
||||
* *
|
||||
* $Modtime:: 07/12/02 10:31a $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
* 07/12/02 KM Removed legacy mesh conversion *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
*---------------------------------------------------------------------------------------------*/
|
||||
|
||||
#include "shddefmanager.h"
|
||||
#include "shdsubmesh.h"
|
||||
#include "shdrenderer.h"
|
||||
#include "shdlegacyw3d.h"
|
||||
#include "shdclassids.h"
|
||||
|
||||
#include "chunkio.h"
|
||||
#include "texture.h"
|
||||
#include "w3d_file.h"
|
||||
#include "ww3d.h"
|
||||
#include "dx8fvf.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "meshmdl.h"
|
||||
#include "texture.h"
|
||||
#include "aabtree.h"
|
||||
#include "sharebuf.h"
|
||||
|
||||
ShdSubMeshClass::ShdSubMeshClass(void)
|
||||
:
|
||||
Shader(NULL),
|
||||
S(NULL),
|
||||
T(NULL),
|
||||
SxT(NULL),
|
||||
Diffuse(NULL),
|
||||
FirstVisiblePolygon(0),
|
||||
VisiblePolygonCount(0),
|
||||
Sorting(false)
|
||||
{
|
||||
for (int i=0;i<MAX_TEXTURE_STAGES;++i)
|
||||
{
|
||||
UV[i]=NULL;
|
||||
}
|
||||
}
|
||||
|
||||
ShdSubMeshClass::ShdSubMeshClass(const ShdSubMeshClass& that)
|
||||
:
|
||||
Shader(NULL),
|
||||
S(NULL),
|
||||
T(NULL),
|
||||
SxT(NULL),
|
||||
Diffuse(NULL),
|
||||
FirstVisiblePolygon(that.FirstVisiblePolygon),
|
||||
VisiblePolygonCount(that.VisiblePolygonCount),
|
||||
Sorting(false)
|
||||
{
|
||||
for (int i=0;i<MAX_TEXTURE_STAGES;++i)
|
||||
{
|
||||
UV[i]=NULL;
|
||||
}
|
||||
*this = that;
|
||||
}
|
||||
|
||||
ShdSubMeshClass & ShdSubMeshClass::operator = (const ShdSubMeshClass & that)
|
||||
{
|
||||
if (this != &that)
|
||||
{
|
||||
FirstVisiblePolygon=that.FirstVisiblePolygon;
|
||||
VisiblePolygonCount=that.VisiblePolygonCount;
|
||||
Sorting=that.Sorting;
|
||||
REF_PTR_SET(Shader,that.Shader);
|
||||
for (int i=0;i<MAX_TEXTURE_STAGES;++i)
|
||||
{
|
||||
REF_PTR_SET(UV[i],that.UV[i]);
|
||||
}
|
||||
|
||||
REF_PTR_SET(S,that.S);
|
||||
REF_PTR_SET(T,that.T);
|
||||
REF_PTR_SET(SxT,that.SxT);
|
||||
|
||||
REF_PTR_SET(Diffuse,that.Diffuse);
|
||||
MeshGeometryClass::operator =(that);
|
||||
}
|
||||
return * this;
|
||||
}
|
||||
|
||||
|
||||
ShdSubMeshClass::~ShdSubMeshClass(void)
|
||||
{
|
||||
REF_PTR_RELEASE(Shader);
|
||||
for (int i=0;i<MAX_TEXTURE_STAGES;++i)
|
||||
{
|
||||
REF_PTR_RELEASE(UV[i]);
|
||||
}
|
||||
|
||||
REF_PTR_RELEASE(S);
|
||||
REF_PTR_RELEASE(T);
|
||||
REF_PTR_RELEASE(SxT);
|
||||
|
||||
REF_PTR_RELEASE(Diffuse);
|
||||
}
|
||||
|
||||
// The legacy renderer is FVF-based so we need to figure out what FVF format to use
|
||||
static unsigned Define_FVF(MeshModelClass* mmc,bool enable_lighting)
|
||||
{
|
||||
if (mmc->Get_Flag(MeshGeometryClass::SKIN)) {
|
||||
return dynamic_fvf_type;
|
||||
}
|
||||
if ((!!mmc->Get_Flag(MeshGeometryClass::SORT)) && WW3D::Is_Sorting_Enabled()) {
|
||||
return dynamic_fvf_type;
|
||||
}
|
||||
|
||||
unsigned fvf=D3DFVF_XYZ;
|
||||
|
||||
int tex_coord_count=mmc->Get_UV_Array_Count();
|
||||
|
||||
if (mmc->Get_Color_Array(0,false)) {
|
||||
fvf|=D3DFVF_DIFFUSE;
|
||||
}
|
||||
if (mmc->Get_Color_Array(1,false)) {
|
||||
fvf|=D3DFVF_SPECULAR;
|
||||
}
|
||||
|
||||
switch (tex_coord_count) {
|
||||
default:
|
||||
case 0:
|
||||
break;
|
||||
case 1: fvf|=D3DFVF_TEX1; break;
|
||||
case 2: fvf|=D3DFVF_TEX2; break;
|
||||
case 3: fvf|=D3DFVF_TEX3; break;
|
||||
case 4: fvf|=D3DFVF_TEX4; break;
|
||||
case 5: fvf|=D3DFVF_TEX5; break;
|
||||
case 6: fvf|=D3DFVF_TEX6; break;
|
||||
case 7: fvf|=D3DFVF_TEX7; break;
|
||||
case 8: fvf|=D3DFVF_TEX8; break;
|
||||
}
|
||||
|
||||
if (!mmc->Needs_Vertex_Normals()) { //enable_lighting || mmc->Get_Flag(MeshModelClass::PRELIT_MASK)) {
|
||||
return fvf;
|
||||
}
|
||||
|
||||
fvf|=D3DFVF_NORMAL; // Realtime-lit
|
||||
return fvf;
|
||||
}
|
||||
|
||||
|
||||
// The legacy renderer is FVF-based so we need to figure out what FVF format to use
|
||||
static unsigned Define_FVF(ShdSubMeshClass* ssm,bool enable_lighting)
|
||||
{
|
||||
if (ssm->Get_Flag(MeshGeometryClass::SKIN)) {
|
||||
return dynamic_fvf_type;
|
||||
}
|
||||
if ((!!ssm->Get_Flag(MeshGeometryClass::SORT)) && WW3D::Is_Sorting_Enabled()) {
|
||||
return dynamic_fvf_type;
|
||||
}
|
||||
|
||||
unsigned fvf=D3DFVF_XYZ;
|
||||
|
||||
int tex_coord_count=0;
|
||||
for (tex_coord_count=0;tex_coord_count < MeshMatDescClass::MAX_TEX_STAGES; tex_coord_count++) {
|
||||
if (ssm->Get_UV_Array(tex_coord_count) == NULL) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (ssm->Get_Diffuse_Array() != NULL) {
|
||||
fvf|=D3DFVF_DIFFUSE;
|
||||
}
|
||||
|
||||
switch (tex_coord_count) {
|
||||
default:
|
||||
case 0:
|
||||
break;
|
||||
case 1: fvf|=D3DFVF_TEX1; break;
|
||||
case 2: fvf|=D3DFVF_TEX2; break;
|
||||
case 3: fvf|=D3DFVF_TEX3; break;
|
||||
case 4: fvf|=D3DFVF_TEX4; break;
|
||||
case 5: fvf|=D3DFVF_TEX5; break;
|
||||
case 6: fvf|=D3DFVF_TEX6; break;
|
||||
case 7: fvf|=D3DFVF_TEX7; break;
|
||||
case 8: fvf|=D3DFVF_TEX8; break;
|
||||
}
|
||||
|
||||
if (ssm->Get_Vertex_Normal_Array() != NULL) {
|
||||
fvf|=D3DFVF_NORMAL; // Realtime-lit
|
||||
}
|
||||
|
||||
return fvf;
|
||||
}
|
||||
|
||||
|
||||
void ShdSubMeshClass::Init_From_Legacy_Mesh_Model(MeshModelClass* model,int first_polygon)
|
||||
{
|
||||
WWASSERT(first_polygon<model->Get_Polygon_Count());
|
||||
|
||||
Sorting=!!model->Get_Flag(MeshGeometryClass::SORT) && WW3D::Is_Sorting_Enabled();
|
||||
|
||||
int pass;
|
||||
|
||||
// Figure out how many polygons we can use
|
||||
int active_polygon_count=0;
|
||||
bool arrays_used=false;
|
||||
for (pass=0;pass<model->Get_Pass_Count() && !arrays_used;++pass) {
|
||||
if (model->Has_Shader_Array(pass) || model->Has_Material_Array(pass)) {
|
||||
arrays_used=true;
|
||||
break;
|
||||
}
|
||||
for (int stage=0;stage<MeshMatDescClass::MAX_TEX_STAGES;++stage) {
|
||||
TextureClass* texture=NULL;
|
||||
if (model->Has_Texture_Array(pass,stage)) {
|
||||
arrays_used=true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// If any arrays are used by the mesh, count how many polygons we have that share properties.
|
||||
if (arrays_used) {
|
||||
bool stop=false;
|
||||
active_polygon_count=0;
|
||||
for (int poly=first_polygon;poly<model->Get_Polygon_Count() && !stop;++poly) {
|
||||
for (pass=0;pass<model->Get_Pass_Count();++pass) {
|
||||
if (model->Has_Shader_Array(pass)) {
|
||||
if (model->Get_Shader(first_polygon,pass)!=model->Get_Shader(poly,pass)) {
|
||||
stop=true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (model->Has_Material_Array(pass)) {
|
||||
TriIndex first_tri=model->Get_Polygon_Array()[first_polygon];
|
||||
TriIndex cur_tri=model->Get_Polygon_Array()[poly];
|
||||
if (model->Peek_Material(first_tri[0],pass)!=model->Peek_Material(cur_tri[0],pass) ||
|
||||
model->Peek_Material(first_tri[1],pass)!=model->Peek_Material(cur_tri[1],pass) ||
|
||||
model->Peek_Material(first_tri[2],pass)!=model->Peek_Material(cur_tri[2],pass)) {
|
||||
stop=true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
for (int stage=0;stage<MeshMatDescClass::MAX_TEX_STAGES;++stage) {
|
||||
if (model->Has_Texture_Array(pass,stage)) {
|
||||
if (model->Peek_Texture(first_polygon,pass,stage)!=model->Peek_Texture(poly,pass,stage)) {
|
||||
stop=true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
active_polygon_count++;
|
||||
}
|
||||
}
|
||||
FirstVisiblePolygon=first_polygon;
|
||||
VisiblePolygonCount=active_polygon_count;
|
||||
if (FirstVisiblePolygon!=0 && VisiblePolygonCount==0) {
|
||||
VisiblePolygonCount=model->Get_Polygon_Count()-FirstVisiblePolygon;
|
||||
}
|
||||
WWASSERT(FirstVisiblePolygon+VisiblePolygonCount<=model->Get_Polygon_Count());
|
||||
|
||||
// Now that the definition is initialized, create a shader instance (there's really
|
||||
// only one def/instance pair with the legacy meshes, no optimization planned currently)
|
||||
ShdLegacyW3DDefClass* shader_def=NEW_REF( ShdLegacyW3DDefClass, () );
|
||||
Shader=shader_def->Create();
|
||||
REF_PTR_RELEASE(shader_def);
|
||||
|
||||
// Danger! We're assuming Shd6LegacyW3DClass is the only type created by legacy shader!!!
|
||||
((Shd6LegacyW3DClass*)Shader)->Set_FVF(Define_FVF(model,true));
|
||||
((Shd6LegacyW3DClass*)Shader)->Set_Pass_Count(model->Get_Pass_Count());
|
||||
|
||||
for (pass=0;pass<model->Get_Pass_Count();++pass) {
|
||||
ShaderClass legacy_shader=ShaderClass::_PresetOpaqueShader;
|
||||
if (model->Has_Shader_Array(pass)) {
|
||||
legacy_shader=model->Get_Shader(first_polygon,pass);
|
||||
}
|
||||
else {
|
||||
legacy_shader=model->Get_Single_Shader(pass);
|
||||
}
|
||||
|
||||
VertexMaterialClass* legacy_material=NULL;
|
||||
if (model->Has_Material_Array(pass)) {
|
||||
TriIndex first_tri=model->Get_Polygon_Array()[first_polygon];
|
||||
legacy_material=model->Get_Material(first_tri[0],pass);
|
||||
}
|
||||
else {
|
||||
legacy_material=model->Get_Single_Material(pass);
|
||||
}
|
||||
|
||||
for (int stage=0;stage<MeshMatDescClass::MAX_TEX_STAGES;++stage) {
|
||||
TextureClass* texture=NULL;
|
||||
if (model->Has_Texture_Array(pass,stage)) {
|
||||
texture=model->Get_Texture(first_polygon,pass,stage);
|
||||
}
|
||||
else {
|
||||
texture=model->Get_Single_Texture(pass,stage);
|
||||
}
|
||||
|
||||
if (texture) {
|
||||
// StringClass texture_name=texture->Get_Full_Path();
|
||||
// texture->Release_Ref();
|
||||
// shader_def->Set_Texture_Name(pass,stage,texture_name);
|
||||
((Shd6LegacyW3DClass*)Shader)->Set_Texture(pass,stage,texture);
|
||||
texture->Release_Ref();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
((Shd6LegacyW3DClass*)Shader)->Set_Shader(pass,legacy_shader);
|
||||
((Shd6LegacyW3DClass*)Shader)->Set_Material(pass,legacy_material);
|
||||
}
|
||||
|
||||
*(MeshGeometryClass*)this = *(MeshGeometryClass*)model;
|
||||
if (CullTree)
|
||||
CullTree->Set_Mesh(this);
|
||||
|
||||
// Copy texture coordinates
|
||||
int uv_array_count=model->Get_UV_Array_Count();
|
||||
WWASSERT(uv_array_count<=MAX_TEXTURE_STAGES);
|
||||
for (int uvi=0;uvi<uv_array_count;++uvi) {
|
||||
const Vector2 *uv=model->Get_UV_Array_By_Index(uvi);
|
||||
if (uv) {
|
||||
UV[uvi]=NEW_REF(ShareBufferClass<Vector2>,(model->Get_Vertex_Count(),"ShdSubMeshClass::UVCoords"));
|
||||
memcpy(UV[uvi]->Get_Array(),uv,sizeof(Vector2)*model->Get_Vertex_Count());
|
||||
}
|
||||
}
|
||||
|
||||
// Copy vertex color array
|
||||
const unsigned* diffuse=model->Get_DCG_Array(0);
|
||||
if (diffuse) {
|
||||
Diffuse=NEW_REF(ShareBufferClass<unsigned>,(model->Get_Vertex_Count(),"ShdSubMeshClass::Diffuse"));
|
||||
memcpy(Diffuse->Get_Array(),diffuse,sizeof(unsigned)*model->Get_Vertex_Count());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
WW3DErrorType ShdSubMeshClass::Load_W3D(ChunkLoadClass& cload)
|
||||
{
|
||||
// read header
|
||||
W3dShdSubMeshHeaderStruct hdr;
|
||||
cload.Open_Chunk();
|
||||
if
|
||||
(
|
||||
cload.Read
|
||||
(
|
||||
&hdr,
|
||||
sizeof(W3dShdSubMeshHeaderStruct)
|
||||
)!=sizeof(W3dShdSubMeshHeaderStruct)
|
||||
)
|
||||
{
|
||||
return WW3D_ERROR_LOAD_FAILED;
|
||||
}
|
||||
cload.Close_Chunk();
|
||||
|
||||
// process header
|
||||
PolyCount=hdr.NumTris;
|
||||
VertexCount=hdr.NumVertices;
|
||||
|
||||
if ((PolyCount!=0) && (VertexCount!=0))
|
||||
{
|
||||
Poly = NEW_REF(ShareBufferClass<TriIndex>,(PolyCount,"ShdSubMesh::Poly"));
|
||||
PolySurfaceType = NEW_REF(ShareBufferClass<uint8>,(PolyCount,"ShdSubMesh::PolySurfaceType"));
|
||||
Vertex = NEW_REF(ShareBufferClass<Vector3>,(VertexCount,"ShdSubMesh::Vertex"));
|
||||
|
||||
Poly->Clear();
|
||||
PolySurfaceType->Clear();
|
||||
Vertex->Clear();
|
||||
|
||||
#if (!OPTIMIZE_VNORM_RAM)
|
||||
VertexNorm =NEW_REF(ShareBufferClass<Vector3>,(VertexCount,"ShdSubMesh::VertexNorm"));
|
||||
VertexNorm->Clear();
|
||||
#endif
|
||||
}
|
||||
|
||||
BoundBoxMin.Set(hdr.BoxMin.X,hdr.BoxMin.Y,hdr.BoxMin.Z);
|
||||
BoundBoxMax.Set(hdr.BoxMax.X,hdr.BoxMax.Y,hdr.BoxMax.Z);
|
||||
BoundSphereCenter.Set(hdr.SphCenter.X,hdr.SphCenter.Y,hdr.SphCenter.Z);
|
||||
BoundSphereRadius=hdr.SphRadius;
|
||||
|
||||
read_chunks(cload);
|
||||
|
||||
if ((Shader->Peek_Definition() != NULL) && (Shader->Peek_Definition()->Get_Class_ID() == SHDDEF_CLASSID_LEGACYW3D)) {
|
||||
// Danger! We're assuming Shd6LegacyW3DClass is the only type created by legacy shader!!!
|
||||
Shd6LegacyW3DClass * legacy_shader = (Shd6LegacyW3DClass*)Shader;
|
||||
legacy_shader->Set_FVF(Define_FVF(this,true));
|
||||
if (!legacy_shader->Is_Opaque()) {
|
||||
Set_Flag(MeshGeometryClass::SORT,true);
|
||||
}
|
||||
}
|
||||
|
||||
return WW3D_ERROR_OK;
|
||||
}
|
||||
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdSubMeshClass::read_chunks -- read w3d chunks *
|
||||
* *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 5/21/2002 kjm : Created. *
|
||||
*=============================================================================================*/
|
||||
WW3DErrorType ShdSubMeshClass::read_chunks(ChunkLoadClass& cload)
|
||||
{
|
||||
// If there are no more chunks within the mesh chunk,
|
||||
// we are done.
|
||||
|
||||
while (cload.Open_Chunk())
|
||||
{
|
||||
// Process the chunk
|
||||
WW3DErrorType error=WW3D_ERROR_OK;
|
||||
|
||||
switch (cload.Cur_Chunk_ID())
|
||||
{
|
||||
case W3D_CHUNK_SHDSUBMESH_VERTICES : error=read_vertices(cload); break;
|
||||
case W3D_CHUNK_SHDSUBMESH_VERTEX_NORMALS : error=read_vertex_normals(cload); break;
|
||||
case W3D_CHUNK_SHDSUBMESH_UV0 : error=read_uv0(cload); break;
|
||||
case W3D_CHUNK_SHDSUBMESH_UV1 : error=read_uv1(cload); break;
|
||||
|
||||
case W3D_CHUNK_SHDSUBMESH_TANGENT_BASIS_S : error=read_tangent_basis_s(cload); break;
|
||||
case W3D_CHUNK_SHDSUBMESH_TANGENT_BASIS_T : error=read_tangent_basis_t(cload); break;
|
||||
case W3D_CHUNK_SHDSUBMESH_TANGENT_BASIS_SxT : error=read_tangent_basis_sxt(cload); break;
|
||||
|
||||
case W3D_CHUNK_SHDSUBMESH_TRIANGLES : error=read_triangles(cload); break;
|
||||
case W3D_CHUNK_SHDSUBMESH_VERTEX_SHADE_INDICES : error=read_vertex_shade_indices(cload); break;
|
||||
case W3D_CHUNK_SHDSUBMESH_SHADER : error=read_shader(cload); break;
|
||||
case W3D_CHUNK_SHDSUBMESH_VERTEX_INFLUENCES : error=read_vertex_influences(cload); break;
|
||||
default: break;
|
||||
}
|
||||
|
||||
cload.Close_Chunk();
|
||||
|
||||
if (error!=WW3D_ERROR_OK)
|
||||
{
|
||||
return error;
|
||||
}
|
||||
}
|
||||
|
||||
return WW3D_ERROR_OK;
|
||||
}
|
||||
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdSubMeshClass::read_vertices -- read the vertex chunk from a W3D file *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 5/21/2002 kjm : Created. *
|
||||
*=============================================================================================*/
|
||||
WW3DErrorType ShdSubMeshClass::read_vertices(ChunkLoadClass& cload)
|
||||
{
|
||||
W3dVectorStruct vert;
|
||||
Vector3* loc=Vertex->Get_Array();
|
||||
assert(loc);
|
||||
|
||||
for (int i=0; i<Get_Vertex_Count(); i++)
|
||||
{
|
||||
if (cload.Read(&vert,sizeof(W3dVectorStruct)) != sizeof(W3dVectorStruct))
|
||||
{
|
||||
return WW3D_ERROR_LOAD_FAILED;
|
||||
}
|
||||
|
||||
loc[i].X=vert.X;
|
||||
loc[i].Y=vert.Y;
|
||||
loc[i].Z=vert.Z;
|
||||
}
|
||||
|
||||
return WW3D_ERROR_OK;
|
||||
}
|
||||
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdSubMeshClass::read_vertex_normals -- read the vertex normals chunk from a w3d file *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 5/21/2002 kjm : Created. *
|
||||
*=============================================================================================*/
|
||||
WW3DErrorType ShdSubMeshClass::read_vertex_normals(ChunkLoadClass& cload)
|
||||
{
|
||||
W3dVectorStruct norm;
|
||||
Vector3 * mdlnorms=get_vert_normals();
|
||||
WWASSERT(mdlnorms);
|
||||
|
||||
for (int i=0; i<VertexCount; i++)
|
||||
{
|
||||
if (cload.Read(&norm,sizeof(W3dVectorStruct)) != sizeof(W3dVectorStruct))
|
||||
{
|
||||
return WW3D_ERROR_LOAD_FAILED;
|
||||
}
|
||||
|
||||
mdlnorms[i].Set(norm.X,norm.Y,norm.Z);
|
||||
}
|
||||
|
||||
return WW3D_ERROR_OK;
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdSubMeshClass::read_uv0 -- read the texture coords chunk from a w3d file *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 5/26/2002 kjm : Created. *
|
||||
*=============================================================================================*/
|
||||
WW3DErrorType ShdSubMeshClass::read_uv0(ChunkLoadClass& cload)
|
||||
{
|
||||
UV[0]=NEW_REF(ShareBufferClass<Vector2>,(VertexCount,"ShdSubMeshClass::UV"));
|
||||
UV[0]->Clear();
|
||||
|
||||
Vector2* uv=UV[0]->Get_Array();
|
||||
|
||||
for (int i=0; i<VertexCount; i++)
|
||||
{
|
||||
if
|
||||
(
|
||||
cload.Read
|
||||
(
|
||||
uv++,
|
||||
sizeof(Vector2)
|
||||
)!=sizeof(Vector2)
|
||||
)
|
||||
{
|
||||
return WW3D_ERROR_LOAD_FAILED;
|
||||
}
|
||||
}
|
||||
|
||||
return WW3D_ERROR_OK;
|
||||
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdSubMeshClass::read_uv1 -- read the texture coords chunk from a w3d file *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 5/26/2002 kjm : Created. *
|
||||
*=============================================================================================*/
|
||||
WW3DErrorType ShdSubMeshClass::read_uv1(ChunkLoadClass& cload)
|
||||
{
|
||||
UV[1]=NEW_REF(ShareBufferClass<Vector2>,(VertexCount,"ShdSubMeshClass::UV"));
|
||||
UV[1]->Clear();
|
||||
|
||||
Vector2* uv=UV[1]->Get_Array();
|
||||
|
||||
for (int i=0; i<VertexCount; i++)
|
||||
{
|
||||
if
|
||||
(
|
||||
cload.Read
|
||||
(
|
||||
uv++,
|
||||
sizeof(Vector2)
|
||||
)!=sizeof(Vector2)
|
||||
)
|
||||
{
|
||||
return WW3D_ERROR_LOAD_FAILED;
|
||||
}
|
||||
}
|
||||
|
||||
return WW3D_ERROR_OK;
|
||||
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdSubMeshClass::read_tangent_basis_s -- read the tangent basis chunk from a w3d file *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 5/26/2002 kjm : Created. *
|
||||
*=============================================================================================*/
|
||||
WW3DErrorType ShdSubMeshClass::read_tangent_basis_s(ChunkLoadClass& cload)
|
||||
{
|
||||
S=NEW_REF(ShareBufferClass<Vector3>,(VertexCount,"ShdSubMeshClass::S"));
|
||||
S->Clear();
|
||||
|
||||
Vector3* t=S->Get_Array();
|
||||
|
||||
for (int i=0; i<VertexCount; i++)
|
||||
{
|
||||
if
|
||||
(
|
||||
cload.Read
|
||||
(
|
||||
t++,
|
||||
sizeof(Vector3)
|
||||
)!=sizeof(Vector3)
|
||||
)
|
||||
{
|
||||
return WW3D_ERROR_LOAD_FAILED;
|
||||
}
|
||||
}
|
||||
|
||||
return WW3D_ERROR_OK;
|
||||
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdSubMeshClass::read_tangent_basis_t -- read the tangent basis chunk from a w3d file *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 5/26/2002 kjm : Created. *
|
||||
*=============================================================================================*/
|
||||
WW3DErrorType ShdSubMeshClass::read_tangent_basis_t(ChunkLoadClass& cload)
|
||||
{
|
||||
T=NEW_REF(ShareBufferClass<Vector3>,(VertexCount,"ShdSubMeshClass::T"));
|
||||
T->Clear();
|
||||
|
||||
Vector3* t=T->Get_Array();
|
||||
|
||||
for (int i=0; i<VertexCount; i++)
|
||||
{
|
||||
if
|
||||
(
|
||||
cload.Read
|
||||
(
|
||||
t++,
|
||||
sizeof(Vector3)
|
||||
)!=sizeof(Vector3)
|
||||
)
|
||||
{
|
||||
return WW3D_ERROR_LOAD_FAILED;
|
||||
}
|
||||
}
|
||||
|
||||
return WW3D_ERROR_OK;
|
||||
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdSubMeshClass::read_tangent_basis_sxt -- read the tangent basis chunk from a w3d file *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 5/26/2002 kjm : Created. *
|
||||
*=============================================================================================*/
|
||||
WW3DErrorType ShdSubMeshClass::read_tangent_basis_sxt(ChunkLoadClass& cload)
|
||||
{
|
||||
SxT=NEW_REF(ShareBufferClass<Vector3>,(VertexCount,"ShdSubMeshClass::SxT"));
|
||||
SxT->Clear();
|
||||
|
||||
Vector3* t=SxT->Get_Array();
|
||||
|
||||
for (int i=0; i<VertexCount; i++)
|
||||
{
|
||||
if
|
||||
(
|
||||
cload.Read
|
||||
(
|
||||
t++,
|
||||
sizeof(Vector3)
|
||||
)!=sizeof(Vector3)
|
||||
)
|
||||
{
|
||||
return WW3D_ERROR_LOAD_FAILED;
|
||||
}
|
||||
}
|
||||
|
||||
return WW3D_ERROR_OK;
|
||||
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdSubMeshClass::read_vertex_influences -- read the vertex bone links from a w3d file *
|
||||
* *
|
||||
* This is for WWSKin support, presumably when we implement HW skining this may become obsolete*
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 11/07/2002 gth: Created *
|
||||
*=============================================================================================*/
|
||||
WW3DErrorType ShdSubMeshClass::read_vertex_influences(ChunkLoadClass& cload)
|
||||
{
|
||||
uint16 * bone_links = get_bone_links();
|
||||
|
||||
for (int i=0; i<VertexCount; i++)
|
||||
{
|
||||
if
|
||||
(
|
||||
cload.Read
|
||||
(
|
||||
bone_links++,
|
||||
sizeof(uint8)
|
||||
)!=sizeof(uint8)
|
||||
)
|
||||
{
|
||||
return WW3D_ERROR_LOAD_FAILED;
|
||||
}
|
||||
}
|
||||
|
||||
Set_Flag(SKIN,true);
|
||||
|
||||
return WW3D_ERROR_OK;
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdSubMeshClass::read_triangles -- read the triangles chunk from a w3d file *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 5/21/2002 kjm : Created. *
|
||||
*=============================================================================================*/
|
||||
WW3DErrorType ShdSubMeshClass::read_triangles(ChunkLoadClass & cload)
|
||||
{
|
||||
unsigned short tri[3];
|
||||
|
||||
// cache pointers to various arrays in the surrender mesh
|
||||
TriIndex * vi = get_polys();
|
||||
Set_Flag(DIRTY_PLANES,false);
|
||||
// Vector4 * peq = get_planes();
|
||||
// uint8 * surface_types = Get_Poly_Surface_Type_Array();
|
||||
|
||||
// read in each polygon one by one
|
||||
for (int i=0; i<Get_Polygon_Count(); i++)
|
||||
{
|
||||
if
|
||||
(
|
||||
cload.Read
|
||||
(
|
||||
tri,
|
||||
sizeof(unsigned short)*3
|
||||
)!=sizeof(unsigned short)*3
|
||||
)
|
||||
{
|
||||
return WW3D_ERROR_LOAD_FAILED;
|
||||
}
|
||||
|
||||
// set the vertex indices
|
||||
vi[i].I = tri[0];
|
||||
vi[i].J = tri[1];
|
||||
vi[i].K = tri[2];
|
||||
|
||||
// set the normal
|
||||
/*peq[i].X = tri.Normal.X;
|
||||
peq[i].Y = tri.Normal.Y;
|
||||
peq[i].Z = tri.Normal.Z;
|
||||
peq[i].W = -tri.Dist;
|
||||
|
||||
// set the surface type
|
||||
WWASSERT(tri.Attributes < 256);
|
||||
surface_types[i] = (uint8)(tri.Attributes);*/
|
||||
}
|
||||
|
||||
return WW3D_ERROR_OK;
|
||||
}
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdSubMeshClass::read_vertex_shade_indices -- read the vertex shade indices chunk *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 5/21/2002 kjm : Created. *
|
||||
*=============================================================================================*/
|
||||
WW3DErrorType ShdSubMeshClass::read_vertex_shade_indices(ChunkLoadClass & cload)
|
||||
{
|
||||
uint32 * shade_index = get_shade_indices(true);
|
||||
uint32 si;
|
||||
|
||||
for (int i=0; i<Get_Vertex_Count(); i++)
|
||||
{
|
||||
if (cload.Read(&si,sizeof(uint32)) != sizeof(uint32))
|
||||
{
|
||||
return WW3D_ERROR_LOAD_FAILED;
|
||||
}
|
||||
shade_index[i] = si;
|
||||
}
|
||||
return WW3D_ERROR_OK;
|
||||
}
|
||||
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdSubMeshClass::read_shader -- read the shader chunk *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 5/21/2002 kjm : Created. *
|
||||
*=============================================================================================*/
|
||||
WW3DErrorType ShdSubMeshClass::read_shader(ChunkLoadClass& cload)
|
||||
{
|
||||
// load the shader definition
|
||||
ShdDefClass* shddef=NULL;
|
||||
|
||||
ShdDefManagerClass::Load_Shader(cload, &shddef);
|
||||
|
||||
// create the shader interface
|
||||
Shader=shddef->Create();
|
||||
|
||||
REF_PTR_RELEASE(shddef);
|
||||
return WW3D_ERROR_OK;
|
||||
}
|
||||
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdSubMesh::Get_Deformed_Vertices -- Gets the deformed vertices for a skin *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 3/4/2001 gth : Created. *
|
||||
*=============================================================================================*/
|
||||
void ShdSubMeshClass::Get_Deformed_Vertices(Vector3 *dst_vert, Vector3 *dst_norm, const HTreeClass* htree)
|
||||
{
|
||||
WWASSERT(Get_Flag(MeshGeometryClass::SKIN));
|
||||
WWASSERT(htree);
|
||||
get_deformed_vertices(dst_vert,dst_norm,htree);
|
||||
}
|
||||
|
||||
|
||||
/***********************************************************************************************
|
||||
* ShdSubMeshClass::Get_Deformed_Vertices -- Gets the deformed vertices for a skin *
|
||||
* *
|
||||
* INPUT: *
|
||||
* *
|
||||
* OUTPUT: *
|
||||
* *
|
||||
* WARNINGS: *
|
||||
* *
|
||||
* HISTORY: *
|
||||
* 3/4/2001 gth : Created. *
|
||||
*=============================================================================================*/
|
||||
void ShdSubMeshClass::Get_Deformed_Vertices(Vector3 *dst_vert,const HTreeClass* htree)
|
||||
{
|
||||
WWASSERT(Get_Flag(MeshGeometryClass::SKIN));
|
||||
WWASSERT(htree);
|
||||
|
||||
get_deformed_vertices(dst_vert,htree);
|
||||
}
|
||||
173
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdsubmesh.h
Normal file
173
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/shdsubmesh.h
Normal file
@@ -0,0 +1,173 @@
|
||||
/*
|
||||
** Command & Conquer Generals Zero Hour(tm)
|
||||
** Copyright 2025 Electronic Arts Inc.
|
||||
**
|
||||
** This program is free software: you can redistribute it and/or modify
|
||||
** it under the terms of the GNU General Public License as published by
|
||||
** the Free Software Foundation, either version 3 of the License, or
|
||||
** (at your option) any later version.
|
||||
**
|
||||
** This program is distributed in the hope that it will be useful,
|
||||
** but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
** GNU General Public License for more details.
|
||||
**
|
||||
** You should have received a copy of the GNU General Public License
|
||||
** along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/***********************************************************************************************
|
||||
*** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ***
|
||||
***********************************************************************************************
|
||||
* *
|
||||
* Project Name : WWShade *
|
||||
* *
|
||||
* $Archive:: wwshade/shdsubmesh.h $*
|
||||
* *
|
||||
* Org Author:: Jani P *
|
||||
* *
|
||||
* Author : Kenny Mitchell *
|
||||
* *
|
||||
* $Modtime:: 07/12/02 10:31a $*
|
||||
* *
|
||||
* $Revision:: 1 $*
|
||||
* *
|
||||
* 07/12/02 KM Removed legacy mesh conversion *
|
||||
*---------------------------------------------------------------------------------------------*
|
||||
*---------------------------------------------------------------------------------------------*/
|
||||
|
||||
#ifndef SHDSUBMESH_H
|
||||
#define SHDSUBMESH_H
|
||||
|
||||
#include "always.h"
|
||||
#include "meshgeometry.h"
|
||||
#include "shdinterface.h"
|
||||
#include "dx8wrapper.h"
|
||||
#include "sharebuf.h"
|
||||
|
||||
class DecalGeneratorClass;
|
||||
class ShdInterfaceClass;
|
||||
class RenderInfoClass;
|
||||
class MeshModelClass;
|
||||
class HTreeClass;
|
||||
|
||||
/**
|
||||
** ShdSubMeshClass - A single ShdMeshClass instance will contain one or more ShdSubMeshClass.
|
||||
** The "sub-mesh" is a collection of polygons who all use the same shader.
|
||||
*/
|
||||
class ShdSubMeshClass : public MeshGeometryClass
|
||||
{
|
||||
public:
|
||||
W3DMPO_GLUE(ShdSubMeshClass);
|
||||
|
||||
ShdSubMeshClass(void);
|
||||
ShdSubMeshClass(const ShdSubMeshClass & that);
|
||||
~ShdSubMeshClass(void);
|
||||
|
||||
ShdSubMeshClass & operator = (const ShdSubMeshClass & that);
|
||||
void Reset(int polycount,int vertcount);
|
||||
|
||||
// unsigned Get_Vertex_Stream_Count();
|
||||
// unsigned Get_Vertex_Size(unsigned stream);
|
||||
// void Copy_Vertex_Stream(unsigned stream, void* buffer);
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// Material interface, All of these functions call through to the current
|
||||
// material decription.
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
void Set_Shader(ShdInterfaceClass * shader) { REF_PTR_SET(Shader,shader); }
|
||||
ShdInterfaceClass * Peek_Shader(void) const { return Shader; }
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// Decal interface
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
void Create_Decal(DecalGeneratorClass * generator);
|
||||
void Delete_Decal(uint32 decal_id);
|
||||
|
||||
void Init_From_Legacy_Mesh_Model(MeshModelClass* model,int first_polygon);
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
// Load from a W3D File
|
||||
/////////////////////////////////////////////////////////////////////////////////////
|
||||
WW3DErrorType Load_W3D(ChunkLoadClass& cload);
|
||||
|
||||
const Vector2* Get_UV_Array(unsigned stage) { return UV[stage] ? UV[stage]->Get_Array() : NULL; }
|
||||
const unsigned* Get_Diffuse_Array() { return Diffuse ? Diffuse->Get_Array() : NULL; }
|
||||
const Vector3* Get_Tangent_Basis_S_Array() { return S ? S->Get_Array() : NULL; }
|
||||
const Vector3* Get_Tangent_Basis_T_Array() { return T ? T->Get_Array() : NULL; }
|
||||
const Vector3* Get_Tangent_Basis_SxT_Array() { return SxT ? SxT->Get_Array() : NULL; }
|
||||
|
||||
// First and last visible polygon. Default is both zero, which means that all polygons
|
||||
// are visible.
|
||||
int Get_First_Visible_Polygon() const { return FirstVisiblePolygon; }
|
||||
int Get_Visible_Polygon_Count() const { return VisiblePolygonCount; }
|
||||
bool Is_Sorting() const { return Sorting; }
|
||||
|
||||
void Get_Deformed_Vertices(Vector3 *dst_vert, Vector3 *dst_norm, const HTreeClass* htree);
|
||||
void Get_Deformed_Vertices(Vector3 *dst_vert, const HTreeClass* htree);
|
||||
|
||||
protected:
|
||||
ShareBufferClass<Vector2> * UV[MAX_TEXTURE_STAGES];
|
||||
ShareBufferClass<unsigned> * Diffuse;
|
||||
|
||||
ShareBufferClass<Vector3>* S;
|
||||
ShareBufferClass<Vector3>* T;
|
||||
ShareBufferClass<Vector3>* SxT;
|
||||
|
||||
int FirstVisiblePolygon;
|
||||
int VisiblePolygonCount;
|
||||
bool Sorting;
|
||||
|
||||
// MeshClass will set this for skins so that they can get the bone transforms
|
||||
// void Set_HTree(const HTreeClass * htree);
|
||||
|
||||
protected:
|
||||
// functions to compute the deformed vertices of skins.
|
||||
// Destination pointers MUST point to arrays large enough to hold all vertices
|
||||
// void get_deformed_vertices(Vector3 *dst_vert, Vector3 *dst_norm, const HTreeClass * htree);
|
||||
// void get_deformed_vertices(Vector3 *dst_vert, const HTreeClass * htree);
|
||||
// void get_deformed_screenspace_vertices(Vector4 *dst_vert,const RenderInfoClass & rinfo,const Matrix3D & mesh_tm,const HTreeClass * htree);
|
||||
|
||||
// loading
|
||||
WW3DErrorType read_chunks(ChunkLoadClass& cload);
|
||||
WW3DErrorType read_vertices(ChunkLoadClass& cload);
|
||||
WW3DErrorType read_vertex_normals(ChunkLoadClass& cload);
|
||||
|
||||
WW3DErrorType read_uv0(ChunkLoadClass& cload);
|
||||
WW3DErrorType read_uv1(ChunkLoadClass& cload);
|
||||
|
||||
WW3DErrorType read_tangent_basis_s(ChunkLoadClass& cload);
|
||||
WW3DErrorType read_tangent_basis_t(ChunkLoadClass& cload);
|
||||
WW3DErrorType read_tangent_basis_sxt(ChunkLoadClass& cload);
|
||||
WW3DErrorType read_vertex_influences(ChunkLoadClass& cload);
|
||||
|
||||
WW3DErrorType read_triangles(ChunkLoadClass& cload);
|
||||
WW3DErrorType read_vertex_shade_indices(ChunkLoadClass& cload);
|
||||
WW3DErrorType read_shader(ChunkLoadClass& cload);
|
||||
|
||||
// WW3DErrorType read_texcoords(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_materials(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_v2_materials(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_v3_materials(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_per_tri_materials(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_vertex_colors(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_material_info(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_shaders(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_vertex_materials(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_textures(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_material_pass(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_vertex_material_ids(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_shader_ids(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_scg(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_dig(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_dcg(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_texture_stage(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_texture_ids(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_stage_texcoords(ChunkLoadClass & cload,ShdMeshLoadContextClass * context);
|
||||
// WW3DErrorType read_per_face_texcoord_ids (ChunkLoadClass &cload, ShdMeshLoadContextClass *context);
|
||||
// WW3DErrorType read_prelit_material (ChunkLoadClass &cload, ShdMeshLoadContextClass *context);
|
||||
|
||||
ShdInterfaceClass * Shader;
|
||||
};
|
||||
|
||||
#endif //SHDSUBMESH_H
|
||||
1214
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/wwshade.dsp
Normal file
1214
GeneralsMD/Code/Libraries/Source/WWVegas/wwshade/wwshade.dsp
Normal file
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user