source: GTP/trunk/App/Demos/Illum/Ogre/Media/materials/programs/MetalTeapotNew.hlsl @ 1860

Revision 1860, 6.8 KB checked in by szirmay, 18 years ago (diff)
Line 
1float3 F0;
2
3float4 readCubeMap(samplerCUBE cm, float3 coord)               
4{
5        float4 color = texCUBElod( cm, float4(coord.xy, - coord.z,0) );
6        return color;
7}
8
9float readDistanceCubeMap(samplerCUBE dcm, float3 coord)               
10{
11        float dist = texCUBElod(dcm, float4(coord.xy, - coord.z,0)).a;
12        return dist;
13}
14
15#define MAX_LIN_ITERATIONCOUNT 20
16#define MIN_LIN_ITERATIONCOUNT 6
17#define SECANT_ITERATIONCOUNT 1
18#define MAX_RAY_DEPTH 5
19
20void linearSearch(  float3 x, float3 R, float3 N, samplerCUBE mp,
21                    out float3 p,
22                    out float dl,
23                    out float dp,
24                    out float llp,
25                    out float ppp)
26{
27 float3 Ra = abs(R), xa = abs(x);
28 float xm =  max(max(xa.x,xa.y),xa.z);
29 float Rm = max(max(Ra.x,Ra.y),Ra.z);
30 float a = xm / Rm;
31           
32 bool undershoot = false, overshoot = false;
33 
34 float dt =  length(x / xm - R / Rm) * MAX_LIN_ITERATIONCOUNT;
35 dt = max(dt, MIN_LIN_ITERATIONCOUNT);
36 dt = 1.0 / dt;
37   
38 float t = 0.01;//dt;
39 float pa;
40 bool first = true;
41 //Linear iteration
42 while(t <= 1.0 && !overshoot)
43 {
44   dp = a * t / (1 - t);
45   p = x + R * dp;
46   pa = readDistanceCubeMap(mp, p);
47   if(pa > 0)
48   {
49    ppp = length(p) / pa;
50    if(ppp < 1)
51    {
52      dl = dp;
53      llp = ppp;
54      undershoot = true;
55    }
56    else if(undershoot)
57      overshoot = true;
58   }
59   else
60     undershoot = false;
61   t += dt; 
62 }
63 
64 if(!overshoot)
65  p = float3(0,0,0);
66/* else if(t == 2 * dt)
67 {
68         float3 hitp = pa * normalize(p);
69    if(dot(normalize(hitp - x), N) < 0.1f)
70           p = float3(0,0,0);
71 }*/
72}
73
74void secantSearch(float3 x, float3 R, samplerCUBE mp,
75                       float dl,
76                       float dp,
77                       float llp,
78                       float ppp,
79                       out float3 p)
80{
81  for(int i= 0; i < SECANT_ITERATIONCOUNT; i++)
82  {
83   float dnew;
84   dnew = dl + (dp - dl) * (1 - llp) / (ppp - llp);
85   p = x + R * dnew;
86   half pppnew = length(p) / readDistanceCubeMap(mp, p);
87   if(pppnew < 1)
88   {
89    llp = pppnew;
90    dl = dnew;
91   }
92   else
93   {
94    ppp = pppnew;
95    dp = dnew;
96   }
97  }
98}
99
100float3 Hit(float3 x, float3 R, float3 N,
101           samplerCUBE mp1,
102           samplerCUBE mp2,
103           samplerCUBE mp3Color,
104           samplerCUBE mp3Dist,
105           out float4 Il, out float3 Nl)
106{
107 float dl1 = 0, dp1, llp1, ppp1;
108 float3 p1;
109 linearSearch(x, R, N, mp1, p1, dl1, dp1, llp1, ppp1);
110 float dl2 = 0, dp2, llp2, ppp2;
111 float3 p2;
112 linearSearch(x, R, N, mp2, p2, dl2, dp2, llp2, ppp2);
113 
114 bool valid1 = dot(p1,p1) != 0;
115 bool valid2 = dot(p2,p2) != 0;
116               
117 float dl, dp, llp, ppp;
118 float3 p;
119 
120 if(!valid1 && ! valid2)
121 {
122    linearSearch(x, R, N, mp3Dist, p, dl, dp, llp, ppp);
123    Il.a = 1;
124    secantSearch(x, R, mp3Dist, dl, dp, llp, ppp, p);
125    Il.rgb =  Nl.rgb = readCubeMap(mp3Color, p).rgb; 
126 }
127 else
128 {
129    if( !valid2 || (valid1 && dp1 < dp2))
130    {
131     secantSearch(x, R, mp1, dl1, dp1, llp1, ppp1, p1);
132     Il.rgb =  Nl.rgb = readCubeMap(mp1, p1).rgb;
133     p = p1;
134    }
135    else
136    {
137     secantSearch(x, R, mp2, dl2, dp2, llp2, ppp2, p2);
138     Il.rgb =  Nl.rgb = readCubeMap(mp2, p2).rgb;
139     p = p2;
140    }
141    Il.a = 0;   
142 }
143 
144 return p;
145}
146
147struct VertOut
148{
149        float3 wPos     : TEXCOORD1;
150        float3 cPos     : TEXCOORD3;
151        float2 texCoord : TEXCOORD0;
152        float3 mNormal  : TEXCOORD2;
153        float4 hPos : POSITION;                 
154};
155
156VertOut DefaultVS(float4 position : POSITION,                                           
157                                float2 texCoord : TEXCOORD0,
158                                float3 normal   : NORMAL,
159                                uniform float4x4 worldViewProj,
160                                uniform float4x4 world,
161                                uniform float4x4 worldview,
162                                uniform float4x4 worldI )
163{
164  VertOut OUT;
165  OUT.hPos = mul(worldViewProj, position);
166  OUT.wPos = mul(world, position).xyz; 
167  OUT.cPos = mul(worldview, position).xyz; 
168  OUT.mNormal = mul(normal, worldI); 
169  //OUT.mNormal = normal;
170  OUT.texCoord = texCoord;
171  return OUT;
172}
173
174float4 SingleReflectionPS(VertOut IN,
175                                                        uniform float3 cameraPos,
176                                                        uniform samplerCUBE CubeMap : register(s0),
177                                                        uniform samplerCUBE DistanceMap : register(s1),
178                                                        uniform samplerCUBE NormDistMap1 : register(s2),
179                                                        uniform samplerCUBE NormDistMap2 : register(s3),
180                                                        uniform float3 lastCenter,
181                                                        uniform float refIndex)
182{
183 float4 Color = float4(1,1,1,1);
184               
185 float3 N = normalize(IN.mNormal);
186 float3 newTexCoord;   
187 float3 x = IN.wPos - lastCenter;
188 float3 V  = (IN.wPos - cameraPos);
189 
190 V = normalize(V);
191
192float3 R;         
193if(refIndex > 100.0)
194    R = normalize(reflect( V, N));
195else
196{
197        refIndex = 1.0 / refIndex;
198    R = normalize(refract( V, N, refIndex));
199}
200                       
201 float3 Nl;
202 float4 Il;
203 float3 l = Hit(x, R, N, NormDistMap1, NormDistMap2, CubeMap, DistanceMap, Il, Nl);
204 if(Il.a == 0)
205  Il = readCubeMap(CubeMap, l);
206 
207 return Il;
208}
209
210
211float4 MultipleReflectionPS(VertOut IN,
212                                                        uniform float3 cameraPos,
213                                                        uniform samplerCUBE CubeMap : register(s0),
214                                                        uniform samplerCUBE DistanceMap : register(s1),
215                                                        uniform samplerCUBE NormDistMap1 : register(s2),
216                                                        uniform samplerCUBE NormDistMap2 : register(s3),
217                                                        uniform float3 lastCenter,
218                                                        uniform float refIndex)
219{
220         float4 I = float4(0,0,0,0);
221                       
222         float3 N = normalize(IN.mNormal) * refIndex;
223         float3 newTexCoord;   
224         float3 x = IN.wPos - lastCenter;
225         float3 V  = (IN.wPos - cameraPos);
226         
227         V = normalize(V);
228         float3 l;
229         
230         int depth = 0;
231         while(depth < MAX_RAY_DEPTH)
232         {
233           float3 R;
234           float refIndex = length(N);
235           refIndex = 1.0 / refIndex;
236           N = normalize(N);
237           
238           if(refIndex > 100.0)
239            R = normalize(reflect( V, N));
240           else
241            R = normalize(refract( V, N, refIndex));
242                               
243           float3 Nl;
244           float4 Il;
245           l = Hit(x, R, N, NormDistMap1, NormDistMap2, CubeMap, DistanceMap, Il, Nl);
246           if(Il.a == 0)
247           {
248                   depth += 1;
249                  // I = float4(0.2,0.2,0.2,1.0);
250           }
251           else
252           {
253                   I = Il;
254                   depth = MAX_RAY_DEPTH;
255           }
256           x = l;         
257           N = normalize(Nl);
258           V = R;
259           
260          if(refIndex <= 100.0)
261            if(dot(N, V) > 0) N = -N;
262        }
263       
264//      if(I.a == 0)
265 //      I = readCubeMap(CubeMap, l);
266 
267        return I;
268}
269
270float4 mainPS(VertOut IN,
271                                                        uniform float3 cameraPos,
272                                                        uniform samplerCUBE CubeMap : register(s0),
273                                                        uniform samplerCUBE DistanceMap : register(s1),
274                                                        uniform samplerCUBE NormDistMap1 : register(s2),
275                                                        uniform samplerCUBE NormDistMap2 : register(s3),
276                                                        uniform float3 lastCenter,
277                                                        uniform float SingleBounce,
278                                                        uniform float refIndex):COLOR
279{
280        float4 Color = 1.0;
281        if(SingleBounce == 1)
282         Color = SingleReflectionPS(IN,cameraPos, CubeMap, DistanceMap, NormDistMap1,NormDistMap2,lastCenter,refIndex);
283        else
284         Color = MultipleReflectionPS(IN,cameraPos, CubeMap, DistanceMap, NormDistMap1,NormDistMap2,lastCenter,refIndex);
285         
286        return Color;
287}
Note: See TracBrowser for help on using the repository browser.