Cycles: add random walk subsurface scattering to Principled BSDF.
[blender.git] / intern / cycles / render / nodes.h
1 /*
2  * Copyright 2011-2013 Blender Foundation
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 #ifndef __NODES_H__
18 #define __NODES_H__
19
20 #include "render/graph.h"
21 #include "graph/node.h"
22
23 #include "util/util_string.h"
24
25 CCL_NAMESPACE_BEGIN
26
27 class ImageManager;
28 class Scene;
29 class Shader;
30
31 /* Texture Mapping */
32
33 class TextureMapping {
34 public:
35         TextureMapping();
36         Transform compute_transform();
37         bool skip();
38         void compile(SVMCompiler& compiler, int offset_in, int offset_out);
39         int compile(SVMCompiler& compiler, ShaderInput *vector_in);
40         void compile(OSLCompiler &compiler);
41
42         int compile_begin(SVMCompiler& compiler, ShaderInput *vector_in);
43         void compile_end(SVMCompiler& compiler, ShaderInput *vector_in, int vector_offset);
44
45         float3 translation;
46         float3 rotation;
47         float3 scale;
48
49         float3 min, max;
50         bool use_minmax;
51
52         enum Type { POINT = 0, TEXTURE = 1, VECTOR = 2, NORMAL = 3 };
53         Type type;
54
55         enum Mapping { NONE = 0, X = 1, Y = 2, Z = 3 };
56         Mapping x_mapping, y_mapping, z_mapping;
57
58         enum Projection { FLAT, CUBE, TUBE, SPHERE };
59         Projection projection;
60 };
61
62 /* Nodes */
63
64 class TextureNode : public ShaderNode {
65 public:
66         explicit TextureNode(const NodeType *node_type) : ShaderNode(node_type) {}
67         TextureMapping tex_mapping;
68 };
69
70 /* Any node which uses image manager's slot should be a subclass of this one. */
71 class ImageSlotTextureNode : public TextureNode {
72 public:
73         explicit ImageSlotTextureNode(const NodeType *node_type) : TextureNode(node_type) {
74                 special_type = SHADER_SPECIAL_TYPE_IMAGE_SLOT;
75         }
76         int slot;
77 };
78
79 class ImageTextureNode : public ImageSlotTextureNode {
80 public:
81         SHADER_NODE_NO_CLONE_CLASS(ImageTextureNode)
82         ~ImageTextureNode();
83         ShaderNode *clone() const;
84         void attributes(Shader *shader, AttributeRequestSet *attributes);
85
86         ImageManager *image_manager;
87         int is_float;
88         bool is_linear;
89         bool use_alpha;
90         ustring filename;
91         void *builtin_data;
92         NodeImageColorSpace color_space;
93         NodeImageProjection projection;
94         InterpolationType interpolation;
95         ExtensionType extension;
96         float projection_blend;
97         bool animated;
98         float3 vector;
99
100         virtual bool equals(const ShaderNode& other)
101         {
102                 const ImageTextureNode& image_node = (const ImageTextureNode&)other;
103                 return ImageSlotTextureNode::equals(other) &&
104                        builtin_data == image_node.builtin_data &&
105                        animated == image_node.animated;
106         }
107 };
108
109 class EnvironmentTextureNode : public ImageSlotTextureNode {
110 public:
111         SHADER_NODE_NO_CLONE_CLASS(EnvironmentTextureNode)
112         ~EnvironmentTextureNode();
113         ShaderNode *clone() const;
114         void attributes(Shader *shader, AttributeRequestSet *attributes);
115         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
116
117         ImageManager *image_manager;
118         int is_float;
119         bool is_linear;
120         bool use_alpha;
121         ustring filename;
122         void *builtin_data;
123         NodeImageColorSpace color_space;
124         NodeEnvironmentProjection projection;
125         InterpolationType interpolation;
126         bool animated;
127         float3 vector;
128
129         virtual bool equals(const ShaderNode& other)
130         {
131                 const EnvironmentTextureNode& env_node = (const EnvironmentTextureNode&)other;
132                 return ImageSlotTextureNode::equals(other) &&
133                        builtin_data == env_node.builtin_data &&
134                        animated == env_node.animated;
135         }
136 };
137
138 class SkyTextureNode : public TextureNode {
139 public:
140         SHADER_NODE_CLASS(SkyTextureNode)
141
142         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
143
144         NodeSkyType type;
145         float3 sun_direction;
146         float turbidity;
147         float ground_albedo;
148         float3 vector;
149 };
150
151 class OutputNode : public ShaderNode {
152 public:
153         SHADER_NODE_CLASS(OutputNode)
154
155         void *surface;
156         void *volume;
157         float3 displacement;
158         float3 normal;
159
160         /* Don't allow output node de-duplication. */
161         virtual bool equals(const ShaderNode& /*other*/) { return false; }
162 };
163
164 class GradientTextureNode : public TextureNode {
165 public:
166         SHADER_NODE_CLASS(GradientTextureNode)
167
168         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
169
170         NodeGradientType type;
171         float3 vector;
172 };
173
174 class NoiseTextureNode : public TextureNode {
175 public:
176         SHADER_NODE_CLASS(NoiseTextureNode)
177
178         float scale, detail, distortion;
179         float3 vector;
180 };
181
182 class VoronoiTextureNode : public TextureNode {
183 public:
184         SHADER_NODE_CLASS(VoronoiTextureNode)
185
186         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
187
188         NodeVoronoiColoring coloring;
189         float scale;
190         float3 vector;
191 };
192
193 class MusgraveTextureNode : public TextureNode {
194 public:
195         SHADER_NODE_CLASS(MusgraveTextureNode)
196
197         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
198
199         NodeMusgraveType type;
200         float scale, detail, dimension, lacunarity, offset, gain;
201         float3 vector;
202 };
203
204 class WaveTextureNode : public TextureNode {
205 public:
206         SHADER_NODE_CLASS(WaveTextureNode)
207
208         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
209
210         NodeWaveType type;
211         NodeWaveProfile profile;
212
213         float scale, distortion, detail, detail_scale;
214         float3 vector;
215 };
216
217 class MagicTextureNode : public TextureNode {
218 public:
219         SHADER_NODE_CLASS(MagicTextureNode)
220
221         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
222
223         int depth;
224         float3 vector;
225         float scale, distortion;
226 };
227
228 class CheckerTextureNode : public TextureNode {
229 public:
230         SHADER_NODE_CLASS(CheckerTextureNode)
231
232         float3 vector, color1, color2;
233         float scale;
234
235         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
236 };
237
238 class BrickTextureNode : public TextureNode {
239 public:
240         SHADER_NODE_CLASS(BrickTextureNode)
241
242         float offset, squash;
243         int offset_frequency, squash_frequency;
244
245         float3 color1, color2, mortar;
246         float scale, mortar_size, mortar_smooth, bias, brick_width, row_height;
247         float3 vector;
248
249         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
250 };
251
252 class PointDensityTextureNode : public ShaderNode {
253 public:
254         SHADER_NODE_NO_CLONE_CLASS(PointDensityTextureNode)
255         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
256
257         ~PointDensityTextureNode();
258         ShaderNode *clone() const;
259         void attributes(Shader *shader, AttributeRequestSet *attributes);
260
261         bool has_spatial_varying() { return true; }
262         bool has_object_dependency() { return true; }
263
264         ustring filename;
265         NodeTexVoxelSpace space;
266         InterpolationType interpolation;
267         Transform tfm;
268         float3 vector;
269
270         ImageManager *image_manager;
271         int slot;
272         void *builtin_data;
273
274         virtual bool equals(const ShaderNode& other) {
275                 const PointDensityTextureNode& point_dendity_node = (const PointDensityTextureNode&)other;
276                 return ShaderNode::equals(other) &&
277                        builtin_data == point_dendity_node.builtin_data;
278         }
279 };
280
281 class MappingNode : public ShaderNode {
282 public:
283         SHADER_NODE_CLASS(MappingNode)
284         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
285
286         float3 vector;
287         TextureMapping tex_mapping;
288 };
289
290 class RGBToBWNode : public ShaderNode {
291 public:
292         SHADER_NODE_CLASS(RGBToBWNode)
293         void constant_fold(const ConstantFolder& folder);
294
295         float3 color;
296 };
297
298 class ConvertNode : public ShaderNode {
299 public:
300         ConvertNode(SocketType::Type from, SocketType::Type to, bool autoconvert = false);
301         SHADER_NODE_BASE_CLASS(ConvertNode)
302
303         void constant_fold(const ConstantFolder& folder);
304
305         SocketType::Type from, to;
306
307         union {
308                 float value_float;
309                 int value_int;
310                 float3 value_color;
311                 float3 value_vector;
312                 float3 value_point;
313                 float3 value_normal;
314         };
315         ustring value_string;
316
317 private:
318         static const int MAX_TYPE = 12;
319         static bool register_types();
320         static Node* create(const NodeType *type);
321         static const NodeType *node_types[MAX_TYPE][MAX_TYPE];
322         static bool initialized;
323 };
324
325 class BsdfBaseNode : public ShaderNode {
326 public:
327         BsdfBaseNode(const NodeType *node_type);
328
329         bool has_spatial_varying() { return true; }
330         virtual ClosureType get_closure_type() { return closure; }
331         virtual bool has_bump();
332
333         virtual bool equals(const ShaderNode& /*other*/)
334         {
335                 /* TODO(sergey): With some care BSDF nodes can be de-duplicated. */
336                 return false;
337         }
338
339         ClosureType closure;
340 };
341
342 class BsdfNode : public BsdfBaseNode {
343 public:
344         explicit BsdfNode(const NodeType *node_type);
345         SHADER_NODE_BASE_CLASS(BsdfNode)
346
347         void compile(SVMCompiler& compiler, ShaderInput *param1, ShaderInput *param2, ShaderInput *param3 = NULL, ShaderInput *param4 = NULL);
348
349         float3 color;
350         float3 normal;
351         float surface_mix_weight;
352 };
353
354 class AnisotropicBsdfNode : public BsdfNode {
355 public:
356         SHADER_NODE_CLASS(AnisotropicBsdfNode)
357
358         float3 tangent;
359         float roughness, anisotropy, rotation;
360         ClosureType distribution;
361
362         ClosureType get_closure_type() { return distribution; }
363         void attributes(Shader *shader, AttributeRequestSet *attributes);
364 };
365
366 class DiffuseBsdfNode : public BsdfNode {
367 public:
368         SHADER_NODE_CLASS(DiffuseBsdfNode)
369
370         float roughness;
371 };
372
373 /* Disney principled BRDF */
374 class PrincipledBsdfNode : public BsdfBaseNode {
375 public:
376         SHADER_NODE_CLASS(PrincipledBsdfNode)
377
378         bool has_surface_bssrdf();
379         bool has_bssrdf_bump();
380         void compile(SVMCompiler& compiler, ShaderInput *metallic, ShaderInput *subsurface, ShaderInput *subsurface_radius,
381                 ShaderInput *specular, ShaderInput *roughness, ShaderInput *specular_tint, ShaderInput *anisotropic,
382                 ShaderInput *sheen, ShaderInput *sheen_tint, ShaderInput *clearcoat, ShaderInput *clearcoat_roughness,
383                 ShaderInput *ior, ShaderInput *transmission, ShaderInput *anisotropic_rotation, ShaderInput *transmission_roughness);
384
385         float3 base_color;
386         float3 subsurface_color, subsurface_radius;
387         float metallic, subsurface, specular, roughness, specular_tint, anisotropic,
388                 sheen, sheen_tint, clearcoat, clearcoat_roughness, ior, transmission,
389                 anisotropic_rotation, transmission_roughness;
390         float3 normal, clearcoat_normal, tangent;
391         float surface_mix_weight;
392         ClosureType distribution, distribution_orig;
393         ClosureType subsurface_method;
394
395         bool has_integrator_dependency();
396         void attributes(Shader *shader, AttributeRequestSet *attributes);
397 };
398
399 class TranslucentBsdfNode : public BsdfNode {
400 public:
401         SHADER_NODE_CLASS(TranslucentBsdfNode)
402 };
403
404 class TransparentBsdfNode : public BsdfNode {
405 public:
406         SHADER_NODE_CLASS(TransparentBsdfNode)
407
408         bool has_surface_transparent() { return true; }
409 };
410
411 class VelvetBsdfNode : public BsdfNode {
412 public:
413         SHADER_NODE_CLASS(VelvetBsdfNode)
414
415         float sigma;
416 };
417
418 class GlossyBsdfNode : public BsdfNode {
419 public:
420         SHADER_NODE_CLASS(GlossyBsdfNode)
421
422         void simplify_settings(Scene *scene);
423         bool has_integrator_dependency();
424         ClosureType get_closure_type() { return distribution; }
425
426         float roughness, roughness_orig;
427         ClosureType distribution, distribution_orig;
428 };
429
430 class GlassBsdfNode : public BsdfNode {
431 public:
432         SHADER_NODE_CLASS(GlassBsdfNode)
433
434         void simplify_settings(Scene *scene);
435         bool has_integrator_dependency();
436         ClosureType get_closure_type() { return distribution; }
437
438         float roughness, roughness_orig, IOR;
439         ClosureType distribution, distribution_orig;
440 };
441
442 class RefractionBsdfNode : public BsdfNode {
443 public:
444         SHADER_NODE_CLASS(RefractionBsdfNode)
445
446         void simplify_settings(Scene *scene);
447         bool has_integrator_dependency();
448         ClosureType get_closure_type() { return distribution; }
449
450         float roughness, roughness_orig, IOR;
451         ClosureType distribution, distribution_orig;
452 };
453
454 class ToonBsdfNode : public BsdfNode {
455 public:
456         SHADER_NODE_CLASS(ToonBsdfNode)
457
458         float smooth, size;
459         ClosureType component;
460 };
461
462 class SubsurfaceScatteringNode : public BsdfNode {
463 public:
464         SHADER_NODE_CLASS(SubsurfaceScatteringNode)
465         bool has_surface_bssrdf() { return true; }
466         bool has_bssrdf_bump();
467         ClosureType get_closure_type() { return falloff; }
468
469         float scale;
470         float3 radius;
471         float sharpness;
472         float texture_blur;
473         ClosureType falloff;
474 };
475
476 class EmissionNode : public ShaderNode {
477 public:
478         SHADER_NODE_CLASS(EmissionNode)
479         void constant_fold(const ConstantFolder& folder);
480
481         bool has_surface_emission() { return true; }
482         bool has_volume_support() { return true; }
483
484         float3 color;
485         float strength;
486         float surface_mix_weight;
487 };
488
489 class BackgroundNode : public ShaderNode {
490 public:
491         SHADER_NODE_CLASS(BackgroundNode)
492         void constant_fold(const ConstantFolder& folder);
493
494         float3 color;
495         float strength;
496         float surface_mix_weight;
497 };
498
499 class HoldoutNode : public ShaderNode {
500 public:
501         SHADER_NODE_CLASS(HoldoutNode)
502         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
503         virtual ClosureType get_closure_type() { return CLOSURE_HOLDOUT_ID; }
504
505         float surface_mix_weight;
506         float volume_mix_weight;
507 };
508
509 class AmbientOcclusionNode : public ShaderNode {
510 public:
511         SHADER_NODE_CLASS(AmbientOcclusionNode)
512
513         bool has_spatial_varying() { return true; }
514         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
515         virtual ClosureType get_closure_type() { return CLOSURE_AMBIENT_OCCLUSION_ID; }
516
517         float3 normal_osl;
518         float3 color;
519         float surface_mix_weight;
520 };
521
522 class VolumeNode : public ShaderNode {
523 public:
524         VolumeNode(const NodeType *node_type);
525         SHADER_NODE_BASE_CLASS(VolumeNode)
526
527         void compile(SVMCompiler& compiler, ShaderInput *param1, ShaderInput *param2);
528         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
529         virtual int get_feature() {
530                 return ShaderNode::get_feature() | NODE_FEATURE_VOLUME;
531         }
532         virtual ClosureType get_closure_type() { return closure; }
533         virtual bool has_volume_support() { return true; }
534
535         float3 color;
536         float density;
537         float volume_mix_weight;
538         ClosureType closure;
539
540         virtual bool equals(const ShaderNode& /*other*/)
541         {
542                 /* TODO(sergey): With some care Volume nodes can be de-duplicated. */
543                 return false;
544         }
545 };
546
547 class AbsorptionVolumeNode : public VolumeNode {
548 public:
549         SHADER_NODE_CLASS(AbsorptionVolumeNode)
550 };
551
552 class ScatterVolumeNode : public VolumeNode {
553 public:
554         SHADER_NODE_CLASS(ScatterVolumeNode)
555
556         float anisotropy;
557 };
558
559 class HairBsdfNode : public BsdfNode {
560 public:
561         SHADER_NODE_CLASS(HairBsdfNode)
562         ClosureType get_closure_type() { return component; }
563
564         ClosureType component;
565         float offset;
566         float roughness_u;
567         float roughness_v;
568         float3 tangent;
569 };
570
571 class GeometryNode : public ShaderNode {
572 public:
573         SHADER_NODE_CLASS(GeometryNode)
574         void attributes(Shader *shader, AttributeRequestSet *attributes);
575         bool has_spatial_varying() { return true; }
576
577         float3 normal_osl;
578 };
579
580 class TextureCoordinateNode : public ShaderNode {
581 public:
582         SHADER_NODE_CLASS(TextureCoordinateNode)
583         void attributes(Shader *shader, AttributeRequestSet *attributes);
584         bool has_spatial_varying() { return true; }
585         bool has_object_dependency() { return use_transform; }
586
587         float3 normal_osl;
588         bool from_dupli;
589         bool use_transform;
590         Transform ob_tfm;
591 };
592
593 class UVMapNode : public ShaderNode {
594 public:
595         SHADER_NODE_CLASS(UVMapNode)
596         void attributes(Shader *shader, AttributeRequestSet *attributes);
597         bool has_spatial_varying() { return true; }
598         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
599
600         ustring attribute;
601         bool from_dupli;
602 };
603
604 class LightPathNode : public ShaderNode {
605 public:
606         SHADER_NODE_CLASS(LightPathNode)
607         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
608 };
609
610 class LightFalloffNode : public ShaderNode {
611 public:
612         SHADER_NODE_CLASS(LightFalloffNode)
613         bool has_spatial_varying() { return true; }
614         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
615
616         float strength;
617         float smooth;
618 };
619
620 class ObjectInfoNode : public ShaderNode {
621 public:
622         SHADER_NODE_CLASS(ObjectInfoNode)
623         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
624 };
625
626 class ParticleInfoNode : public ShaderNode {
627 public:
628         SHADER_NODE_CLASS(ParticleInfoNode)
629         void attributes(Shader *shader, AttributeRequestSet *attributes);
630         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
631 };
632
633 class HairInfoNode : public ShaderNode {
634 public:
635         SHADER_NODE_CLASS(HairInfoNode)
636
637         void attributes(Shader *shader, AttributeRequestSet *attributes);
638         bool has_spatial_varying() { return true; }
639         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
640         virtual int get_feature() {
641                 return ShaderNode::get_feature() | NODE_FEATURE_HAIR;
642         }
643 };
644
645 class ValueNode : public ShaderNode {
646 public:
647         SHADER_NODE_CLASS(ValueNode)
648
649         void constant_fold(const ConstantFolder& folder);
650
651         float value;
652 };
653
654 class ColorNode : public ShaderNode {
655 public:
656         SHADER_NODE_CLASS(ColorNode)
657
658         void constant_fold(const ConstantFolder& folder);
659
660         float3 value;
661 };
662
663 class AddClosureNode : public ShaderNode {
664 public:
665         SHADER_NODE_CLASS(AddClosureNode)
666         void constant_fold(const ConstantFolder& folder);
667 };
668
669 class MixClosureNode : public ShaderNode {
670 public:
671         SHADER_NODE_CLASS(MixClosureNode)
672         void constant_fold(const ConstantFolder& folder);
673
674         float fac;
675 };
676
677 class MixClosureWeightNode : public ShaderNode {
678 public:
679         SHADER_NODE_CLASS(MixClosureWeightNode)
680
681         float weight;
682         float fac;
683 };
684
685 class InvertNode : public ShaderNode {
686 public:
687         SHADER_NODE_CLASS(InvertNode)
688         void constant_fold(const ConstantFolder& folder);
689         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
690
691         float fac;
692         float3 color;
693 };
694
695 class MixNode : public ShaderNode {
696 public:
697         SHADER_NODE_CLASS(MixNode)
698         void constant_fold(const ConstantFolder& folder);
699
700         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
701
702         NodeMix type;
703         bool use_clamp;
704         float3 color1;
705         float3 color2;
706         float fac;
707 };
708
709 class CombineRGBNode : public ShaderNode {
710 public:
711         SHADER_NODE_CLASS(CombineRGBNode)
712         void constant_fold(const ConstantFolder& folder);
713         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
714
715         float r, g, b;
716 };
717
718 class CombineHSVNode : public ShaderNode {
719 public:
720         SHADER_NODE_CLASS(CombineHSVNode)
721         void constant_fold(const ConstantFolder& folder);
722         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
723
724         float h, s, v;
725 };
726
727 class CombineXYZNode : public ShaderNode {
728 public:
729         SHADER_NODE_CLASS(CombineXYZNode)
730         void constant_fold(const ConstantFolder& folder);
731         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
732
733         float x, y, z;
734 };
735
736 class GammaNode : public ShaderNode {
737 public:
738         SHADER_NODE_CLASS(GammaNode)
739         void constant_fold(const ConstantFolder& folder);
740         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
741
742         float3 color;
743         float gamma;
744 };
745
746 class BrightContrastNode : public ShaderNode {
747 public:
748         SHADER_NODE_CLASS(BrightContrastNode)
749         void constant_fold(const ConstantFolder& folder);
750         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
751
752         float3 color;
753         float bright;
754         float contrast;
755 };
756
757 class SeparateRGBNode : public ShaderNode {
758 public:
759         SHADER_NODE_CLASS(SeparateRGBNode)
760         void constant_fold(const ConstantFolder& folder);
761         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
762
763         float3 color;
764 };
765
766 class SeparateHSVNode : public ShaderNode {
767 public:
768         SHADER_NODE_CLASS(SeparateHSVNode)
769         void constant_fold(const ConstantFolder& folder);
770         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
771
772         float3 color;
773 };
774
775 class SeparateXYZNode : public ShaderNode {
776 public:
777         SHADER_NODE_CLASS(SeparateXYZNode)
778         void constant_fold(const ConstantFolder& folder);
779         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
780
781         float3 vector;
782 };
783
784 class HSVNode : public ShaderNode {
785 public:
786         SHADER_NODE_CLASS(HSVNode)
787
788         float hue;
789         float saturation;
790         float value;
791         float fac;
792         float3 color;
793 };
794
795 class AttributeNode : public ShaderNode {
796 public:
797         SHADER_NODE_CLASS(AttributeNode)
798         void attributes(Shader *shader, AttributeRequestSet *attributes);
799         bool has_spatial_varying() { return true; }
800
801         ustring attribute;
802 };
803
804 class CameraNode : public ShaderNode {
805 public:
806         SHADER_NODE_CLASS(CameraNode)
807         bool has_spatial_varying() { return true; }
808         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
809 };
810
811 class FresnelNode : public ShaderNode {
812 public:
813         SHADER_NODE_CLASS(FresnelNode)
814         bool has_spatial_varying() { return true; }
815         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
816
817         float3 normal;
818         float IOR;
819 };
820
821 class LayerWeightNode : public ShaderNode {
822 public:
823         SHADER_NODE_CLASS(LayerWeightNode)
824         bool has_spatial_varying() { return true; }
825         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
826
827         float3 normal;
828         float blend;
829 };
830
831 class WireframeNode : public ShaderNode {
832 public:
833         SHADER_NODE_CLASS(WireframeNode)
834         bool has_spatial_varying() { return true; }
835         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
836
837         float size;
838         bool use_pixel_size;
839 };
840
841 class WavelengthNode : public ShaderNode {
842 public:
843         SHADER_NODE_CLASS(WavelengthNode)
844         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
845
846         float wavelength;
847 };
848
849 class BlackbodyNode : public ShaderNode {
850 public:
851         SHADER_NODE_CLASS(BlackbodyNode)
852         void constant_fold(const ConstantFolder& folder);
853         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
854
855         float temperature;
856 };
857
858 class MathNode : public ShaderNode {
859 public:
860         SHADER_NODE_CLASS(MathNode)
861         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
862         void constant_fold(const ConstantFolder& folder);
863
864         float value1;
865         float value2;
866         NodeMath type;
867         bool use_clamp;
868 };
869
870 class NormalNode : public ShaderNode {
871 public:
872         SHADER_NODE_CLASS(NormalNode)
873         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
874
875         float3 direction;
876         float3 normal;
877 };
878
879 class VectorMathNode : public ShaderNode {
880 public:
881         SHADER_NODE_CLASS(VectorMathNode)
882         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
883         void constant_fold(const ConstantFolder& folder);
884
885         float3 vector1;
886         float3 vector2;
887         NodeVectorMath type;
888 };
889
890 class VectorTransformNode : public ShaderNode {
891 public:
892         SHADER_NODE_CLASS(VectorTransformNode)
893
894         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
895
896         NodeVectorTransformType type;
897         NodeVectorTransformConvertSpace convert_from;
898         NodeVectorTransformConvertSpace convert_to;
899         float3 vector;
900 };
901
902 class BumpNode : public ShaderNode {
903 public:
904         SHADER_NODE_CLASS(BumpNode)
905         void constant_fold(const ConstantFolder& folder);
906         bool has_spatial_varying() { return true; }
907         virtual int get_feature() {
908                 return NODE_FEATURE_BUMP;
909         }
910
911         bool invert;
912         bool use_object_space;
913         float height;
914         float sample_center;
915         float sample_x;
916         float sample_y;
917         float3 normal;
918         float strength;
919         float distance;
920 };
921
922 class CurvesNode : public ShaderNode {
923 public:
924         explicit CurvesNode(const NodeType *node_type);
925         SHADER_NODE_BASE_CLASS(CurvesNode)
926
927         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
928
929         array<float3> curves;
930         float min_x, max_x, fac;
931         float3 value;
932
933 protected:
934         void constant_fold(const ConstantFolder& folder, ShaderInput *value_in);
935         void compile(SVMCompiler& compiler, int type, ShaderInput *value_in, ShaderOutput *value_out);
936         void compile(OSLCompiler& compiler, const char *name);
937 };
938
939 class RGBCurvesNode : public CurvesNode {
940 public:
941         SHADER_NODE_CLASS(RGBCurvesNode)
942         void constant_fold(const ConstantFolder& folder);
943 };
944
945 class VectorCurvesNode : public CurvesNode {
946 public:
947         SHADER_NODE_CLASS(VectorCurvesNode)
948         void constant_fold(const ConstantFolder& folder);
949 };
950
951 class RGBRampNode : public ShaderNode {
952 public:
953         SHADER_NODE_CLASS(RGBRampNode)
954         void constant_fold(const ConstantFolder& folder);
955         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
956
957         array<float3> ramp;
958         array<float> ramp_alpha;
959         float fac;
960         bool interpolate;
961 };
962
963 class SetNormalNode : public ShaderNode {
964 public:
965         SHADER_NODE_CLASS(SetNormalNode)
966         float3 direction;
967 };
968
969 class OSLNode : public ShaderNode {
970 public:
971         static OSLNode *create(size_t num_inputs, const OSLNode *from = NULL);
972         ~OSLNode();
973
974         ShaderNode *clone() const;
975
976         char* input_default_value();
977         void add_input(ustring name, SocketType::Type type);
978         void add_output(ustring name, SocketType::Type type);
979
980         SHADER_NODE_NO_CLONE_CLASS(OSLNode)
981
982         /* ideally we could beter detect this, but we can't query this now */
983         bool has_spatial_varying() { return true; }
984         bool has_volume_support() { return true; }
985
986         virtual bool equals(const ShaderNode& /*other*/) { return false; }
987
988         string filepath;
989         string bytecode_hash;
990 };
991
992 class NormalMapNode : public ShaderNode {
993 public:
994         SHADER_NODE_CLASS(NormalMapNode)
995         void attributes(Shader *shader, AttributeRequestSet *attributes);
996         bool has_spatial_varying() { return true; }
997         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
998
999         NodeNormalMapSpace space;
1000         ustring attribute;
1001         float strength;
1002         float3 color;
1003         float3 normal_osl;
1004 };
1005
1006 class TangentNode : public ShaderNode {
1007 public:
1008         SHADER_NODE_CLASS(TangentNode)
1009         void attributes(Shader *shader, AttributeRequestSet *attributes);
1010         bool has_spatial_varying() { return true; }
1011         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
1012
1013         NodeTangentDirectionType direction_type;
1014         NodeTangentAxis axis;
1015         ustring attribute;
1016         float3 normal_osl;
1017 };
1018
1019 class BevelNode : public ShaderNode {
1020 public:
1021         SHADER_NODE_CLASS(BevelNode)
1022         bool has_spatial_varying() { return true; }
1023         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
1024         virtual bool has_raytrace() { return true; }
1025
1026         float radius;
1027         float3 normal;
1028         int samples;
1029 };
1030
1031 class DisplacementNode : public ShaderNode {
1032 public:
1033         SHADER_NODE_CLASS(DisplacementNode)
1034         virtual int get_feature() {
1035                 return NODE_FEATURE_BUMP;
1036         }
1037
1038         NodeNormalMapSpace space;
1039         float height;
1040         float midlevel;
1041         float scale;
1042         float3 normal;
1043 };
1044
1045 class VectorDisplacementNode : public ShaderNode {
1046 public:
1047         SHADER_NODE_CLASS(VectorDisplacementNode)
1048         void attributes(Shader *shader, AttributeRequestSet *attributes);
1049         virtual int get_feature() {
1050                 return NODE_FEATURE_BUMP;
1051         }
1052
1053         NodeNormalMapSpace space;
1054         ustring attribute;
1055         float3 vector;
1056         float midlevel;
1057         float scale;
1058 };
1059
1060 CCL_NAMESPACE_END
1061
1062 #endif /* __NODES_H__ */
1063