normalmap for animate models

Post those lines of code you feel like sharing or find what you require for your project here; or simply use them as tutorials.
Post Reply
_TamerLAN_
Posts: 2
Joined: Sun May 04, 2008 9:54 am

normalmap for animate models

Post by _TamerLAN_ »

Hi, I am from Ukraina. I like irrlicht and i have some questions:
recently, I read some about normalmap for animate models, and this code

#include <irrlicht.h>

// --------------------------------------------------------------------------

using namespace irr;
using namespace core;
using namespace scene;
using namespace video;
using namespace io;
using namespace gui;



IrrlichtDevice *device;


const stringc vertBumpShader =
"uniform vec3 fvLightPosition1;"
"uniform vec3 fvLightPosition2;"
"uniform vec3 fvLightPosition3;"
"uniform vec3 fvLightPosition4;"
""
"uniform float fLightStrength1;"
"uniform float fLightStrength2;"
"uniform float fLightStrength3;"
"uniform float fLightStrength4;"
""
"uniform mat4 matWorldInverse;"
""
"varying vec2 Texcoord;"
"varying vec3 ViewDirection;"
"varying vec3 LightDirection1;"
"varying vec3 LightDirection2;"
"varying vec3 LightDirection3;"
"varying vec3 LightDirection4;"
"varying vec4 LightDistMultiplier;"
""
"float getLengthSQR (vec3 vec)"
"{"
"return(vec.x*vec.x+vec.y*vec.y+vec.z*vec.z);"
"}"
""
"void main( void )"
"{"
""
" mat4 LightTransform= gl_ModelViewMatrix;"
" LightTransform=LightTransform*matWorldInverse;"
""
" gl_Position = ftransform();"
" Texcoord = gl_MultiTexCoord0.xy;"
""
" vec4 fvObjectPosition = gl_ModelViewMatrix * gl_Vertex;"
" vec4 fvLightPos1 = LightTransform * vec4(fvLightPosition1,1.0);"
" vec4 fvLightPos2 = LightTransform * vec4(fvLightPosition2,1.0);"
" vec4 fvLightPos3 = LightTransform * vec4(fvLightPosition3,1.0);"
" vec4 fvLightPos4 = LightTransform * vec4(fvLightPosition4,1.0);"
""
" vec3 fvViewDirection = - fvObjectPosition.xyz;"
""
" vec3 fvLightDirection1 = (fvLightPos1.xyz - fvObjectPosition.xyz);"
" vec3 fvLightDirection2 = (fvLightPos2.xyz - fvObjectPosition.xyz);"
" vec3 fvLightDirection3 = (fvLightPos3.xyz - fvObjectPosition.xyz);"
" vec3 fvLightDirection4 = (fvLightPos4.xyz - fvObjectPosition.xyz);"
""
" LightDistMultiplier[0]=1.0/(getLengthSQR (fvLightDirection1)/(fLightStrength1*10000.0));"
" LightDistMultiplier[1]=1.0/(getLengthSQR (fvLightDirection2)/(fLightStrength2*10000.0));"
" LightDistMultiplier[2]=1.0/(getLengthSQR (fvLightDirection3)/(fLightStrength3*10000.0));"
" LightDistMultiplier[3]=1.0/(getLengthSQR (fvLightDirection4)/(fLightStrength4*10000.0));"
""
" vec3 fvNormal = gl_NormalMatrix * gl_Normal;"
""
" vec3 fvTangent = -vec3(abs(gl_Normal.y) + abs(gl_Normal.z), abs(gl_Normal.x), 0);"
" vec3 fvBinormal =cross(fvTangent,gl_Normal); "
" fvTangent=gl_NormalMatrix*cross(fvBinormal,gl_Normal);"
" fvBinormal=gl_NormalMatrix*fvBinormal;"
""
""
" ViewDirection.x = dot( fvTangent, fvViewDirection );"
" ViewDirection.y = dot( fvBinormal, fvViewDirection );"
" ViewDirection.z = dot( fvNormal, fvViewDirection );"
""
" LightDirection1.x = dot( fvTangent, fvLightDirection1.xyz );"
" LightDirection1.y = dot( fvBinormal, fvLightDirection1.xyz );"
" LightDirection1.z = dot( fvNormal, fvLightDirection1.xyz );"
""
" LightDirection2.x = dot( fvTangent, fvLightDirection2.xyz );"
" LightDirection2.y = dot( fvBinormal, fvLightDirection2.xyz );"
" LightDirection2.z = dot( fvNormal, fvLightDirection2.xyz );"
""
" LightDirection3.x = dot( fvTangent, fvLightDirection3.xyz );"
" LightDirection3.y = dot( fvBinormal, fvLightDirection3.xyz );"
" LightDirection3.z = dot( fvNormal, fvLightDirection3.xyz );"
""
" LightDirection4.x = dot( fvTangent, fvLightDirection4.xyz );"
" LightDirection4.y = dot( fvBinormal, fvLightDirection4.xyz );"
" LightDirection4.z = dot( fvNormal, fvLightDirection4.xyz );"
""
"}";
// --------------------------------------------------------------------------

