-
Notifications
You must be signed in to change notification settings - Fork 11
Materials and Compiled States (.smt_t and .rw4)
Materials define the way an object is rendered in the game. All models have at least one material that will tell the renderer which texture, shader, color, etc to use when rendering.
Materials are actually made of:
- One or multiple compiled states. Compiled states contain most information about the material; usually only one is used, we don't knw what multiple states might be used for.
- Textures
You can find materials in two places:
- Inside
.rw4
models. There can be more than one material there, and they are calledCompiledStates
. - In
.smt_t
files, which are part of material packs. Material packs contain all those general materials that are not used in an specific model (for example, water, creature, etc)
Material packs are stored in the materials_compiled_states_link~
(0x40212000) folder, in a .smt
file; when unpacked, they finish with the extension .smt_t
. It is possible to create your custom material packs. You can have your own MyMaterials.smt.unpacked
folder (where MyMaterials is whatever name you want, unique to your mod) containing material files.
A .smt_t file contains one or multiple compiled states that will be used by your material. Then, it contains only one material
instruction that follows this structure:
material ID -states stateNames... -textures textureIDs
-
ID
is the exported name of your shader. That will be the ID you have to reference to use this material. - At
states
you must specify the names of the compiled states in the file that the material will use. -
textures
is optional, you can specify the folder and file name (with no extension) of any textures this material requires.
Example of a .smt_t
file:
Compiled states are defined with the compiledState
block, they take a name as a parameter. The name of the state only affects the file and so it's not really important. They can have the following attributes:
shaderID id
Sets the shader that wil be used to render this material. This is the ID of either a Standard Shader or a Shader Builder.
materialColor colorRGBA
The color of the material, with opacity; when defined, it can be used in shaders with the materialColor
shader data. Takes an RGBA ArgScript Color.
ambientColor colorRGB
The ambient color of the material; when defined, it can be used in shaders with the ambientColor
shader data. Takes an RGB ArgScript Color.
primitiveType value
Determines the type of primitive used in the model data, generally you don't need to touch this. The value is any of the D3DPRIMITIVETYPE enumeration.
flags1 value
Unknown usage.
flags3 value
Unknown usage.
unkData3 17values
Unknown usage, maybe related with textures. Takes 17 boolean values.
shaderData dataName data...
Compiled states can define Shader Data that will be used when rendering the material. You must specify the name of the data (sometimes it's an hexadecimal number) and then all the values it takes. Unfortunately, values can only be displayed as integers so if you, for example, want to use a floating point number, you will need to convert it beforehand. You can use this instruction multiple times to define more than one data.
Render States are different variables that affect the rendering pipeline. In a material you can specify multiple render states with this instruction:
renderState name value
You must specify the name, which is any in the D3DRENDERSTATETYPE enumeration. The type of value expected depends on the specific render state.
Rende states can be grouped inside a statesGroup
block, which takes an integer as parameter. For example:
statesGroup 0
renderState D3DRS_SRCBLEND D3DBLEND_SRCALPHA
renderState D3DRS_DESTBLEND D3DBLEND_INVSRCALPHA
renderState D3DRS_ALPHABLENDENABLE TRUE
end
Materials can use textures, those are defined through texture slots. Keep in mind, a slot means that a texture could be used there, but it's not the texture itself. This means taht you can't have two texture slots without assigning them any texture, because maybe the game code will add that texture when using the material.
Texture slots are defined using the textureSlot
block, which takes the slot index (starting at 0) as parameter. The block can have the following attributes:
samplerState name value
You must specify the name, which is any in the D3DSAMPLERSTATETYPE enumeration. The type of value expected depends on the specific render state.
stageState name value
You must specify the name, which is any in the D3DTEXTURESTAGESTATETYPE enumeration. The type of value expected depends on the specific render state.
raster objectIndex
Only available in the materials of a .rw4
model. This attribute holds the index of the raster object used as a texture.
Example of two texture slots in a .smt_t
file:
textureSlot 0
samplerState D3DSAMP_ADDRESSU D3DTADDRESS_BORDER
samplerState D3DSAMP_ADDRESSV D3DTADDRESS_BORDER
samplerState D3DSAMP_MAGFILTER D3DTEXF_LINEAR
samplerState D3DSAMP_MINFILTER D3DTEXF_LINEAR
end
textureSlot 1
samplerState D3DSAMP_ADDRESSU D3DTADDRESS_BORDER
samplerState D3DSAMP_ADDRESSV D3DTADDRESS_BORDER
samplerState D3DSAMP_MAGFILTER D3DTEXF_LINEAR
samplerState D3DSAMP_MINFILTER D3DTEXF_LINEAR
end
The vertexDescription
lock is really important as it defines the elements (e.g. position, normals, UV coordinates, vertex colors, etc) that vertices in the models that use this material must use. Therefore, the vertex description is used to read data from vertices and defines the data that is sent to the shaders.
The vertex description block is made up of multiple element instructions (order is important), which follow this structure:
element type usage shaderUsage -usageIndex int -stream int -method D3DDECLMETHOD
Every attribute must define the shaderUsage
and the D3DDECLTYPE of the element. The shader usage is one of the values allowed in the vertex fragments input.
Optionally you can also specify the -method
and -stream
, although these are rarely used.
Example of a vertex description:
vertexDescription
element position D3DDECLTYPE_FLOAT3
element texcoord0 D3DDECLTYPE_FLOAT2
element texcoord1 D3DDECLTYPE_FLOAT3
element color D3DDECLTYPE_D3DCOLOR
end