506c9641d12d40e89548c029a55c1405409ae0ad
[blender.git] / source / blender / gpu / shaders / gpu_shader_material.glsl
1 /* Converters */
2
3 float convert_rgba_to_float(vec4 color)
4 {
5 #ifdef USE_NEW_SHADING
6         return color.r*0.2126 + color.g*0.7152 + color.b*0.0722;
7 #else
8         return (color.r + color.g + color.b) / 3.0;
9 #endif
10 }
11
12 float exp_blender(float f)
13 {
14         return pow(2.71828182846, f);
15 }
16
17 float compatible_pow(float x, float y)
18 {
19         if (y == 0.0) /* x^0 -> 1, including 0^0 */
20                 return 1.0;
21
22         /* glsl pow doesn't accept negative x */
23         if (x < 0.0) {
24                 if (mod(-y, 2.0) == 0.0)
25                         return pow(-x, y);
26                 else
27                         return -pow(-x, y);
28         }
29         else if (x == 0.0)
30                 return 0.0;
31
32         return pow(x, y);
33 }
34
35 void rgb_to_hsv(vec4 rgb, out vec4 outcol)
36 {
37         float cmax, cmin, h, s, v, cdelta;
38         vec3 c;
39
40         cmax = max(rgb[0], max(rgb[1], rgb[2]));
41         cmin = min(rgb[0], min(rgb[1], rgb[2]));
42         cdelta = cmax-cmin;
43
44         v = cmax;
45         if (cmax!=0.0)
46                 s = cdelta/cmax;
47         else {
48                 s = 0.0;
49                 h = 0.0;
50         }
51
52         if (s == 0.0) {
53                 h = 0.0;
54         }
55         else {
56                 c = (vec3(cmax, cmax, cmax) - rgb.xyz)/cdelta;
57
58                 if (rgb.x==cmax) h = c[2] - c[1];
59                 else if (rgb.y==cmax) h = 2.0 + c[0] -  c[2];
60                 else h = 4.0 + c[1] - c[0];
61
62                 h /= 6.0;
63
64                 if (h<0.0)
65                         h += 1.0;
66         }
67
68         outcol = vec4(h, s, v, rgb.w);
69 }
70
71 void hsv_to_rgb(vec4 hsv, out vec4 outcol)
72 {
73         float i, f, p, q, t, h, s, v;
74         vec3 rgb;
75
76         h = hsv[0];
77         s = hsv[1];
78         v = hsv[2];
79
80         if (s==0.0) {
81                 rgb = vec3(v, v, v);
82         }
83         else {
84                 if (h==1.0)
85                         h = 0.0;
86                 
87                 h *= 6.0;
88                 i = floor(h);
89                 f = h - i;
90                 rgb = vec3(f, f, f);
91                 p = v*(1.0-s);
92                 q = v*(1.0-(s*f));
93                 t = v*(1.0-(s*(1.0-f)));
94                 
95                 if (i == 0.0) rgb = vec3(v, t, p);
96                 else if (i == 1.0) rgb = vec3(q, v, p);
97                 else if (i == 2.0) rgb = vec3(p, v, t);
98                 else if (i == 3.0) rgb = vec3(p, q, v);
99                 else if (i == 4.0) rgb = vec3(t, p, v);
100                 else rgb = vec3(v, p, q);
101         }
102
103         outcol = vec4(rgb, hsv.w);
104 }
105
106 float srgb_to_linearrgb(float c)
107 {
108         if (c < 0.04045)
109                 return (c < 0.0) ? 0.0: c * (1.0 / 12.92);
110         else
111                 return pow((c + 0.055)*(1.0/1.055), 2.4);
112 }
113
114 float linearrgb_to_srgb(float c)
115 {
116         if (c < 0.0031308)
117                 return (c < 0.0) ? 0.0: c * 12.92;
118         else
119                 return 1.055 * pow(c, 1.0/2.4) - 0.055;
120 }
121
122 void srgb_to_linearrgb(vec4 col_from, out vec4 col_to)
123 {
124         col_to.r = srgb_to_linearrgb(col_from.r);
125         col_to.g = srgb_to_linearrgb(col_from.g);
126         col_to.b = srgb_to_linearrgb(col_from.b);
127         col_to.a = col_from.a;
128 }
129
130 void linearrgb_to_srgb(vec4 col_from, out vec4 col_to)
131 {
132         col_to.r = linearrgb_to_srgb(col_from.r);
133         col_to.g = linearrgb_to_srgb(col_from.g);
134         col_to.b = linearrgb_to_srgb(col_from.b);
135         col_to.a = col_from.a;
136 }
137
138 void color_to_normal(vec3 color, out vec3 normal)
139 {
140         normal.x =  2.0 * ((color.r) - 0.5);
141         normal.y = -2.0 * ((color.g) - 0.5);
142         normal.z =  2.0 * ((color.b) - 0.5);
143 }
144
145 #define M_PI 3.14159265358979323846
146 #define M_1_PI 0.31830988618379069
147
148 /*********** SHADER NODES ***************/
149
150 void vcol_attribute(vec4 attvcol, out vec4 vcol)
151 {
152         vcol = vec4(attvcol.x/255.0, attvcol.y/255.0, attvcol.z/255.0, 1.0);
153 }
154
155 void uv_attribute(vec2 attuv, out vec3 uv)
156 {
157         uv = vec3(attuv*2.0 - vec2(1.0, 1.0), 0.0);
158 }
159
160 void geom(
161         vec3 co, vec3 nor, mat4 viewinvmat, vec3 attorco, vec2 attuv, vec4 attvcol,
162         out vec3 global, out vec3 local, out vec3 view, out vec3 orco, out vec3 uv,
163         out vec3 normal, out vec4 vcol, out float vcol_alpha, out float frontback)
164 {
165         local = co;
166         view = (gl_ProjectionMatrix[3][3] == 0.0)? normalize(local): vec3(0.0, 0.0, -1.0);
167         global = (viewinvmat*vec4(local, 1.0)).xyz;
168         orco = attorco;
169         uv_attribute(attuv, uv);
170         normal = -normalize(nor);       /* blender render normal is negated */
171         vcol_attribute(attvcol, vcol);
172         srgb_to_linearrgb(vcol, vcol);
173         vcol_alpha = attvcol.a;
174         frontback = (gl_FrontFacing)? 1.0: 0.0;
175 }
176
177 void particle_info(
178         vec4 sprops, vec3 loc, vec3 vel, vec3 avel,
179         out float index, out float age, out float life_time, out vec3 location,
180         out float size, out vec3 velocity, out vec3 angular_velocity)
181 {
182         index = sprops.x;
183         age = sprops.y;
184         life_time = sprops.z;
185         size = sprops.w;
186
187         location = loc;
188         velocity = vel;
189         angular_velocity = avel;
190 }
191
192 void vect_normalize(vec3 vin, out vec3 vout)
193 {
194         vout = normalize(vin);
195 }
196
197 void direction_transform_m4v3(vec3 vin, mat4 mat, out vec3 vout)
198 {
199         vout = (mat*vec4(vin, 0.0)).xyz;
200 }
201
202 void point_transform_m4v3(vec3 vin, mat4 mat, out vec3 vout)
203 {
204         vout = (mat*vec4(vin, 1.0)).xyz;
205 }
206
207 void mapping(vec3 vec, mat4 mat, vec3 minvec, vec3 maxvec, float domin, float domax, out vec3 outvec)
208 {
209         outvec = (mat * vec4(vec, 1.0)).xyz;
210         if (domin == 1.0)
211                 outvec = max(outvec, minvec);
212         if (domax == 1.0)
213                 outvec = min(outvec, maxvec);
214 }
215
216 void camera(vec3 co, out vec3 outview, out float outdepth, out float outdist)
217 {
218         outdepth = abs(co.z);
219         outdist = length(co);
220         outview = normalize(co);
221 }
222
223 void lamp(
224         vec4 col, float energy, vec3 lv, float dist, vec3 shadow, float visifac,
225         out vec4 outcol, out vec3 outlv, out float outdist, out vec4 outshadow, out float outvisifac)
226 {
227         outcol = col * energy;
228         outlv = lv;
229         outdist = dist;
230         outshadow = vec4(shadow, 1.0);
231         outvisifac = visifac;
232 }
233
234 void math_add(float val1, float val2, out float outval)
235 {
236         outval = val1 + val2;
237 }
238
239 void math_subtract(float val1, float val2, out float outval)
240 {
241         outval = val1 - val2;
242 }
243
244 void math_multiply(float val1, float val2, out float outval)
245 {
246         outval = val1 * val2;
247 }
248
249 void math_divide(float val1, float val2, out float outval)
250 {
251         if (val2 == 0.0)
252                 outval = 0.0;
253         else
254                 outval = val1 / val2;
255 }
256
257 void math_sine(float val, out float outval)
258 {
259         outval = sin(val);
260 }
261
262 void math_cosine(float val, out float outval)
263 {
264         outval = cos(val);
265 }
266
267 void math_tangent(float val, out float outval)
268 {
269         outval = tan(val);
270 }
271
272 void math_asin(float val, out float outval)
273 {
274         if (val <= 1.0 && val >= -1.0)
275                 outval = asin(val);
276         else
277                 outval = 0.0;
278 }
279
280 void math_acos(float val, out float outval)
281 {
282         if (val <= 1.0 && val >= -1.0)
283                 outval = acos(val);
284         else
285                 outval = 0.0;
286 }
287
288 void math_atan(float val, out float outval)
289 {
290         outval = atan(val);
291 }
292
293 void math_pow(float val1, float val2, out float outval)
294 {
295         if (val1 >= 0.0) {
296                 outval = compatible_pow(val1, val2);
297         }
298         else {
299                 float val2_mod_1 = mod(abs(val2), 1.0);
300
301                 if (val2_mod_1 > 0.999 || val2_mod_1 < 0.001)
302                         outval = compatible_pow(val1, floor(val2 + 0.5));
303                 else
304                         outval = 0.0;
305         }
306 }
307
308 void math_log(float val1, float val2, out float outval)
309 {
310         if (val1 > 0.0  && val2 > 0.0)
311                 outval= log2(val1) / log2(val2);
312         else
313                 outval= 0.0;
314 }
315
316 void math_max(float val1, float val2, out float outval)
317 {
318         outval = max(val1, val2);
319 }
320
321 void math_min(float val1, float val2, out float outval)
322 {
323         outval = min(val1, val2);
324 }
325
326 void math_round(float val, out float outval)
327 {
328         outval= floor(val + 0.5);
329 }
330
331 void math_less_than(float val1, float val2, out float outval)
332 {
333         if (val1 < val2)
334                 outval = 1.0;
335         else
336                 outval = 0.0;
337 }
338
339 void math_greater_than(float val1, float val2, out float outval)
340 {
341         if (val1 > val2)
342                 outval = 1.0;
343         else
344                 outval = 0.0;
345 }
346
347 void math_modulo(float val1, float val2, out float outval)
348 {
349         if (val2 == 0.0)
350                 outval = 0.0;
351         else
352                 outval = mod(val1, val2);
353
354         /* change sign to match C convention, mod in GLSL will take absolute for negative numbers,
355          * see https://www.opengl.org/sdk/docs/man/html/mod.xhtml */
356         outval = (val1 > 0.0) ? outval : -outval;
357 }
358
359 void math_abs(float val1, out float outval)
360 {
361         outval = abs(val1);
362 }
363
364 void squeeze(float val, float width, float center, out float outval)
365 {
366         outval = 1.0/(1.0 + pow(2.71828183, -((val-center)*width)));
367 }
368
369 void vec_math_add(vec3 v1, vec3 v2, out vec3 outvec, out float outval)
370 {
371         outvec = v1 + v2;
372         outval = (abs(outvec[0]) + abs(outvec[1]) + abs(outvec[2]))/3.0;
373 }
374
375 void vec_math_sub(vec3 v1, vec3 v2, out vec3 outvec, out float outval)
376 {
377         outvec = v1 - v2;
378         outval = (abs(outvec[0]) + abs(outvec[1]) + abs(outvec[2]))/3.0;
379 }
380
381 void vec_math_average(vec3 v1, vec3 v2, out vec3 outvec, out float outval)
382 {
383         outvec = v1 + v2;
384         outval = length(outvec);
385         outvec = normalize(outvec);
386 }
387 void vec_math_mix(float strength, vec3 v1, vec3 v2, out vec3 outvec)
388 {
389         outvec = strength*v1 + (1 - strength) * v2;
390 }
391
392 void vec_math_dot(vec3 v1, vec3 v2, out vec3 outvec, out float outval)
393 {
394         outvec = vec3(0, 0, 0);
395         outval = dot(v1, v2);
396 }
397
398 void vec_math_cross(vec3 v1, vec3 v2, out vec3 outvec, out float outval)
399 {
400         outvec = cross(v1, v2);
401         outval = length(outvec);
402         outvec /= outval;
403 }
404
405 void vec_math_normalize(vec3 v, out vec3 outvec, out float outval)
406 {
407         outval = length(v);
408         outvec = normalize(v);
409 }
410
411 void vec_math_negate(vec3 v, out vec3 outv)
412 {
413         outv = -v;
414 }
415
416 void invert_z(vec3 v, out vec3 outv)
417 {
418         v.z = -v.z;
419         outv = v;
420 }
421
422 void normal(vec3 dir, vec3 nor, out vec3 outnor, out float outdot)
423 {
424         outnor = nor;
425         outdot = -dot(dir, nor);
426 }
427
428 void normal_new_shading(vec3 dir, vec3 nor, out vec3 outnor, out float outdot)
429 {
430         outnor = normalize(nor);
431         outdot = dot(normalize(dir), nor);
432 }
433
434 void curves_vec(float fac, vec3 vec, sampler2D curvemap, out vec3 outvec)
435 {
436         outvec.x = texture2D(curvemap, vec2((vec.x + 1.0)*0.5, 0.0)).x;
437         outvec.y = texture2D(curvemap, vec2((vec.y + 1.0)*0.5, 0.0)).y;
438         outvec.z = texture2D(curvemap, vec2((vec.z + 1.0)*0.5, 0.0)).z;
439
440         if (fac != 1.0)
441                 outvec = (outvec*fac) + (vec*(1.0-fac));
442
443 }
444
445 void curves_rgb(float fac, vec4 col, sampler2D curvemap, out vec4 outcol)
446 {
447         outcol.r = texture2D(curvemap, vec2(texture2D(curvemap, vec2(col.r, 0.0)).a, 0.0)).r;
448         outcol.g = texture2D(curvemap, vec2(texture2D(curvemap, vec2(col.g, 0.0)).a, 0.0)).g;
449         outcol.b = texture2D(curvemap, vec2(texture2D(curvemap, vec2(col.b, 0.0)).a, 0.0)).b;
450
451         if (fac != 1.0)
452                 outcol = (outcol*fac) + (col*(1.0-fac));
453
454         outcol.a = col.a;
455 }
456
457 void set_value(float val, out float outval)
458 {
459         outval = val;
460 }
461
462 void set_rgb(vec3 col, out vec3 outcol)
463 {
464         outcol = col;
465 }
466
467 void set_rgba(vec4 col, out vec4 outcol)
468 {
469         outcol = col;
470 }
471
472 void set_value_zero(out float outval)
473 {
474         outval = 0.0;
475 }
476
477 void set_value_one(out float outval)
478 {
479         outval = 1.0;
480 }
481
482 void set_rgb_zero(out vec3 outval)
483 {
484         outval = vec3(0.0);
485 }
486
487 void set_rgb_one(out vec3 outval)
488 {
489         outval = vec3(1.0);
490 }
491
492 void set_rgba_zero(out vec4 outval)
493 {
494         outval = vec4(0.0);
495 }
496
497 void set_rgba_one(out vec4 outval)
498 {
499         outval = vec4(1.0);
500 }
501
502 void brightness_contrast(vec4 col, float brightness, float contrast, out vec4 outcol)
503 {
504         float a = 1.0 + contrast;
505         float b = brightness - contrast*0.5;
506
507         outcol.r = max(a*col.r + b, 0.0);
508         outcol.g = max(a*col.g + b, 0.0);
509         outcol.b = max(a*col.b + b, 0.0);
510         outcol.a = col.a;
511 }
512
513 void mix_blend(float fac, vec4 col1, vec4 col2, out vec4 outcol)
514 {
515         fac = clamp(fac, 0.0, 1.0);
516         outcol = mix(col1, col2, fac);
517         outcol.a = col1.a;
518 }
519
520 void mix_add(float fac, vec4 col1, vec4 col2, out vec4 outcol)
521 {
522         fac = clamp(fac, 0.0, 1.0);
523         outcol = mix(col1, col1 + col2, fac);
524         outcol.a = col1.a;
525 }
526
527 void mix_mult(float fac, vec4 col1, vec4 col2, out vec4 outcol)
528 {
529         fac = clamp(fac, 0.0, 1.0);
530         outcol = mix(col1, col1 * col2, fac);
531         outcol.a = col1.a;
532 }
533
534 void mix_screen(float fac, vec4 col1, vec4 col2, out vec4 outcol)
535 {
536         fac = clamp(fac, 0.0, 1.0);
537         float facm = 1.0 - fac;
538
539         outcol = vec4(1.0) - (vec4(facm) + fac*(vec4(1.0) - col2))*(vec4(1.0) - col1);
540         outcol.a = col1.a;
541 }
542
543 void mix_overlay(float fac, vec4 col1, vec4 col2, out vec4 outcol)
544 {
545         fac = clamp(fac, 0.0, 1.0);
546         float facm = 1.0 - fac;
547
548         outcol = col1;
549
550         if (outcol.r < 0.5)
551                 outcol.r *= facm + 2.0*fac*col2.r;
552         else
553                 outcol.r = 1.0 - (facm + 2.0*fac*(1.0 - col2.r))*(1.0 - outcol.r);
554
555         if (outcol.g < 0.5)
556                 outcol.g *= facm + 2.0*fac*col2.g;
557         else
558                 outcol.g = 1.0 - (facm + 2.0*fac*(1.0 - col2.g))*(1.0 - outcol.g);
559
560         if (outcol.b < 0.5)
561                 outcol.b *= facm + 2.0*fac*col2.b;
562         else
563                 outcol.b = 1.0 - (facm + 2.0*fac*(1.0 - col2.b))*(1.0 - outcol.b);
564 }
565
566 void mix_sub(float fac, vec4 col1, vec4 col2, out vec4 outcol)
567 {
568         fac = clamp(fac, 0.0, 1.0);
569         outcol = mix(col1, col1 - col2, fac);
570         outcol.a = col1.a;
571 }
572
573 void mix_div(float fac, vec4 col1, vec4 col2, out vec4 outcol)
574 {
575         fac = clamp(fac, 0.0, 1.0);
576         float facm = 1.0 - fac;
577
578         outcol = col1;
579
580         if (col2.r != 0.0) outcol.r = facm*outcol.r + fac*outcol.r/col2.r;
581         if (col2.g != 0.0) outcol.g = facm*outcol.g + fac*outcol.g/col2.g;
582         if (col2.b != 0.0) outcol.b = facm*outcol.b + fac*outcol.b/col2.b;
583 }
584
585 void mix_diff(float fac, vec4 col1, vec4 col2, out vec4 outcol)
586 {
587         fac = clamp(fac, 0.0, 1.0);
588         outcol = mix(col1, abs(col1 - col2), fac);
589         outcol.a = col1.a;
590 }
591
592 void mix_dark(float fac, vec4 col1, vec4 col2, out vec4 outcol)
593 {
594         fac = clamp(fac, 0.0, 1.0);
595         outcol.rgb = min(col1.rgb, col2.rgb*fac);
596         outcol.a = col1.a;
597 }
598
599 void mix_light(float fac, vec4 col1, vec4 col2, out vec4 outcol)
600 {
601         fac = clamp(fac, 0.0, 1.0);
602         outcol.rgb = max(col1.rgb, col2.rgb*fac);
603         outcol.a = col1.a;
604 }
605
606 void mix_dodge(float fac, vec4 col1, vec4 col2, out vec4 outcol)
607 {
608         fac = clamp(fac, 0.0, 1.0);
609         outcol = col1;
610
611         if (outcol.r != 0.0) {
612                 float tmp = 1.0 - fac*col2.r;
613                 if (tmp <= 0.0)
614                         outcol.r = 1.0;
615                 else if ((tmp = outcol.r/tmp) > 1.0)
616                         outcol.r = 1.0;
617                 else
618                         outcol.r = tmp;
619         }
620         if (outcol.g != 0.0) {
621                 float tmp = 1.0 - fac*col2.g;
622                 if (tmp <= 0.0)
623                         outcol.g = 1.0;
624                 else if ((tmp = outcol.g/tmp) > 1.0)
625                         outcol.g = 1.0;
626                 else
627                         outcol.g = tmp;
628         }
629         if (outcol.b != 0.0) {
630                 float tmp = 1.0 - fac*col2.b;
631                 if (tmp <= 0.0)
632                         outcol.b = 1.0;
633                 else if ((tmp = outcol.b/tmp) > 1.0)
634                         outcol.b = 1.0;
635                 else
636                         outcol.b = tmp;
637         }
638 }
639
640 void mix_burn(float fac, vec4 col1, vec4 col2, out vec4 outcol)
641 {
642         fac = clamp(fac, 0.0, 1.0);
643         float tmp, facm = 1.0 - fac;
644
645         outcol = col1;
646
647         tmp = facm + fac*col2.r;
648         if (tmp <= 0.0)
649                 outcol.r = 0.0;
650         else if ((tmp = (1.0 - (1.0 - outcol.r)/tmp)) < 0.0)
651                 outcol.r = 0.0;
652         else if (tmp > 1.0)
653                 outcol.r = 1.0;
654         else
655                 outcol.r = tmp;
656
657         tmp = facm + fac*col2.g;
658         if (tmp <= 0.0)
659                 outcol.g = 0.0;
660         else if ((tmp = (1.0 - (1.0 - outcol.g)/tmp)) < 0.0)
661                 outcol.g = 0.0;
662         else if (tmp > 1.0)
663                 outcol.g = 1.0;
664         else
665                 outcol.g = tmp;
666
667         tmp = facm + fac*col2.b;
668         if (tmp <= 0.0)
669                 outcol.b = 0.0;
670         else if ((tmp = (1.0 - (1.0 - outcol.b)/tmp)) < 0.0)
671                 outcol.b = 0.0;
672         else if (tmp > 1.0)
673                 outcol.b = 1.0;
674         else
675                 outcol.b = tmp;
676 }
677
678 void mix_hue(float fac, vec4 col1, vec4 col2, out vec4 outcol)
679 {
680         fac = clamp(fac, 0.0, 1.0);
681         float facm = 1.0 - fac;
682
683         outcol = col1;
684
685         vec4 hsv, hsv2, tmp;
686         rgb_to_hsv(col2, hsv2);
687
688         if (hsv2.y != 0.0) {
689                 rgb_to_hsv(outcol, hsv);
690                 hsv.x = hsv2.x;
691                 hsv_to_rgb(hsv, tmp); 
692
693                 outcol = mix(outcol, tmp, fac);
694                 outcol.a = col1.a;
695         }
696 }
697
698 void mix_sat(float fac, vec4 col1, vec4 col2, out vec4 outcol)
699 {
700         fac = clamp(fac, 0.0, 1.0);
701         float facm = 1.0 - fac;
702
703         outcol = col1;
704
705         vec4 hsv, hsv2;
706         rgb_to_hsv(outcol, hsv);
707
708         if (hsv.y != 0.0) {
709                 rgb_to_hsv(col2, hsv2);
710
711                 hsv.y = facm*hsv.y + fac*hsv2.y;
712                 hsv_to_rgb(hsv, outcol);
713         }
714 }
715
716 void mix_val(float fac, vec4 col1, vec4 col2, out vec4 outcol)
717 {
718         fac = clamp(fac, 0.0, 1.0);
719         float facm = 1.0 - fac;
720
721         vec4 hsv, hsv2;
722         rgb_to_hsv(col1, hsv);
723         rgb_to_hsv(col2, hsv2);
724
725         hsv.z = facm*hsv.z + fac*hsv2.z;
726         hsv_to_rgb(hsv, outcol);
727 }
728
729 void mix_color(float fac, vec4 col1, vec4 col2, out vec4 outcol)
730 {
731         fac = clamp(fac, 0.0, 1.0);
732         float facm = 1.0 - fac;
733
734         outcol = col1;
735
736         vec4 hsv, hsv2, tmp;
737         rgb_to_hsv(col2, hsv2);
738
739         if (hsv2.y != 0.0) {
740                 rgb_to_hsv(outcol, hsv);
741                 hsv.x = hsv2.x;
742                 hsv.y = hsv2.y;
743                 hsv_to_rgb(hsv, tmp); 
744
745                 outcol = mix(outcol, tmp, fac);
746                 outcol.a = col1.a;
747         }
748 }
749
750 void mix_soft(float fac, vec4 col1, vec4 col2, out vec4 outcol)
751 {
752         fac = clamp(fac, 0.0, 1.0);
753         float facm = 1.0 - fac;
754
755         vec4 one= vec4(1.0);
756         vec4 scr= one - (one - col2)*(one - col1);
757         outcol = facm*col1 + fac*((one - col1)*col2*col1 + col1*scr);
758 }
759
760 void mix_linear(float fac, vec4 col1, vec4 col2, out vec4 outcol)
761 {
762         fac = clamp(fac, 0.0, 1.0);
763
764         outcol = col1 + fac*(2.0*(col2 - vec4(0.5)));
765 }
766
767 void valtorgb(float fac, sampler2D colormap, out vec4 outcol, out float outalpha)
768 {
769         outcol = texture2D(colormap, vec2(fac, 0.0));
770         outalpha = outcol.a;
771 }
772
773 void rgbtobw(vec4 color, out float outval)  
774 {
775 #ifdef USE_NEW_SHADING
776         outval = color.r*0.2126 + color.g*0.7152 + color.b*0.0722;
777 #else
778         outval = color.r*0.35 + color.g*0.45 + color.b*0.2; /* keep these factors in sync with texture.h:RGBTOBW */
779 #endif
780 }
781
782 void invert(float fac, vec4 col, out vec4 outcol)
783 {
784         outcol.xyz = mix(col.xyz, vec3(1.0, 1.0, 1.0) - col.xyz, fac);
785         outcol.w = col.w;
786 }
787
788 void clamp_vec3(vec3 vec, vec3 min, vec3 max, out vec3 out_vec)
789 {
790         out_vec = clamp(vec, min, max);
791 }
792
793 void clamp_val(float value, float min, float max, out float out_value)
794 {
795         out_value = clamp(value, min, max);
796 }
797
798 void hue_sat(float hue, float sat, float value, float fac, vec4 col, out vec4 outcol)
799 {
800         vec4 hsv;
801
802         rgb_to_hsv(col, hsv);
803
804         hsv[0] += (hue - 0.5);
805         if (hsv[0]>1.0) hsv[0]-=1.0; else if (hsv[0]<0.0) hsv[0]+= 1.0;
806         hsv[1] *= sat;
807         if (hsv[1]>1.0) hsv[1]= 1.0; else if (hsv[1]<0.0) hsv[1]= 0.0;
808         hsv[2] *= value;
809         if (hsv[2]>1.0) hsv[2]= 1.0; else if (hsv[2]<0.0) hsv[2]= 0.0;
810
811         hsv_to_rgb(hsv, outcol);
812
813         outcol = mix(col, outcol, fac);
814 }
815
816 void separate_rgb(vec4 col, out float r, out float g, out float b)
817 {
818         r = col.r;
819         g = col.g;
820         b = col.b;
821 }
822
823 void combine_rgb(float r, float g, float b, out vec4 col)
824 {
825         col = vec4(r, g, b, 1.0);
826 }
827
828 void separate_xyz(vec3 vec, out float x, out float y, out float z)
829 {
830         x = vec.r;
831         y = vec.g;
832         z = vec.b;
833 }
834
835 void combine_xyz(float x, float y, float z, out vec3 vec)
836 {
837         vec = vec3(x, y, z);
838 }
839
840 void separate_hsv(vec4 col, out float h, out float s, out float v)
841 {
842         vec4 hsv;
843
844         rgb_to_hsv(col, hsv);
845         h = hsv[0];
846         s = hsv[1];
847         v = hsv[2];
848 }
849
850 void combine_hsv(float h, float s, float v, out vec4 col)
851 {
852         hsv_to_rgb(vec4(h, s, v, 1.0), col);
853 }
854
855 void output_node(vec4 rgb, float alpha, out vec4 outrgb)
856 {
857         outrgb = vec4(rgb.rgb, alpha);
858 }
859
860 /*********** TEXTURES ***************/
861
862 void texture_flip_blend(vec3 vec, out vec3 outvec)
863 {
864         outvec = vec.yxz;
865 }
866
867 void texture_blend_lin(vec3 vec, out float outval)
868 {
869         outval = (1.0+vec.x)/2.0;
870 }
871
872 void texture_blend_quad(vec3 vec, out float outval)
873 {
874         outval = max((1.0+vec.x)/2.0, 0.0);
875         outval *= outval;
876 }
877
878 void texture_wood_sin(vec3 vec, out float value, out vec4 color, out vec3 normal)
879 {
880         float a = sqrt(vec.x*vec.x + vec.y*vec.y + vec.z*vec.z)*20.0;
881         float wi = 0.5 + 0.5*sin(a);
882
883         value = wi;
884         color = vec4(wi, wi, wi, 1.0);
885         normal = vec3(0.0, 0.0, 0.0);
886 }
887
888 void texture_image(vec3 vec, sampler2D ima, out float value, out vec4 color, out vec3 normal)
889 {
890         color = texture2D(ima, (vec.xy + vec2(1.0, 1.0))*0.5);
891         value = color.a;
892
893         normal.x = 2.0*(color.r - 0.5);
894         normal.y = 2.0*(0.5 - color.g);
895         normal.z = 2.0*(color.b - 0.5);
896 }
897
898 /************* MTEX *****************/
899
900 void texco_orco(vec3 attorco, out vec3 orco)
901 {
902         orco = attorco;
903 }
904
905 void texco_uv(vec2 attuv, out vec3 uv)
906 {
907         /* disabled for now, works together with leaving out mtex_2d_mapping
908            uv = vec3(attuv*2.0 - vec2(1.0, 1.0), 0.0); */
909         uv = vec3(attuv, 0.0);
910 }
911
912 void texco_norm(vec3 normal, out vec3 outnormal)
913 {
914         /* corresponds to shi->orn, which is negated so cancels
915            out blender normal negation */
916         outnormal = normalize(normal);
917 }
918
919 void texco_tangent(vec4 tangent, out vec3 outtangent)
920 {
921         outtangent = normalize(tangent.xyz);
922 }
923
924 void texco_global(mat4 viewinvmat, vec3 co, out vec3 global)
925 {
926         global = (viewinvmat*vec4(co, 1.0)).xyz;
927 }
928
929 void texco_object(mat4 viewinvmat, mat4 obinvmat, vec3 co, out vec3 object)
930 {
931         object = (obinvmat*(viewinvmat*vec4(co, 1.0))).xyz;
932 }
933
934 void texco_refl(vec3 vn, vec3 view, out vec3 ref)
935 {
936         ref = view - 2.0*dot(vn, view)*vn;
937 }
938
939 void shade_norm(vec3 normal, out vec3 outnormal)
940 {
941         /* blender render normal is negated */
942         outnormal = -normalize(normal);
943 }
944
945 void mtex_mirror(vec3 tcol, vec4 refcol, float tin, float colmirfac, out vec4 outrefcol)
946 {
947         outrefcol = mix(refcol, vec4(1.0, tcol), tin * colmirfac);
948 }
949
950 void mtex_rgb_blend(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
951 {
952         float facm;
953
954         fact *= facg;
955         facm = 1.0-fact;
956
957         incol = fact*texcol + facm*outcol;
958 }
959
960 void mtex_rgb_mul(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
961 {
962         float facm;
963
964         fact *= facg;
965         facm = 1.0-fact;
966
967         incol = (facm + fact*texcol)*outcol;
968 }
969
970 void mtex_rgb_screen(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
971 {
972         float facm;
973
974         fact *= facg;
975         facm = 1.0-fact;
976
977         incol = vec3(1.0) - (vec3(facm) + fact*(vec3(1.0) - texcol))*(vec3(1.0) - outcol);
978 }
979
980 void mtex_rgb_overlay(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
981 {
982         float facm;
983
984         fact *= facg;
985         facm = 1.0-fact;
986
987         if (outcol.r < 0.5)
988                 incol.r = outcol.r*(facm + 2.0*fact*texcol.r);
989         else
990                 incol.r = 1.0 - (facm + 2.0*fact*(1.0 - texcol.r))*(1.0 - outcol.r);
991
992         if (outcol.g < 0.5)
993                 incol.g = outcol.g*(facm + 2.0*fact*texcol.g);
994         else
995                 incol.g = 1.0 - (facm + 2.0*fact*(1.0 - texcol.g))*(1.0 - outcol.g);
996
997         if (outcol.b < 0.5)
998                 incol.b = outcol.b*(facm + 2.0*fact*texcol.b);
999         else
1000                 incol.b = 1.0 - (facm + 2.0*fact*(1.0 - texcol.b))*(1.0 - outcol.b);
1001 }
1002
1003 void mtex_rgb_sub(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
1004 {
1005         incol = -fact*facg*texcol + outcol;
1006 }
1007
1008 void mtex_rgb_add(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
1009 {
1010         incol = fact*facg*texcol + outcol;
1011 }
1012
1013 void mtex_rgb_div(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
1014 {
1015         float facm;
1016
1017         fact *= facg;
1018         facm = 1.0-fact;
1019
1020         if (texcol.r != 0.0) incol.r = facm*outcol.r + fact*outcol.r/texcol.r;
1021         if (texcol.g != 0.0) incol.g = facm*outcol.g + fact*outcol.g/texcol.g;
1022         if (texcol.b != 0.0) incol.b = facm*outcol.b + fact*outcol.b/texcol.b;
1023 }
1024
1025 void mtex_rgb_diff(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
1026 {
1027         float facm;
1028
1029         fact *= facg;
1030         facm = 1.0-fact;
1031
1032         incol = facm*outcol + fact*abs(texcol - outcol);
1033 }
1034
1035 void mtex_rgb_dark(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
1036 {
1037         float facm, col;
1038
1039         fact *= facg;
1040         facm = 1.0-fact;
1041
1042         incol.r = min(outcol.r, texcol.r) * fact + outcol.r * facm;
1043         incol.g = min(outcol.g, texcol.g) * fact + outcol.g * facm;
1044         incol.b = min(outcol.b, texcol.b) * fact + outcol.b * facm;
1045 }
1046
1047 void mtex_rgb_light(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
1048 {
1049         float facm, col;
1050
1051         fact *= facg;
1052
1053         col = fact*texcol.r;
1054         if (col > outcol.r) incol.r = col; else incol.r = outcol.r;
1055         col = fact*texcol.g;
1056         if (col > outcol.g) incol.g = col; else incol.g = outcol.g;
1057         col = fact*texcol.b;
1058         if (col > outcol.b) incol.b = col; else incol.b = outcol.b;
1059 }
1060
1061 void mtex_rgb_hue(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
1062 {
1063         vec4 col;
1064
1065         mix_hue(fact*facg, vec4(outcol, 1.0), vec4(texcol, 1.0), col);
1066         incol.rgb = col.rgb;
1067 }
1068
1069 void mtex_rgb_sat(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
1070 {
1071         vec4 col;
1072
1073         mix_sat(fact*facg, vec4(outcol, 1.0), vec4(texcol, 1.0), col);
1074         incol.rgb = col.rgb;
1075 }
1076
1077 void mtex_rgb_val(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
1078 {
1079         vec4 col;
1080
1081         mix_val(fact*facg, vec4(outcol, 1.0), vec4(texcol, 1.0), col);
1082         incol.rgb = col.rgb;
1083 }
1084
1085 void mtex_rgb_color(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
1086 {
1087         vec4 col;
1088
1089         mix_color(fact*facg, vec4(outcol, 1.0), vec4(texcol, 1.0), col);
1090         incol.rgb = col.rgb;
1091 }
1092
1093 void mtex_rgb_soft(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
1094 {
1095         float facm;
1096
1097         fact *= facg;
1098         facm = 1.0-fact;
1099
1100         vec3 one = vec3(1.0);
1101         vec3 scr = one - (one - texcol)*(one - outcol);
1102         incol = facm*outcol + fact*((one - texcol)*outcol*texcol + outcol*scr);
1103 }
1104
1105 void mtex_rgb_linear(vec3 outcol, vec3 texcol, float fact, float facg, out vec3 incol)
1106 {
1107         fact *= facg;
1108
1109         if (texcol.r > 0.5)
1110                 incol.r = outcol.r + fact*(2.0*(texcol.r - 0.5));
1111         else
1112                 incol.r = outcol.r + fact*(2.0*(texcol.r) - 1.0);
1113
1114         if (texcol.g > 0.5)
1115                 incol.g = outcol.g + fact*(2.0*(texcol.g - 0.5));
1116         else
1117                 incol.g = outcol.g + fact*(2.0*(texcol.g) - 1.0);
1118
1119         if (texcol.b > 0.5)
1120                 incol.b = outcol.b + fact*(2.0*(texcol.b - 0.5));
1121         else
1122                 incol.b = outcol.b + fact*(2.0*(texcol.b) - 1.0);
1123 }
1124
1125 void mtex_value_vars(inout float fact, float facg, out float facm)
1126 {
1127         fact *= abs(facg);
1128         facm = 1.0-fact;
1129
1130         if (facg < 0.0) {
1131                 float tmp = fact;
1132                 fact = facm;
1133                 facm = tmp;
1134         }
1135 }
1136
1137 void mtex_value_blend(float outcol, float texcol, float fact, float facg, out float incol)
1138 {
1139         float facm;
1140         mtex_value_vars(fact, facg, facm);
1141
1142         incol = fact*texcol + facm*outcol;
1143 }
1144
1145 void mtex_value_mul(float outcol, float texcol, float fact, float facg, out float incol)
1146 {
1147         float facm;
1148         mtex_value_vars(fact, facg, facm);
1149
1150         facm = 1.0 - facg;
1151         incol = (facm + fact*texcol)*outcol;
1152 }
1153
1154 void mtex_value_screen(float outcol, float texcol, float fact, float facg, out float incol)
1155 {
1156         float facm;
1157         mtex_value_vars(fact, facg, facm);
1158
1159         facm = 1.0 - facg;
1160         incol = 1.0 - (facm + fact*(1.0 - texcol))*(1.0 - outcol);
1161 }
1162
1163 void mtex_value_sub(float outcol, float texcol, float fact, float facg, out float incol)
1164 {
1165         float facm;
1166         mtex_value_vars(fact, facg, facm);
1167
1168         fact = -fact;
1169         incol = fact*texcol + outcol;
1170 }
1171
1172 void mtex_value_add(float outcol, float texcol, float fact, float facg, out float incol)
1173 {
1174         float facm;
1175         mtex_value_vars(fact, facg, facm);
1176
1177         fact = fact;
1178         incol = fact*texcol + outcol;
1179 }
1180
1181 void mtex_value_div(float outcol, float texcol, float fact, float facg, out float incol)
1182 {
1183         float facm;
1184         mtex_value_vars(fact, facg, facm);
1185
1186         if (texcol != 0.0)
1187                 incol = facm*outcol + fact*outcol/texcol;
1188         else
1189                 incol = 0.0;
1190 }
1191
1192 void mtex_value_diff(float outcol, float texcol, float fact, float facg, out float incol)
1193 {
1194         float facm;
1195         mtex_value_vars(fact, facg, facm);
1196
1197         incol = facm*outcol + fact*abs(texcol - outcol);
1198 }
1199
1200 void mtex_value_dark(float outcol, float texcol, float fact, float facg, out float incol)
1201 {
1202         float facm;
1203         mtex_value_vars(fact, facg, facm);
1204
1205         incol = facm*outcol + fact*min(outcol, texcol);
1206 }
1207
1208 void mtex_value_light(float outcol, float texcol, float fact, float facg, out float incol)
1209 {
1210         float facm;
1211         mtex_value_vars(fact, facg, facm);
1212
1213         float col = fact*texcol;
1214         if (col > outcol) incol = col; else incol = outcol;
1215 }
1216
1217 void mtex_value_clamp_positive(float fac, out float outfac)
1218 {
1219         outfac = max(fac, 0.0);
1220 }
1221
1222 void mtex_value_clamp(float fac, out float outfac)
1223 {
1224         outfac = clamp(fac, 0.0, 1.0);
1225 }
1226
1227 void mtex_har_divide(float har, out float outhar)
1228 {
1229         outhar = har/128.0;
1230 }
1231
1232 void mtex_har_multiply_clamp(float har, out float outhar)
1233 {
1234         har *= 128.0;
1235
1236         if (har < 1.0) outhar = 1.0;
1237         else if (har > 511.0) outhar = 511.0;
1238         else outhar = har;
1239 }
1240
1241 void mtex_alpha_from_col(vec4 col, out float alpha)
1242 {
1243         alpha = col.a;
1244 }
1245
1246 void mtex_alpha_to_col(vec4 col, float alpha, out vec4 outcol)
1247 {
1248         outcol = vec4(col.rgb, alpha);
1249 }
1250
1251 void mtex_alpha_multiply_value(vec4 col, float value, out vec4 outcol)
1252 {
1253         outcol = vec4(col.rgb, col.a * value);
1254 }
1255
1256 void mtex_rgbtoint(vec4 rgb, out float intensity)
1257 {
1258         intensity = dot(vec3(0.35, 0.45, 0.2), rgb.rgb);
1259 }
1260
1261 void mtex_value_invert(float invalue, out float outvalue)
1262 {
1263         outvalue = 1.0 - invalue;
1264 }
1265
1266 void mtex_rgb_invert(vec4 inrgb, out vec4 outrgb)
1267 {
1268         outrgb = vec4(vec3(1.0) - inrgb.rgb, inrgb.a);
1269 }
1270
1271 void mtex_value_stencil(float stencil, float intensity, out float outstencil, out float outintensity)
1272 {
1273         float fact = intensity;
1274         outintensity = intensity*stencil;
1275         outstencil = stencil*fact;
1276 }
1277
1278 void mtex_rgb_stencil(float stencil, vec4 rgb, out float outstencil, out vec4 outrgb)
1279 {
1280         float fact = rgb.a;
1281         outrgb = vec4(rgb.rgb, rgb.a*stencil);
1282         outstencil = stencil*fact;
1283 }
1284
1285 void mtex_mapping_ofs(vec3 texco, vec3 ofs, out vec3 outtexco)
1286 {
1287         outtexco = texco + ofs;
1288 }
1289
1290 void mtex_mapping_size(vec3 texco, vec3 size, out vec3 outtexco)
1291 {
1292         outtexco = size*texco;
1293 }
1294
1295 void mtex_2d_mapping(vec3 vec, out vec3 outvec)
1296 {
1297         outvec = vec3(vec.xy*0.5 + vec2(0.5), vec.z);
1298 }
1299
1300 vec3 mtex_2d_mapping(vec3 vec)
1301 {
1302         return vec3(vec.xy*0.5 + vec2(0.5), vec.z);
1303 }
1304
1305 void mtex_cube_map(vec3 co, samplerCube ima, out float value, out vec4 color)
1306 {
1307         color = textureCube(ima, co);
1308         value = 1.0;
1309 }
1310
1311 void mtex_cube_map_refl(
1312         samplerCube ima, vec3 vp, vec3 vn, mat4 viewmatrixinverse, mat4 viewmatrix,
1313         out float value, out vec4 color)
1314 {
1315         vec3 viewdirection = vec3(viewmatrixinverse * vec4(vp, 0.0));
1316         vec3 normaldirection = normalize(vec3(vec4(vn, 0.0) * viewmatrix));
1317         vec3 reflecteddirection = reflect(viewdirection, normaldirection);
1318         color = textureCube(ima, reflecteddirection);
1319         value = 1.0;
1320 }
1321
1322 void mtex_image(vec3 texco, sampler2D ima, out float value, out vec4 color)
1323 {
1324         color = texture2D(ima, texco.xy);
1325         value = 1.0;
1326 }
1327
1328 void mtex_normal(vec3 texco, sampler2D ima, out vec3 normal)
1329 {
1330         // The invert of the red channel is to make
1331         // the normal map compliant with the outside world.
1332         // It needs to be done because in Blender
1333         // the normal used points inward.
1334         // Should this ever change this negate must be removed.
1335         vec4 color = texture2D(ima, texco.xy);
1336         normal = 2.0*(vec3(-color.r, color.g, color.b) - vec3(-0.5, 0.5, 0.5));
1337 }
1338
1339 void mtex_bump_normals_init( vec3 vN, out vec3 vNorg, out vec3 vNacc, out float fPrevMagnitude )
1340 {
1341         vNorg = vN;
1342         vNacc = vN;
1343         fPrevMagnitude = 1.0;
1344 }
1345
1346 /** helper method to extract the upper left 3x3 matrix from a 4x4 matrix */
1347 mat3 to_mat3(mat4 m4)
1348 {
1349         mat3 m3;
1350         m3[0] = m4[0].xyz;
1351         m3[1] = m4[1].xyz;
1352         m3[2] = m4[2].xyz;
1353         return m3;
1354 }
1355
1356 void mtex_bump_init_objspace(
1357         vec3 surf_pos, vec3 surf_norm,
1358         mat4 mView, mat4 mViewInv, mat4 mObj, mat4 mObjInv,
1359         float fPrevMagnitude_in, vec3 vNacc_in,
1360         out float fPrevMagnitude_out, out vec3 vNacc_out,
1361         out vec3 vR1, out vec3 vR2, out float fDet)
1362 {
1363         mat3 obj2view = to_mat3(gl_ModelViewMatrix);
1364         mat3 view2obj = to_mat3(gl_ModelViewMatrixInverse);
1365         
1366         vec3 vSigmaS = view2obj * dFdx( surf_pos );
1367         vec3 vSigmaT = view2obj * dFdy( surf_pos );
1368         vec3 vN = normalize( surf_norm * obj2view );
1369
1370         vR1 = cross( vSigmaT, vN );
1371         vR2 = cross( vN, vSigmaS ) ;
1372         fDet = dot ( vSigmaS, vR1 );
1373         
1374         /* pretransform vNacc (in mtex_bump_apply) using the inverse transposed */
1375         vR1 = vR1 * view2obj;
1376         vR2 = vR2 * view2obj;
1377         vN = vN * view2obj;
1378         
1379         float fMagnitude = abs(fDet) * length(vN);
1380         vNacc_out = vNacc_in * (fMagnitude / fPrevMagnitude_in);
1381         fPrevMagnitude_out = fMagnitude;
1382 }
1383
1384 void mtex_bump_init_texturespace(
1385         vec3 surf_pos, vec3 surf_norm,
1386         float fPrevMagnitude_in, vec3 vNacc_in,
1387         out float fPrevMagnitude_out, out vec3 vNacc_out,
1388         out vec3 vR1, out vec3 vR2, out float fDet)
1389 {
1390         vec3 vSigmaS = dFdx( surf_pos );
1391         vec3 vSigmaT = dFdy( surf_pos );
1392         vec3 vN = surf_norm; /* normalized interpolated vertex normal */
1393         
1394         vR1 = normalize( cross( vSigmaT, vN ) );
1395         vR2 = normalize( cross( vN, vSigmaS ) );
1396         fDet = sign( dot(vSigmaS, vR1) );
1397         
1398         float fMagnitude = abs(fDet);
1399         vNacc_out = vNacc_in * (fMagnitude / fPrevMagnitude_in);
1400         fPrevMagnitude_out = fMagnitude;
1401 }
1402
1403 void mtex_bump_init_viewspace(
1404         vec3 surf_pos, vec3 surf_norm,
1405         float fPrevMagnitude_in, vec3 vNacc_in,
1406         out float fPrevMagnitude_out, out vec3 vNacc_out,
1407         out vec3 vR1, out vec3 vR2, out float fDet)
1408 {
1409         vec3 vSigmaS = dFdx( surf_pos );
1410         vec3 vSigmaT = dFdy( surf_pos );
1411         vec3 vN = surf_norm; /* normalized interpolated vertex normal */
1412         
1413         vR1 = cross( vSigmaT, vN );
1414         vR2 = cross( vN, vSigmaS ) ;
1415         fDet = dot ( vSigmaS, vR1 );
1416         
1417         float fMagnitude = abs(fDet);
1418         vNacc_out = vNacc_in * (fMagnitude / fPrevMagnitude_in);
1419         fPrevMagnitude_out = fMagnitude;
1420 }
1421
1422 void mtex_bump_tap3(
1423         vec3 texco, sampler2D ima, float hScale,
1424         out float dBs, out float dBt)
1425 {
1426         vec2 STll = texco.xy;
1427         vec2 STlr = texco.xy + dFdx(texco.xy) ;
1428         vec2 STul = texco.xy + dFdy(texco.xy) ;
1429         
1430         float Hll,Hlr,Hul;
1431         rgbtobw( texture2D(ima, STll), Hll );
1432         rgbtobw( texture2D(ima, STlr), Hlr );
1433         rgbtobw( texture2D(ima, STul), Hul );
1434         
1435         dBs = hScale * (Hlr - Hll);
1436         dBt = hScale * (Hul - Hll);
1437 }
1438
1439 #ifdef BUMP_BICUBIC
1440
1441 void mtex_bump_bicubic(
1442         vec3 texco, sampler2D ima, float hScale,
1443         out float dBs, out float dBt )
1444 {
1445         float Hl;
1446         float Hr;
1447         float Hd;
1448         float Hu;
1449         
1450         vec2 TexDx = dFdx(texco.xy);
1451         vec2 TexDy = dFdy(texco.xy);
1452  
1453         vec2 STl = texco.xy - 0.5 * TexDx ;
1454         vec2 STr = texco.xy + 0.5 * TexDx ;
1455         vec2 STd = texco.xy - 0.5 * TexDy ;
1456         vec2 STu = texco.xy + 0.5 * TexDy ;
1457         
1458         rgbtobw(texture2D(ima, STl), Hl);
1459         rgbtobw(texture2D(ima, STr), Hr);
1460         rgbtobw(texture2D(ima, STd), Hd);
1461         rgbtobw(texture2D(ima, STu), Hu);
1462         
1463         vec2 dHdxy = vec2(Hr - Hl, Hu - Hd);
1464         float fBlend = clamp(1.0-textureQueryLOD(ima, texco.xy).x, 0.0, 1.0);
1465         if (fBlend!=0.0)
1466         {
1467                 // the derivative of the bicubic sampling of level 0
1468                 ivec2 vDim;
1469                 vDim = textureSize(ima, 0);
1470
1471                 // taking the fract part of the texture coordinate is a hardcoded wrap mode.
1472                 // this is acceptable as textures use wrap mode exclusively in 3D view elsewhere in blender. 
1473                 // this is done so that we can still get a valid texel with uvs outside the 0,1 range
1474                 // by texelFetch below, as coordinates are clamped when using this function.
1475                 vec2 fTexLoc = vDim*fract(texco.xy) - vec2(0.5, 0.5);
1476                 ivec2 iTexLoc = ivec2(floor(fTexLoc));
1477                 vec2 t = clamp(fTexLoc - iTexLoc, 0.0, 1.0);            // sat just to be pedantic
1478
1479 /*******************************************************************************************
1480  * This block will replace the one below when one channel textures are properly supported. *
1481  *******************************************************************************************
1482                 vec4 vSamplesUL = textureGather(ima, (iTexLoc+ivec2(-1,-1) + vec2(0.5,0.5))/vDim );
1483                 vec4 vSamplesUR = textureGather(ima, (iTexLoc+ivec2(1,-1) + vec2(0.5,0.5))/vDim );
1484                 vec4 vSamplesLL = textureGather(ima, (iTexLoc+ivec2(-1,1) + vec2(0.5,0.5))/vDim );
1485                 vec4 vSamplesLR = textureGather(ima, (iTexLoc+ivec2(1,1) + vec2(0.5,0.5))/vDim );
1486
1487                 mat4 H = mat4(vSamplesUL.w, vSamplesUL.x, vSamplesLL.w, vSamplesLL.x,
1488                                         vSamplesUL.z, vSamplesUL.y, vSamplesLL.z, vSamplesLL.y,
1489                                         vSamplesUR.w, vSamplesUR.x, vSamplesLR.w, vSamplesLR.x,
1490                                         vSamplesUR.z, vSamplesUR.y, vSamplesLR.z, vSamplesLR.y);
1491 */      
1492                 ivec2 iTexLocMod = iTexLoc + ivec2(-1, -1);
1493
1494                 mat4 H;
1495                 
1496                 for (int i = 0; i < 4; i++) {
1497                         for (int j = 0; j < 4; j++) {
1498                                 ivec2 iTexTmp = iTexLocMod + ivec2(i,j);
1499                                 
1500                                 // wrap texture coordinates manually for texelFetch to work on uvs oitside the 0,1 range.
1501                                 // this is guaranteed to work since we take the fractional part of the uv above.
1502                                 iTexTmp.x = (iTexTmp.x < 0)? iTexTmp.x + vDim.x : ((iTexTmp.x >= vDim.x)? iTexTmp.x - vDim.x : iTexTmp.x);
1503                                 iTexTmp.y = (iTexTmp.y < 0)? iTexTmp.y + vDim.y : ((iTexTmp.y >= vDim.y)? iTexTmp.y - vDim.y : iTexTmp.y);
1504
1505                                 rgbtobw(texelFetch(ima, iTexTmp, 0), H[i][j]);
1506                         }
1507                 }
1508                 
1509                 float x = t.x, y = t.y;
1510                 float x2 = x * x, x3 = x2 * x, y2 = y * y, y3 = y2 * y;
1511
1512                 vec4 X = vec4(-0.5*(x3+x)+x2,           1.5*x3-2.5*x2+1,        -1.5*x3+2*x2+0.5*x,             0.5*(x3-x2));
1513                 vec4 Y = vec4(-0.5*(y3+y)+y2,           1.5*y3-2.5*y2+1,        -1.5*y3+2*y2+0.5*y,             0.5*(y3-y2));
1514                 vec4 dX = vec4(-1.5*x2+2*x-0.5,         4.5*x2-5*x,                     -4.5*x2+4*x+0.5,                1.5*x2-x);
1515                 vec4 dY = vec4(-1.5*y2+2*y-0.5,         4.5*y2-5*y,                     -4.5*y2+4*y+0.5,                1.5*y2-y);
1516         
1517                 // complete derivative in normalized coordinates (mul by vDim)
1518                 vec2 dHdST = vDim * vec2(dot(Y, H * dX), dot(dY, H * X));
1519
1520                 // transform derivative to screen-space
1521                 vec2 dHdxy_bicubic = vec2( dHdST.x * TexDx.x + dHdST.y * TexDx.y,
1522                                                                    dHdST.x * TexDy.x + dHdST.y * TexDy.y );
1523
1524                 // blend between the two
1525                 dHdxy = dHdxy*(1-fBlend) + dHdxy_bicubic*fBlend;
1526         }
1527
1528         dBs = hScale * dHdxy.x;
1529         dBt = hScale * dHdxy.y;
1530 }
1531
1532 #endif
1533
1534 void mtex_bump_tap5(
1535         vec3 texco, sampler2D ima, float hScale,
1536         out float dBs, out float dBt)
1537 {
1538         vec2 TexDx = dFdx(texco.xy);
1539         vec2 TexDy = dFdy(texco.xy);
1540
1541         vec2 STc = texco.xy;
1542         vec2 STl = texco.xy - 0.5 * TexDx ;
1543         vec2 STr = texco.xy + 0.5 * TexDx ;
1544         vec2 STd = texco.xy - 0.5 * TexDy ;
1545         vec2 STu = texco.xy + 0.5 * TexDy ;
1546         
1547         float Hc,Hl,Hr,Hd,Hu;
1548         rgbtobw( texture2D(ima, STc), Hc );
1549         rgbtobw( texture2D(ima, STl), Hl );
1550         rgbtobw( texture2D(ima, STr), Hr );
1551         rgbtobw( texture2D(ima, STd), Hd );
1552         rgbtobw( texture2D(ima, STu), Hu );
1553         
1554         dBs = hScale * (Hr - Hl);
1555         dBt = hScale * (Hu - Hd);
1556 }
1557
1558 void mtex_bump_deriv(
1559         vec3 texco, sampler2D ima, float ima_x, float ima_y, float hScale,
1560         out float dBs, out float dBt)
1561 {
1562         float s = 1.0;          // negate this if flipped texture coordinate
1563         vec2 TexDx = dFdx(texco.xy);
1564         vec2 TexDy = dFdy(texco.xy);
1565         
1566         // this variant using a derivative map is described here
1567         // http://mmikkelsen3d.blogspot.com/2011/07/derivative-maps.html
1568         vec2 dim = vec2(ima_x, ima_y);
1569         vec2 dBduv = hScale*dim*(2.0*texture2D(ima, texco.xy).xy-1.0);
1570         
1571         dBs = dBduv.x*TexDx.x + s*dBduv.y*TexDx.y;
1572         dBt = dBduv.x*TexDy.x + s*dBduv.y*TexDy.y;
1573 }
1574
1575 void mtex_bump_apply(
1576         float fDet, float dBs, float dBt, vec3 vR1, vec3 vR2, vec3 vNacc_in,
1577         out vec3 vNacc_out, out vec3 perturbed_norm)
1578 {
1579         vec3 vSurfGrad = sign(fDet) * ( dBs * vR1 + dBt * vR2 );
1580         
1581         vNacc_out = vNacc_in - vSurfGrad;
1582         perturbed_norm = normalize( vNacc_out );
1583 }
1584
1585 void mtex_bump_apply_texspace(
1586         float fDet, float dBs, float dBt, vec3 vR1, vec3 vR2,
1587         sampler2D ima, vec3 texco, float ima_x, float ima_y, vec3 vNacc_in,
1588         out vec3 vNacc_out, out vec3 perturbed_norm)
1589 {
1590         vec2 TexDx = dFdx(texco.xy);
1591         vec2 TexDy = dFdy(texco.xy);
1592
1593         vec3 vSurfGrad = sign(fDet) * ( 
1594                     dBs / length( vec2(ima_x*TexDx.x, ima_y*TexDx.y) ) * vR1 + 
1595                     dBt / length( vec2(ima_x*TexDy.x, ima_y*TexDy.y) ) * vR2 );
1596
1597         vNacc_out = vNacc_in - vSurfGrad;
1598         perturbed_norm = normalize( vNacc_out );
1599 }
1600
1601 void mtex_negate_texnormal(vec3 normal, out vec3 outnormal)
1602 {
1603         outnormal = vec3(-normal.x, -normal.y, normal.z);
1604 }
1605
1606 void mtex_nspace_tangent(vec4 tangent, vec3 normal, vec3 texnormal, out vec3 outnormal)
1607 {
1608         vec3 B = tangent.w * cross(normal, tangent.xyz);
1609
1610         outnormal = texnormal.x*tangent.xyz + texnormal.y*B + texnormal.z*normal;
1611         outnormal = normalize(outnormal);
1612 }
1613
1614 void mtex_nspace_world(mat4 viewmat, vec3 texnormal, out vec3 outnormal)
1615 {
1616         outnormal = normalize((viewmat*vec4(texnormal, 0.0)).xyz);
1617 }
1618
1619 void mtex_nspace_object(vec3 texnormal, out vec3 outnormal)
1620 {
1621         outnormal = normalize(gl_NormalMatrix * texnormal);
1622 }
1623
1624 void mtex_blend_normal(float norfac, vec3 normal, vec3 newnormal, out vec3 outnormal)
1625 {
1626         outnormal = (1.0 - norfac)*normal + norfac*newnormal;
1627         outnormal = normalize(outnormal);
1628 }
1629
1630 /******* MATERIAL *********/
1631
1632 void lamp_visibility_sun_hemi(vec3 lampvec, out vec3 lv, out float dist, out float visifac)
1633 {
1634         lv = lampvec;
1635         dist = 1.0;
1636         visifac = 1.0;
1637 }
1638
1639 void lamp_visibility_other(vec3 co, vec3 lampco, out vec3 lv, out float dist, out float visifac)
1640 {
1641         lv = co - lampco;
1642         dist = length(lv);
1643         lv = normalize(lv);
1644         visifac = 1.0;
1645 }
1646
1647 void lamp_falloff_invlinear(float lampdist, float dist, out float visifac)
1648 {
1649         visifac = lampdist/(lampdist + dist);
1650 }
1651
1652 void lamp_falloff_invsquare(float lampdist, float dist, out float visifac)
1653 {
1654         visifac = lampdist/(lampdist + dist*dist);
1655 }
1656
1657 void lamp_falloff_sliders(float lampdist, float ld1, float ld2, float dist, out float visifac)
1658 {
1659         float lampdistkw = lampdist*lampdist;
1660
1661         visifac = lampdist/(lampdist + ld1*dist);
1662         visifac *= lampdistkw/(lampdistkw + ld2*dist*dist);
1663 }
1664
1665 void lamp_falloff_invcoefficients(float coeff_const, float coeff_lin, float coeff_quad, float dist, out float visifac)
1666 {
1667         vec3 coeff = vec3(coeff_const, coeff_lin, coeff_quad);
1668         vec3 d_coeff = vec3(1.0, dist, dist*dist);
1669         float visifac_r = dot(coeff, d_coeff);
1670         if (visifac_r > 0.0)
1671                 visifac = 1.0 / visifac_r;
1672         else
1673                 visifac = 0.0;
1674 }
1675
1676 void lamp_falloff_curve(float lampdist, sampler2D curvemap, float dist, out float visifac)
1677 {
1678         visifac = texture2D(curvemap, vec2(dist/lampdist, 0.0)).x;
1679 }
1680
1681 void lamp_visibility_sphere(float lampdist, float dist, float visifac, out float outvisifac)
1682 {
1683         float t= lampdist - dist;
1684
1685         outvisifac= visifac*max(t, 0.0)/lampdist;
1686 }
1687
1688 void lamp_visibility_spot_square(vec3 lampvec, mat4 lampimat, vec2 scale, vec3 lv, out float inpr)
1689 {
1690         if (dot(lv, lampvec) > 0.0) {
1691                 vec3 lvrot = (lampimat*vec4(lv, 0.0)).xyz;
1692                 /* without clever non-uniform scale, we could do: */
1693                 // float x = max(abs(lvrot.x / lvrot.z), abs(lvrot.y / lvrot.z));
1694                 float x = max(abs((lvrot.x / scale.x) / lvrot.z), abs((lvrot.y / scale.y) / lvrot.z));
1695
1696                 inpr = 1.0/sqrt(1.0 + x*x);
1697         }
1698         else
1699                 inpr = 0.0;
1700 }
1701
1702 void lamp_visibility_spot_circle(vec3 lampvec, mat4 lampimat, vec2 scale, vec3 lv, out float inpr)
1703 {
1704         /* without clever non-uniform scale, we could do: */
1705         // inpr = dot(lv, lampvec);
1706         if (dot(lv, lampvec) > 0.0) {
1707                 vec3 lvrot = (lampimat * vec4(lv, 0.0)).xyz;
1708                 float x = abs(lvrot.x / lvrot.z);
1709                 float y = abs(lvrot.y / lvrot.z);
1710
1711                 float ellipse = abs((x * x) / (scale.x * scale.x) + (y * y) / (scale.y * scale.y));
1712
1713                 inpr = 1.0 / sqrt(1.0 + ellipse);
1714         }
1715         else
1716                 inpr = 0.0;
1717 }
1718
1719 void lamp_visibility_spot(float spotsi, float spotbl, float inpr, float visifac, out float outvisifac)
1720 {
1721         float t = spotsi;
1722
1723         if (inpr <= t) {
1724                 outvisifac = 0.0;
1725         }
1726         else {
1727                 t = inpr - t;
1728
1729                 /* soft area */
1730                 if (spotbl != 0.0)
1731                         inpr *= smoothstep(0.0, 1.0, t/spotbl);
1732
1733                 outvisifac = visifac*inpr;
1734         }
1735 }
1736
1737 void lamp_visibility_clamp(float visifac, out float outvisifac)
1738 {
1739         outvisifac = (visifac < 0.001)? 0.0: visifac;
1740 }
1741
1742 void world_paper_view(vec3 vec, out vec3 outvec)
1743 {
1744         vec3 nvec = normalize(vec);
1745         outvec = (gl_ProjectionMatrix[3][3] == 0.0) ? vec3(nvec.x, 0.0, nvec.y) : vec3(0.0, 0.0, -1.0);
1746 }
1747
1748 void world_zen_mapping(vec3 view, float zenup, float zendown, out float zenfac)
1749 {
1750         if (view.z >= 0.0)
1751                 zenfac = zenup;
1752         else
1753                 zenfac = zendown;
1754 }
1755
1756 void world_blend_paper_real(vec3 vec, out float blend)
1757 {
1758         blend = abs(vec.y);
1759 }
1760
1761 void world_blend_paper(vec3 vec, out float blend)
1762 {
1763         blend = (vec.y + 1.0) * 0.5;
1764 }
1765
1766 void world_blend_real(vec3 vec, out float blend)
1767 {
1768         blend = abs(normalize(vec).z);
1769 }
1770
1771 void world_blend(vec3 vec, out float blend)
1772 {
1773         blend = (normalize(vec).z + 1) * 0.5;
1774 }
1775
1776 void shade_view(vec3 co, out vec3 view)
1777 {
1778         /* handle perspective/orthographic */
1779         view = (gl_ProjectionMatrix[3][3] == 0.0)? normalize(co): vec3(0.0, 0.0, -1.0);
1780 }
1781
1782 void shade_tangent_v(vec3 lv, vec3 tang, out vec3 vn)
1783 {
1784         vec3 c = cross(lv, tang);
1785         vec3 vnor = cross(c, tang);
1786
1787         vn = -normalize(vnor);
1788 }
1789
1790 void shade_inp(vec3 vn, vec3 lv, out float inp)
1791 {
1792         inp = dot(vn, lv);
1793 }
1794
1795 void shade_is_no_diffuse(out float is)
1796 {
1797         is = 0.0;
1798 }
1799
1800 void shade_is_hemi(float inp, out float is)
1801 {
1802         is = 0.5*inp + 0.5;
1803 }
1804
1805 float area_lamp_energy(mat4 area, vec3 co, vec3 vn)
1806 {
1807         vec3 vec[4], c[4];
1808         float rad[4], fac;
1809         
1810         vec[0] = normalize(co - area[0].xyz);
1811         vec[1] = normalize(co - area[1].xyz);
1812         vec[2] = normalize(co - area[2].xyz);
1813         vec[3] = normalize(co - area[3].xyz);
1814
1815         c[0] = normalize(cross(vec[0], vec[1]));
1816         c[1] = normalize(cross(vec[1], vec[2]));
1817         c[2] = normalize(cross(vec[2], vec[3]));
1818         c[3] = normalize(cross(vec[3], vec[0]));
1819
1820         rad[0] = acos(dot(vec[0], vec[1]));
1821         rad[1] = acos(dot(vec[1], vec[2]));
1822         rad[2] = acos(dot(vec[2], vec[3]));
1823         rad[3] = acos(dot(vec[3], vec[0]));
1824
1825         fac=  rad[0]*dot(vn, c[0]);
1826         fac+= rad[1]*dot(vn, c[1]);
1827         fac+= rad[2]*dot(vn, c[2]);
1828         fac+= rad[3]*dot(vn, c[3]);
1829
1830         return max(fac, 0.0);
1831 }
1832
1833 void shade_inp_area(
1834         vec3 position, vec3 lampco, vec3 lampvec, vec3 vn, mat4 area, float areasize, float k,
1835         out float inp)
1836 {
1837         vec3 co = position;
1838         vec3 vec = co - lampco;
1839
1840         if (dot(vec, lampvec) < 0.0) {
1841                 inp = 0.0;
1842         }
1843         else {
1844                 float intens = area_lamp_energy(area, co, vn);
1845
1846                 inp = pow(intens*areasize, k);
1847         }
1848 }
1849
1850 void shade_diffuse_oren_nayer(float nl, vec3 n, vec3 l, vec3 v, float rough, out float is)
1851 {
1852         vec3 h = normalize(v + l);
1853         float nh = max(dot(n, h), 0.0);
1854         float nv = max(dot(n, v), 0.0);
1855         float realnl = dot(n, l);
1856
1857         if (realnl < 0.0) {
1858                 is = 0.0;
1859         }
1860         else if (nl < 0.0) {
1861                 is = 0.0;
1862         }
1863         else {
1864                 float vh = max(dot(v, h), 0.0);
1865                 float Lit_A = acos(realnl);
1866                 float View_A = acos(nv);
1867
1868                 vec3 Lit_B = normalize(l - realnl*n);
1869                 vec3 View_B = normalize(v - nv*n);
1870
1871                 float t = max(dot(Lit_B, View_B), 0.0);
1872
1873                 float a, b;
1874
1875                 if (Lit_A > View_A) {
1876                         a = Lit_A;
1877                         b = View_A;
1878                 }
1879                 else {
1880                         a = View_A;
1881                         b = Lit_A;
1882                 }
1883
1884                 float A = 1.0 - (0.5*((rough*rough)/((rough*rough) + 0.33)));
1885                 float B = 0.45*((rough*rough)/((rough*rough) + 0.09));
1886
1887                 b *= 0.95;
1888                 is = nl*(A + (B * t * sin(a) * tan(b)));
1889         }
1890 }
1891
1892 void shade_diffuse_toon(vec3 n, vec3 l, vec3 v, float size, float tsmooth, out float is)
1893 {
1894         float rslt = dot(n, l);
1895         float ang = acos(rslt);
1896
1897         if (ang < size) is = 1.0;
1898         else if (ang > (size + tsmooth) || tsmooth == 0.0) is = 0.0;
1899         else is = 1.0 - ((ang - size)/tsmooth);
1900 }
1901
1902 void shade_diffuse_minnaert(float nl, vec3 n, vec3 v, float darkness, out float is)
1903 {
1904         if (nl <= 0.0) {
1905                 is = 0.0;
1906         }
1907         else {
1908                 float nv = max(dot(n, v), 0.0);
1909
1910                 if (darkness <= 1.0)
1911                         is = nl*pow(max(nv*nl, 0.1), darkness - 1.0);
1912                 else
1913                         is = nl*pow(1.0001 - nv, darkness - 1.0);
1914         }
1915 }
1916
1917 float fresnel_fac(vec3 view, vec3 vn, float grad, float fac)
1918 {
1919         float t1, t2;
1920         float ffac;
1921
1922         if (fac==0.0) {
1923                 ffac = 1.0;
1924         }
1925         else {
1926                 t1= dot(view, vn);
1927                 if (t1>0.0)  t2= 1.0+t1;
1928                 else t2= 1.0-t1;
1929
1930                 t2= grad + (1.0-grad)*pow(t2, fac);
1931
1932                 if (t2<0.0) ffac = 0.0;
1933                 else if (t2>1.0) ffac = 1.0;
1934                 else ffac = t2;
1935         }
1936
1937         return ffac;
1938 }
1939
1940 void shade_diffuse_fresnel(vec3 vn, vec3 lv, vec3 view, float fac_i, float fac, out float is)
1941 {
1942         is = fresnel_fac(lv, vn, fac_i, fac);
1943 }
1944
1945 void shade_cubic(float is, out float outis)
1946 {
1947         if (is>0.0 && is<1.0)
1948                 outis= smoothstep(0.0, 1.0, is);
1949         else
1950                 outis= is;
1951 }
1952
1953 void shade_visifac(float i, float visifac, float refl, out float outi)
1954 {
1955         /*if (i > 0.0)*/
1956                 outi = max(i*visifac*refl, 0.0);
1957         /*else
1958                 outi = i;*/
1959 }
1960
1961 void shade_tangent_v_spec(vec3 tang, out vec3 vn)
1962 {
1963         vn = tang;
1964 }
1965
1966 void shade_add_to_diffuse(float i, vec3 lampcol, vec3 col, out vec3 outcol)
1967 {
1968         if (i > 0.0)
1969                 outcol = i*lampcol*col;
1970         else
1971                 outcol = vec3(0.0, 0.0, 0.0);
1972 }
1973
1974 void shade_hemi_spec(vec3 vn, vec3 lv, vec3 view, float spec, float hard, float visifac, out float t)
1975 {
1976         lv += view;
1977         lv = normalize(lv);
1978
1979         t = dot(vn, lv);
1980         t = 0.5*t + 0.5;
1981
1982         t = visifac*spec*pow(t, hard);
1983 }
1984
1985 void shade_phong_spec(vec3 n, vec3 l, vec3 v, float hard, out float specfac)
1986 {
1987         vec3 h = normalize(l + v);
1988         float rslt = max(dot(h, n), 0.0);
1989
1990         specfac = pow(rslt, hard);
1991 }
1992
1993 void shade_cooktorr_spec(vec3 n, vec3 l, vec3 v, float hard, out float specfac)
1994 {
1995         vec3 h = normalize(v + l);
1996         float nh = dot(n, h);
1997
1998         if (nh < 0.0) {
1999                 specfac = 0.0;
2000         }
2001         else {
2002                 float nv = max(dot(n, v), 0.0);
2003                 float i = pow(nh, hard);
2004
2005                 i = i/(0.1+nv);
2006                 specfac = i;
2007         }
2008 }
2009
2010 void shade_blinn_spec(vec3 n, vec3 l, vec3 v, float refrac, float spec_power, out float specfac)
2011 {
2012         if (refrac < 1.0) {
2013                 specfac = 0.0;
2014         }
2015         else if (spec_power == 0.0) {
2016                 specfac = 0.0;
2017         }
2018         else {
2019                 if (spec_power<100.0)
2020                         spec_power= sqrt(1.0/spec_power);
2021                 else
2022                         spec_power= 10.0/spec_power;
2023
2024                 vec3 h = normalize(v + l);
2025                 float nh = dot(n, h);
2026                 if (nh < 0.0) {
2027                         specfac = 0.0;
2028                 }
2029                 else {
2030                         float nv = max(dot(n, v), 0.01);
2031                         float nl = dot(n, l);
2032                         if (nl <= 0.01) {
2033                                 specfac = 0.0;
2034                         }
2035                         else {
2036                                 float vh = max(dot(v, h), 0.01);
2037
2038                                 float a = 1.0;
2039                                 float b = (2.0*nh*nv)/vh;
2040                                 float c = (2.0*nh*nl)/vh;
2041
2042                                 float g = 0.0;
2043
2044                                 if (a < b && a < c) g = a;
2045                                 else if (b < a && b < c) g = b;
2046                                 else if (c < a && c < b) g = c;
2047
2048                                 float p = sqrt(((refrac * refrac) + (vh * vh) - 1.0));
2049                                 float f = ((((p - vh) * (p - vh)) / ((p + vh) * (p + vh))) *
2050                                            (1.0 + ((((vh * (p + vh)) - 1.0) * ((vh * (p + vh)) - 1.0)) /
2051                                                    (((vh * (p - vh)) + 1.0) * ((vh * (p - vh)) + 1.0)))));
2052                                 float ang = acos(nh);
2053
2054                                 specfac = max(f*g*exp_blender((-(ang*ang)/(2.0*spec_power*spec_power))), 0.0);
2055                         }
2056                 }
2057         }
2058 }
2059
2060 void shade_wardiso_spec(vec3 n, vec3 l, vec3 v, float rms, out float specfac)
2061 {
2062         vec3 h = normalize(l + v);
2063         float nh = max(dot(n, h), 0.001);
2064         float nv = max(dot(n, v), 0.001);
2065         float nl = max(dot(n, l), 0.001);
2066         float angle = tan(acos(nh));
2067         float alpha = max(rms, 0.001);
2068
2069         specfac= nl * (1.0/(4.0*M_PI*alpha*alpha))*(exp_blender(-(angle*angle)/(alpha*alpha))/(sqrt(nv*nl)));
2070 }
2071
2072 void shade_toon_spec(vec3 n, vec3 l, vec3 v, float size, float tsmooth, out float specfac)
2073 {
2074         vec3 h = normalize(l + v);
2075         float rslt = dot(h, n);
2076         float ang = acos(rslt);
2077
2078         if (ang < size) rslt = 1.0;
2079         else if (ang >= (size + tsmooth) || tsmooth == 0.0) rslt = 0.0;
2080         else rslt = 1.0 - ((ang - size)/tsmooth);
2081
2082         specfac = rslt;
2083 }
2084
2085 void shade_spec_area_inp(float specfac, float inp, out float outspecfac)
2086 {
2087         outspecfac = specfac*inp;
2088 }
2089
2090 void shade_spec_t(float shadfac, float spec, float visifac, float specfac, out float t)
2091 {
2092         t = shadfac*spec*visifac*specfac;
2093 }
2094
2095 void shade_add_spec(float t, vec3 lampcol, vec3 speccol, out vec3 outcol)
2096 {
2097         outcol = t*lampcol*speccol;
2098 }
2099
2100 void shade_add_mirror(vec3 mir, vec4 refcol, vec3 combined, out vec3 result)
2101 {
2102         result = mir * refcol.gba + (vec3(1.0) - mir * refcol.rrr) * combined;
2103 }
2104
2105 void alpha_spec_correction(vec3 spec, float spectra, float alpha, out float outalpha)
2106 {
2107         if (spectra > 0.0) {
2108                 float t = clamp(max(max(spec.r, spec.g), spec.b) * spectra, 0.0, 1.0);
2109                 outalpha = (1.0 - t) * alpha + t;
2110         }
2111         else {
2112                 outalpha = alpha;
2113         }
2114 }
2115
2116 void shade_add(vec4 col1, vec4 col2, out vec4 outcol)
2117 {
2118         outcol = col1 + col2;
2119 }
2120
2121 void shade_madd(vec4 col, vec4 col1, vec4 col2, out vec4 outcol)
2122 {
2123         outcol = col + col1*col2;
2124 }
2125
2126 void shade_add_clamped(vec4 col1, vec4 col2, out vec4 outcol)
2127 {
2128         outcol = col1 + max(col2, vec4(0.0, 0.0, 0.0, 0.0));
2129 }
2130
2131 void shade_madd_clamped(vec4 col, vec4 col1, vec4 col2, out vec4 outcol)
2132 {
2133         outcol = col + max(col1*col2, vec4(0.0, 0.0, 0.0, 0.0));
2134 }
2135
2136 void shade_maddf(vec4 col, float f, vec4 col1, out vec4 outcol)
2137 {
2138         outcol = col + f*col1;
2139 }
2140
2141 void shade_mul(vec4 col1, vec4 col2, out vec4 outcol)
2142 {
2143         outcol = col1*col2;
2144 }
2145
2146 void shade_mul_value(float fac, vec4 col, out vec4 outcol)
2147 {
2148         outcol = col*fac;
2149 }
2150
2151 void shade_mul_value_v3(float fac, vec3 col, out vec3 outcol)
2152 {
2153         outcol = col*fac;
2154 }
2155
2156 void shade_obcolor(vec4 col, vec4 obcol, out vec4 outcol)
2157 {
2158         outcol = vec4(col.rgb*obcol.rgb, col.a);
2159 }
2160
2161 void ramp_rgbtobw(vec3 color, out float outval)
2162 {
2163         outval = color.r*0.3 + color.g*0.58 + color.b*0.12;
2164 }
2165
2166 void shade_only_shadow(float i, float shadfac, float energy, vec3 shadcol, out vec3 outshadrgb)
2167 {
2168         outshadrgb = i*energy*(1.0 - shadfac)*(vec3(1.0)-shadcol);
2169 }
2170
2171 void shade_only_shadow_diffuse(vec3 shadrgb, vec3 rgb, vec4 diff, out vec4 outdiff)
2172 {
2173         outdiff = diff - vec4(rgb*shadrgb, 0.0);
2174 }
2175
2176 void shade_only_shadow_specular(vec3 shadrgb, vec3 specrgb, vec4 spec, out vec4 outspec)
2177 {
2178         outspec = spec - vec4(specrgb*shadrgb, 0.0);
2179 }
2180
2181 void shade_clamp_positive(vec4 col, out vec4 outcol)
2182 {
2183         outcol = max(col, vec4(0.0));
2184 }
2185
2186 void test_shadowbuf(
2187         vec3 rco, sampler2DShadow shadowmap, mat4 shadowpersmat, float shadowbias, float inp,
2188         out float result)
2189 {
2190         if (inp <= 0.0) {
2191                 result = 0.0;
2192         }
2193         else {
2194                 vec4 co = shadowpersmat*vec4(rco, 1.0);
2195
2196                 //float bias = (1.5 - inp*inp)*shadowbias;
2197                 co.z -= shadowbias*co.w;
2198                 
2199                 if (co.w > 0.0 && co.x > 0.0 && co.x/co.w < 1.0 && co.y > 0.0 && co.y/co.w < 1.0)
2200                         result = shadow2DProj(shadowmap, co).x;
2201                 else
2202                         result = 1.0;
2203         }
2204 }
2205
2206 void test_shadowbuf_vsm(
2207         vec3 rco, sampler2D shadowmap, mat4 shadowpersmat, float shadowbias, float bleedbias, float inp,
2208         out float result)
2209 {
2210         if (inp <= 0.0) {
2211                 result = 0.0;
2212         }
2213         else {
2214                 vec4 co = shadowpersmat*vec4(rco, 1.0);
2215                 if (co.w > 0.0 && co.x > 0.0 && co.x/co.w < 1.0 && co.y > 0.0 && co.y/co.w < 1.0) {
2216                         vec2 moments = texture2DProj(shadowmap, co).rg;
2217                         float dist = co.z/co.w;
2218                         float p = 0.0;
2219                         
2220                         if (dist <= moments.x)
2221                                 p = 1.0;
2222
2223                         float variance = moments.y - (moments.x*moments.x);
2224                         variance = max(variance, shadowbias/10.0);
2225
2226                         float d = moments.x - dist;
2227                         float p_max = variance / (variance + d*d);
2228
2229                         // Now reduce light-bleeding by removing the [0, x] tail and linearly rescaling (x, 1]
2230                         p_max = clamp((p_max-bleedbias)/(1.0-bleedbias), 0.0, 1.0);
2231
2232                         result = max(p, p_max);
2233                 }
2234                 else {
2235                         result = 1.0;
2236                 }
2237         }
2238 }
2239
2240 void shadows_only(
2241         vec3 rco, sampler2DShadow shadowmap, mat4 shadowpersmat,
2242         float shadowbias, vec3 shadowcolor, float inp,
2243         out vec3 result)
2244 {
2245         result = vec3(1.0);
2246
2247         if (inp > 0.0) {
2248                 float shadfac;
2249
2250                 test_shadowbuf(rco, shadowmap, shadowpersmat, shadowbias, inp, shadfac);
2251                 result -= (1.0 - shadfac) * (vec3(1.0) - shadowcolor);
2252         }
2253 }
2254
2255 void shadows_only_vsm(
2256         vec3 rco, sampler2D shadowmap, mat4 shadowpersmat,
2257         float shadowbias, float bleedbias, vec3 shadowcolor, float inp,
2258         out vec3 result)
2259 {
2260         result = vec3(1.0);
2261
2262         if (inp > 0.0) {
2263                 float shadfac;
2264
2265                 test_shadowbuf_vsm(rco, shadowmap, shadowpersmat, shadowbias, bleedbias, inp, shadfac);
2266                 result -= (1.0 - shadfac) * (vec3(1.0) - shadowcolor);
2267         }
2268 }
2269
2270 void shade_light_texture(vec3 rco, sampler2D cookie, mat4 shadowpersmat, out vec4 result)
2271 {
2272
2273         vec4 co = shadowpersmat*vec4(rco, 1.0);
2274
2275         result = texture2DProj(cookie, co);
2276 }
2277
2278 void shade_exposure_correct(vec3 col, float linfac, float logfac, out vec3 outcol)
2279 {
2280         outcol = linfac*(1.0 - exp(col*logfac));
2281 }
2282
2283 void shade_mist_factor(
2284         vec3 co, float enable, float miststa, float mistdist, float misttype, float misi,
2285         out float outfac)
2286 {
2287         if (enable == 1.0) {
2288                 float fac, zcor;
2289
2290                 zcor = (gl_ProjectionMatrix[3][3] == 0.0)? length(co): -co[2];
2291                 
2292                 fac = clamp((zcor - miststa) / mistdist, 0.0, 1.0);
2293                 if (misttype == 0.0) fac *= fac;
2294                 else if (misttype == 1.0);
2295                 else fac = sqrt(fac);
2296
2297                 outfac = 1.0 - (1.0 - fac) * (1.0 - misi);
2298         }
2299         else {
2300                 outfac = 0.0;
2301         }
2302 }
2303
2304 void shade_world_mix(vec3 hor, vec4 col, out vec4 outcol)
2305 {
2306         float fac = clamp(col.a, 0.0, 1.0);
2307         outcol = vec4(mix(hor, col.rgb, fac), col.a);
2308 }
2309
2310 void shade_alpha_opaque(vec4 col, out vec4 outcol)
2311 {
2312         outcol = vec4(col.rgb, 1.0);
2313 }
2314
2315 void shade_alpha_obcolor(vec4 col, vec4 obcol, out vec4 outcol)
2316 {
2317         outcol = vec4(col.rgb, col.a*obcol.a);
2318 }
2319
2320 /*********** NEW SHADER UTILITIES **************/
2321
2322 float fresnel_dielectric(vec3 Incoming, vec3 Normal, float eta)
2323 {
2324         /* compute fresnel reflectance without explicitly computing
2325          * the refracted direction */
2326         float c = abs(dot(Incoming, Normal));
2327         float g = eta * eta - 1.0 + c * c;
2328         float result;
2329
2330         if (g > 0.0) {
2331                 g = sqrt(g);
2332                 float A =(g - c)/(g + c);
2333                 float B =(c *(g + c)- 1.0)/(c *(g - c)+ 1.0);
2334                 result = 0.5 * A * A *(1.0 + B * B);
2335         }
2336         else {
2337                 result = 1.0;  /* TIR (no refracted component) */
2338         }
2339
2340         return result;
2341 }
2342
2343 float hypot(float x, float y)
2344 {
2345         return sqrt(x*x + y*y);
2346 }
2347
2348 void generated_from_orco(vec3 orco, out vec3 generated)
2349 {
2350         generated = orco * 0.5 + vec3(0.5);
2351 }
2352
2353 float integer_noise(int n)
2354 {
2355         int nn;
2356         n = (n + 1013) & 0x7fffffff;
2357         n = (n >> 13) ^ n;
2358         nn = (n * (n * n * 60493 + 19990303) + 1376312589) & 0x7fffffff;
2359         return 0.5 * (float(nn) / 1073741824.0);
2360 }
2361
2362 int floor_to_int(float x)
2363 {
2364         return int(floor(x));
2365 }
2366
2367 #ifdef BIT_OPERATIONS
2368 uint hash(uint kx, uint ky, uint kz)
2369 {
2370 #define rot(x,k) (((x)<<(k)) | ((x)>>(32-(k))))
2371 #define final(a,b,c) \
2372 { \
2373         c ^= b; c -= rot(b,14); \
2374         a ^= c; a -= rot(c,11); \
2375         b ^= a; b -= rot(a,25); \
2376         c ^= b; c -= rot(b,16); \
2377         a ^= c; a -= rot(c,4);  \
2378         b ^= a; b -= rot(a,14); \
2379         c ^= b; c -= rot(b,24); \
2380 }
2381         // now hash the data!
2382         uint a, b, c, len = 3u;
2383         a = b = c = 0xdeadbeefu + (len << 2u) + 13u;
2384
2385         c += kz;
2386         b += ky;
2387         a += kx;
2388         final(a, b, c);
2389
2390         return c;
2391 #undef rot
2392 #undef final
2393 }
2394
2395 uint hash(int kx, int ky, int kz)
2396 {
2397         return hash(uint(kx), uint(ky), uint(kz));
2398 }
2399
2400 float bits_to_01(uint bits)
2401 {
2402         float x = float(bits) * (1.0 / float(0xffffffffu));
2403         return x;
2404 }
2405
2406 float cellnoise(vec3 p)
2407 {
2408         int ix = floor_to_int(p.x);
2409         int iy = floor_to_int(p.y);
2410         int iz = floor_to_int(p.z);
2411
2412         return bits_to_01(hash(uint(ix), uint(iy), uint(iz)));
2413 }
2414
2415 vec3 cellnoise_color(vec3 p)
2416 {
2417         float r = cellnoise(p);
2418         float g = cellnoise(vec3(p.y, p.x, p.z));
2419         float b = cellnoise(vec3(p.y, p.z, p.x));
2420
2421         return vec3(r, g, b);
2422 }
2423 #endif  // BIT_OPERATIONS
2424
2425 float floorfrac(float x, out int i)
2426 {
2427         i = floor_to_int(x);
2428         return x - i;
2429 }
2430
2431 /*********** NEW SHADER NODES ***************/
2432
2433 #define NUM_LIGHTS 3
2434
2435 /* bsdfs */
2436
2437 void node_bsdf_diffuse(vec4 color, float roughness, vec3 N, out vec4 result)
2438 {
2439         /* ambient light */
2440         vec3 L = vec3(0.2);
2441
2442         /* directional lights */
2443         for (int i = 0; i < NUM_LIGHTS; i++) {
2444                 vec3 light_position = gl_LightSource[i].position.xyz;
2445                 vec3 light_diffuse = gl_LightSource[i].diffuse.rgb;
2446
2447                 float bsdf = max(dot(N, light_position), 0.0);
2448                 L += light_diffuse*bsdf;
2449         }
2450
2451         result = vec4(L*color.rgb, 1.0);
2452 }
2453
2454 void node_bsdf_glossy(vec4 color, float roughness, vec3 N, out vec4 result)
2455 {
2456         /* ambient light */
2457         vec3 L = vec3(0.2);
2458
2459         /* directional lights */
2460         for (int i = 0; i < NUM_LIGHTS; i++) {
2461                 vec3 light_position = gl_LightSource[i].position.xyz;
2462                 vec3 H = gl_LightSource[i].halfVector.xyz;
2463                 vec3 light_diffuse = gl_LightSource[i].diffuse.rgb;
2464                 vec3 light_specular = gl_LightSource[i].specular.rgb;
2465
2466                 /* we mix in some diffuse so low roughness still shows up */
2467                 float bsdf = 0.5*pow(max(dot(N, H), 0.0), 1.0/roughness);
2468                 bsdf += 0.5*max(dot(N, light_position), 0.0);
2469                 L += light_specular*bsdf;
2470         }
2471
2472         result = vec4(L*color.rgb, 1.0);
2473 }
2474
2475 void node_bsdf_anisotropic(
2476         vec4 color, float roughness, float anisotropy, float rotation, vec3 N, vec3 T,
2477         out vec4 result)
2478 {
2479         node_bsdf_diffuse(color, 0.0, N, result);
2480 }
2481
2482 void node_bsdf_glass(vec4 color, float roughness, float ior, vec3 N, out vec4 result)
2483 {
2484         node_bsdf_diffuse(color, 0.0, N, result);
2485 }
2486
2487 void node_bsdf_toon(vec4 color, float size, float tsmooth, vec3 N, out vec4 result)
2488 {
2489         node_bsdf_diffuse(color, 0.0, N, result);
2490 }
2491
2492 void node_bsdf_translucent(vec4 color, vec3 N, out vec4 result)
2493 {
2494         node_bsdf_diffuse(color, 0.0, N, result);
2495 }
2496
2497 void node_bsdf_transparent(vec4 color, out vec4 result)
2498 {
2499         /* this isn't right */
2500         result.r = color.r;
2501         result.g = color.g;
2502         result.b = color.b;
2503         result.a = 0.0;
2504 }
2505
2506 void node_bsdf_velvet(vec4 color, float sigma, vec3 N, out vec4 result)
2507 {
2508         node_bsdf_diffuse(color, 0.0, N, result);
2509 }
2510
2511 void node_subsurface_scattering(
2512         vec4 color, float scale, vec3 radius, float sharpen, float texture_blur, vec3 N,
2513         out vec4 result)
2514 {
2515         node_bsdf_diffuse(color, 0.0, N, result);
2516 }
2517
2518 void node_bsdf_hair(vec4 color, float offset, float roughnessu, float roughnessv, vec3 tangent, out vec4 result)
2519 {
2520         result = color;
2521 }
2522
2523 void node_bsdf_refraction(vec4 color, float roughness, float ior, vec3 N, out vec4 result)
2524 {
2525         node_bsdf_diffuse(color, 0.0, N, result);
2526 }
2527
2528 void node_ambient_occlusion(vec4 color, out vec4 result)
2529 {
2530         result = color;
2531 }
2532
2533 /* emission */
2534
2535 void node_emission(vec4 color, float strength, vec3 N, out vec4 result)
2536 {
2537         result = color*strength;
2538 }
2539
2540 /* background */
2541
2542 void background_transform_to_world(vec3 viewvec, out vec3 worldvec)
2543 {
2544         vec4 v = (gl_ProjectionMatrix[3][3] == 0.0) ? vec4(viewvec, 1.0) : vec4(0.0, 0.0, 1.0, 1.0);
2545         vec4 co_homogenous = (gl_ProjectionMatrixInverse * v);
2546
2547         vec4 co = vec4(co_homogenous.xyz / co_homogenous.w, 0.0);
2548         worldvec = (gl_ModelViewMatrixInverse * co).xyz;
2549 }
2550
2551 void node_background(vec4 color, float strength, vec3 N, out vec4 result)
2552 {
2553         result = color*strength;
2554 }
2555
2556 /* closures */
2557
2558 void node_mix_shader(float fac, vec4 shader1, vec4 shader2, out vec4 shader)
2559 {
2560         shader = mix(shader1, shader2, fac);
2561 }
2562
2563 void node_add_shader(vec4 shader1, vec4 shader2, out vec4 shader)
2564 {
2565         shader = shader1 + shader2;
2566 }
2567
2568 /* fresnel */
2569
2570 void node_fresnel(float ior, vec3 N, vec3 I, out float result)
2571 {
2572         /* handle perspective/orthographic */
2573         vec3 I_view = (gl_ProjectionMatrix[3][3] == 0.0)? normalize(I): vec3(0.0, 0.0, -1.0);
2574
2575         float eta = max(ior, 0.00001);
2576         result = fresnel_dielectric(I_view, N, (gl_FrontFacing)? eta: 1.0/eta);
2577 }
2578
2579 /* layer_weight */
2580
2581 void node_layer_weight(float blend, vec3 N, vec3 I, out float fresnel, out float facing)
2582 {
2583         /* fresnel */
2584         float eta = max(1.0 - blend, 0.00001);
2585         vec3 I_view = (gl_ProjectionMatrix[3][3] == 0.0)? normalize(I): vec3(0.0, 0.0, -1.0);
2586
2587         fresnel = fresnel_dielectric(I_view, N, (gl_FrontFacing)? 1.0/eta : eta );
2588
2589         /* facing */
2590         facing = abs(dot(I_view, N));
2591         if (blend != 0.5) {
2592                 blend = clamp(blend, 0.0, 0.99999);
2593                 blend = (blend < 0.5)? 2.0*blend: 0.5/(1.0 - blend);
2594                 facing = pow(facing, blend);
2595         }
2596         facing = 1.0 - facing;
2597 }
2598
2599 /* gamma */
2600
2601 void node_gamma(vec4 col, float gamma, out vec4 outcol)
2602 {
2603         outcol = col;
2604
2605         if (col.r > 0.0)
2606                 outcol.r = compatible_pow(col.r, gamma);
2607         if (col.g > 0.0)
2608                 outcol.g = compatible_pow(col.g, gamma);
2609         if (col.b > 0.0)
2610                 outcol.b = compatible_pow(col.b, gamma);
2611 }
2612
2613 /* geometry */
2614
2615 void node_attribute(vec3 attr, out vec4 outcol, out vec3 outvec, out float outf)
2616 {
2617         outcol = vec4(attr, 1.0);
2618         outvec = attr;
2619         outf = (attr.x + attr.y + attr.z)/3.0;
2620 }
2621
2622 void node_uvmap(vec3 attr_uv, out vec3 outvec)
2623 {
2624         outvec = attr_uv;
2625 }
2626
2627 void node_geometry(vec3 I, vec3 N, mat4 toworld,
2628         out vec3 position, out vec3 normal, out vec3 tangent,
2629         out vec3 true_normal, out vec3 incoming, out vec3 parametric,
2630         out float backfacing, out float pointiness)
2631 {
2632         position = (toworld*vec4(I, 1.0)).xyz;
2633         normal = (toworld*vec4(N, 0.0)).xyz;
2634         tangent = vec3(0.0);
2635         true_normal = normal;
2636
2637         /* handle perspective/orthographic */
2638         vec3 I_view = (gl_ProjectionMatrix[3][3] == 0.0)? normalize(I): vec3(0.0, 0.0, -1.0);
2639         incoming = -(toworld*vec4(I_view, 0.0)).xyz;
2640
2641         parametric = vec3(0.0);
2642         backfacing = (gl_FrontFacing)? 0.0: 1.0;
2643         pointiness = 0.0;
2644 }
2645
2646 void node_tex_coord(vec3 I, vec3 N, mat4 viewinvmat, mat4 obinvmat, vec4 camerafac,
2647         vec3 attr_orco, vec3 attr_uv,
2648         out vec3 generated, out vec3 normal, out vec3 uv, out vec3 object,
2649         out vec3 camera, out vec3 window, out vec3 reflection)
2650 {
2651         generated = attr_orco * 0.5 + vec3(0.5);
2652         normal = normalize((obinvmat*(viewinvmat*vec4(N, 0.0))).xyz);
2653         uv = attr_uv;
2654         object = (obinvmat*(viewinvmat*vec4(I, 1.0))).xyz;
2655         camera = vec3(I.xy, -I.z);
2656         vec4 projvec = gl_ProjectionMatrix * vec4(I, 1.0);
2657         window = vec3(mtex_2d_mapping(projvec.xyz/projvec.w).xy * camerafac.xy + camerafac.zw, 0.0);
2658
2659         vec3 shade_I;
2660         shade_view(I, shade_I);
2661         vec3 view_reflection = reflect(shade_I, normalize(N));
2662         reflection = (viewinvmat*vec4(view_reflection, 0.0)).xyz;
2663 }
2664
2665 void node_tex_coord_background(vec3 I, vec3 N, mat4 viewinvmat, mat4 obinvmat, vec4 camerafac,
2666         vec3 attr_orco, vec3 attr_uv,
2667         out vec3 generated, out vec3 normal, out vec3 uv, out vec3 object,
2668         out vec3 camera, out vec3 window, out vec3 reflection)
2669 {
2670         vec4 v = (gl_ProjectionMatrix[3][3] == 0.0) ? vec4(I, 1.0) : vec4(0.0, 0.0, 1.0, 1.0);
2671         vec4 co_homogenous = (gl_ProjectionMatrixInverse * v);
2672
2673         vec4 co = vec4(co_homogenous.xyz / co_homogenous.w, 0.0);
2674
2675         co = normalize(co);
2676         vec3 coords = (gl_ModelViewMatrixInverse * co).xyz;
2677
2678         generated = coords;
2679         normal = -coords;
2680         uv = vec3(attr_uv.xy, 0.0);
2681         object = coords;
2682
2683         camera = vec3(co.xy, -co.z);
2684         window = (gl_ProjectionMatrix[3][3] == 0.0) ? 
2685                       vec3(mtex_2d_mapping(I).xy * camerafac.xy + camerafac.zw, 0.0) : 
2686                       vec3(vec2(0.5) * camerafac.xy + camerafac.zw, 0.0);
2687
2688         reflection = -coords;
2689 }
2690
2691 /* textures */
2692
2693 float calc_gradient(vec3 p, int gradient_type)
2694 {
2695         float x, y, z;
2696         x = p.x;
2697         y = p.y;
2698         z = p.z;
2699         if (gradient_type == 0) {  /* linear */
2700                 return x;
2701         }
2702         else if (gradient_type == 1) {  /* quadratic */
2703                 float r = max(x, 0.0);
2704                 return r*r;
2705         }
2706         else if (gradient_type == 2) {  /* easing */
2707                 float r = min(max(x, 0.0), 1.0);
2708                 float t = r*r;
2709                 return (3.0*t - 2.0*t*r);
2710         }
2711         else if (gradient_type == 3) {  /* diagonal */
2712                 return (x + y) * 0.5;
2713         }
2714         else if (gradient_type == 4) {  /* radial */
2715                 return atan(y, x) / (M_PI * 2) + 0.5;
2716         }
2717         else {
2718                 float r = max(1.0 - sqrt(x*x + y*y + z*z), 0.0);
2719                 if (gradient_type == 5) {  /* quadratic sphere */
2720                         return r*r;
2721                 }
2722                 else if (gradient_type == 6) {  /* sphere */
2723                         return r;
2724                 }
2725         }
2726         return 0.0;
2727 }
2728
2729 void node_tex_gradient(vec3 co, float gradient_type, out vec4 color, out float fac)
2730 {
2731         float f = calc_gradient(co, int(gradient_type));
2732         f = clamp(f, 0.0, 1.0);
2733
2734         color = vec4(f, f, f, 1.0);
2735         fac = f;
2736 }
2737
2738 void node_tex_checker(vec3 co, vec4 color1, vec4 color2, float scale, out vec4 color, out float fac)
2739 {
2740         vec3 p = co * scale;
2741
2742         /* Prevent precision issues on unit coordinates. */
2743         p.x = (p.x + 0.000001)*0.999999;
2744         p.y = (p.y + 0.000001)*0.999999;
2745         p.z = (p.z + 0.000001)*0.999999;
2746
2747         int xi = abs(int(floor(p.x)));
2748         int yi = abs(int(floor(p.y)));
2749         int zi = abs(int(floor(p.z)));
2750
2751         bool check = ((xi % 2 == yi % 2) == bool(zi % 2));
2752
2753         color = check ? color1 : color2;
2754         fac = check ? 1.0 : 0.0;
2755 }
2756
2757 vec2 calc_brick_texture(vec3 p, float mortar_size, float bias,
2758                         float brick_width, float row_height,
2759                         float offset_amount, int offset_frequency,
2760                         float squash_amount, int squash_frequency)
2761 {
2762         int bricknum, rownum;
2763         float offset = 0.0;
2764         float x, y;
2765
2766         rownum = floor_to_int(p.y / row_height);
2767
2768         if (offset_frequency != 0 && squash_frequency != 0) {
2769                 brick_width *= (rownum % squash_frequency != 0) ? 1.0 : squash_amount; /* squash */
2770                 offset = (rownum % offset_frequency != 0) ? 0.0 : (brick_width*offset_amount); /* offset */
2771         }
2772
2773         bricknum = floor_to_int((p.x+offset) / brick_width);
2774
2775         x = (p.x+offset) - brick_width*bricknum;
2776         y = p.y - row_height*rownum;
2777
2778         return vec2(clamp((integer_noise((rownum << 16) + (bricknum & 0xFFFF)) + bias), 0.0, 1.0),
2779                     (x < mortar_size || y < mortar_size ||
2780                      x > (brick_width - mortar_size) ||
2781                      y > (row_height - mortar_size)) ? 1.0 : 0.0);
2782 }
2783
2784 void node_tex_brick(vec3 co,
2785                     vec4 color1, vec4 color2,
2786                     vec4 mortar, float scale,
2787                     float mortar_size, float bias,
2788                     float brick_width, float row_height,
2789                     float offset_amount, float offset_frequency,
2790                     float squash_amount, float squash_frequency,
2791                     out vec4 color, out float fac)
2792 {
2793         vec2 f2 = calc_brick_texture(co*scale,
2794                                      mortar_size, bias,
2795                                      brick_width, row_height,
2796                                      offset_amount, int(offset_frequency),
2797                                      squash_amount, int(squash_frequency));
2798         float tint = f2.x;
2799         float f = f2.y;
2800         if (f != 1.0) {
2801                 float facm = 1.0 - tint;
2802                 color1 = facm * color1 + tint * color2;
2803         }
2804         color = (f == 1.0) ? mortar : color1;
2805         fac = f;
2806 }
2807
2808 void node_tex_clouds(vec3 co, float size, out vec4 color, out float fac)
2809 {
2810         color = vec4(1.0);
2811         fac = 1.0;
2812 }
2813
2814 void node_tex_environment_equirectangular(vec3 co, sampler2D ima, out vec4 color)
2815 {
2816         vec3 nco = normalize(co);
2817         float u = -atan(nco.y, nco.x)/(2.0*M_PI) + 0.5;
2818         float v = atan(nco.z, hypot(nco.x, nco.y))/M_PI + 0.5;
2819
2820         color = texture2D(ima, vec2(u, v));
2821 }
2822
2823 void node_tex_environment_mirror_ball(vec3 co, sampler2D ima, out vec4 color)
2824 {
2825         vec3 nco = normalize(co);
2826
2827         nco.y -= 1.0;
2828
2829         float div = 2.0*sqrt(max(-0.5*nco.y, 0.0));
2830         if (div > 0.0)
2831                 nco /= div;
2832
2833         float u = 0.5*(nco.x + 1.0);
2834         float v = 0.5*(nco.z + 1.0);
2835
2836         color = texture2D(ima, vec2(u, v));
2837 }
2838
2839 void node_tex_environment_empty(vec3 co, out vec4 color)
2840 {
2841         color = vec4(1.0, 0.0, 1.0, 1.0);
2842 }
2843
2844 void node_tex_image(vec3 co, sampler2D ima, out vec4 color, out float alpha)
2845 {
2846         color = texture2D(ima, co.xy);
2847         alpha = color.a;
2848 }
2849
2850 void node_tex_image_empty(vec3 co, out vec4 color, out float alpha)
2851 {
2852         color = vec4(0.0);
2853         alpha = 0.0;
2854 }
2855
2856 void node_tex_magic(vec3 co, float scale, float distortion, float depth, out vec4 color, out float fac)
2857 {
2858         vec3 p = co * scale;
2859         float x = sin((p.x + p.y + p.z)*5.0);
2860         float y = cos((-p.x + p.y - p.z)*5.0);
2861         float z = -cos((-p.x - p.y + p.z)*5.0);
2862
2863         if (depth > 0) {
2864                 x *= distortion;
2865                 y *= distortion;
2866                 z *= distortion;
2867                 y = -cos(x-y+z);
2868                 y *= distortion;
2869                 if (depth > 1) {
2870                         x = cos(x-y-z);
2871                         x *= distortion;
2872                         if (depth > 2) {
2873                                 z = sin(-x-y-z);
2874                                 z *= distortion;
2875                                 if (depth > 3) {
2876                                         x = -cos(-x+y-z);
2877                                         x *= distortion;
2878                                         if (depth > 4) {
2879                                                 y = -sin(-x+y+z);
2880                                                 y *= distortion;
2881                                                 if (depth > 5) {
2882                                                         y = -cos(-x+y+z);
2883                                                         y *= distortion;
2884                                                         if (depth > 6) {
2885                                                                 x = cos(x+y+z);
2886                                                                 x *= distortion;
2887                                                                 if (depth > 7) {
2888                                                                         z = sin(x+y-z);
2889                                                                         z *= distortion;
2890                                                                         if (depth > 8) {
2891                                                                                 x = -cos(-x-y+z);
2892                                                                                 x *= distortion;
2893                                                                                 if (depth > 9) {
2894                                                                                         y = -sin(x-y+z);
2895                                                                                         y *= distortion;
2896                                                                                 }
2897                                                                         }
2898                                                                 }
2899                                                         }
2900                                                 }
2901                                         }
2902                                 }
2903                         }
2904                 }
2905         }
2906         if (distortion != 0.0) {
2907                 distortion *= 2.0;
2908                 x /= distortion;
2909                 y /= distortion;
2910                 z /= distortion;
2911         }
2912
2913         color = vec4(0.5 - x, 0.5 - y, 0.f - z, 1.0);
2914         fac = (color.x + color.y + color.z) / 3.0;
2915 }
2916
2917 #ifdef BIT_OPERATIONS
2918 float noise_fade(float t)
2919 {
2920         return t * t * t * (t * (t * 6.0 - 15.0) + 10.0);
2921 }
2922
2923 float noise_scale3(float result)
2924 {
2925         return 0.9820 * result;
2926 }
2927
2928 float noise_nerp(float t, float a, float b)
2929 {
2930         return (1.0 - t) * a + t * b;
2931 }
2932
2933 float noise_grad(uint hash, float x, float y, float z)
2934 {
2935         uint h = hash & 15u;
2936         float u = h < 8u ? x : y;
2937         float vt = ((h == 12u) || (h == 14u)) ? x : z;
2938         float v = h < 4u ? y : vt;
2939         return (((h & 1u) != 0u) ? -u : u) + (((h & 2u) != 0u) ? -v : v);
2940 }
2941
2942 float noise_perlin(float x, float y, float z)
2943 {
2944         int X; float fx = floorfrac(x, X);
2945         int Y; float fy = floorfrac(y, Y);
2946         int Z; float fz = floorfrac(z, Z);
2947
2948         float u = noise_fade(fx);
2949         float v = noise_fade(fy);
2950         float w = noise_fade(fz);
2951
2952         float result;
2953
2954         result = noise_nerp(w, noise_nerp(v, noise_nerp(u, noise_grad(hash(X, Y, Z), fx, fy, fz ),
2955                                                         noise_grad(hash(X+1, Y, Z), fx-1.0, fy, fz)),
2956                                           noise_nerp(u, noise_grad(hash(X, Y+1, Z), fx, fy - 1.0, fz),
2957                                                      noise_grad(hash(X+1, Y+1, Z), fx-1.0, fy-1.0, fz))),
2958                             noise_nerp(v, noise_nerp(u, noise_grad(hash(X, Y, Z+1), fx, fy, fz-1.0),
2959                                                      noise_grad(hash(X+1, Y, Z+1), fx-1.0, fy, fz-1.0)),
2960                                        noise_nerp(u, noise_grad(hash(X, Y+1, Z+1), fx, fy-1.0, fz-1.0),
2961                                                   noise_grad(hash(X+1, Y+1, Z+1), fx-1.0, fy-1.0, fz-1.0))));
2962         return noise_scale3(result);
2963 }
2964
2965 float noise(vec3 p)
2966 {
2967         return 0.5 * noise_perlin(p.x, p.y, p.z) + 0.5;
2968 }
2969
2970 float snoise(vec3 p)
2971 {
2972         return noise_perlin(p.x, p.y, p.z);
2973 }
2974
2975 float noise_turbulence(vec3 p, float octaves, int hard)
2976 {
2977         float fscale = 1.0;
2978         float amp = 1.0;
2979         float sum = 0.0;
2980         int i, n;
2981         octaves = clamp(octaves, 0.0, 16.0);
2982         n = int(octaves);
2983         for (i = 0; i <= n; i++) {
2984                 float t = noise(fscale*p);
2985                 if (hard != 0) {
2986                         t = abs(2.0*t - 1.0);
2987                 }
2988                 sum += t*amp;
2989                 amp *= 0.5;
2990                 fscale *= 2.0;
2991         }
2992         float rmd = octaves - floor(octaves);
2993         if  (rmd != 0.0) {
2994                 float t = noise(fscale*p);
2995                 if (hard != 0) {
2996                         t = abs(2.0*t - 1.0);
2997                 }
2998                 float sum2 = sum + t*amp;
2999                 sum *= (float(1 << n) / float((1 << (n+1)) - 1));
3000                 sum2 *= (float(1 << (n+1)) / float((1 << (n+2)) - 1));
3001                 return (1.0 - rmd)*sum + rmd*sum2;
3002         }
3003         else {
3004                 sum *= (float(1 << n) / float((1 << (n+1)) - 1));
3005                 return sum;
3006         }
3007 }
3008 #endif  // BIT_OPERATIONS
3009
3010 void node_tex_noise(vec3 co, float scale, float detail, float distortion, out vec4 color, out float fac)
3011 {
3012 #ifdef BIT_OPERATIONS
3013         vec3 p = co * scale;
3014         int hard = 0;
3015         if (distortion != 0.0) {
3016                 vec3 r, offset = vec3(13.5, 13.5, 13.5);
3017                 r.x = noise(p + offset) * distortion;
3018                 r.y = noise(p) * distortion;
3019                 r.z = noise(p - offset) * distortion;
3020                 p += r;
3021         }
3022
3023         fac = noise_turbulence(p, detail, hard);
3024         color = vec4(fac,
3025                      noise_turbulence(vec3(p.y, p.x, p.z), detail, hard),
3026                      noise_turbulence(vec3(p.y, p.z, p.x), detail, hard),
3027                      1);
3028 #else  // BIT_OPERATIONS
3029         color = vec4(1.0);
3030         fac = 1.0;
3031 #endif  // BIT_OPERATIONS
3032 }
3033
3034
3035 #ifdef BIT_OPERATIONS
3036
3037 /* Musgrave fBm
3038  *
3039  * H: fractal increment parameter
3040  * lacunarity: gap between successive frequencies
3041  * octaves: number of frequencies in the fBm
3042  *
3043  * from "Texturing and Modelling: A procedural approach"
3044  */
3045
3046 float noise_musgrave_fBm(vec3 p, float H, float lacunarity, float octaves)
3047 {
3048         float rmd;
3049         float value = 0.0;
3050         float pwr = 1.0;
3051         float pwHL = pow(lacunarity, -H);
3052         int i;
3053
3054         for (i = 0; i < int(octaves); i++) {
3055                 value += snoise(p) * pwr;
3056                 pwr *= pwHL;
3057                 p *= lacunarity;
3058         }
3059
3060         rmd = octaves - floor(octaves);
3061         if (rmd != 0.0)
3062                 value += rmd * snoise(p) * pwr;
3063
3064         return value;
3065 }
3066
3067 /* Musgrave Multifractal
3068  *
3069  * H: highest fractal dimension
3070  * lacunarity: gap between successive frequencies
3071  * octaves: number of frequencies in the fBm
3072  */
3073
3074 float noise_musgrave_multi_fractal(vec3 p, float H, float lacunarity, float octaves)
3075 {
3076         float rmd;
3077         float value = 1.0;
3078         float pwr = 1.0;
3079         float pwHL = pow(lacunarity, -H);
3080         int i;
3081
3082         for (i = 0; i < int(octaves); i++) {
3083                 value *= (pwr * snoise(p) + 1.0);
3084                 pwr *= pwHL;
3085                 p *= lacunarity;
3086         }
3087
3088         rmd = octaves - floor(octaves);
3089         if (rmd != 0.0)
3090                 value *= (rmd * pwr * snoise(p) + 1.0); /* correct? */
3091
3092         return value;
3093 }
3094
3095 /* Musgrave Heterogeneous Terrain
3096  *
3097  * H: fractal dimension of the roughest area
3098  * lacunarity: gap between successive frequencies
3099  * octaves: number of frequencies in the fBm
3100  * offset: raises the terrain from `sea level'
3101  */
3102
3103 float noise_musgrave_hetero_terrain(vec3 p, float H, float lacunarity, float octaves, float offset)
3104 {
3105         float value, increment, rmd;
3106         float pwHL = pow(lacunarity, -H);
3107         float pwr = pwHL;
3108         int i;
3109
3110         /* first unscaled octave of function; later octaves are scaled */
3111         value = offset + snoise(p);
3112         p *= lacunarity;
3113
3114         for (i = 1; i < int(octaves); i++) {
3115                 increment = (snoise(p) + offset) * pwr * value;
3116                 value += increment;
3117                 pwr *= pwHL;
3118                 p *= lacunarity;
3119         }
3120
3121         rmd = octaves - floor(octaves);
3122         if (rmd != 0.0) {
3123                 increment = (snoise(p) + offset) * pwr * value;
3124                 value += rmd * increment;
3125         }
3126
3127         return value;
3128 }
3129
3130 /* Hybrid Additive/Multiplicative Multifractal Terrain
3131  *
3132  * H: fractal dimension of the roughest area
3133  * lacunarity: gap between successive frequencies
3134  * octaves: number of frequencies in the fBm
3135  * offset: raises the terrain from `sea level'
3136  */
3137
3138 float noise_musgrave_hybrid_multi_fractal(vec3 p, float H, float lacunarity, float octaves, float offset, float gain)
3139 {
3140         float result, signal, weight, rmd;
3141         float pwHL = pow(lacunarity, -H);
3142         float pwr = pwHL;
3143         int i;
3144
3145         result = snoise(p) + offset;
3146         weight = gain * result;
3147         p *= lacunarity;
3148
3149         for (i = 1; (weight > 0.001f) && (i < int(octaves)); i++) {
3150                 if (weight > 1.0)
3151                         weight = 1.0;
3152
3153                 signal = (snoise(p) + offset) * pwr;
3154                 pwr *= pwHL;
3155                 result += weight * signal;
3156                 weight *= gain * signal;
3157                 p *= lacunarity;
3158         }
3159
3160         rmd = octaves - floor(octaves);
3161         if (rmd != 0.0)
3162                 result += rmd * ((snoise(p) + offset) * pwr);
3163
3164         return result;
3165 }
3166
3167 /* Ridged Multifractal Terrain
3168  *
3169  * H: fractal dimension of the roughest area
3170  * lacunarity: gap between successive frequencies
3171  * octaves: number of frequencies in the fBm
3172  * offset: raises the terrain from `sea level'
3173  */
3174
3175 float noise_musgrave_ridged_multi_fractal(vec3 p, float H, float lacunarity, float octaves, float offset, float gain)
3176 {
3177         float result, signal, weight;
3178         float pwHL = pow(lacunarity, -H);
3179         float pwr = pwHL;
3180         int i;
3181
3182         signal = offset - abs(snoise(p));
3183         signal *= signal;
3184         result = signal;
3185         weight = 1.0;
3186
3187         for (i = 1; i < int(octaves); i++) {
3188                 p *= lacunarity;
3189                 weight = clamp(signal * gain, 0.0, 1.0);
3190                 signal = offset - abs(snoise(p));
3191                 signal *= signal;
3192                 signal *= weight;
3193                 result += signal * pwr;
3194                 pwr *= pwHL;
3195         }
3196
3197         return result;
3198 }
3199
3200 float svm_musgrave(int type,
3201                    float dimension,
3202                    float lacunarity,
3203                    float octaves,
3204                    float offset,
3205                    float intensity,
3206                    float gain,
3207                    vec3 p)
3208 {
3209         if (type == 0 /*NODE_MUSGRAVE_MULTIFRACTAL*/)
3210                 return intensity*noise_musgrave_multi_fractal(p, dimension, lacunarity, octaves);
3211         else if (type == 1 /*NODE_MUSGRAVE_FBM*/)
3212                 return intensity*noise_musgrave_fBm(p, dimension, lacunarity, octaves);
3213         else if (type == 2 /*NODE_MUSGRAVE_HYBRID_MULTIFRACTAL*/)
3214                 return intensity*noise_musgrave_hybrid_multi_fractal(p, dimension, lacunarity, octaves, offset, gain);
3215         else if (type == 3 /*NODE_MUSGRAVE_RIDGED_MULTIFRACTAL*/)
3216                 return intensity*noise_musgrave_ridged_multi_fractal(p, dimension, lacunarity, octaves, offset, gain);
3217         else if (type == 4 /*NODE_MUSGRAVE_HETERO_TERRAIN*/)
3218                 return intensity*noise_musgrave_hetero_terrain(p, dimension, lacunarity, octaves, offset);
3219         return 0.0;
3220 }
3221 #endif  // #ifdef BIT_OPERATIONS
3222
3223 void node_tex_musgrave(vec3 co,
3224                        float scale,
3225                        float detail,
3226                        float dimension,
3227                        float lacunarity,
3228                        float offset,
3229                        float gain,
3230                        float type,
3231                        out vec4 color,
3232                        out float fac)
3233 {
3234 #ifdef BIT_OPERATIONS
3235         fac = svm_musgrave(int(type),
3236                            dimension,
3237                            lacunarity,
3238                            detail,
3239                            offset,
3240                            1.0,
3241                            gain,
3242                            co*scale);
3243 #else
3244         fac = 1.0;
3245 #endif
3246
3247         color = vec4(fac, fac, fac, 1.0);
3248 }
3249
3250 void node_tex_sky(vec3 co, out vec4 color)
3251 {
3252         color = vec4(1.0);
3253 }
3254
3255 void node_tex_voronoi(vec3 co, float scale, float coloring, out vec4 color, out float fac)
3256 {
3257 #ifdef BIT_OPERATIONS
3258         vec3 p = co * scale;
3259         int xx, yy, zz, xi, yi, zi;
3260         float da[4];
3261         vec3 pa[4];
3262
3263         xi = floor_to_int(p[0]);
3264         yi = floor_to_int(p[1]);
3265         zi = floor_to_int(p[2]);
3266
3267         da[0] = 1e+10;
3268         da[1] = 1e+10;
3269         da[2] = 1e+10;
3270         da[3] = 1e+10;
3271
3272         for (xx = xi - 1; xx <= xi + 1; xx++) {
3273                 for (yy = yi - 1; yy <= yi + 1; yy++) {
3274                         for (zz = zi - 1; zz <= zi + 1; zz++) {
3275                                 vec3 ip = vec3(xx, yy, zz);
3276                                 vec3 vp = cellnoise_color(ip);
3277                                 vec3 pd = p - (vp + ip);
3278                                 float d = dot(pd, pd);
3279                                 vp += vec3(xx, yy, zz);
3280                                 if (d < da[0]) {
3281                                         da[3] = da[2];
3282                                         da[2] = da[1];
3283                                         da[1] = da[0];
3284                                         da[0] = d;
3285                                         pa[3] = pa[2];
3286                                         pa[2] = pa[1];
3287                                         pa[1] = pa[0];
3288                                         pa[0] = vp;
3289                                 }
3290                                 else if (d < da[1]) {
3291                                         da[3] = da[2];
3292                                         da[2] = da[1];
3293                                         da[1] = d;
3294
3295                                         pa[3] = pa[2];
3296                                         pa[2] = pa[1];
3297                                         pa[1] = vp;
3298                                 }
3299                                 else if (d < da[2]) {
3300                                         da[3] = da[2];
3301                                         da[2] = d;
3302
3303                                         pa[3] = pa[2];
3304                                         pa[2] = vp;
3305                                 }
3306                                 else if (d < da[3]) {
3307                                         da[3] = d;
3308                                         pa[3] = vp;
3309                                 }
3310                         }
3311                 }
3312         }
3313
3314         if (coloring == 0.0) {
3315                 fac = abs(da[0]);
3316                 color = vec4(fac, fac, fac, 1);
3317         }
3318         else {
3319                 color = vec4(cellnoise_color(pa[0]), 1);
3320                 fac = (color.x + color.y + color.z) * (1.0 / 3.0);
3321         }
3322 #else  // BIT_OPERATIONS
3323         color = vec4(1.0);
3324         fac = 1.0;
3325 #endif  // BIT_OPERATIONS
3326 }
3327
3328 #ifdef BIT_OPERATIONS
3329 float calc_wave(vec3 p, float distortion, float detail, float detail_scale, int wave_type, int wave_profile)
3330 {
3331         float n;
3332
3333         if (wave_type == 0) /* type bands */
3334                 n = (p.x + p.y + p.z) * 10.0;
3335         else /* type rings */
3336                 n = length(p) * 20.0;
3337
3338         if (distortion != 0.0)
3339                 n += distortion * noise_turbulence(p*detail_scale, detail, 0);
3340
3341         if (wave_profile == 0) { /* profile sin */
3342                 return 0.5 + 0.5 * sin(n);
3343         }
3344         else { /* profile saw */
3345                 n /= 2.0 * M_PI;
3346                 n -= int(n);
3347                 return (n < 0.0)? n + 1.0: n;
3348         }
3349 }
3350 #endif  // BIT_OPERATIONS
3351
3352 void node_tex_wave(
3353         vec3 co, float scale, float distortion, float detail, float detail_scale, float wave_type, float wave_profile,
3354         out vec4 color, out float fac)
3355 {
3356 #ifdef BIT_OPERATIONS
3357         float f;
3358         f = calc_wave(co*scale, distortion, detail, detail_scale, int(wave_type), int(wave_profile));
3359
3360         color = vec4(f, f, f, 1.0);
3361         fac = f;
3362 #else  // BIT_OPERATIONS
3363         color = vec4(1.0);
3364         fac = 1;
3365 #endif  // BIT_OPERATIONS
3366 }
3367
3368 /* light path */
3369
3370 void node_light_path(
3371         out float is_camera_ray,
3372         out float is_shadow_ray,
3373         out float is_diffuse_ray,
3374         out float is_glossy_ray,
3375         out float is_singular_ray,
3376         out float is_reflection_ray,
3377         out float is_transmission_ray,
3378         out float ray_length,
3379         out float ray_depth,
3380         out float transparent_depth,
3381         out float transmission_depth)
3382 {
3383         is_camera_ray = 1.0;
3384         is_shadow_ray = 0.0;
3385         is_diffuse_ray = 0.0;
3386         is_glossy_ray = 0.0;
3387         is_singular_ray = 0.0;
3388         is_reflection_ray = 0.0;
3389         is_transmission_ray = 0.0;
3390         ray_length = 1.0;
3391         ray_depth = 1.0;
3392         transparent_depth = 1.0;
3393         transmission_depth = 1.0;
3394 }
3395
3396 void node_light_falloff(float strength, float tsmooth, out float quadratic, out float linear, out float constant)
3397 {
3398         quadratic = strength;
3399         linear = strength;
3400         constant = strength;
3401 }
3402
3403 void node_object_info(out vec3 location, out float object_index, out float material_index, out float random)
3404 {
3405         location = vec3(0.0);
3406         object_index = 0.0;
3407         material_index = 0.0;
3408         random = 0.0;
3409 }
3410
3411 void node_normal_map(vec4 tangent, vec3 normal, vec3 texnormal, out vec3 outnormal)
3412 {
3413         vec3 B = tangent.w * cross(normal, tangent.xyz);
3414
3415         outnormal = texnormal.x * tangent.xyz + texnormal.y * B + texnormal.z * normal;
3416         outnormal = normalize(outnormal);
3417 }
3418
3419 void node_bump(float strength, float dist, float height, vec3 N, vec3 surf_pos, float invert, out vec3 result)
3420 {
3421         if (invert != 0.0) {
3422                 dist *= -1.0;
3423         }
3424         vec3 dPdx = dFdx(surf_pos);
3425         vec3 dPdy = dFdy(surf_pos);
3426
3427         /* Get surface tangents from normal. */
3428         vec3 Rx = cross(dPdy, N);
3429         vec3 Ry = cross(N, dPdx);
3430
3431         /* Compute surface gradient and determinant. */
3432         float det = dot(dPdx, Rx);
3433         float absdet = abs(det);
3434
3435         float dHdx = dFdx(height);
3436         float dHdy = dFdy(height);
3437         vec3 surfgrad = dHdx*Rx + dHdy*Ry;
3438
3439         strength = max(strength, 0.0);
3440
3441         result = normalize(absdet*N - dist*sign(det)*surfgrad);
3442         result = normalize(strength*result + (1.0 - strength)*N);
3443 }
3444
3445 /* output */