// OpenGL Fragment Program 1.1
const stringc fragBumpShader =
"uniform vec4 fvAmbient;"
"uniform vec4 fvLight1Color;"
"uniform vec4 fvLight2Color;"
"uniform vec4 fvLight3Color;"
"uniform vec4 fvLight4Color;"

"uniform float fSpecularPower;"
"uniform float fSpecularStrength;"
"uniform float fBumpStrength;"

"uniform sampler2D baseMap;"
"uniform sampler2D bumpMap;"

"varying vec2 Texcoord;"
"varying vec3 ViewDirection;"
"varying vec3 LightDirection1;"
"varying vec3 LightDirection2;"
"varying vec3 LightDirection3;"
"varying vec3 LightDirection4;"
"varying vec4 LightDistMultiplier;"

"void main( void )"
"{"

" vec3 fvLightDirection1 = normalize( LightDirection1 );"
" vec3 fvLightDirection2 = normalize( LightDirection2 );"
" vec3 fvLightDirection3 = normalize( LightDirection3 );"
" vec3 fvLightDirection4 = normalize( LightDirection4 );"

" vec3 fvNormal = texture2D( bumpMap, Texcoord ).yxz;"
" fvNormal.xy*=2.0;"
" fvNormal.xy-=1.0;"

" fvNormal=(vec3(0.0,0.0,1.0)-fvNormal)*fBumpStrength+fvNormal;"

" fvNormal=normalize(fvNormal);"

" float fNDotL1 = max(dot(fvNormal, fvLightDirection1),0.0)-0.1; "
" float fNDotL2 = max(dot(fvNormal, fvLightDirection2),0.0)-0.1; "
" float fNDotL3 = max(dot(fvNormal, fvLightDirection3),0.0)-0.1; "
" float fNDotL4 = max(dot(fvNormal, fvLightDirection4),0.0)-0.1; "

" vec3 fvReflection1 = normalize( ( ( 2.0 * fvNormal ) ) - fvLightDirection1 ); "
" vec3 fvReflection2 = normalize( ( ( 2.0 * fvNormal ) ) - fvLightDirection2 ); "
" vec3 fvReflection3 = normalize( ( ( 2.0 * fvNormal ) ) - fvLightDirection3 ); "
" vec3 fvReflection4 = normalize( ( ( 2.0 * fvNormal ) ) - fvLightDirection4 ); "

" vec3 fvViewDirection = normalize( ViewDirection );"

" float fRDotV1 = max( 0.0, dot( fvReflection1, fvViewDirection ) );"
" float fRDotV2 = max( 0.0, dot( fvReflection2, fvViewDirection ) );"
" float fRDotV3 = max( 0.0, dot( fvReflection3, fvViewDirection ) );"
" float fRDotV4 = max( 0.0, dot( fvReflection4, fvViewDirection ) );"

" vec4 fvBaseColor = texture2D( baseMap, Texcoord );"

" vec4 fvTotalAmbient = fvAmbient * fvBaseColor; "

" vec4 fvTotalDiffuse = fvLight1Color * fNDotL1* fvBaseColor*LightDistMultiplier[0]; "
" vec4 fvTotalSpecular = fNDotL1*fvLight1Color * ( pow( fRDotV1, fSpecularPower ) )*LightDistMultiplier[0];"

" fvTotalDiffuse += fvLight2Color * fNDotL2* fvBaseColor*LightDistMultiplier[1]; "
" fvTotalSpecular += fNDotL2*fvLight2Color * ( pow( fRDotV2, fSpecularPower ) )*LightDistMultiplier[1]; "

