本篇是
创建游戏内核(6)的续篇,其中涉及到的材质知识请参阅
D3D
中的材质和光照处理。
材质和MATERIAL
通过改变绘制表面的颜色值,就可以改变渲染对象的外观,MATERIAL类可以使改变材质颜色值变得更容易一些。
来看看MATERIAL类的定义:
//================================================================================
// Defines for class MATERIAL.
//================================================================================
class MATERIAL
{
protected:
D3DMATERIAL9 _material;
public:
MATERIAL();
D3DMATERIAL9* Get_Material();
void Set_Diffuse_Color(unsigned char red, unsigned char green, unsigned char blue);
void Get_Diffuse_Color(unsigned char* red, unsigned char* green, unsigned char* blue);
void Set_Ambient_Color(unsigned char red, unsigned char green, unsigned char blue);
void Get_Ambient_Color(unsigned char* red, unsigned char* green, unsigned char* blue);
void Set_Specular_Color(unsigned char red, unsigned char green, unsigned char blue);
void Get_Specular_Color(unsigned char* red, unsigned char* green, unsigned char* blue);
void Set_Emissive_Color(unsigned char red, unsigned char green, unsigned char blue);
void Get_Emissive_Color(unsigned char* red, unsigned char* green, unsigned char* blue);
void Set_Power(float power);
float Get_Power();
};
接着是类MATERIAL的实现:
//-------------------------------------------------------------------
// Constructor, set a default material (white).
//-------------------------------------------------------------------
MATERIAL::MATERIAL()
{
ZeroMemory(&_material, sizeof(D3DMATERIAL9));
Set_Diffuse_Color(255, 255, 255);
Set_Ambient_Color(255, 255, 255);
Set_Specular_Color(255, 255, 255);
Set_Emissive_Color(255, 255, 255);
Set_Power(1.0f);
}
//-------------------------------------------------------------------
// Set diffuse color.
//-------------------------------------------------------------------
void MATERIAL::Set_Diffuse_Color(unsigned char red, unsigned char green, unsigned char blue)
{
_material.Diffuse.r = red / 255.0f;
_material.Diffuse.g = green / 255.0f;
_material.Diffuse.b = blue / 255.0f;
}
//-------------------------------------------------------------------
// Get diffuse color.
//-------------------------------------------------------------------
void MATERIAL::Get_Diffuse_Color(unsigned char* red, unsigned char* green, unsigned char* blue)
{
if(red != NULL)
*red = (unsigned char)(255.0 * _material.Diffuse.r);
if(green != NULL)
*green = (unsigned char)(255.0 * _material.Diffuse.g);
if(blue != NULL)
*blue = (unsigned char)(255.0 * _material.Diffuse.b);
}
//-------------------------------------------------------------------
// Set ambient color.
//-------------------------------------------------------------------
void MATERIAL::Set_Ambient_Color(unsigned char red, unsigned char green, unsigned char blue)
{
_material.Ambient.r = red / 255.0f;
_material.Ambient.g = green / 255.0f;
_material.Ambient.b = blue / 255.0f;
}
//-------------------------------------------------------------------
// Get ambient color.
//-------------------------------------------------------------------
void MATERIAL::Get_Ambient_Color(unsigned char *red, unsigned char *green, unsigned char *blue)
{
if(red != NULL)
*red = (unsigned char)(255.0f * _material.Ambient.r);
if(green != NULL)
*green = (unsigned char)(255.0f * _material.Ambient.g);
if(blue != NULL)
*blue = (unsigned char)(255.0f * _material.Ambient.b);
}
//-------------------------------------------------------------------
// Set specular color.
//-------------------------------------------------------------------
void MATERIAL::Set_Specular_Color(unsigned char red, unsigned char green, unsigned char blue)
{
_material.Specular.r = red / 255.0f;
_material.Specular.g = green / 255.0f;
_material.Specular.b = blue / 255.0f;
}
//-------------------------------------------------------------------
// Get specular color.
//-------------------------------------------------------------------
void MATERIAL::Get_Specular_Color(unsigned char* red, unsigned char* green, unsigned char* blue)
{
if(red != NULL)
*red = (unsigned char)(255.0 * _material.Specular.r);
if(green != NULL)
*green = (unsigned char)(255.0 * _material.Specular.g);
if(blue != NULL)
*blue = (unsigned char)(255.0 * _material.Specular.b);
}
//-------------------------------------------------------------------
// Set emissive color.
//-------------------------------------------------------------------
void MATERIAL::Set_Emissive_Color(unsigned char red, unsigned char green, unsigned char blue)
{
_material.Emissive.r = red / 255.0f;
_material.Emissive.g = green / 255.0f;
_material.Emissive.b = blue / 255.0f;
}
//-------------------------------------------------------------------
// Get emmisive color.
//-------------------------------------------------------------------
void MATERIAL::Get_Emissive_Color(unsigned char *red, unsigned char *green, unsigned char *blue)
{
if(red != NULL)
*red = (unsigned char)(255.0 * _material.Emissive.r);
if(green != NULL)
*green = (unsigned char)(255.0 * _material.Emissive.g);
if(blue != NULL)
*blue = (unsigned char)(255.0 * _material.Emissive.b);
}
//-------------------------------------------------------------------
// Set power for material, which specifying the sharpness of specular
// highlights.
//-------------------------------------------------------------------
void MATERIAL::Set_Power(float power)
{
_material.Power = power;
}
//-------------------------------------------------------------------
// Get power for material, which specifying the sharpness of specular
// highlights.
//-------------------------------------------------------------------
float MATERIAL::Get_Power()
{
return _material.Power;
}
//-------------------------------------------------------------------
// Get material.
//-------------------------------------------------------------------
D3DMATERIAL9* MATERIAL::Get_Material()
{
return &_material;
}
MATERIAL类保存了一个D3DMATERIAL9结构体,还提供了能够设置和取得各种颜色分量的函数。要设置一个颜色分量,指定一个0 -
255之间的数字即可。要取得一个颜色分量,给适当的函数提供一个unsigned char类型的指针即可。