首页 诗词 字典 板报 句子 名言 友答 励志 学校 网站地图
当前位置: 首页 > 教程频道 > 网络游戏 >

HLSL多灯日照射效果怎样融合

2013-01-02 
HLSL多灯光照射效果怎样融合?本帖最后由 Renyq 于 2012-11-06 18:19:53 编辑下面是两个点光照射的效果:flo

HLSL多灯光照射效果怎样融合?
本帖最后由 Renyq 于 2012-11-06 18:19:53 编辑 下面是两个点光照射的效果:
float3 Col1 =... ...;//灯光1照射下的物体颜色
float3 Col2 =... ...;//灯光2照射下的物体颜色

我想得到两个灯光共同作用的效果float3 FinalColor,该怎样使用每个灯光的效果?下面两种都不理想:
FinalColor = ( Col1 + Col2 )/2 ; //在两个灯光共同影响的区域出现两圆相交的黑色弧线,而且共同区域过亮。
FinalColor = max( Col1 + Col2 ) ;//在两个灯光照射区域的中间出现一条黑色直线。

我不知道还有什么计算方法可以让两个灯光的影响很好的融合,请大侠们指点一下。谢谢!
附上效果文件,也让有兴趣的朋友们调试。


matrix world ; //这是物体的世界矩阵
matrix wvp ;//这是世界矩阵*视图矩阵*投影矩阵
float3 Lig0Pos;//这是第一个灯光的位置
float3 Lig1Pos;//这是第二个灯光的位置
           /*在D3D中传入以上四个变量的指针就看到效果了*/
struct VS_INPUT
{
float4 pos   :POSITION;
float3 nor   :NORMAL ;
};

struct VS_OUTPUT
{
float4 pos  :POSITION;
float3 nor  :TEXCOORD0;
float3 LigVec0 :TEXCOORD2;
float3 LigVec1 :TEXCOORD3;
};

VS_OUTPUT vsMain(VS_INPUT In,VS_OUTPUT Out)
{
Out.pos  =  mul(In.pos,wvp);
Out.nor  =  mul(In.nor,world);

Out.LigVec0 = Lig0Pos- mul(In.pos,world);
Out.LigVec1 = Lig1Pos- mul(In.pos,world);

return Out;
}

float4 psMain(VS_OUTPUT In):COLOR
{
float3 N = normalize(In.nor);
float3 L0 = normalize(In.LigVec0);
float3 L1 = normalize(In.LigVec1);
float  ligint0 = saturate(dot(N,L0));
float  ligint1 = saturate(dot(N,L1));
float3 Dif = float3(1,1,1) * max(ligint0,ligint1);//????????????????????
//float3 Dif = float3(1,1,1) * (ligint0+ligint1)/2;
/*要命的就是上面两行的算法我不会搞*/
return float4(Dif,1);
}

technique RenderColor
{
pass p0
{
VertexShader = compile vs_2_0 vsMain();
PixelShader  = compile ps_2_0 psMain();
}
}

[解决办法]
直接light0+light1就可以了,非HDR的话可能会溢出
[解决办法]
另外:
Out.nor  =  mul(In.nor,world); 
这句话有问题,normal不能直接用世界矩阵变换,矩阵里面有位移的话,得到normal是错误的。

还有就是,light是点光源还是什么东西?
看样子好像是点光源,但是没做距离衰减,右边那个图里面的黑线兴许与这个有关。

normal算法

float4x4 mw=mW;
mw[3][0]=mw[3][1]=mw[3][2]=0;
Normal=mul(Normal,mw);

point light

float maxdist=100;(最大照亮距离)
dist=distance(pos,light0pos);
float lightPower=pow((100.0-dist)/maxdist,2); //pow 系数2 只模拟单位范围的光照强度)



最后
float lightAcc=saturate(dot(N,L0))*lightPower0+saturate(dot(N,L1))*lightPower1;

o.color=diffuse*(lightAcc+ x); //x是环境光常量

热点排行