" fvTotalDiffuse += fvLight3Color * fNDotL3* fvBaseColor*LightDistMultiplier[2]; "
" fvTotalSpecular += fNDotL3*fvLight3Color * ( pow( fRDotV3, fSpecularPower ) )*LightDistMultiplier[2]; "

" fvTotalDiffuse += fvLight4Color * fNDotL4* fvBaseColor*LightDistMultiplier[3]; "
" fvTotalSpecular += fNDotL4*fvLight4Color * ( pow( fRDotV4, fSpecularPower ) )*LightDistMultiplier[3]; "

" vec4 color=( fvTotalAmbient + fvTotalDiffuse+ (fvTotalSpecular*fSpecularStrength));"
" if(color.r>1.0){color.gb+=color.r-1.0;}"
" if(color.g>1.0){color.rb+=color.g-1.0;}"
" if(color.b>1.0){color.rg+=color.b-1.0;}"
" gl_FragColor = color;"

"}"
;

class Shader_Bump_callback: public video::IShaderConstantSetCallBack
{
public:
float fLightStrength[4]; //you know I=1/r??? i changed it to I=1/(r?/fLightStrength) for better results
vector3df fvLightPosition[4]; //the light positions
SColorf fvLightColor[4];
SColorf fvAmbient;
float fSpecularPower; // S=pow(fDiffuseIntensity,fSpecularPower)*fSpecularStrength;
float fSpecularStrength;// will result in less glossing surfaces
float fBumpStrength; //strength of the bumpmapping.. higher values will result in more "bumpy" surfaces

virtual void OnSetConstants(video::IMaterialRendererServices* services, s32 userData)
{

int var0=0;
services->setPixelShaderConstant("baseMap", (float*)(&var0), 1); //the colormap
int var1=1;
services->setPixelShaderConstant("bumpMap", (float*)(&var1), 1); //the normalmap

core::matrix4 invWorld = services->getVideoDriver()->getTransform(video::ETS_WORLD);
invWorld.makeInverse();
services->setPixelShaderConstant("matWorldInverse", (float*)(&invWorld), 16);

services->setPixelShaderConstant("fLightStrength1", (float*)(&fLightStrength[0]), 1);
services->setPixelShaderConstant("fLightStrength2", (float*)(&fLightStrength[1]), 1);
services->setPixelShaderConstant("fLightStrength3", (float*)(&fLightStrength[2]), 1);
services->setPixelShaderConstant("fLightStrength4", (float*)(&fLightStrength[3]), 1);

services->setPixelShaderConstant("fvLightPosition1", (float*)(&fvLightPosition[0]), 3);
services->setPixelShaderConstant("fvLightPosition2", (float*)(&fvLightPosition[1]), 3);
services->setPixelShaderConstant("fvLightPosition3", (float*)(&fvLightPosition[2]), 3);
services->setPixelShaderConstant("fvLightPosition4", (float*)(&fvLightPosition[3]), 3);

services->setPixelShaderConstant("fvAmbient", (float*)(&fvAmbient), 4);
services->setPixelShaderConstant("fvLight1Color", (float*)(&fvLightColor[0]), 4);
services->setPixelShaderConstant("fvLight2Color", (float*)(&fvLightColor[1]), 4);
services->setPixelShaderConstant("fvLight3Color", (float*)(&fvLightColor[2]), 4);
services->setPixelShaderConstant("fvLight4Color", (float*)(&fvLightColor[3]), 4);

services->setPixelShaderConstant("fSpecularPower", (float*)(&fSpecularPower), 1);
services->setPixelShaderConstant("fSpecularStrength", (float*)(&fSpecularStrength), 1);
services->setPixelShaderConstant("fBumpStrength", (float*)(&fBumpStrength), 1);


}
};




// --------------------------------------------------------------------------

#pragma comment(lib, "Irrlicht.lib")


