Game Development Community

Help] Shader introduction

by Alex Huck · in Torque Game Engine Advanced · 11/17/2006 (1:09 pm) · 3 replies

Hi, can someone please get me started on Torque Shader Engines shader programming? I have a few questions that will give me a real shot in the arm if I can understand better.
I suppose the easiest way to get most of my questions out of the way would be to take a file from the TSE/shaders folder, and put my own questions commented in. I'll use WaterReflectRefractP and WaterReflectRefractV.hlsl for an example

First off, correct my understanding: The way I see it, a Vertex shader is code which modifies the way a shape is rendered based on attributes taken from the shape its self. (i.e, if the viewing angle of the shape is 60 degrees color that area red)

Whereas a Pixel Shader is code that changes render information based in pixel info, (i.e, inverse the color of each pixel of a texture, red becomes blue; white, black)

Correct so far?

On to the file from example/shaders/water/waterReflectRefractP(and V).hlsl

Continued in next post, max post length is 4096

#1
11/17/2006 (1:09 pm)
Vertex shader:

//*****************************************************************************
// TSE -- water shader                                               
//*****************************************************************************
//-----------------------------------------------------------------------------
// Structures                                                                  
//-----------------------------------------------------------------------------
#define IN_HLSL
#include "..\shdrConsts.h"

struct VertData
{
   float4 position        : POSITION; // Question: Is this the position of where the water block is? 
                                                      //   If so, what is a complete listing of such variables which are 
                                                      //   taken from the game itself?
};


struct ConnectData
{
   float4 hpos             : POSITION; // hPos = Horizontal position?
   float4 texCoord         : TEXCOORD0;
   float3 lightVec         : TEXCOORD1;
   float2 texCoord2        : TEXCOORD2;
   float4 texCoord3        : TEXCOORD3; // Question: All of these TEXCOORDS I don't understand Texture 
                                                             //   Coordinates of what?
   float2 fogCoord         : TEXCOORD4;
   float3 pos              : TEXCOORD6;
   float3 eyePos           : TEXCOORD7;
};


//-----------------------------------------------------------------------------
// Main                                                                        
//-----------------------------------------------------------------------------
ConnectData main( VertData IN,
                  uniform float4x4 modelview       : register(C0),
                  uniform float3x3 cubeTrans       : register(VC_CUBE_TRANS),
                  uniform float3   cubeEyePos      : register(VC_CUBE_EYE_POS),
                  uniform float3   eyePos          : register(VC_EYE_POS),
                  uniform float3   lightVec        : register(VC_LIGHT_DIR1),
                  uniform float3   fogData         : register(VC_FOGDATA),
                  uniform float4x4 objTrans        : register(VC_OBJ_TRANS),
                  uniform float4   waveData[4]     : register(C50),
                  uniform float4   timeData        : register(C54),
                  uniform float2   waveTexScale[4] : register(C55),
                  uniform float    reflectTexSize  : register(C59)
)
// Question: All of the above (ConnectData) I assume is the game, connecting shader data, with data taken 
//  from the game? If so, what does the register function do, What arguments does it take (What does C0, 
//  C54,55,and59 mean?

{
   ConnectData OUT; // Telling it to output this data back to the game?
   OUT.hpos = mul(modelview, IN.position); // Question: Mul? Mule?

   // set up tex coordinates for the 3 interacting normal maps
   OUT.texCoord.xy = IN.position.xy * waveTexScale[0];
   OUT.texCoord.xy += waveData[0].xy * timeData[0];

   OUT.texCoord.zw = IN.position.xy * waveTexScale[1];
   OUT.texCoord.zw += waveData[1].xy * timeData[1];

   OUT.texCoord2.xy = IN.position.xy * waveTexScale[2];
   OUT.texCoord2.xy += waveData[2].xy * timeData[2];

   // send misc data to pixel shaders
   OUT.pos = IN.position;
   OUT.eyePos = eyePos;
   OUT.lightVec = -lightVec;
   
   // use projection matrix for reflection / refraction texture coords
   float4x4 texGen = { 0.5,  0.0,  0.0,  0.5 + 0.5 / reflectTexSize, // Question: What is a float4x4 datatype?
                       0.0, -0.5,  0.0,  0.5 + 1.0 / reflectTexSize,
                       0.0,  0.0,  1.0,  0.0,
                       0.0,  0.0,  0.0,  1.0 };

   OUT.texCoord3 = mul( texGen, OUT.hpos );


   // fog setup - may want to make this per-pixel
   float3 transPos = mul( objTrans, IN.position );
   OUT.fogCoord.x = 1.0 - ( distance( IN.position, eyePos ) / fogData.z );
   OUT.fogCoord.y = (transPos.z - fogData.x) * fogData.y;
   
   return OUT;

}

Only questions for the Pixel side is what is Lerp, looked it up (Linear interpolation?) And couldn't find any good laymans explainations

Also from the pixel side; What is Fragout, Fragment shader output? If so is a fragment shader A type that means it's a small part of a larger group? I notice the water shader has a variety of shaders applied to it, when a shape has so many shaders are the individual shaders called fragments?

Any other Useful information I should know about how Torque handles shaders is also greatly appreciated

Many thanks,
Alex huck
#2
11/20/2006 (8:46 pm)
Within TSE is not exactly the best of places to be learning about shader programming... ;-)

A couple quick answers -- a "lerp" is a linear interpolation, which is essentially computing a value between two other values. TSE uses procedural shaders, so individual shaders are combined according to attributes set in the materials.cs files; however, "Fragout" in this context refers to the output of a pixel shader, aka fragment shader, specifically. (Check out what appears in the shaders/procedural directory.) The C50, etc. tokens are references to GPU register constants. Some of these registers have standard uses withing TSE, as declared in the shdrConsts.h file.

I recommend looking at either FX Composer, RenderMonkey, or both, for a place to tinker with shader technology. There is also a general overview of shaders at Wikipedia.

Hopefully the above can get you started. Good luck! ;-)

Tom
#3
11/20/2006 (10:02 pm)
This is a fantastic resource. I'd also recommend buying some of the ShaderX books.