7b4748056a79c2f8c74b8bf3d7c776b0f170547d
[blender.git] / source / blender / gpu / shaders / gpu_shader_material.glsl
1
2 uniform mat4 ModelViewMatrix;
3 uniform mat4 ModelViewMatrixInverse;
4 uniform mat3 NormalMatrix;
5
6 #ifndef ATTRIB
7 uniform mat4 ModelMatrix;
8 uniform mat4 ModelMatrixInverse;
9 #endif
10
11 /* Converters */
12
13 float convert_rgba_to_float(vec4 color)
14 {
15         return dot(color.rgb, vec3(0.2126, 0.7152, 0.0722));
16 }
17
18 float exp_blender(float f)
19 {
20         return pow(2.71828182846, f);
21 }
22
23 float compatible_pow(float x, float y)
24 {
25         if (y == 0.0) /* x^0 -> 1, including 0^0 */
26                 return 1.0;
27
28         /* glsl pow doesn't accept negative x */
29         if (x < 0.0) {
30                 if (mod(-y, 2.0) == 0.0)
31                         return pow(-x, y);
32                 else
33                         return -pow(-x, y);
34         }
35         else if (x == 0.0)
36                 return 0.0;
37
38         return pow(x, y);
39 }
40
41 void rgb_to_hsv(vec4 rgb, out vec4 outcol)
42 {
43         float cmax, cmin, h, s, v, cdelta;
44         vec3 c;
45
46         cmax = max(rgb[0], max(rgb[1], rgb[2]));
47         cmin = min(rgb[0], min(rgb[1], rgb[2]));
48         cdelta = cmax - cmin;
49
50         v = cmax;
51         if (cmax != 0.0)
52                 s = cdelta / cmax;
53         else {
54                 s = 0.0;
55                 h = 0.0;
56         }
57
58         if (s == 0.0) {
59                 h = 0.0;
60         }
61         else {
62                 c = (vec3(cmax) - rgb.xyz) / cdelta;
63
64                 if (rgb.x == cmax) h = c[2] - c[1];
65                 else if (rgb.y == cmax) h = 2.0 + c[0] -  c[2];
66                 else h = 4.0 + c[1] - c[0];
67
68                 h /= 6.0;
69
70                 if (h < 0.0)
71                         h += 1.0;
72         }
73
74         outcol = vec4(h, s, v, rgb.w);
75 }
76
77 void hsv_to_rgb(vec4 hsv, out vec4 outcol)
78 {
79         float i, f, p, q, t, h, s, v;
80         vec3 rgb;
81
82         h = hsv[0];
83         s = hsv[1];
84         v = hsv[2];
85
86         if (s == 0.0) {
87                 rgb = vec3(v, v, v);
88         }
89         else {
90                 if (h == 1.0)
91                         h = 0.0;
92
93                 h *= 6.0;
94                 i = floor(h);
95                 f = h - i;
96                 rgb = vec3(f, f, f);
97                 p = v * (1.0 - s);
98                 q = v * (1.0 - (s * f));
99                 t = v * (1.0 - (s * (1.0 - f)));
100
101                 if (i == 0.0) rgb = vec3(v, t, p);
102                 else if (i == 1.0) rgb = vec3(q, v, p);
103                 else if (i == 2.0) rgb = vec3(p, v, t);
104                 else if (i == 3.0) rgb = vec3(p, q, v);
105                 else if (i == 4.0) rgb = vec3(t, p, v);
106                 else rgb = vec3(v, p, q);
107         }
108
109         outcol = vec4(rgb, hsv.w);
110 }
111
112 float srgb_to_linearrgb(float c)
113 {
114         if (c < 0.04045)
115                 return (c < 0.0) ? 0.0 : c * (1.0 / 12.92);
116         else
117                 return pow((c + 0.055) * (1.0 / 1.055), 2.4);
118 }
119
120 float linearrgb_to_srgb(float c)
121 {
122         if (c < 0.0031308)
123                 return (c < 0.0) ? 0.0 : c * 12.92;
124         else
125                 return 1.055 * pow(c, 1.0 / 2.4) - 0.055;
126 }
127
128 void srgb_to_linearrgb(vec4 col_from, out vec4 col_to)
129 {
130         col_to.r = srgb_to_linearrgb(col_from.r);
131         col_to.g = srgb_to_linearrgb(col_from.g);
132         col_to.b = srgb_to_linearrgb(col_from.b);
133         col_to.a = col_from.a;
134 }
135
136 void linearrgb_to_srgb(vec4 col_from, out vec4 col_to)
137 {
138         col_to.r = linearrgb_to_srgb(col_from.r);
139         col_to.g = linearrgb_to_srgb(col_from.g);
140         col_to.b = linearrgb_to_srgb(col_from.b);
141         col_to.a = col_from.a;
142 }
143
144 void color_to_normal(vec3 color, out vec3 normal)
145 {
146         normal.x =  2.0 * ((color.r) - 0.5);
147         normal.y = -2.0 * ((color.g) - 0.5);
148         normal.z =  2.0 * ((color.b) - 0.5);
149 }
150
151 void color_to_normal_new_shading(vec3 color, out vec3 normal)
152 {
153         normal.x =  2.0 * ((color.r) - 0.5);
154         normal.y =  2.0 * ((color.g) - 0.5);
155         normal.z =  2.0 * ((color.b) - 0.5);
156 }
157
158 void color_to_blender_normal_new_shading(vec3 color, out vec3 normal)
159 {
160         normal.x =  2.0 * ((color.r) - 0.5);
161         normal.y = -2.0 * ((color.g) - 0.5);
162         normal.z = -2.0 * ((color.b) - 0.5);
163 }
164 #ifndef M_PI
165 #define M_PI 3.14159265358979323846
166 #endif
167 #ifndef M_1_PI
168 #define M_1_PI 0.318309886183790671538
169 #endif
170
171 /*********** SHADER NODES ***************/
172
173 void particle_info(
174         vec4 sprops, vec4 loc, vec3 vel, vec3 avel,
175         out float index, out float random, out float age,
176         out float life_time, out vec3 location,
177         out float size, out vec3 velocity, out vec3 angular_velocity)
178 {
179         index = sprops.x;
180         random = loc.w;
181         age = sprops.y;
182         life_time = sprops.z;
183         size = sprops.w;
184
185         location = loc.xyz;
186         velocity = vel;
187         angular_velocity = avel;
188 }
189
190 void vect_normalize(vec3 vin, out vec3 vout)
191 {
192         vout = normalize(vin);
193 }
194
195 void direction_transform_m4v3(vec3 vin, mat4 mat, out vec3 vout)
196 {
197         vout = (mat * vec4(vin, 0.0)).xyz;
198 }
199
200 void point_transform_m4v3(vec3 vin, mat4 mat, out vec3 vout)
201 {
202         vout = (mat * vec4(vin, 1.0)).xyz;
203 }
204
205 void point_texco_remap_square(vec3 vin, out vec3 vout)
206 {
207         vout = vec3(vin - vec3(0.5, 0.5, 0.5)) * 2.0;
208 }
209
210 void point_map_to_sphere(vec3 vin, out vec3 vout)
211 {
212         float len = length(vin);
213         float v, u;
214         if (len > 0.0) {
215                 if (vin.x == 0.0 && vin.y == 0.0)
216                         u = 0.0;
217                 else
218                         u = (1.0 - atan(vin.x, vin.y) / M_PI) / 2.0;
219
220                 v = 1.0 - acos(vin.z / len) / M_PI;
221         }
222         else
223                 v = u = 0.0;
224
225         vout = vec3(u, v, 0.0);
226 }
227
228 void point_map_to_tube(vec3 vin, out vec3 vout)
229 {
230         float u, v;
231         v = (vin.z + 1.0) * 0.5;
232         float len = sqrt(vin.x * vin.x + vin.y * vin[1]);
233         if (len > 0.0)
234                 u = (1.0 - (atan(vin.x / len, vin.y / len) / M_PI)) * 0.5;
235         else
236                 v = u = 0.0;
237
238         vout = vec3(u, v, 0.0);
239 }
240
241 void mapping(vec3 vec, vec4 m0, vec4 m1, vec4 m2, vec4 m3, vec3 minvec, vec3 maxvec, out vec3 outvec)
242 {
243         mat4 mat = mat4(m0, m1, m2, m3);
244         outvec = (mat * vec4(vec, 1.0)).xyz;
245         outvec = clamp(outvec, minvec, maxvec);
246 }
247
248 void camera(vec3 co, out vec3 outview, out float outdepth, out float outdist)
249 {
250         outdepth = abs(co.z);
251         outdist = length(co);
252         outview = normalize(co);
253 }
254
255 void math_add(float val1, float val2, out float outval)
256 {
257         outval = val1 + val2;
258 }
259
260 void math_subtract(float val1, float val2, out float outval)
261 {
262         outval = val1 - val2;
263 }
264
265 void math_multiply(float val1, float val2, out float outval)
266 {
267         outval = val1 * val2;
268 }
269
270 void math_divide(float val1, float val2, out float outval)
271 {
272         if (val2 == 0.0)
273                 outval = 0.0;
274         else
275                 outval = val1 / val2;
276 }
277
278 void math_sine(float val, out float outval)
279 {
280         outval = sin(val);
281 }
282
283 void math_cosine(float val, out float outval)
284 {
285         outval = cos(val);
286 }
287
288 void math_tangent(float val, out float outval)
289 {
290         outval = tan(val);
291 }
292
293 void math_asin(float val, out float outval)
294 {
295         if (val <= 1.0 && val >= -1.0)
296                 outval = asin(val);
297         else
298                 outval = 0.0;
299 }
300
301 void math_acos(float val, out float outval)
302 {
303         if (val <= 1.0 && val >= -1.0)
304                 outval = acos(val);
305         else
306                 outval = 0.0;
307 }
308
309 void math_atan(float val, out float outval)
310 {
311         outval = atan(val);
312 }
313
314 void math_pow(float val1, float val2, out float outval)
315 {
316         if (val1 >= 0.0) {
317                 outval = compatible_pow(val1, val2);
318         }
319         else {
320                 float val2_mod_1 = mod(abs(val2), 1.0);
321
322                 if (val2_mod_1 > 0.999 || val2_mod_1 < 0.001)
323                         outval = compatible_pow(val1, floor(val2 + 0.5));
324                 else
325                         outval = 0.0;
326         }
327 }
328
329 void math_log(float val1, float val2, out float outval)
330 {
331         if (val1 > 0.0  && val2 > 0.0)
332                 outval = log2(val1) / log2(val2);
333         else
334                 outval = 0.0;
335 }
336
337 void math_max(float val1, float val2, out float outval)
338 {
339         outval = max(val1, val2);
340 }
341
342 void math_min(float val1, float val2, out float outval)
343 {
344         outval = min(val1, val2);
345 }
346
347 void math_round(float val, out float outval)
348 {
349         outval = floor(val + 0.5);
350 }
351
352 void math_less_than(float val1, float val2, out float outval)
353 {
354         if (val1 < val2)
355                 outval = 1.0;
356         else
357                 outval = 0.0;
358 }
359
360 void math_greater_than(float val1, float val2, out float outval)
361 {
362         if (val1 > val2)
363                 outval = 1.0;
364         else
365                 outval = 0.0;
366 }
367
368 void math_modulo(float val1, float val2, out float outval)
369 {
370         if (val2 == 0.0)
371                 outval = 0.0;
372         else
373                 outval = mod(val1, val2);
374
375         /* change sign to match C convention, mod in GLSL will take absolute for negative numbers,
376          * see https://www.opengl.org/sdk/docs/man/html/mod.xhtml */
377         outval = (val1 > 0.0) ? outval : outval - val2;
378 }
379
380 void math_abs(float val1, out float outval)
381 {
382         outval = abs(val1);
383 }
384
385 void math_atan2(float val1, float val2, out float outval)
386 {
387         outval = atan(val1, val2);
388 }
389
390 void math_floor(float val, out float outval)
391 {
392         outval = floor(val);
393 }
394
395 void math_ceil(float val, out float outval)
396 {
397         outval = ceil(val);
398 }
399
400 void math_fract(float val, out float outval)
401 {
402         outval = val - floor(val);
403 }
404
405 void math_sqrt(float val, out float outval)
406 {
407         if (val > 0.0)
408                 outval = sqrt(val);
409         else
410                 outval = 0.0;
411 }
412
413 void squeeze(float val, float width, float center, out float outval)
414 {
415         outval = 1.0 / (1.0 + pow(2.71828183, -((val - center) * width)));
416 }
417
418 void vec_math_add(vec3 v1, vec3 v2, out vec3 outvec, out float outval)
419 {
420         outvec = v1 + v2;
421         outval = (abs(outvec[0]) + abs(outvec[1]) + abs(outvec[2])) * 0.333333;
422 }
423
424 void vec_math_sub(vec3 v1, vec3 v2, out vec3 outvec, out float outval)
425 {
426         outvec = v1 - v2;
427         outval = (abs(outvec[0]) + abs(outvec[1]) + abs(outvec[2])) * 0.333333;
428 }
429
430 void vec_math_average(vec3 v1, vec3 v2, out vec3 outvec, out float outval)
431 {
432         outvec = v1 + v2;
433         outval = length(outvec);
434         outvec = normalize(outvec);
435 }
436 void vec_math_mix(float strength, vec3 v1, vec3 v2, out vec3 outvec)
437 {
438         outvec = strength * v1 + (1 - strength) * v2;
439 }
440
441 void vec_math_dot(vec3 v1, vec3 v2, out vec3 outvec, out float outval)
442 {
443         outvec = vec3(0);
444         outval = dot(v1, v2);
445 }
446
447 void vec_math_cross(vec3 v1, vec3 v2, out vec3 outvec, out float outval)
448 {
449         outvec = cross(v1, v2);
450         outval = length(outvec);
451         outvec /= outval;
452 }
453
454 void vec_math_normalize(vec3 v, out vec3 outvec, out float outval)
455 {
456         outval = length(v);
457         outvec = normalize(v);
458 }
459
460 void vec_math_negate(vec3 v, out vec3 outv)
461 {
462         outv = -v;
463 }
464
465 void invert_z(vec3 v, out vec3 outv)
466 {
467         v.z = -v.z;
468         outv = v;
469 }
470
471 void normal(vec3 dir, vec3 nor, out vec3 outnor, out float outdot)
472 {
473         outnor = nor;
474         outdot = -dot(dir, nor);
475 }
476
477 void normal_new_shading(vec3 dir, vec3 nor, out vec3 outnor, out float outdot)
478 {
479         outnor = normalize(nor);
480         outdot = dot(normalize(dir), nor);
481 }
482
483 void curves_vec(float fac, vec3 vec, sampler1DArray curvemap, float layer, out vec3 outvec)
484 {
485         vec4 co = vec4(vec * 0.5 + 0.5, layer);
486         outvec.x = texture(curvemap, co.xw).x;
487         outvec.y = texture(curvemap, co.yw).y;
488         outvec.z = texture(curvemap, co.zw).z;
489         outvec = mix(vec, outvec, fac);
490 }
491
492 void curves_rgb(float fac, vec4 col, sampler1DArray curvemap, float layer, out vec4 outcol)
493 {
494         vec4 co = vec4(col.rgb, layer);
495         co.x = texture(curvemap, co.xw).a;
496         co.y = texture(curvemap, co.yw).a;
497         co.z = texture(curvemap, co.zw).a;
498         outcol.r = texture(curvemap, co.xw).r;
499         outcol.g = texture(curvemap, co.yw).g;
500         outcol.b = texture(curvemap, co.zw).b;
501         outcol.a = col.a;
502         outcol = mix(col, outcol, fac);
503 }
504
505 void set_value(float val, out float outval)
506 {
507         outval = val;
508 }
509
510 void set_rgb(vec3 col, out vec3 outcol)
511 {
512         outcol = col;
513 }
514
515 void set_rgba(vec4 col, out vec4 outcol)
516 {
517         outcol = col;
518 }
519
520 void set_value_zero(out float outval)
521 {
522         outval = 0.0;
523 }
524
525 void set_value_one(out float outval)
526 {
527         outval = 1.0;
528 }
529
530 void set_rgb_zero(out vec3 outval)
531 {
532         outval = vec3(0.0);
533 }
534
535 void set_rgb_one(out vec3 outval)
536 {
537         outval = vec3(1.0);
538 }
539
540 void set_rgba_zero(out vec4 outval)
541 {
542         outval = vec4(0.0);
543 }
544
545 void set_rgba_one(out vec4 outval)
546 {
547         outval = vec4(1.0);
548 }
549
550 void brightness_contrast(vec4 col, float brightness, float contrast, out vec4 outcol)
551 {
552         float a = 1.0 + contrast;
553         float b = brightness - contrast * 0.5;
554
555         outcol.r = max(a * col.r + b, 0.0);
556         outcol.g = max(a * col.g + b, 0.0);
557         outcol.b = max(a * col.b + b, 0.0);
558         outcol.a = col.a;
559 }
560
561 void mix_blend(float fac, vec4 col1, vec4 col2, out vec4 outcol)
562 {
563         fac = clamp(fac, 0.0, 1.0);
564         outcol = mix(col1, col2, fac);
565         outcol.a = col1.a;
566 }
567
568 void mix_add(float fac, vec4 col1, vec4 col2, out vec4 outcol)
569 {
570         fac = clamp(fac, 0.0, 1.0);
571         outcol = mix(col1, col1 + col2, fac);
572         outcol.a = col1.a;
573 }
574
575 void mix_mult(float fac, vec4 col1, vec4 col2, out vec4 outcol)
576 {
577         fac = clamp(fac, 0.0, 1.0);
578         outcol = mix(col1, col1 * col2, fac);
579         outcol.a = col1.a;
580 }
581
582 void mix_screen(float fac, vec4 col1, vec4 col2, out vec4 outcol)
583 {
584         fac = clamp(fac, 0.0, 1.0);
585         float facm = 1.0 - fac;
586
587         outcol = vec4(1.0) - (vec4(facm) + fac * (vec4(1.0) - col2)) * (vec4(1.0) - col1);
588         outcol.a = col1.a;
589 }
590
591 void mix_overlay(float fac, vec4 col1, vec4 col2, out vec4 outcol)
592 {
593         fac = clamp(fac, 0.0, 1.0);
594         float facm = 1.0 - fac;
595
596         outcol = col1;
597
598         if (outcol.r < 0.5)
599                 outcol.r *= facm + 2.0 * fac * col2.r;
600         else
601                 outcol.r = 1.0 - (facm + 2.0 * fac * (1.0 - col2.r)) * (1.0 - outcol.r);
602
603         if (outcol.g < 0.5)
604                 outcol.g *= facm + 2.0 * fac * col2.g;
605         else
606                 outcol.g = 1.0 - (facm + 2.0 * fac * (1.0 - col2.g)) * (1.0 - outcol.g);
607
608         if (outcol.b < 0.5)
609                 outcol.b *= facm + 2.0 * fac * col2.b;
610         else
611                 outcol.b = 1.0 - (facm + 2.0 * fac * (1.0 - col2.b)) * (1.0 - outcol.b);
612 }
613
614 void mix_sub(float fac, vec4 col1, vec4 col2, out vec4 outcol)
615 {
616         fac = clamp(fac, 0.0, 1.0);
617         outcol = mix(col1, col1 - col2, fac);
618         outcol.a = col1.a;
619 }
620
621 void mix_div(float fac, vec4 col1, vec4 col2, out vec4 outcol)
622 {
623         fac = clamp(fac, 0.0, 1.0);
624         float facm = 1.0 - fac;
625
626         outcol = col1;
627
628         if (col2.r != 0.0) outcol.r = facm * outcol.r + fac * outcol.r / col2.r;
629         if (col2.g != 0.0) outcol.g = facm * outcol.g + fac * outcol.g / col2.g;
630         if (col2.b != 0.0) outcol.b = facm * outcol.b + fac * outcol.b / col2.b;
631 }
632
633 void mix_diff(float fac, vec4 col1, vec4 col2, out vec4 outcol)
634 {
635         fac = clamp(fac, 0.0, 1.0);
636         outcol = mix(col1, abs(col1 - col2), fac);
637         outcol.a = col1.a;
638 }
639
640 void mix_dark(float fac, vec4 col1, vec4 col2, out vec4 outcol)
641 {
642         fac = clamp(fac, 0.0, 1.0);
643         outcol.rgb = min(col1.rgb, col2.rgb * fac);
644         outcol.a = col1.a;
645 }
646
647 void mix_light(float fac, vec4 col1, vec4 col2, out vec4 outcol)
648 {
649         fac = clamp(fac, 0.0, 1.0);
650         outcol.rgb = max(col1.rgb, col2.rgb * fac);
651         outcol.a = col1.a;
652 }
653
654 void mix_dodge(float fac, vec4 col1, vec4 col2, out vec4 outcol)
655 {
656         fac = clamp(fac, 0.0, 1.0);
657         outcol = col1;
658
659         if (outcol.r != 0.0) {
660                 float tmp = 1.0 - fac * col2.r;
661                 if (tmp <= 0.0)
662                         outcol.r = 1.0;
663                 else if ((tmp = outcol.r / tmp) > 1.0)
664                         outcol.r = 1.0;
665                 else
666                         outcol.r = tmp;
667         }
668         if (outcol.g != 0.0) {
669                 float tmp = 1.0 - fac * col2.g;
670                 if (tmp <= 0.0)
671                         outcol.g = 1.0;
672                 else if ((tmp = outcol.g / tmp) > 1.0)
673                         outcol.g = 1.0;
674                 else
675                         outcol.g = tmp;
676         }
677         if (outcol.b != 0.0) {
678                 float tmp = 1.0 - fac * col2.b;
679                 if (tmp <= 0.0)
680                         outcol.b = 1.0;
681                 else if ((tmp = outcol.b / tmp) > 1.0)
682                         outcol.b = 1.0;
683                 else
684                         outcol.b = tmp;
685         }
686 }
687
688 void mix_burn(float fac, vec4 col1, vec4 col2, out vec4 outcol)
689 {
690         fac = clamp(fac, 0.0, 1.0);
691         float tmp, facm = 1.0 - fac;
692
693         outcol = col1;
694
695         tmp = facm + fac * col2.r;
696         if (tmp <= 0.0)
697                 outcol.r = 0.0;
698         else if ((tmp = (1.0 - (1.0 - outcol.r) / tmp)) < 0.0)
699                 outcol.r = 0.0;
700         else if (tmp > 1.0)
701                 outcol.r = 1.0;
702         else
703                 outcol.r = tmp;
704
705         tmp = facm + fac * col2.g;
706         if (tmp <= 0.0)
707                 outcol.g = 0.0;
708         else if ((tmp = (1.0 - (1.0 - outcol.g) / tmp)) < 0.0)
709                 outcol.g = 0.0;
710         else if (tmp > 1.0)
711                 outcol.g = 1.0;
712         else
713                 outcol.g = tmp;
714
715         tmp = facm + fac * col2.b;
716         if (tmp <= 0.0)
717                 outcol.b = 0.0;
718         else if ((tmp = (1.0 - (1.0 - outcol.b) / tmp)) < 0.0)
719                 outcol.b = 0.0;
720         else if (tmp > 1.0)
721                 outcol.b = 1.0;
722         else
723                 outcol.b = tmp;
724 }
725
726 void mix_hue(float fac, vec4 col1, vec4 col2, out vec4 outcol)
727 {
728         fac = clamp(fac, 0.0, 1.0);
729         float facm = 1.0 - fac;
730
731         outcol = col1;
732
733         vec4 hsv, hsv2, tmp;
734         rgb_to_hsv(col2, hsv2);
735
736         if (hsv2.y != 0.0) {
737                 rgb_to_hsv(outcol, hsv);
738                 hsv.x = hsv2.x;
739                 hsv_to_rgb(hsv, tmp);
740
741                 outcol = mix(outcol, tmp, fac);
742                 outcol.a = col1.a;
743         }
744 }
745
746 void mix_sat(float fac, vec4 col1, vec4 col2, out vec4 outcol)
747 {
748         fac = clamp(fac, 0.0, 1.0);
749         float facm = 1.0 - fac;
750
751         outcol = col1;
752
753         vec4 hsv, hsv2;
754         rgb_to_hsv(outcol, hsv);
755
756         if (hsv.y != 0.0) {
757                 rgb_to_hsv(col2, hsv2);
758
759                 hsv.y = facm * hsv.y + fac * hsv2.y;
760                 hsv_to_rgb(hsv, outcol);
761         }
762 }
763
764 void mix_val(float fac, vec4 col1, vec4 col2, out vec4 outcol)
765 {
766         fac = clamp(fac, 0.0, 1.0);
767         float facm = 1.0 - fac;
768
769         vec4 hsv, hsv2;
770         rgb_to_hsv(col1, hsv);
771         rgb_to_hsv(col2, hsv2);
772
773         hsv.z = facm * hsv.z + fac * hsv2.z;
774         hsv_to_rgb(hsv, outcol);
775 }
776
777 void mix_color(float fac, vec4 col1, vec4 col2, out vec4 outcol)
778 {
779         fac = clamp(fac, 0.0, 1.0);
780         float facm = 1.0 - fac;
781
782         outcol = col1;
783
784         vec4 hsv, hsv2, tmp;
785         rgb_to_hsv(col2, hsv2);
786
787         if (hsv2.y != 0.0) {
788                 rgb_to_hsv(outcol, hsv);
789                 hsv.x = hsv2.x;
790                 hsv.y = hsv2.y;
791                 hsv_to_rgb(hsv, tmp);
792
793                 outcol = mix(outcol, tmp, fac);
794                 outcol.a = col1.a;
795         }
796 }
797
798 void mix_soft(float fac, vec4 col1, vec4 col2, out vec4 outcol)
799 {
800         fac = clamp(fac, 0.0, 1.0);
801         float facm = 1.0 - fac;
802
803         vec4 one = vec4(1.0);
804         vec4 scr = one - (one - col2) * (one - col1);
805         outcol = facm * col1 + fac * ((one - col1) * col2 * col1 + col1 * scr);
806 }
807
808 void mix_linear(float fac, vec4 col1, vec4 col2, out vec4 outcol)
809 {
810         fac = clamp(fac, 0.0, 1.0);
811
812         outcol = col1 + fac * (2.0 * (col2 - vec4(0.5)));
813 }
814
815 void valtorgb(float fac, sampler1DArray colormap, float layer, out vec4 outcol, out float outalpha)
816 {
817         outcol = texture(colormap, vec2(fac, layer));
818         outalpha = outcol.a;
819 }
820
821 void valtorgb_nearest(float fac, sampler1DArray colormap, float layer, out vec4 outcol, out float outalpha)
822 {
823         fac = clamp(fac, 0.0, 1.0);
824         outcol = texelFetch(colormap, ivec2(fac * (textureSize(colormap, 0).x - 1), layer), 0);
825         outalpha = outcol.a;
826 }
827
828 void rgbtobw(vec4 color, out float outval)
829 {
830         vec3 factors = vec3(0.2126, 0.7152, 0.0722);
831         outval = dot(color.rgb, factors);
832 }
833
834 void invert(float fac, vec4 col, out vec4 outcol)
835 {
836         outcol.xyz = mix(col.xyz, vec3(1.0) - col.xyz, fac);
837         outcol.w = col.w;
838 }
839
840 void clamp_vec3(vec3 vec, vec3 min, vec3 max, out vec3 out_vec)
841 {
842         out_vec = clamp(vec, min, max);
843 }
844
845 void clamp_val(float value, float min, float max, out float out_value)
846 {
847         out_value = clamp(value, min, max);
848 }
849
850 void hue_sat(float hue, float sat, float value, float fac, vec4 col, out vec4 outcol)
851 {
852         vec4 hsv;
853
854         rgb_to_hsv(col, hsv);
855
856         hsv[0] += (hue - 0.5);
857         if (hsv[0] > 1.0) hsv[0] -= 1.0; else if (hsv[0] < 0.0) hsv[0] += 1.0;
858         hsv[1] *= sat;
859         if (hsv[1] > 1.0) hsv[1] = 1.0; else if (hsv[1] < 0.0) hsv[1] = 0.0;
860         hsv[2] *= value;
861         if (hsv[2] > 1.0) hsv[2] = 1.0; else if (hsv[2] < 0.0) hsv[2] = 0.0;
862
863         hsv_to_rgb(hsv, outcol);
864
865         outcol = mix(col, outcol, fac);
866 }
867
868 void separate_rgb(vec4 col, out float r, out float g, out float b)
869 {
870         r = col.r;
871         g = col.g;
872         b = col.b;
873 }
874
875 void combine_rgb(float r, float g, float b, out vec4 col)
876 {
877         col = vec4(r, g, b, 1.0);
878 }
879
880 void separate_xyz(vec3 vec, out float x, out float y, out float z)
881 {
882         x = vec.r;
883         y = vec.g;
884         z = vec.b;
885 }
886
887 void combine_xyz(float x, float y, float z, out vec3 vec)
888 {
889         vec = vec3(x, y, z);
890 }
891
892 void separate_hsv(vec4 col, out float h, out float s, out float v)
893 {
894         vec4 hsv;
895
896         rgb_to_hsv(col, hsv);
897         h = hsv[0];
898         s = hsv[1];
899         v = hsv[2];
900 }
901
902 void combine_hsv(float h, float s, float v, out vec4 col)
903 {
904         hsv_to_rgb(vec4(h, s, v, 1.0), col);
905 }
906
907 void output_node(vec4 rgb, float alpha, out vec4 outrgb)
908 {
909         outrgb = vec4(rgb.rgb, alpha);
910 }
911
912 /*********** TEXTURES ***************/
913
914 void texco_norm(vec3 normal, out vec3 outnormal)
915 {
916         /* corresponds to shi->orn, which is negated so cancels
917            out blender normal negation */
918         outnormal = normalize(normal);
919 }
920
921 vec3 mtex_2d_mapping(vec3 vec)
922 {
923         return vec3(vec.xy * 0.5 + vec2(0.5), vec.z);
924 }
925
926 /** helper method to extract the upper left 3x3 matrix from a 4x4 matrix */
927 mat3 to_mat3(mat4 m4)
928 {
929         mat3 m3;
930         m3[0] = m4[0].xyz;
931         m3[1] = m4[1].xyz;
932         m3[2] = m4[2].xyz;
933         return m3;
934 }
935
936 /*********** NEW SHADER UTILITIES **************/
937
938 float fresnel_dielectric_0(float eta)
939 {
940         /* compute fresnel reflactance at normal incidence => cosi = 1.0 */
941         float A = (eta - 1.0) / (eta + 1.0);
942
943         return A * A;
944 }
945
946 float fresnel_dielectric_cos(float cosi, float eta)
947 {
948         /* compute fresnel reflectance without explicitly computing
949          * the refracted direction */
950         float c = abs(cosi);
951         float g = eta * eta - 1.0 + c * c;
952         float result;
953
954         if (g > 0.0) {
955                 g = sqrt(g);
956                 float A = (g - c) / (g + c);
957                 float B = (c * (g + c) - 1.0) / (c * (g - c) + 1.0);
958                 result = 0.5 * A * A * (1.0 + B * B);
959         }
960         else {
961                 result = 1.0;  /* TIR (no refracted component) */
962         }
963
964         return result;
965 }
966
967 float fresnel_dielectric(vec3 Incoming, vec3 Normal, float eta)
968 {
969         /* compute fresnel reflectance without explicitly computing
970          * the refracted direction */
971         return fresnel_dielectric_cos(dot(Incoming, Normal), eta);
972 }
973
974 float hypot(float x, float y)
975 {
976         return sqrt(x * x + y * y);
977 }
978
979 void generated_from_orco(vec3 orco, out vec3 generated)
980 {
981 #ifdef VOLUMETRICS
982 #ifdef MESH_SHADER
983         generated = volumeObjectLocalCoord;
984 #else
985         generated = worldPosition;
986 #endif
987 #else
988         generated = orco;
989 #endif
990 }
991
992 int floor_to_int(float x)
993 {
994         return int(floor(x));
995 }
996
997 int quick_floor(float x)
998 {
999         return int(x) - ((x < 0) ? 1 : 0);
1000 }
1001
1002 float integer_noise(int n)
1003 {
1004         int nn;
1005         n = (n + 1013) & 0x7fffffff;
1006         n = (n >> 13) ^ n;
1007         nn = (n * (n * n * 60493 + 19990303) + 1376312589) & 0x7fffffff;
1008         return 0.5 * (float(nn) / 1073741824.0);
1009 }
1010
1011 uint hash(uint kx, uint ky, uint kz)
1012 {
1013 #define rot(x, k) (((x) << (k)) | ((x) >> (32 - (k))))
1014 #define final(a, b, c) \
1015 { \
1016         c ^= b; c -= rot(b, 14); \
1017         a ^= c; a -= rot(c, 11); \
1018         b ^= a; b -= rot(a, 25); \
1019         c ^= b; c -= rot(b, 16); \
1020         a ^= c; a -= rot(c, 4);  \
1021         b ^= a; b -= rot(a, 14); \
1022         c ^= b; c -= rot(b, 24); \
1023 }
1024         // now hash the data!
1025         uint a, b, c, len = 3u;
1026         a = b = c = 0xdeadbeefu + (len << 2u) + 13u;
1027
1028         c += kz;
1029         b += ky;
1030         a += kx;
1031         final (a, b, c);
1032
1033         return c;
1034 #undef rot
1035 #undef final
1036 }
1037
1038 uint hash(int kx, int ky, int kz)
1039 {
1040         return hash(uint(kx), uint(ky), uint(kz));
1041 }
1042
1043 float bits_to_01(uint bits)
1044 {
1045         return (float(bits) / 4294967295.0);
1046 }
1047
1048 float cellnoise(vec3 p)
1049 {
1050         int ix = quick_floor(p.x);
1051         int iy = quick_floor(p.y);
1052         int iz = quick_floor(p.z);
1053
1054         return bits_to_01(hash(uint(ix), uint(iy), uint(iz)));
1055 }
1056
1057 vec3 cellnoise_color(vec3 p)
1058 {
1059         float r = cellnoise(p);
1060         float g = cellnoise(vec3(p.y, p.x, p.z));
1061         float b = cellnoise(vec3(p.y, p.z, p.x));
1062
1063         return vec3(r, g, b);
1064 }
1065
1066 float floorfrac(float x, out int i)
1067 {
1068         i = floor_to_int(x);
1069         return x - i;
1070 }
1071
1072 /* bsdfs */
1073
1074 vec3 tint_from_color(vec3 color)
1075 {
1076         float lum = dot(color, vec3(0.3, 0.6, 0.1)); /* luminance approx. */
1077         return (lum > 0) ? color / lum : vec3(1.0); /* normalize lum. to isolate hue+sat */
1078 }
1079
1080 void convert_metallic_to_specular_tinted(
1081         vec3 basecol, vec3 basecol_tint, float metallic, float specular_fac, float specular_tint,
1082         out vec3 diffuse, out vec3 f0)
1083 {
1084         vec3 tmp_col = mix(vec3(1.0), basecol_tint, specular_tint);
1085         f0 = mix((0.08 * specular_fac) * tmp_col, basecol, metallic);
1086         diffuse = basecol * (1.0 - metallic);
1087 }
1088
1089 vec3 principled_sheen(float NV, vec3 basecol_tint, float sheen_tint)
1090 {
1091         float f = 1.0 - NV;
1092         /* Empirical approximation (manual curve fitting). Can be refined. */
1093         float sheen = f*f*f*0.077 + f*0.01 + 0.00026;
1094         return sheen * mix(vec3(1.0), basecol_tint, sheen_tint);
1095 }
1096
1097 #ifndef VOLUMETRICS
1098 void node_bsdf_diffuse(vec4 color, float roughness, vec3 N, out Closure result)
1099 {
1100         vec3 vN = normalize(mat3(ViewMatrix) * N);
1101         result = CLOSURE_DEFAULT;
1102         result.ssr_normal = normal_encode(vN, viewCameraVec);
1103         eevee_closure_diffuse(N, color.rgb, 1.0, result.radiance);
1104         result.radiance *= color.rgb;
1105 }
1106
1107 void node_bsdf_glossy(vec4 color, float roughness, vec3 N, float ssr_id, out Closure result)
1108 {
1109         vec3 out_spec, ssr_spec;
1110         eevee_closure_glossy(N, vec3(1.0), int(ssr_id), roughness, 1.0, out_spec, ssr_spec);
1111         vec3 vN = normalize(mat3(ViewMatrix) * N);
1112         result = CLOSURE_DEFAULT;
1113         result.radiance = out_spec * color.rgb;
1114         result.ssr_data = vec4(ssr_spec * color.rgb, roughness);
1115         result.ssr_normal = normal_encode(vN, viewCameraVec);
1116         result.ssr_id = int(ssr_id);
1117 }
1118
1119 void node_bsdf_anisotropic(
1120         vec4 color, float roughness, float anisotropy, float rotation, vec3 N, vec3 T,
1121         out Closure result)
1122 {
1123         node_bsdf_glossy(color, roughness, N, -1, result);
1124 }
1125
1126 void node_bsdf_glass(vec4 color, float roughness, float ior, vec3 N, float ssr_id, out Closure result)
1127 {
1128         vec3 out_spec, out_refr, ssr_spec;
1129         vec3 refr_color = (refractionDepth > 0.0) ? color.rgb * color.rgb : color.rgb; /* Simulate 2 transmission event */
1130         eevee_closure_glass(N, vec3(1.0), int(ssr_id), roughness, 1.0, ior, out_spec, out_refr, ssr_spec);
1131         out_refr *= refr_color;
1132         out_spec *= color.rgb;
1133         float fresnel = F_eta(ior, dot(N, cameraVec));
1134         vec3 vN = normalize(mat3(ViewMatrix) * N);
1135         result = CLOSURE_DEFAULT;
1136         result.radiance = mix(out_refr, out_spec, fresnel);
1137         result.ssr_data = vec4(ssr_spec * color.rgb * fresnel, roughness);
1138         result.ssr_normal = normal_encode(vN, viewCameraVec);
1139         result.ssr_id = int(ssr_id);
1140 }
1141
1142 void node_bsdf_toon(vec4 color, float size, float tsmooth, vec3 N, out Closure result)
1143 {
1144         node_bsdf_diffuse(color, 0.0, N, result);
1145 }
1146
1147 void node_bsdf_principled(
1148         vec4 base_color, float subsurface, vec3 subsurface_radius, vec4 subsurface_color, float metallic, float specular,
1149         float specular_tint, float roughness, float anisotropic, float anisotropic_rotation, float sheen, float sheen_tint, float clearcoat,
1150         float clearcoat_roughness, float ior, float transmission, float transmission_roughness, vec3 N, vec3 CN, vec3 T, vec3 I, float ssr_id,
1151         float sss_id, vec3 sss_scale, out Closure result)
1152 {
1153         ior = max(ior, 1e-5);
1154         metallic = saturate(metallic);
1155         transmission = saturate(transmission);
1156         float dielectric = 1.0 - metallic;
1157         transmission *= dielectric;
1158         sheen *= dielectric;
1159         subsurface_color *= dielectric;
1160
1161         vec3 diffuse, f0, out_diff, out_spec, out_trans, out_refr, ssr_spec;
1162         vec3 ctint = tint_from_color(base_color.rgb);
1163         convert_metallic_to_specular_tinted(base_color.rgb, ctint, metallic, specular, specular_tint, diffuse, f0);
1164
1165         float NV = dot(N, cameraVec);
1166         vec3 out_sheen = sheen * principled_sheen(NV, ctint, sheen_tint);
1167
1168         /* Far from being accurate, but 2 glossy evaluation is too expensive.
1169          * Most noticeable difference is at grazing angles since the bsdf lut
1170          * f0 color interpolation is done on top of this interpolation. */
1171         vec3 f0_glass = mix(vec3(1.0), base_color.rgb, specular_tint);
1172         float fresnel = F_eta(ior, NV);
1173         vec3 spec_col = F_color_blend(ior, fresnel, f0_glass) * fresnel;
1174         f0 = mix(f0, spec_col, transmission);
1175
1176         vec3 mixed_ss_base_color = mix(diffuse, subsurface_color.rgb, subsurface);
1177
1178         float sss_scalef = dot(sss_scale, vec3(1.0 / 3.0)) * subsurface;
1179         eevee_closure_principled(N, mixed_ss_base_color, f0, int(ssr_id), roughness,
1180                                  CN, clearcoat * 0.25, clearcoat_roughness, 1.0, sss_scalef, ior,
1181                                  out_diff, out_trans, out_spec, out_refr, ssr_spec);
1182
1183         vec3 refr_color = base_color.rgb;
1184         refr_color *= (refractionDepth > 0.0) ? refr_color : vec3(1.0); /* Simulate 2 transmission event */
1185         out_refr *= refr_color * (1.0 - fresnel) * transmission;
1186
1187         vec3 vN = normalize(mat3(ViewMatrix) * N);
1188         result = CLOSURE_DEFAULT;
1189         result.radiance = out_spec + out_refr;
1190         result.radiance += out_diff * out_sheen; /* Coarse approx. */
1191 #ifndef USE_SSS
1192         result.radiance += (out_diff + out_trans) * mixed_ss_base_color *  (1.0 - transmission);
1193 #endif
1194         result.ssr_data = vec4(ssr_spec, roughness);
1195         result.ssr_normal = normal_encode(vN, viewCameraVec);
1196         result.ssr_id = int(ssr_id);
1197 #ifdef USE_SSS
1198         result.sss_data.a = sss_scalef;
1199         result.sss_data.rgb = out_diff + out_trans;
1200 #  ifdef USE_SSS_ALBEDO
1201         result.sss_albedo.rgb = mixed_ss_base_color;
1202 #  else
1203         result.sss_data.rgb *= mixed_ss_base_color;
1204 #  endif
1205         result.sss_data.rgb *= (1.0 - transmission);
1206 #endif
1207 }
1208
1209 void node_bsdf_principled_dielectric(
1210         vec4 base_color, float subsurface, vec3 subsurface_radius, vec4 subsurface_color, float metallic, float specular,
1211         float specular_tint, float roughness, float anisotropic, float anisotropic_rotation, float sheen, float sheen_tint, float clearcoat,
1212         float clearcoat_roughness, float ior, float transmission, float transmission_roughness, vec3 N, vec3 CN, vec3 T, vec3 I, float ssr_id,
1213         float sss_id, vec3 sss_scale, out Closure result)
1214 {
1215         metallic = saturate(metallic);
1216         float dielectric = 1.0 - metallic;
1217
1218         vec3 diffuse, f0, out_diff, out_spec, ssr_spec;
1219         vec3 ctint = tint_from_color(base_color.rgb);
1220         convert_metallic_to_specular_tinted(base_color.rgb, ctint, metallic, specular, specular_tint, diffuse, f0);
1221
1222         float NV = dot(N, cameraVec);
1223         vec3 out_sheen = sheen * principled_sheen(NV, ctint, sheen_tint);
1224
1225         eevee_closure_default(N, diffuse, f0, int(ssr_id), roughness, 1.0, out_diff, out_spec, ssr_spec);
1226
1227         vec3 vN = normalize(mat3(ViewMatrix) * N);
1228         result = CLOSURE_DEFAULT;
1229         result.radiance = out_spec + out_diff * (diffuse + out_sheen);
1230         result.ssr_data = vec4(ssr_spec, roughness);
1231         result.ssr_normal = normal_encode(vN, viewCameraVec);
1232         result.ssr_id = int(ssr_id);
1233 }
1234
1235 void node_bsdf_principled_metallic(
1236         vec4 base_color, float subsurface, vec3 subsurface_radius, vec4 subsurface_color, float metallic, float specular,
1237         float specular_tint, float roughness, float anisotropic, float anisotropic_rotation, float sheen, float sheen_tint, float clearcoat,
1238         float clearcoat_roughness, float ior, float transmission, float transmission_roughness, vec3 N, vec3 CN, vec3 T, vec3 I, float ssr_id,
1239         float sss_id, vec3 sss_scale, out Closure result)
1240 {
1241         vec3 out_spec, ssr_spec;
1242
1243         eevee_closure_glossy(N, base_color.rgb, int(ssr_id), roughness, 1.0, out_spec, ssr_spec);
1244
1245         vec3 vN = normalize(mat3(ViewMatrix) * N);
1246         result = CLOSURE_DEFAULT;
1247         result.radiance = out_spec;
1248         result.ssr_data = vec4(ssr_spec, roughness);
1249         result.ssr_normal = normal_encode(vN, viewCameraVec);
1250         result.ssr_id = int(ssr_id);
1251 }
1252
1253 void node_bsdf_principled_clearcoat(
1254         vec4 base_color, float subsurface, vec3 subsurface_radius, vec4 subsurface_color, float metallic, float specular,
1255         float specular_tint, float roughness, float anisotropic, float anisotropic_rotation, float sheen, float sheen_tint, float clearcoat,
1256         float clearcoat_roughness, float ior, float transmission, float transmission_roughness, vec3 N, vec3 CN, vec3 T, vec3 I, float ssr_id,
1257         float sss_id, vec3 sss_scale, out Closure result)
1258 {
1259         vec3 out_spec, ssr_spec;
1260
1261         eevee_closure_clearcoat(N, base_color.rgb, int(ssr_id), roughness, CN, clearcoat * 0.25, clearcoat_roughness,
1262                                 1.0, out_spec, ssr_spec);
1263
1264         vec3 vN = normalize(mat3(ViewMatrix) * N);
1265         result = CLOSURE_DEFAULT;
1266         result.radiance = out_spec;
1267         result.ssr_data = vec4(ssr_spec, roughness);
1268         result.ssr_normal = normal_encode(vN, viewCameraVec);
1269         result.ssr_id = int(ssr_id);
1270 }
1271
1272 void node_bsdf_principled_subsurface(
1273         vec4 base_color, float subsurface, vec3 subsurface_radius, vec4 subsurface_color, float metallic, float specular,
1274         float specular_tint, float roughness, float anisotropic, float anisotropic_rotation, float sheen, float sheen_tint, float clearcoat,
1275         float clearcoat_roughness, float ior, float transmission, float transmission_roughness, vec3 N, vec3 CN, vec3 T, vec3 I, float ssr_id,
1276         float sss_id, vec3 sss_scale, out Closure result)
1277 {
1278         metallic = saturate(metallic);
1279
1280         vec3 diffuse, f0, out_diff, out_spec, out_trans, ssr_spec;
1281         vec3 ctint = tint_from_color(base_color.rgb);
1282         convert_metallic_to_specular_tinted(base_color.rgb, ctint, metallic, specular, specular_tint, diffuse, f0);
1283
1284         subsurface_color = subsurface_color * (1.0 - metallic);
1285         vec3 mixed_ss_base_color = mix(diffuse, subsurface_color.rgb, subsurface);
1286         float sss_scalef = dot(sss_scale, vec3(1.0 / 3.0)) * subsurface;
1287
1288         float NV = dot(N, cameraVec);
1289         vec3 out_sheen = sheen * principled_sheen(NV, ctint, sheen_tint);
1290
1291         eevee_closure_skin(N, mixed_ss_base_color, f0, int(ssr_id), roughness, 1.0, sss_scalef,
1292                            out_diff, out_trans, out_spec, ssr_spec);
1293
1294         vec3 vN = normalize(mat3(ViewMatrix) * N);
1295         result = CLOSURE_DEFAULT;
1296         result.radiance = out_spec;
1297         result.ssr_data = vec4(ssr_spec, roughness);
1298         result.ssr_normal = normal_encode(vN, viewCameraVec);
1299         result.ssr_id = int(ssr_id);
1300 #ifdef USE_SSS
1301         result.sss_data.a = sss_scalef;
1302         result.sss_data.rgb = out_diff + out_trans;
1303 #  ifdef USE_SSS_ALBEDO
1304         result.sss_albedo.rgb = mixed_ss_base_color;
1305 #  else
1306         result.sss_data.rgb *= mixed_ss_base_color;
1307 #  endif
1308 #else
1309         result.radiance += (out_diff + out_trans) * mixed_ss_base_color;
1310 #endif
1311         result.radiance += out_diff * out_sheen;
1312 }
1313
1314 void node_bsdf_principled_glass(
1315         vec4 base_color, float subsurface, vec3 subsurface_radius, vec4 subsurface_color, float metallic, float specular,
1316         float specular_tint, float roughness, float anisotropic, float anisotropic_rotation, float sheen, float sheen_tint, float clearcoat,
1317         float clearcoat_roughness, float ior, float transmission, float transmission_roughness, vec3 N, vec3 CN, vec3 T, vec3 I, float ssr_id,
1318         float sss_id, vec3 sss_scale, out Closure result)
1319 {
1320         ior = max(ior, 1e-5);
1321
1322         vec3 f0, out_spec, out_refr, ssr_spec;
1323         f0 = mix(vec3(1.0), base_color.rgb, specular_tint);
1324
1325         eevee_closure_glass(N, vec3(1.0), int(ssr_id), roughness, 1.0, ior, out_spec, out_refr, ssr_spec);
1326
1327         vec3 refr_color = base_color.rgb;
1328         refr_color *= (refractionDepth > 0.0) ? refr_color : vec3(1.0); /* Simulate 2 transmission events */
1329         out_refr *= refr_color;
1330
1331         float fresnel = F_eta(ior, dot(N, cameraVec));
1332         vec3 spec_col = F_color_blend(ior, fresnel, f0);
1333         out_spec *= spec_col;
1334         ssr_spec *= spec_col * fresnel;
1335
1336         vec3 vN = normalize(mat3(ViewMatrix) * N);
1337         result = CLOSURE_DEFAULT;
1338         result.radiance = mix(out_refr, out_spec, fresnel);
1339         result.ssr_data = vec4(ssr_spec, roughness);
1340         result.ssr_normal = normal_encode(vN, viewCameraVec);
1341         result.ssr_id = int(ssr_id);
1342 }
1343
1344 void node_bsdf_translucent(vec4 color, vec3 N, out Closure result)
1345 {
1346         node_bsdf_diffuse(color, 0.0, -N, result);
1347 }
1348
1349 void node_bsdf_transparent(vec4 color, out Closure result)
1350 {
1351         /* this isn't right */
1352         result = CLOSURE_DEFAULT;
1353         result.radiance = vec3(0.0);
1354         result.opacity = 0.0;
1355         result.ssr_id = TRANSPARENT_CLOSURE_FLAG;
1356 }
1357
1358 void node_bsdf_velvet(vec4 color, float sigma, vec3 N, out Closure result)
1359 {
1360         node_bsdf_diffuse(color, 0.0, N, result);
1361 }
1362
1363 void node_subsurface_scattering(
1364         vec4 color, float scale, vec3 radius, float sharpen, float texture_blur, vec3 N, float sss_id,
1365         out Closure result)
1366 {
1367 #if defined(USE_SSS)
1368         vec3 out_diff, out_trans;
1369         vec3 vN = normalize(mat3(ViewMatrix) * N);
1370         result = CLOSURE_DEFAULT;
1371         result.ssr_data = vec4(0.0);
1372         result.ssr_normal = normal_encode(vN, viewCameraVec);
1373         result.ssr_id = -1;
1374         result.sss_data.a = scale;
1375         eevee_closure_subsurface(N, color.rgb, 1.0, scale, out_diff, out_trans);
1376         result.sss_data.rgb = out_diff + out_trans;
1377 #  ifdef USE_SSS_ALBEDO
1378         /* Not perfect for texture_blur not exactly equal to 0.0 or 1.0. */
1379         result.sss_albedo.rgb = mix(color.rgb, vec3(1.0), texture_blur);
1380         result.sss_data.rgb *= mix(vec3(1.0), color.rgb, texture_blur);
1381 #  else
1382         result.sss_data.rgb *= color.rgb;
1383 #  endif
1384 #else
1385         node_bsdf_diffuse(color, 0.0, N, result);
1386 #endif
1387 }
1388
1389 void node_bsdf_refraction(vec4 color, float roughness, float ior, vec3 N, out Closure result)
1390 {
1391         vec3 out_refr;
1392         color.rgb *= (refractionDepth > 0.0) ? color.rgb : vec3(1.0); /* Simulate 2 absorption event. */
1393         eevee_closure_refraction(N, roughness, ior, out_refr);
1394         vec3 vN = normalize(mat3(ViewMatrix) * N);
1395         result = CLOSURE_DEFAULT;
1396         result.ssr_normal = normal_encode(vN, viewCameraVec);
1397         result.radiance = out_refr * color.rgb;
1398         result.ssr_id = REFRACT_CLOSURE_FLAG;
1399 }
1400
1401 void node_ambient_occlusion(vec4 color, float distance, vec3 normal, out vec4 result_color, out float result_ao)
1402 {
1403         vec3 bent_normal;
1404         vec4 rand = texelFetch(utilTex, ivec3(ivec2(gl_FragCoord.xy) % LUT_SIZE, 2.0), 0);
1405         result_ao = occlusion_compute(normalize(normal), viewPosition, 1.0, rand, bent_normal);
1406         result_color = result_ao * color;
1407 }
1408
1409 #endif /* VOLUMETRICS */
1410
1411 /* emission */
1412
1413 void node_emission(vec4 color, float strength, vec3 vN, out Closure result)
1414 {
1415 #ifndef VOLUMETRICS
1416         color *= strength;
1417         result = CLOSURE_DEFAULT;
1418         result.radiance = color.rgb;
1419         result.opacity = color.a;
1420         result.ssr_normal = normal_encode(vN, viewCameraVec);
1421 #else
1422         result = Closure(vec3(0.0), vec3(0.0), color.rgb * strength, 0.0);
1423 #endif
1424 }
1425
1426 void node_wireframe(float size, vec2 barycentric, vec3 barycentric_dist, out float fac)
1427 {
1428         vec3 barys = barycentric.xyy;
1429         barys.z = 1.0 - barycentric.x - barycentric.y;
1430
1431         size *= 0.5;
1432         vec3 s = step(-size, -barys * barycentric_dist);
1433
1434         fac = max(s.x, max(s.y, s.z));
1435 }
1436
1437 void node_wireframe_screenspace(float size, vec2 barycentric, out float fac)
1438 {
1439         vec3 barys = barycentric.xyy;
1440         barys.z = 1.0 - barycentric.x - barycentric.y;
1441
1442         size *= (1.0 / 3.0);
1443         vec3 deltas = fwidth(barys);
1444         vec3 s = step(-deltas * size, -barys);
1445
1446         fac = max(s.x, max(s.y, s.z));
1447 }
1448
1449 /* background */
1450
1451 void background_transform_to_world(vec3 viewvec, out vec3 worldvec)
1452 {
1453         vec4 v = (ProjectionMatrix[3][3] == 0.0) ? vec4(viewvec, 1.0) : vec4(0.0, 0.0, 1.0, 1.0);
1454         vec4 co_homogenous = (ProjectionMatrixInverse * v);
1455
1456         vec4 co = vec4(co_homogenous.xyz / co_homogenous.w, 0.0);
1457 #if defined(WORLD_BACKGROUND) || defined(PROBE_CAPTURE)
1458         worldvec = (ViewMatrixInverse * co).xyz;
1459 #else
1460         worldvec = (ModelViewMatrixInverse * co).xyz;
1461 #endif
1462 }
1463
1464 void node_background(vec4 color, float strength, out Closure result)
1465 {
1466 #ifndef VOLUMETRICS
1467         color *= strength;
1468         result = CLOSURE_DEFAULT;
1469         result.radiance = color.rgb;
1470         result.opacity = color.a;
1471 #else
1472         result = CLOSURE_DEFAULT;
1473 #endif
1474 }
1475
1476 /* volumes */
1477
1478 void node_volume_scatter(vec4 color, float density, float anisotropy, out Closure result)
1479 {
1480 #ifdef VOLUMETRICS
1481         result = Closure(vec3(0.0), color.rgb * density, vec3(0.0), anisotropy);
1482 #else
1483         result = CLOSURE_DEFAULT;
1484 #endif
1485 }
1486
1487 void node_volume_absorption(vec4 color, float density, out Closure result)
1488 {
1489 #ifdef VOLUMETRICS
1490         result = Closure((1.0 - color.rgb) * density, vec3(0.0), vec3(0.0), 0.0);
1491 #else
1492         result = CLOSURE_DEFAULT;
1493 #endif
1494 }
1495
1496 void node_blackbody(float temperature, sampler1DArray spectrummap, float layer, out vec4 color)
1497 {
1498     if (temperature >= 12000.0) {
1499         color = vec4(0.826270103, 0.994478524, 1.56626022, 1.0);
1500     }
1501     else if (temperature < 965.0) {
1502         color = vec4(4.70366907, 0.0, 0.0, 1.0);
1503     }
1504         else {
1505                 float t = (temperature - 965.0) / (12000.0 - 965.0);
1506                 color = vec4(texture(spectrummap, vec2(t, layer)).rgb, 1.0);
1507         }
1508 }
1509
1510 void node_volume_principled(
1511         vec4 color,
1512         float density,
1513         float anisotropy,
1514         vec4 absorption_color,
1515         float emission_strength,
1516         vec4 emission_color,
1517         float blackbody_intensity,
1518         vec4 blackbody_tint,
1519         float temperature,
1520         float density_attribute,
1521         vec4 color_attribute,
1522         float temperature_attribute,
1523         sampler1DArray spectrummap,
1524         float layer,
1525         out Closure result)
1526 {
1527 #ifdef VOLUMETRICS
1528         vec3 absorption_coeff = vec3(0.0);
1529         vec3 scatter_coeff = vec3(0.0);
1530         vec3 emission_coeff = vec3(0.0);
1531
1532         /* Compute density. */
1533         density = max(density, 0.0);
1534
1535         if(density > 1e-5) {
1536                 density = max(density * density_attribute, 0.0);
1537         }
1538
1539         if(density > 1e-5) {
1540                 /* Compute scattering and absorption coefficients. */
1541                 vec3 scatter_color = color.rgb * color_attribute.rgb;
1542
1543                 scatter_coeff = scatter_color * density;
1544                 absorption_color.rgb = sqrt(max(absorption_color.rgb, 0.0));
1545                 absorption_coeff = max(1.0 - scatter_color, 0.0) * max(1.0 - absorption_color.rgb, 0.0) * density;
1546         }
1547
1548         /* Compute emission. */
1549         emission_strength = max(emission_strength, 0.0);
1550
1551         if(emission_strength > 1e-5) {
1552                 emission_coeff += emission_strength * emission_color.rgb;
1553         }
1554
1555         if(blackbody_intensity > 1e-3) {
1556                 /* Add temperature from attribute. */
1557                 float T = max(temperature * max(temperature_attribute, 0.0), 0.0);
1558
1559                 /* Stefan-Boltzman law. */
1560                 float T4 = (T * T) * (T * T);
1561                 float sigma = 5.670373e-8 * 1e-6 / M_PI;
1562                 float intensity = sigma * mix(1.0, T4, blackbody_intensity);
1563
1564                 if(intensity > 1e-5) {
1565                         vec4 bb;
1566                         node_blackbody(T, spectrummap, layer, bb);
1567                         emission_coeff += bb.rgb * blackbody_tint.rgb * intensity;
1568                 }
1569         }
1570
1571         result = Closure(absorption_coeff, scatter_coeff, emission_coeff, anisotropy);
1572 #else
1573         result = CLOSURE_DEFAULT;
1574 #endif
1575 }
1576
1577 /* closures */
1578
1579 void node_mix_shader(float fac, Closure shader1, Closure shader2, out Closure shader)
1580 {
1581         shader = closure_mix(shader1, shader2, fac);
1582 }
1583
1584 void node_add_shader(Closure shader1, Closure shader2, out Closure shader)
1585 {
1586         shader = closure_add(shader1, shader2);
1587 }
1588
1589 /* fresnel */
1590
1591 void node_fresnel(float ior, vec3 N, vec3 I, out float result)
1592 {
1593         /* handle perspective/orthographic */
1594         vec3 I_view = (ProjectionMatrix[3][3] == 0.0) ? normalize(I) : vec3(0.0, 0.0, -1.0);
1595
1596         float eta = max(ior, 0.00001);
1597         result = fresnel_dielectric(I_view, N, (gl_FrontFacing) ? eta : 1.0 / eta);
1598 }
1599
1600 /* layer_weight */
1601
1602 void node_layer_weight(float blend, vec3 N, vec3 I, out float fresnel, out float facing)
1603 {
1604         /* fresnel */
1605         float eta = max(1.0 - blend, 0.00001);
1606         vec3 I_view = (ProjectionMatrix[3][3] == 0.0) ? normalize(I) : vec3(0.0, 0.0, -1.0);
1607
1608         fresnel = fresnel_dielectric(I_view, N, (gl_FrontFacing) ? 1.0 / eta : eta);
1609
1610         /* facing */
1611         facing = abs(dot(I_view, N));
1612         if (blend != 0.5) {
1613                 blend = clamp(blend, 0.0, 0.99999);
1614                 blend = (blend < 0.5) ? 2.0 * blend : 0.5 / (1.0 - blend);
1615                 facing = pow(facing, blend);
1616         }
1617         facing = 1.0 - facing;
1618 }
1619
1620 /* gamma */
1621
1622 void node_gamma(vec4 col, float gamma, out vec4 outcol)
1623 {
1624         outcol = col;
1625
1626         if (col.r > 0.0)
1627                 outcol.r = compatible_pow(col.r, gamma);
1628         if (col.g > 0.0)
1629                 outcol.g = compatible_pow(col.g, gamma);
1630         if (col.b > 0.0)
1631                 outcol.b = compatible_pow(col.b, gamma);
1632 }
1633
1634 /* geometry */
1635
1636 void node_attribute_volume_density(sampler3D tex, out vec4 outcol, out vec3 outvec, out float outf)
1637 {
1638 #if defined(MESH_SHADER) && defined(VOLUMETRICS)
1639         vec3 cos = volumeObjectLocalCoord;
1640 #else
1641         vec3 cos = vec3(0.0);
1642 #endif
1643         outvec = texture(tex, cos).aaa;
1644         outcol = vec4(outvec, 1.0);
1645         outf = dot(vec3(1.0 / 3.0), outvec);
1646 }
1647
1648 void node_attribute_volume_color(sampler3D tex, out vec4 outcol, out vec3 outvec, out float outf)
1649 {
1650 #if defined(MESH_SHADER) && defined(VOLUMETRICS)
1651         vec3 cos = volumeObjectLocalCoord;
1652 #else
1653         vec3 cos = vec3(0.0);
1654 #endif
1655
1656         vec4 value = texture(tex, cos).rgba;
1657         /* Density is premultiplied for interpolation, divide it out here. */
1658         if (value.a > 1e-8)
1659                 value.rgb /= value.a;
1660
1661         outvec = value.rgb;
1662         outcol = vec4(outvec, 1.0);
1663         outf = dot(vec3(1.0 / 3.0), outvec);
1664 }
1665
1666 void node_attribute_volume_flame(sampler3D tex, out vec4 outcol, out vec3 outvec, out float outf)
1667 {
1668 #if defined(MESH_SHADER) && defined(VOLUMETRICS)
1669         vec3 cos = volumeObjectLocalCoord;
1670 #else
1671         vec3 cos = vec3(0.0);
1672 #endif
1673         outf = texture(tex, cos).r;
1674         outvec = vec3(outf, outf, outf);
1675         outcol = vec4(outf, outf, outf, 1.0);
1676 }
1677
1678 void node_attribute_volume_temperature(sampler3D tex, vec2 temperature, out vec4 outcol, out vec3 outvec, out float outf)
1679 {
1680 #if defined(MESH_SHADER) && defined(VOLUMETRICS)
1681         vec3 cos = volumeObjectLocalCoord;
1682 #else
1683         vec3 cos = vec3(0.0);
1684 #endif
1685         float flame = texture(tex, cos).r;
1686
1687         outf = (flame > 0.01) ? temperature.x + flame * (temperature.y - temperature.x): 0.0;
1688         outvec = vec3(outf, outf, outf);
1689         outcol = vec4(outf, outf, outf, 1.0);
1690 }
1691
1692 void node_attribute(vec3 attr, out vec4 outcol, out vec3 outvec, out float outf)
1693 {
1694         outcol = vec4(attr, 1.0);
1695         outvec = attr;
1696         outf =  dot(vec3(1.0 / 3.0), attr);
1697 }
1698
1699 void node_uvmap(vec3 attr_uv, out vec3 outvec)
1700 {
1701         outvec = attr_uv;
1702 }
1703
1704 void tangent_orco_x(vec3 orco_in, out vec3 orco_out)
1705 {
1706         orco_out = vec3(0.0, (orco_in.z - 0.5) * -0.5, (orco_in.y - 0.5) * 0.5);
1707 }
1708
1709 void tangent_orco_y(vec3 orco_in, out vec3 orco_out)
1710 {
1711         orco_out = vec3((orco_in.z - 0.5) * -0.5, 0.0, (orco_in.x - 0.5) * 0.5);
1712 }
1713
1714 void tangent_orco_z(vec3 orco_in, out vec3 orco_out)
1715 {
1716         orco_out = vec3((orco_in.y - 0.5) * -0.5, (orco_in.x - 0.5) * 0.5, 0.0);
1717 }
1718
1719 void node_tangentmap(vec4 attr_tangent, mat4 toworld, out vec3 tangent)
1720 {
1721         tangent = (toworld * vec4(attr_tangent.xyz, 0.0)).xyz;
1722 }
1723
1724 void node_tangent(vec3 N, vec3 orco, mat4 objmat, mat4 toworld, out vec3 T)
1725 {
1726         N = (toworld * vec4(N, 0.0)).xyz;
1727         T = (objmat * vec4(orco, 0.0)).xyz;
1728         T = cross(N, normalize(cross(T, N)));
1729 }
1730
1731 void node_geometry(
1732         vec3 I, vec3 N, vec3 orco, mat4 objmat, mat4 toworld, vec2 barycentric,
1733         out vec3 position, out vec3 normal, out vec3 tangent,
1734         out vec3 true_normal, out vec3 incoming, out vec3 parametric,
1735         out float backfacing, out float pointiness)
1736 {
1737         position = worldPosition;
1738         normal = (toworld * vec4(N, 0.0)).xyz;
1739         tangent_orco_z(orco, orco);
1740         node_tangent(N, orco, objmat, toworld, tangent);
1741         true_normal = normal;
1742
1743         /* handle perspective/orthographic */
1744         vec3 I_view = (ProjectionMatrix[3][3] == 0.0) ? normalize(I) : vec3(0.0, 0.0, -1.0);
1745         incoming = -(toworld * vec4(I_view, 0.0)).xyz;
1746
1747         parametric = vec3(barycentric, 0.0);
1748         backfacing = (gl_FrontFacing) ? 0.0 : 1.0;
1749         pointiness = 0.5;
1750 }
1751
1752 void node_tex_coord(
1753         vec3 I, vec3 N, mat4 viewinvmat, mat4 obinvmat, vec4 camerafac,
1754         vec3 attr_orco, vec3 attr_uv,
1755         out vec3 generated, out vec3 normal, out vec3 uv, out vec3 object,
1756         out vec3 camera, out vec3 window, out vec3 reflection)
1757 {
1758         generated = attr_orco;
1759         normal = normalize((obinvmat * (viewinvmat * vec4(N, 0.0))).xyz);
1760         uv = attr_uv;
1761         object = (obinvmat * (viewinvmat * vec4(I, 1.0))).xyz;
1762         camera = vec3(I.xy, -I.z);
1763         vec4 projvec = ProjectionMatrix * vec4(I, 1.0);
1764         window = vec3(mtex_2d_mapping(projvec.xyz / projvec.w).xy * camerafac.xy + camerafac.zw, 0.0);
1765
1766         vec3 shade_I = (ProjectionMatrix[3][3] == 0.0) ? normalize(I) : vec3(0.0, 0.0, -1.0);
1767         vec3 view_reflection = reflect(shade_I, normalize(N));
1768         reflection = (viewinvmat * vec4(view_reflection, 0.0)).xyz;
1769 }
1770
1771 void node_tex_coord_background(
1772         vec3 I, vec3 N, mat4 viewinvmat, mat4 obinvmat, vec4 camerafac,
1773         vec3 attr_orco, vec3 attr_uv,
1774         out vec3 generated, out vec3 normal, out vec3 uv, out vec3 object,
1775         out vec3 camera, out vec3 window, out vec3 reflection)
1776 {
1777         vec4 v = (ProjectionMatrix[3][3] == 0.0) ? vec4(I, 1.0) : vec4(0.0, 0.0, 1.0, 1.0);
1778         vec4 co_homogenous = (ProjectionMatrixInverse * v);
1779
1780         vec4 co = vec4(co_homogenous.xyz / co_homogenous.w, 0.0);
1781
1782         co = normalize(co);
1783
1784 #if defined(WORLD_BACKGROUND) || defined(PROBE_CAPTURE)
1785         vec3 coords = (ViewMatrixInverse * co).xyz;
1786 #else
1787         vec3 coords = (ModelViewMatrixInverse * co).xyz;
1788 #endif
1789
1790         generated = coords;
1791         normal = -coords;
1792         uv = vec3(attr_uv.xy, 0.0);
1793         object = coords;
1794
1795         camera = vec3(co.xy, -co.z);
1796         window = (ProjectionMatrix[3][3] == 0.0) ?
1797                  vec3(mtex_2d_mapping(I).xy * camerafac.xy + camerafac.zw, 0.0) :
1798                  vec3(vec2(0.5) * camerafac.xy + camerafac.zw, 0.0);
1799
1800         reflection = -coords;
1801 }
1802
1803 #if defined(WORLD_BACKGROUND) || (defined(PROBE_CAPTURE) && !defined(MESH_SHADER))
1804 #define node_tex_coord node_tex_coord_background
1805 #endif
1806
1807 /* textures */
1808
1809 float calc_gradient(vec3 p, int gradient_type)
1810 {
1811         float x, y, z;
1812         x = p.x;
1813         y = p.y;
1814         z = p.z;
1815         if (gradient_type == 0) {  /* linear */
1816                 return x;
1817         }
1818         else if (gradient_type == 1) {  /* quadratic */
1819                 float r = max(x, 0.0);
1820                 return r * r;
1821         }
1822         else if (gradient_type == 2) {  /* easing */
1823                 float r = min(max(x, 0.0), 1.0);
1824                 float t = r * r;
1825                 return (3.0 * t - 2.0 * t * r);
1826         }
1827         else if (gradient_type == 3) {  /* diagonal */
1828                 return (x + y) * 0.5;
1829         }
1830         else if (gradient_type == 4) {  /* radial */
1831                 return atan(y, x) / (M_PI * 2) + 0.5;
1832         }
1833         else {
1834                 /* Bias a little bit for the case where p is a unit length vector,
1835                  * to get exactly zero instead of a small random value depending
1836                  * on float precision. */
1837                 float r = max(0.999999 - sqrt(x * x + y * y + z * z), 0.0);
1838                 if (gradient_type == 5) {  /* quadratic sphere */
1839                         return r * r;
1840                 }
1841                 else if (gradient_type == 6) {  /* sphere */
1842                         return r;
1843                 }
1844         }
1845         return 0.0;
1846 }
1847
1848 void node_tex_gradient(vec3 co, float gradient_type, out vec4 color, out float fac)
1849 {
1850         float f = calc_gradient(co, int(gradient_type));
1851         f = clamp(f, 0.0, 1.0);
1852
1853         color = vec4(f, f, f, 1.0);
1854         fac = f;
1855 }
1856
1857 void node_tex_checker(vec3 co, vec4 color1, vec4 color2, float scale, out vec4 color, out float fac)
1858 {
1859         vec3 p = co * scale;
1860
1861         /* Prevent precision issues on unit coordinates. */
1862         p = (p + 0.000001) * 0.999999;
1863
1864         int xi = int(abs(floor(p.x)));
1865         int yi = int(abs(floor(p.y)));
1866         int zi = int(abs(floor(p.z)));
1867
1868         bool check = ((mod(xi, 2) == mod(yi, 2)) == bool(mod(zi, 2)));
1869
1870         color = check ? color1 : color2;
1871         fac = check ? 1.0 : 0.0;
1872 }
1873
1874 vec2 calc_brick_texture(vec3 p, float mortar_size, float mortar_smooth, float bias,
1875                         float brick_width, float row_height,
1876                         float offset_amount, int offset_frequency,
1877                         float squash_amount, int squash_frequency)
1878 {
1879         int bricknum, rownum;
1880         float offset = 0.0;
1881         float x, y;
1882
1883         rownum = floor_to_int(p.y / row_height);
1884
1885         if (offset_frequency != 0 && squash_frequency != 0) {
1886                 brick_width *= (rownum % squash_frequency != 0) ? 1.0 : squash_amount; /* squash */
1887                 offset = (rownum % offset_frequency != 0) ? 0.0 : (brick_width * offset_amount); /* offset */
1888         }
1889
1890         bricknum = floor_to_int((p.x + offset) / brick_width);
1891
1892         x = (p.x + offset) - brick_width * bricknum;
1893         y = p.y - row_height * rownum;
1894
1895         float tint = clamp((integer_noise((rownum << 16) + (bricknum & 0xFFFF)) + bias), 0.0, 1.0);
1896
1897         float min_dist = min(min(x, y), min(brick_width - x, row_height - y));
1898         if (min_dist >= mortar_size) {
1899                 return vec2(tint, 0.0);
1900         }
1901         else if (mortar_smooth == 0.0) {
1902                 return vec2(tint, 1.0);
1903         }
1904         else {
1905                 min_dist = 1.0 - min_dist/mortar_size;
1906                 return vec2(tint, smoothstep(0.0, mortar_smooth, min_dist));
1907         }
1908 }
1909
1910 void node_tex_brick(vec3 co,
1911                     vec4 color1, vec4 color2,
1912                     vec4 mortar, float scale,
1913                     float mortar_size, float mortar_smooth, float bias,
1914                     float brick_width, float row_height,
1915                     float offset_amount, float offset_frequency,
1916                     float squash_amount, float squash_frequency,
1917                     out vec4 color, out float fac)
1918 {
1919         vec2 f2 = calc_brick_texture(co * scale,
1920                                      mortar_size, mortar_smooth, bias,
1921                                      brick_width, row_height,
1922                                      offset_amount, int(offset_frequency),
1923                                      squash_amount, int(squash_frequency));
1924         float tint = f2.x;
1925         float f = f2.y;
1926         if (f != 1.0) {
1927                 float facm = 1.0 - tint;
1928                 color1 = facm * color1 + tint * color2;
1929         }
1930         color = mix(color1, mortar, f);
1931         fac = f;
1932 }
1933
1934 void node_tex_clouds(vec3 co, float size, out vec4 color, out float fac)
1935 {
1936         color = vec4(1.0);
1937         fac = 1.0;
1938 }
1939
1940 void node_tex_environment_equirectangular(vec3 co, sampler2D ima, out vec4 color)
1941 {
1942         vec3 nco = normalize(co);
1943         float u = -atan(nco.y, nco.x) / (2.0 * M_PI) + 0.5;
1944         float v = atan(nco.z, hypot(nco.x, nco.y)) / M_PI + 0.5;
1945
1946         /* Fix pole bleeding */
1947         float half_width = 0.5 / float(textureSize(ima, 0).x);
1948         v = clamp(v, half_width, 1.0 - half_width);
1949
1950         /* Fix u = 0 seam */
1951         /* This is caused by texture filtering, since uv don't have smooth derivatives
1952          * at u = 0 or 2PI, hardware filtering is using the smallest mipmap for certain
1953          * texels. So we force the highest mipmap and don't do anisotropic filtering. */
1954         color = textureLod(ima, vec2(u, v), 0.0);
1955 }
1956
1957 void node_tex_environment_mirror_ball(vec3 co, sampler2D ima, out vec4 color)
1958 {
1959         vec3 nco = normalize(co);
1960
1961         nco.y -= 1.0;
1962
1963         float div = 2.0 * sqrt(max(-0.5 * nco.y, 0.0));
1964         if (div > 0.0)
1965                 nco /= div;
1966
1967         float u = 0.5 * (nco.x + 1.0);
1968         float v = 0.5 * (nco.z + 1.0);
1969
1970         color = texture(ima, vec2(u, v));
1971 }
1972
1973 void node_tex_environment_empty(vec3 co, out vec4 color)
1974 {
1975         color = vec4(1.0, 0.0, 1.0, 1.0);
1976 }
1977
1978 void node_tex_image_linear(vec3 co, sampler2D ima, out vec4 color, out float alpha)
1979 {
1980         color = texture(ima, co.xy);
1981         alpha = color.a;
1982 }
1983
1984 void node_tex_image_nearest(vec3 co, sampler2D ima, out vec4 color, out float alpha)
1985 {
1986         ivec2 pix = ivec2(fract(co.xy) * textureSize(ima, 0).xy);
1987         color = texelFetch(ima, pix, 0);
1988         alpha = color.a;
1989 }
1990
1991 void node_tex_image_cubic(vec3 co, sampler2D ima, out vec4 color, out float alpha)
1992 {
1993         vec2 tex_size = vec2(textureSize(ima, 0).xy);
1994
1995         co.xy *= tex_size;
1996         /* texel center */
1997         vec2 tc = floor(co.xy - 0.5) + 0.5;
1998         vec2 f = co.xy - tc;
1999         vec2 f2 = f * f;
2000         vec2 f3 = f2 * f;
2001         /* Bspline coefs (optimized) */
2002         vec2 w3 =  f3 / 6.0;
2003         vec2 w0 = -w3       + f2 * 0.5 - f * 0.5 + 1.0 / 6.0;
2004         vec2 w1 =  f3 * 0.5 - f2 * 1.0           + 2.0 / 3.0;
2005         vec2 w2 = 1.0 - w0 - w1 - w3;
2006
2007 #if 1 /* Optimized version using 4 filtered tap. */
2008         vec2 s0 = w0 + w1;
2009         vec2 s1 = w2 + w3;
2010
2011         vec2 f0 = w1 / (w0 + w1);
2012         vec2 f1 = w3 / (w2 + w3);
2013
2014         vec4 final_co;
2015         final_co.xy = tc - 1.0 + f0;
2016         final_co.zw = tc + 1.0 + f1;
2017
2018         final_co /= tex_size.xyxy;
2019
2020         color  = texture(ima, final_co.xy) * s0.x * s0.y;
2021         color += texture(ima, final_co.zy) * s1.x * s0.y;
2022         color += texture(ima, final_co.xw) * s0.x * s1.y;
2023         color += texture(ima, final_co.zw) * s1.x * s1.y;
2024
2025 #else /* Reference bruteforce 16 tap. */
2026         color  = texelFetch(ima, ivec2(tc + vec2(-1.0, -1.0)), 0) * w0.x * w0.y;
2027         color += texelFetch(ima, ivec2(tc + vec2( 0.0, -1.0)), 0) * w1.x * w0.y;
2028         color += texelFetch(ima, ivec2(tc + vec2( 1.0, -1.0)), 0) * w2.x * w0.y;
2029         color += texelFetch(ima, ivec2(tc + vec2( 2.0, -1.0)), 0) * w3.x * w0.y;
2030
2031         color += texelFetch(ima, ivec2(tc + vec2(-1.0, 0.0)), 0) * w0.x * w1.y;
2032         color += texelFetch(ima, ivec2(tc + vec2( 0.0, 0.0)), 0) * w1.x * w1.y;
2033         color += texelFetch(ima, ivec2(tc + vec2( 1.0, 0.0)), 0) * w2.x * w1.y;
2034         color += texelFetch(ima, ivec2(tc + vec2( 2.0, 0.0)), 0) * w3.x * w1.y;
2035
2036         color += texelFetch(ima, ivec2(tc + vec2(-1.0, 1.0)), 0) * w0.x * w2.y;
2037         color += texelFetch(ima, ivec2(tc + vec2( 0.0, 1.0)), 0) * w1.x * w2.y;
2038         color += texelFetch(ima, ivec2(tc + vec2( 1.0, 1.0)), 0) * w2.x * w2.y;
2039         color += texelFetch(ima, ivec2(tc + vec2( 2.0, 1.0)), 0) * w3.x * w2.y;
2040
2041         color += texelFetch(ima, ivec2(tc + vec2(-1.0, 2.0)), 0) * w0.x * w3.y;
2042         color += texelFetch(ima, ivec2(tc + vec2( 0.0, 2.0)), 0) * w1.x * w3.y;
2043         color += texelFetch(ima, ivec2(tc + vec2( 1.0, 2.0)), 0) * w2.x * w3.y;
2044         color += texelFetch(ima, ivec2(tc + vec2( 2.0, 2.0)), 0) * w3.x * w3.y;
2045 #endif
2046
2047         alpha = color.a;
2048 }
2049
2050 void node_tex_image_smart(vec3 co, sampler2D ima, out vec4 color, out float alpha)
2051 {
2052         /* use cubic for now */
2053         node_tex_image_cubic(co, ima, color, alpha);
2054 }
2055
2056 void tex_box_sample_linear(vec3 texco,
2057                     vec3 N,
2058                     sampler2D ima,
2059                     out vec4 color1,
2060                     out vec4 color2,
2061                     out vec4 color3)
2062 {
2063         /* X projection */
2064         vec2 uv = texco.yz;
2065         if (N.x < 0.0) {
2066                 uv.x = 1.0 - uv.x;
2067         }
2068         color1 = texture(ima, uv);
2069         /* Y projection */
2070         uv = texco.xz;
2071         if (N.y > 0.0) {
2072                 uv.x = 1.0 - uv.x;
2073         }
2074         color2 = texture(ima, uv);
2075         /* Z projection */
2076         uv = texco.yx;
2077         if (N.z > 0.0) {
2078                 uv.x = 1.0 - uv.x;
2079         }
2080         color3 = texture(ima, uv);
2081 }
2082
2083 void tex_box_sample_nearest(vec3 texco,
2084                     vec3 N,
2085                     sampler2D ima,
2086                     out vec4 color1,
2087                     out vec4 color2,
2088                     out vec4 color3)
2089 {
2090         /* X projection */
2091         vec2 uv = texco.yz;
2092         if (N.x < 0.0) {
2093                 uv.x = 1.0 - uv.x;
2094         }
2095         ivec2 pix = ivec2(uv.xy * textureSize(ima, 0).xy);
2096         color1 = texelFetch(ima, pix, 0);
2097         /* Y projection */
2098         uv = texco.xz;
2099         if (N.y > 0.0) {
2100                 uv.x = 1.0 - uv.x;
2101         }
2102         pix = ivec2(uv.xy * textureSize(ima, 0).xy);
2103         color2 = texelFetch(ima, pix, 0);
2104         /* Z projection */
2105         uv = texco.yx;
2106         if (N.z > 0.0) {
2107                 uv.x = 1.0 - uv.x;
2108         }
2109         pix = ivec2(uv.xy * textureSize(ima, 0).xy);
2110         color3 = texelFetch(ima, pix, 0);
2111 }
2112
2113 void tex_box_sample_cubic(vec3 texco,
2114                     vec3 N,
2115                     sampler2D ima,
2116                     out vec4 color1,
2117                     out vec4 color2,
2118                     out vec4 color3)
2119 {
2120         float alpha;
2121         /* X projection */
2122         vec2 uv = texco.yz;
2123         if (N.x < 0.0) {
2124                 uv.x = 1.0 - uv.x;
2125         }
2126         node_tex_image_cubic(uv.xyy, ima, color1, alpha);
2127         /* Y projection */
2128         uv = texco.xz;
2129         if (N.y > 0.0) {
2130                 uv.x = 1.0 - uv.x;
2131         }
2132         node_tex_image_cubic(uv.xyy, ima, color2, alpha);
2133         /* Z projection */
2134         uv = texco.yx;
2135         if (N.z > 0.0) {
2136                 uv.x = 1.0 - uv.x;
2137         }
2138         node_tex_image_cubic(uv.xyy, ima, color3, alpha);
2139 }
2140
2141 void tex_box_sample_smart(vec3 texco,
2142                     vec3 N,
2143                     sampler2D ima,
2144                     out vec4 color1,
2145                     out vec4 color2,
2146                     out vec4 color3)
2147 {
2148         tex_box_sample_cubic(texco, N, ima, color1, color2, color3);
2149 }
2150
2151 void node_tex_image_box(vec3 texco,
2152                         vec3 N,
2153                         vec4 color1,
2154                         vec4 color2,
2155                         vec4 color3,
2156                         sampler2D ima,
2157                         float blend,
2158                         out vec4 color,
2159                         out float alpha)
2160 {
2161         /* project from direction vector to barycentric coordinates in triangles */
2162         N = abs(N);
2163         N /= dot(N, vec3(1.0));
2164
2165         /* basic idea is to think of this as a triangle, each corner representing
2166          * one of the 3 faces of the cube. in the corners we have single textures,
2167          * in between we blend between two textures, and in the middle we a blend
2168          * between three textures.
2169          *
2170          * the Nxyz values are the barycentric coordinates in an equilateral
2171          * triangle, which in case of blending, in the middle has a smaller
2172          * equilateral triangle where 3 textures blend. this divides things into
2173          * 7 zones, with an if () test for each zone
2174          * EDIT: Now there is only 4 if's. */
2175
2176         float limit = 0.5 + 0.5 * blend;
2177
2178         vec3 weight;
2179         weight.x = N.x / (N.x + N.y);
2180         weight.y = N.y / (N.y + N.z);
2181         weight.z = N.z / (N.x + N.z);
2182         weight = clamp((weight - 0.5 * (1.0 - blend)) / max(1e-8, blend), 0.0, 1.0);
2183
2184         /* test for mixes between two textures */
2185         if (N.z < (1.0 - limit) * (N.y + N.x)) {
2186                 weight.z = 0.0;
2187                 weight.y = 1.0 - weight.x;
2188         }
2189         else if (N.x < (1.0 - limit) * (N.y + N.z)) {
2190                 weight.x = 0.0;
2191                 weight.z = 1.0 - weight.y;
2192         }
2193         else if (N.y < (1.0 - limit) * (N.x + N.z)) {
2194                 weight.y = 0.0;
2195                 weight.x = 1.0 - weight.z;
2196         }
2197         else {
2198                 /* last case, we have a mix between three */
2199                 weight = ((2.0 - limit) * N + (limit - 1.0)) / max(1e-8, 2.0 * limit - 1.0);
2200         }
2201
2202         color = weight.x * color1 + weight.y * color2 + weight.z * color3;
2203         alpha = color.a;
2204 }
2205
2206 void node_tex_image_empty(vec3 co, out vec4 color, out float alpha)
2207 {
2208         color = vec4(0.0);
2209         alpha = 0.0;
2210 }
2211
2212 void node_tex_magic(vec3 co, float scale, float distortion, float depth, out vec4 color, out float fac)
2213 {
2214         vec3 p = co * scale;
2215         float x = sin((p.x + p.y + p.z) * 5.0);
2216         float y = cos((-p.x + p.y - p.z) * 5.0);
2217         float z = -cos((-p.x - p.y + p.z) * 5.0);
2218
2219         if (depth > 0) {
2220                 x *= distortion;
2221                 y *= distortion;
2222                 z *= distortion;
2223                 y = -cos(x - y + z);
2224                 y *= distortion;
2225                 if (depth > 1) {
2226                         x = cos(x - y - z);
2227                         x *= distortion;
2228                         if (depth > 2) {
2229                                 z = sin(-x - y - z);
2230                                 z *= distortion;
2231                                 if (depth > 3) {
2232                                         x = -cos(-x + y - z);
2233                                         x *= distortion;
2234                                         if (depth > 4) {
2235                                                 y = -sin(-x + y + z);
2236                                                 y *= distortion;
2237                                                 if (depth > 5) {
2238                                                         y = -cos(-x + y + z);
2239                                                         y *= distortion;
2240                                                         if (depth > 6) {
2241                                                                 x = cos(x + y + z);
2242                                                                 x *= distortion;
2243                                                                 if (depth > 7) {
2244                                                                         z = sin(x + y - z);
2245                                                                         z *= distortion;
2246                                                                         if (depth > 8) {
2247                                                                                 x = -cos(-x - y + z);
2248                                                                                 x *= distortion;
2249                                                                                 if (depth > 9) {
2250                                                                                         y = -sin(x - y + z);
2251                                                                                         y *= distortion;
2252                                                                                 }
2253                                                                         }
2254                                                                 }
2255                                                         }
2256                                                 }
2257                                         }
2258                                 }
2259                         }
2260                 }
2261         }
2262         if (distortion != 0.0) {
2263                 distortion *= 2.0;
2264                 x /= distortion;
2265                 y /= distortion;
2266                 z /= distortion;
2267         }
2268
2269         color = vec4(0.5 - x, 0.5 - y, 0.5 - z, 1.0);
2270         fac = (color.x + color.y + color.z) / 3.0;
2271 }
2272
2273 float noise_fade(float t)
2274 {
2275         return t * t * t * (t * (t * 6.0 - 15.0) + 10.0);
2276 }
2277
2278 float noise_scale3(float result)
2279 {
2280         return 0.9820 * result;
2281 }
2282
2283 float noise_nerp(float t, float a, float b)
2284 {
2285         return (1.0 - t) * a + t * b;
2286 }
2287
2288 float noise_grad(uint hash, float x, float y, float z)
2289 {
2290         uint h = hash & 15u;
2291         float u = h < 8u ? x : y;
2292         float vt = ((h == 12u) || (h == 14u)) ? x : z;
2293         float v = h < 4u ? y : vt;
2294         return (((h & 1u) != 0u) ? -u : u) + (((h & 2u) != 0u) ? -v : v);
2295 }
2296
2297 float noise_perlin(float x, float y, float z)
2298 {
2299         int X; float fx = floorfrac(x, X);
2300         int Y; float fy = floorfrac(y, Y);
2301         int Z; float fz = floorfrac(z, Z);
2302
2303         float u = noise_fade(fx);
2304         float v = noise_fade(fy);
2305         float w = noise_fade(fz);
2306
2307         float noise_u[2], noise_v[2];
2308
2309         noise_u[0] = noise_nerp(u,
2310                 noise_grad(hash(X, Y, Z), fx, fy, fz),
2311                 noise_grad(hash(X + 1, Y, Z), fx - 1.0, fy, fz));
2312
2313         noise_u[1] = noise_nerp(u,
2314                 noise_grad(hash(X, Y + 1, Z), fx, fy - 1.0, fz),
2315                 noise_grad(hash(X + 1, Y + 1, Z), fx - 1.0, fy - 1.0, fz));
2316
2317         noise_v[0] = noise_nerp(v, noise_u[0], noise_u[1]);
2318
2319         noise_u[0] = noise_nerp(u,
2320                 noise_grad(hash(X, Y, Z + 1), fx, fy, fz - 1.0),
2321                 noise_grad(hash(X + 1, Y, Z + 1), fx - 1.0, fy, fz - 1.0));
2322
2323         noise_u[1] = noise_nerp(u,
2324                 noise_grad(hash(X, Y + 1, Z + 1), fx, fy - 1.0, fz - 1.0),
2325                 noise_grad(hash(X + 1, Y + 1, Z + 1), fx - 1.0, fy - 1.0, fz - 1.0));
2326
2327         noise_v[1] = noise_nerp(v, noise_u[0], noise_u[1]);
2328
2329         return noise_scale3(noise_nerp(w, noise_v[0], noise_v[1]));
2330 }
2331
2332 float noise(vec3 p)
2333 {
2334         return 0.5 * noise_perlin(p.x, p.y, p.z) + 0.5;
2335 }
2336
2337 float snoise(vec3 p)
2338 {
2339         return noise_perlin(p.x, p.y, p.z);
2340 }
2341
2342 float noise_turbulence(vec3 p, float octaves, int hard)
2343 {
2344         float fscale = 1.0;
2345         float amp = 1.0;
2346         float sum = 0.0;
2347         octaves = clamp(octaves, 0.0, 16.0);
2348         int n = int(octaves);
2349         for (int i = 0; i <= n; i++) {
2350                 float t = noise(fscale * p);
2351                 if (hard != 0) {
2352                         t = abs(2.0 * t - 1.0);
2353                 }
2354                 sum += t * amp;
2355                 amp *= 0.5;
2356                 fscale *= 2.0;
2357         }
2358         float rmd = octaves - floor(octaves);
2359         if (rmd != 0.0) {
2360                 float t = noise(fscale * p);
2361                 if (hard != 0) {
2362                         t = abs(2.0 * t - 1.0);
2363                 }
2364                 float sum2 = sum + t * amp;
2365                 sum *= (float(1 << n) / float((1 << (n + 1)) - 1));
2366                 sum2 *= (float(1 << (n + 1)) / float((1 << (n + 2)) - 1));
2367                 return (1.0 - rmd) * sum + rmd * sum2;
2368         }
2369         else {
2370                 sum *= (float(1 << n) / float((1 << (n + 1)) - 1));
2371                 return sum;
2372         }
2373 }
2374
2375 void node_tex_noise(vec3 co, float scale, float detail, float distortion, out vec4 color, out float fac)
2376 {
2377         vec3 p = co * scale;
2378         int hard = 0;
2379         if (distortion != 0.0) {
2380                 vec3 r, offset = vec3(13.5, 13.5, 13.5);
2381                 r.x = noise(p + offset) * distortion;
2382                 r.y = noise(p) * distortion;
2383                 r.z = noise(p - offset) * distortion;
2384                 p += r;
2385         }
2386
2387         fac = noise_turbulence(p, detail, hard);
2388         color = vec4(fac,
2389                      noise_turbulence(vec3(p.y, p.x, p.z), detail, hard),
2390                      noise_turbulence(vec3(p.y, p.z, p.x), detail, hard),
2391                      1);
2392 }
2393
2394 /* Musgrave fBm
2395  *
2396  * H: fractal increment parameter
2397  * lacunarity: gap between successive frequencies
2398  * octaves: number of frequencies in the fBm
2399  *
2400  * from "Texturing and Modelling: A procedural approach"
2401  */
2402
2403 float noise_musgrave_fBm(vec3 p, float H, float lacunarity, float octaves)
2404 {
2405         float rmd;
2406         float value = 0.0;
2407         float pwr = 1.0;
2408         float pwHL = pow(lacunarity, -H);
2409
2410         for (int i = 0; i < int(octaves); i++) {
2411                 value += snoise(p) * pwr;
2412                 pwr *= pwHL;
2413                 p *= lacunarity;
2414         }
2415
2416         rmd = octaves - floor(octaves);
2417         if (rmd != 0.0)
2418                 value += rmd * snoise(p) * pwr;
2419
2420         return value;
2421 }
2422
2423 /* Musgrave Multifractal
2424  *
2425  * H: highest fractal dimension
2426  * lacunarity: gap between successive frequencies
2427  * octaves: number of frequencies in the fBm
2428  */
2429
2430 float noise_musgrave_multi_fractal(vec3 p, float H, float lacunarity, float octaves)
2431 {
2432         float rmd;
2433         float value = 1.0;
2434         float pwr = 1.0;
2435         float pwHL = pow(lacunarity, -H);
2436
2437         for (int i = 0; i < int(octaves); i++) {
2438                 value *= (pwr * snoise(p) + 1.0);
2439                 pwr *= pwHL;
2440                 p *= lacunarity;
2441         }
2442
2443         rmd = octaves - floor(octaves);
2444         if (rmd != 0.0)
2445                 value *= (rmd * pwr * snoise(p) + 1.0); /* correct? */
2446
2447         return value;
2448 }
2449
2450 /* Musgrave Heterogeneous Terrain
2451  *
2452  * H: fractal dimension of the roughest area
2453  * lacunarity: gap between successive frequencies
2454  * octaves: number of frequencies in the fBm
2455  * offset: raises the terrain from `sea level'
2456  */
2457
2458 float noise_musgrave_hetero_terrain(vec3 p, float H, float lacunarity, float octaves, float offset)
2459 {
2460         float value, increment, rmd;
2461         float pwHL = pow(lacunarity, -H);
2462         float pwr = pwHL;
2463
2464         /* first unscaled octave of function; later octaves are scaled */
2465         value = offset + snoise(p);
2466         p *= lacunarity;
2467
2468         for (int i = 1; i < int(octaves); i++) {
2469                 increment = (snoise(p) + offset) * pwr * value;
2470                 value += increment;
2471                 pwr *= pwHL;
2472                 p *= lacunarity;
2473         }
2474
2475         rmd = octaves - floor(octaves);
2476         if (rmd != 0.0) {
2477                 increment = (snoise(p) + offset) * pwr * value;
2478                 value += rmd * increment;
2479         }
2480
2481         return value;
2482 }
2483
2484 /* Hybrid Additive/Multiplicative Multifractal Terrain
2485  *
2486  * H: fractal dimension of the roughest area
2487  * lacunarity: gap between successive frequencies
2488  * octaves: number of frequencies in the fBm
2489  * offset: raises the terrain from `sea level'
2490  */
2491
2492 float noise_musgrave_hybrid_multi_fractal(vec3 p, float H, float lacunarity, float octaves, float offset, float gain)
2493 {
2494         float result, signal, weight, rmd;
2495         float pwHL = pow(lacunarity, -H);
2496         float pwr = pwHL;
2497
2498         result = snoise(p) + offset;
2499         weight = gain * result;
2500         p *= lacunarity;
2501
2502         for (int i = 1; (weight > 0.001f) && (i < int(octaves)); i++) {
2503                 if (weight > 1.0)
2504                         weight = 1.0;
2505
2506                 signal = (snoise(p) + offset) * pwr;
2507                 pwr *= pwHL;
2508                 result += weight * signal;
2509                 weight *= gain * signal;
2510                 p *= lacunarity;
2511         }
2512
2513         rmd = octaves - floor(octaves);
2514         if (rmd != 0.0)
2515                 result += rmd * ((snoise(p) + offset) * pwr);
2516
2517         return result;
2518 }
2519
2520 /* Ridged Multifractal Terrain
2521  *
2522  * H: fractal dimension of the roughest area
2523  * lacunarity: gap between successive frequencies
2524  * octaves: number of frequencies in the fBm
2525  * offset: raises the terrain from `sea level'
2526  */
2527
2528 float noise_musgrave_ridged_multi_fractal(vec3 p, float H, float lacunarity, float octaves, float offset, float gain)
2529 {
2530         float result, signal, weight;
2531         float pwHL = pow(lacunarity, -H);
2532         float pwr = pwHL;
2533
2534         signal = offset - abs(snoise(p));
2535         signal *= signal;
2536         result = signal;
2537         weight = 1.0;
2538
2539         for (int i = 1; i < int(octaves); i++) {
2540                 p *= lacunarity;
2541                 weight = clamp(signal * gain, 0.0, 1.0);
2542                 signal = offset - abs(snoise(p));
2543                 signal *= signal;
2544                 signal *= weight;
2545                 result += signal * pwr;
2546                 pwr *= pwHL;
2547         }
2548
2549         return result;
2550 }
2551
2552 float svm_musgrave(int type,
2553                    float dimension,
2554                    float lacunarity,
2555                    float octaves,
2556                    float offset,
2557                    float intensity,
2558                    float gain,
2559                    vec3 p)
2560 {
2561         if (type == 0 /* NODE_MUSGRAVE_MULTIFRACTAL */)
2562                 return intensity * noise_musgrave_multi_fractal(p, dimension, lacunarity, octaves);
2563         else if (type == 1 /* NODE_MUSGRAVE_FBM */)
2564                 return intensity * noise_musgrave_fBm(p, dimension, lacunarity, octaves);
2565         else if (type == 2 /* NODE_MUSGRAVE_HYBRID_MULTIFRACTAL */)
2566                 return intensity * noise_musgrave_hybrid_multi_fractal(p, dimension, lacunarity, octaves, offset, gain);
2567         else if (type == 3 /* NODE_MUSGRAVE_RIDGED_MULTIFRACTAL */)
2568                 return intensity * noise_musgrave_ridged_multi_fractal(p, dimension, lacunarity, octaves, offset, gain);
2569         else if (type == 4 /* NODE_MUSGRAVE_HETERO_TERRAIN */)
2570                 return intensity * noise_musgrave_hetero_terrain(p, dimension, lacunarity, octaves, offset);
2571         return 0.0;
2572 }
2573
2574 void node_tex_musgrave(vec3 co,
2575                        float scale,
2576                        float detail,
2577                        float dimension,
2578                        float lacunarity,
2579                        float offset,
2580                        float gain,
2581                        float type,
2582                        out vec4 color,
2583                        out float fac)
2584 {
2585         fac = svm_musgrave(int(type),
2586                            dimension,
2587                            lacunarity,
2588                            detail,
2589                            offset,
2590                            1.0,
2591                            gain,
2592                            co * scale);
2593
2594         color = vec4(fac, fac, fac, 1.0);
2595 }
2596
2597 void node_tex_sky(vec3 co, out vec4 color)
2598 {
2599         color = vec4(1.0);
2600 }
2601
2602 void node_tex_voronoi(vec3 co, float scale, float exponent, float coloring, float metric, float feature, out vec4 color, out float fac)
2603 {
2604         vec3 p = co * scale;
2605         int xx, yy, zz, xi, yi, zi;
2606         float da[4];
2607         vec3 pa[4];
2608
2609         xi = floor_to_int(p[0]);
2610         yi = floor_to_int(p[1]);
2611         zi = floor_to_int(p[2]);
2612
2613         da[0] = 1e+10;
2614         da[1] = 1e+10;
2615         da[2] = 1e+10;
2616         da[3] = 1e+10;
2617
2618         for (xx = xi - 1; xx <= xi + 1; xx++) {
2619                 for (yy = yi - 1; yy <= yi + 1; yy++) {
2620                         for (zz = zi - 1; zz <= zi + 1; zz++) {
2621                                 vec3 ip = vec3(xx, yy, zz);
2622                                 vec3 vp = cellnoise_color(ip);
2623                                 vec3 pd = p - (vp + ip);
2624
2625                                 float d = 0.0;
2626                                 if (metric == 0) { /* SHD_VORONOI_DISTANCE 0 */
2627                                         d = dot(pd, pd);
2628                                 }
2629                                 else if (metric == 1) { /* SHD_VORONOI_MANHATTAN 1 */
2630                                         d = abs(pd[0]) + abs(pd[1]) + abs(pd[2]);
2631                                 }
2632                                 else if (metric == 2) { /* SHD_VORONOI_CHEBYCHEV 2 */
2633                                         d = max(abs(pd[0]), max(abs(pd[1]), abs(pd[2])));
2634                                 }
2635                                 else if (metric == 3) { /* SHD_VORONOI_MINKOWSKI 3 */
2636                                         d = pow(pow(abs(pd[0]), exponent) + pow(abs(pd[1]), exponent) + pow(abs(pd[2]), exponent), 1.0/exponent);
2637                                 }
2638
2639                                 vp += vec3(xx, yy, zz);
2640                                 if (d < da[0]) {
2641                                         da[3] = da[2];
2642                                         da[2] = da[1];
2643                                         da[1] = da[0];
2644                                         da[0] = d;
2645                                         pa[3] = pa[2];
2646                                         pa[2] = pa[1];
2647                                         pa[1] = pa[0];
2648                                         pa[0] = vp;
2649                                 }
2650                                 else if (d < da[1]) {
2651                                         da[3] = da[2];
2652                                         da[2] = da[1];
2653                                         da[1] = d;
2654
2655                                         pa[3] = pa[2];
2656                                         pa[2] = pa[1];
2657                                         pa[1] = vp;
2658                                 }
2659                                 else if (d < da[2]) {
2660                                         da[3] = da[2];
2661                                         da[2] = d;
2662
2663                                         pa[3] = pa[2];
2664                                         pa[2] = vp;
2665                                 }
2666                                 else if (d < da[3]) {
2667                                         da[3] = d;
2668                                         pa[3] = vp;
2669                                 }
2670                         }
2671                 }
2672         }
2673
2674         if (coloring == 0.0) {
2675                 /* Intensity output */
2676                 if (feature == 0) { /* F1 */
2677                         fac = abs(da[0]);
2678                 }
2679                 else if (feature == 1) { /* F2 */
2680                         fac = abs(da[1]);
2681                 }
2682                 else if (feature == 2) { /* F3 */
2683                         fac = abs(da[2]);
2684                 }
2685                 else if (feature == 3) { /* F4 */
2686                         fac = abs(da[3]);
2687                 }
2688                 else if (feature == 4) { /* F2F1 */
2689                         fac = abs(da[1] - da[0]);
2690                 }
2691                 color = vec4(fac, fac, fac, 1);
2692         }
2693         else {
2694                 /* Color output */
2695                 vec3 col = vec3(fac, fac, fac);
2696                 if (feature == 0) { /* F1 */
2697                         col = pa[0];
2698                 }
2699                 else if (feature == 1) { /* F2 */
2700                         col = pa[1];
2701                 }
2702                 else if (feature == 2) { /* F3 */
2703                         col = pa[2];
2704                 }
2705                 else if (feature == 3) { /* F4 */
2706                         col = pa[3];
2707                 }
2708                 else if (feature == 4) { /* F2F1 */
2709                         col = abs(pa[1] - pa[0]);
2710                 }
2711
2712                 color = vec4(cellnoise_color(col), 1);
2713                 fac = (color.x + color.y + color.z) * (1.0 / 3.0);
2714         }
2715 }
2716
2717 float calc_wave(vec3 p, float distortion, float detail, float detail_scale, int wave_type, int wave_profile)
2718 {
2719         float n;
2720
2721         if (wave_type == 0) /* type bands */
2722                 n = (p.x + p.y + p.z) * 10.0;
2723         else /* type rings */
2724                 n = length(p) * 20.0;
2725
2726         if (distortion != 0.0)
2727                 n += distortion * noise_turbulence(p * detail_scale, detail, 0);
2728
2729         if (wave_profile == 0) { /* profile sin */
2730                 return 0.5 + 0.5 * sin(n);
2731         }
2732         else { /* profile saw */
2733                 n /= 2.0 * M_PI;
2734                 n -= int(n);
2735                 return (n < 0.0) ? n + 1.0 : n;
2736         }
2737 }
2738
2739 void node_tex_wave(
2740         vec3 co, float scale, float distortion, float detail, float detail_scale, float wave_type, float wave_profile,
2741         out vec4 color, out float fac)
2742 {
2743         float f;
2744         f = calc_wave(co * scale, distortion, detail, detail_scale, int(wave_type), int(wave_profile));
2745
2746         color = vec4(f, f, f, 1.0);
2747         fac = f;
2748 }
2749
2750 /* light path */
2751
2752 void node_light_path(
2753         out float is_camera_ray,
2754         out float is_shadow_ray,
2755         out float is_diffuse_ray,
2756         out float is_glossy_ray,
2757         out float is_singular_ray,
2758         out float is_reflection_ray,
2759         out float is_transmission_ray,
2760         out float ray_length,
2761         out float ray_depth,
2762         out float diffuse_depth,
2763         out float glossy_depth,
2764         out float transparent_depth,
2765         out float transmission_depth)
2766 {
2767 #ifndef PROBE_CAPTURE
2768         is_camera_ray = 1.0;
2769         is_glossy_ray = 0.0;
2770         is_diffuse_ray = 0.0;
2771         is_reflection_ray = 0.0;
2772         is_transmission_ray = 0.0;
2773 #else
2774         is_camera_ray = 0.0;
2775         is_glossy_ray = 1.0;
2776         is_diffuse_ray = 1.0;
2777         is_reflection_ray = 1.0;
2778         is_transmission_ray = 1.0;
2779 #endif
2780         is_shadow_ray = 0.0;
2781         is_singular_ray = 0.0;
2782         ray_length = 1.0;
2783         ray_depth = 1.0;
2784         diffuse_depth = 1.0;
2785         glossy_depth = 1.0;
2786         transparent_depth = 1.0;
2787         transmission_depth = 1.0;
2788 }
2789
2790 void node_light_falloff(float strength, float tsmooth, out float quadratic, out float linear, out float constant)
2791 {
2792         quadratic = strength;
2793         linear = strength;
2794         constant = strength;
2795 }
2796
2797 void node_object_info(mat4 obmat, vec3 info, out vec3 location, out float object_index, out float material_index, out float random)
2798 {
2799         location = obmat[3].xyz;
2800         object_index = info.x;
2801         material_index = info.y;
2802         random = info.z;
2803 }
2804
2805 void node_normal_map(vec4 tangent, vec3 normal, vec3 texnormal, out vec3 outnormal)
2806 {
2807         vec3 B = tangent.w * cross(normal, tangent.xyz);
2808
2809         outnormal = texnormal.x * tangent.xyz + texnormal.y * B + texnormal.z * normal;
2810         outnormal = normalize(outnormal);
2811 }
2812
2813 void node_bump(float strength, float dist, float height, vec3 N, vec3 surf_pos, float invert, out vec3 result)
2814 {
2815         if (invert != 0.0) {
2816                 dist *= -1.0;
2817         }
2818         vec3 dPdx = dFdx(surf_pos);
2819         vec3 dPdy = dFdy(surf_pos);
2820
2821         /* Get surface tangents from normal. */
2822         vec3 Rx = cross(dPdy, N);
2823         vec3 Ry = cross(N, dPdx);
2824
2825         /* Compute surface gradient and determinant. */
2826         float det = dot(dPdx, Rx);
2827         float absdet = abs(det);
2828
2829         float dHdx = dFdx(height);
2830         float dHdy = dFdy(height);
2831         vec3 surfgrad = dHdx * Rx + dHdy * Ry;
2832
2833         strength = max(strength, 0.0);
2834
2835         result = normalize(absdet * N - dist * sign(det) * surfgrad);
2836         result = normalize(strength * result + (1.0 - strength) * N);
2837 }
2838
2839 void node_bevel(float radius, vec3 N, out vec3 result)
2840 {
2841         result = N;
2842 }
2843
2844 void node_hair_info(out float is_strand, out float intercept, out float thickness, out vec3 tangent, out float random)
2845 {
2846 #ifdef HAIR_SHADER
2847         is_strand = 1.0;
2848         intercept = hairTime;
2849         thickness = hairThickness;
2850         tangent = normalize(hairTangent);
2851         random = wang_hash_noise(uint(hairStrandID)); /* TODO: could be precomputed per strand instead. */
2852 #else
2853         is_strand = 0.0;
2854         intercept = 0.0;
2855         thickness = 0.0;
2856         tangent = vec3(1.0);
2857         random = 0.0;
2858 #endif
2859 }
2860
2861 void node_displacement_object(float height, float midlevel, float scale, vec3 N, mat4 obmat, out vec3 result)
2862 {
2863         N = (vec4(N, 0.0) * obmat).xyz;
2864         result = (height - midlevel) * scale * normalize(N);
2865         result = (obmat * vec4(result, 0.0)).xyz;
2866 }
2867
2868 void node_displacement_world(float height, float midlevel, float scale, vec3 N, out vec3 result)
2869 {
2870         result = (height - midlevel) * scale * normalize(N);
2871 }
2872
2873 void node_vector_displacement_tangent(vec4 vector, float midlevel, float scale, vec4 tangent, vec3 normal, mat4 obmat, mat4 viewmat, out vec3 result)
2874 {
2875         vec3 N_object = normalize(((vec4(normal, 0.0) * viewmat) * obmat).xyz);
2876         vec3 T_object = normalize(((vec4(tangent.xyz, 0.0) * viewmat) * obmat).xyz);
2877         vec3 B_object = tangent.w * normalize(cross(N_object, T_object));
2878
2879         vec3 offset = (vector.xyz - vec3(midlevel)) * scale;
2880         result = offset.x * T_object + offset.y * N_object + offset.z * B_object;
2881         result = (obmat * vec4(result, 0.0)).xyz;
2882 }
2883
2884 void node_vector_displacement_object(vec4 vector, float midlevel, float scale, mat4 obmat, out vec3 result)
2885 {
2886         result = (vector.xyz - vec3(midlevel)) * scale;
2887         result = (obmat * vec4(result, 0.0)).xyz;
2888 }
2889
2890 void node_vector_displacement_world(vec4 vector, float midlevel, float scale, out vec3 result)
2891 {
2892         result = (vector.xyz - vec3(midlevel)) * scale;
2893 }
2894
2895 /* output */
2896
2897 void node_output_material(Closure surface, Closure volume, vec3 displacement, out Closure result)
2898 {
2899 #ifdef VOLUMETRICS
2900         result = volume;
2901 #else
2902         result = surface;
2903 #endif
2904 }
2905
2906 uniform float backgroundAlpha;
2907
2908 void node_output_world(Closure surface, Closure volume, out Closure result)
2909 {
2910 #ifndef VOLUMETRICS
2911         result.radiance = surface.radiance;
2912         result.opacity = backgroundAlpha;
2913 #else
2914         result = volume;
2915 #endif /* VOLUMETRICS */
2916 }
2917
2918 #ifndef VOLUMETRICS
2919 /* TODO : clean this ifdef mess */
2920 /* EEVEE output */
2921 void world_normals_get(out vec3 N)
2922 {
2923 #ifdef HAIR_SHADER
2924         vec3 B = normalize(cross(worldNormal, hairTangent));
2925         float cos_theta;
2926         if (hairThicknessRes == 1) {
2927                 vec4 rand = texelFetch(utilTex, ivec3(ivec2(gl_FragCoord.xy) % LUT_SIZE, 2.0), 0);
2928                 /* Random cosine normal distribution on the hair surface. */
2929                 cos_theta = rand.x * 2.0 - 1.0;
2930         }
2931         else {
2932                 /* Shade as a cylinder. */
2933                 cos_theta = hairThickTime / hairThickness;
2934         }
2935         float sin_theta = sqrt(max(0.0, 1.0f - cos_theta*cos_theta));;
2936         N = normalize(worldNormal * sin_theta + B * cos_theta);
2937 #else
2938         N = gl_FrontFacing ? worldNormal : -worldNormal;
2939 #endif
2940 }
2941
2942 void node_eevee_specular(
2943         vec4 diffuse, vec4 specular, float roughness, vec4 emissive, float transp, vec3 normal,
2944         float clearcoat, float clearcoat_roughness, vec3 clearcoat_normal,
2945         float occlusion, float ssr_id, out Closure result)
2946 {
2947         vec3 out_diff, out_spec, ssr_spec;
2948         eevee_closure_default(normal, diffuse.rgb, specular.rgb, int(ssr_id), roughness, occlusion,
2949                               out_diff, out_spec, ssr_spec);
2950
2951         vec3 vN = normalize(mat3(ViewMatrix) * normal);
2952         result = CLOSURE_DEFAULT;
2953         result.radiance = out_diff * diffuse.rgb + out_spec + emissive.rgb;
2954         result.opacity = 1.0 - transp;
2955         result.ssr_data = vec4(ssr_spec, roughness);
2956         result.ssr_normal = normal_encode(vN, viewCameraVec);
2957         result.ssr_id = int(ssr_id);
2958 }
2959
2960 void node_shader_to_rgba(Closure cl, out vec4 outcol, out float outalpha)
2961 {
2962         vec4 spec_accum = vec4(0.0);
2963         if (ssrToggle && cl.ssr_id == outputSsrId) {
2964                 vec3 V = cameraVec;
2965                 vec3 vN = normal_decode(cl.ssr_normal, viewCameraVec);
2966                 vec3 N = transform_direction(ViewMatrixInverse, vN);
2967                 float roughness = cl.ssr_data.a;
2968                 float roughnessSquared = max(1e-3, roughness * roughness);
2969                 fallback_cubemap(N, V, worldPosition, viewPosition, roughness, roughnessSquared, spec_accum);
2970         }
2971
2972         outalpha = cl.opacity;
2973         outcol = vec4((spec_accum.rgb * cl.ssr_data.rgb) + cl.radiance, 1.0);
2974
2975 #   ifdef USE_SSS
2976 #               ifdef USE_SSS_ALBEDO
2977         outcol.rgb += cl.sss_data.rgb * cl.sss_albedo;
2978 #       else
2979         outcol.rgb += cl.sss_data.rgb;
2980 #               endif
2981 #       endif
2982 }
2983
2984 #endif /* VOLUMETRICS */