int main()
{
// Create device
video::E_DRIVER_TYPE driverType = video::EDT_OPENGL;

device = createDevice(driverType, dimension2di(800, 600), 32, false, false, false, 0);
if (!device) {
printf("Error creating Irrlicht device\n");
return 0;
}

// Obtain device internals
IVideoDriver* driver = device->getVideoDriver();
ISceneManager* smgr = device->getSceneManager();
// Set a window caption
device->setWindowCaption(L"NormalMapShader - Irrlicht Engine Demo");

// Create GLSL shaders
video::IGPUProgrammingServices* gpu = driver->getGPUProgrammingServices();
s32 mtlToonShader = video::EMT_SOLID; // Fallback material type
bool bCanDoGLSL_1_1 = false;
if (gpu && (driverType == video::EDT_OPENGL)) {
bCanDoGLSL_1_1 = true; // provisionally accept
if (!driver->queryFeature(video::EVDF_ARB_FRAGMENT_PROGRAM_1)) {
printf("queryFeature(video::EVDF_ARB_FRAGMENT_PROGRAM_1) failed\n");
bCanDoGLSL_1_1 = false;
}
if (!driver->queryFeature(video::EVDF_ARB_VERTEX_PROGRAM_1)) {
printf("queryFeature(video::EVDF_ARB_VERTEX_PROGRAM_1) failed\n");
bCanDoGLSL_1_1 = false;
}
}

if (bCanDoGLSL_1_1) {
Shader_Bump_callback *callback= new Shader_Bump_callback;

callback->fBumpStrength=4;
callback->fSpecularStrength=0.9;
callback->fSpecularPower=20;

callback->fvAmbient=SColorf(0.02,0.02,0.02);

callback->fLightStrength[0]=1;
callback->fvLightColor[0]=SColorf(1.00,0.52,0.31);
callback->fvLightPosition[0]=vector3df(100,-10,0);

callback->fLightStrength[1]=1;
callback->fvLightColor[1]=SColorf(0.31,0.55,1.0);
callback->fvLightPosition[1]=vector3df(-100,10,0);


mtlToonShader = gpu->addHighLevelShaderMaterial(
vertBumpShader.c_str(), "main", video::EVST_VS_1_1,
fragBumpShader.c_str(), "main", video::EPST_PS_1_1,
callback, video::EMT_SOLID);
} else {
// This demo is for OpenGL!
printf("This demo requires OpenGL with GLSL High-Level shaders\n");
mtlToonShader = video::EMT_SOLID;
}

// Add an animated mesh
IAnimatedMesh* mesh = smgr->getMesh("dwarf.x");


ISceneNode* node = smgr->addAnimatedMeshSceneNode(mesh);
if (node)
{
node->setMaterialFlag(EMF_LIGHTING, false);
node->setMaterialTexture( 0, driver->getTexture("Fieldstone.tga") );
node->setMaterialTexture( 1, driver->getTexture("Fieldstonebumpdot3.tga") );
node->setMaterialType((video::E_MATERIAL_TYPE)mtlToonShader); // Override material type
}

// Add a viewing camera
smgr->addCameraSceneNodeFPS();

// Main rendering loop
while(device->run())
{
vector3df rot=node->getRotation();
rot.Y+=0.1;
node->setRotation(rot);
driver->beginScene(true, true, SColor(0,0,0,0));
smgr->drawAll();
driver->endScene();
}

device->drop();

// Done
return 0;
}


this code is very good work, but I want do this in video::E_DRIVER_TYPE driverType = video::EDT_DIRECT3D9 ;, because my project use DirectX9...
If anybody knows how do this in DirectX9 mode, write me please...
TheGameMaker
Posts: 275
Joined: Fri May 12, 2006 6:37 pm
Location: Germany

Post by TheGameMaker »

you have to convert the GLSL shader to a HLSL shader..
GLSL ist the shaderlanguage of openGL.. hence you only can use it with opengl... :wink: so what you have to do is learning HLSL shader language and convert it..
BlindSide
Admin
Posts: 2821
Joined: Thu Dec 08, 2005 9:09 am
Location: NZ!

Post by BlindSide »

It's possible to use ordinary Irrlicht normal mapping on animated meshes ever since SkinnedMesh was introduced in version 1.4. You just have to convert the mesh to tangents using "irr::scene::ISkinnedMesh::convertMeshToTangents()". (First you must load an animated mesh and cast it to a skinned mesh eg.:

Code: Select all

IAnimatedMesh* mesh = smgr->getMesh("mymesh.x");
((ISkinnedMesh*)mesh)->convertMeshToTangents();
Cheers
ShadowMapping for Irrlicht!: Get it here
Need help? Come on the IRC!: #irrlicht on irc://irc.freenode.net
Post Reply