Fix T51849: change Cycles clearcoat gloss to roughness.
[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         float 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         ClosureType closure;
330 };
331
332 class BsdfNode : public BsdfBaseNode {
333 public:
334         explicit BsdfNode(const NodeType *node_type);
335         SHADER_NODE_BASE_CLASS(BsdfNode)
336
337         bool has_spatial_varying() { return true; }
338         void compile(SVMCompiler& compiler, ShaderInput *param1, ShaderInput *param2, ShaderInput *param3 = NULL, ShaderInput *param4 = NULL);
339         virtual ClosureType get_closure_type() { return closure; }
340
341         float3 color;
342         float3 normal;
343         float surface_mix_weight;
344
345         virtual bool equals(const ShaderNode& /*other*/)
346         {
347                 /* TODO(sergey): With some care BSDF nodes can be de-duplicated. */
348                 return false;
349         }
350 };
351
352 class AnisotropicBsdfNode : public BsdfNode {
353 public:
354         SHADER_NODE_CLASS(AnisotropicBsdfNode)
355
356         float3 tangent;
357         float roughness, anisotropy, rotation;
358         ClosureType distribution;
359
360         ClosureType get_closure_type() { return distribution; }
361         void attributes(Shader *shader, AttributeRequestSet *attributes);
362 };
363
364 class DiffuseBsdfNode : public BsdfNode {
365 public:
366         SHADER_NODE_CLASS(DiffuseBsdfNode)
367
368         float roughness;
369 };
370
371 /* Disney principled BRDF */
372 class PrincipledBsdfNode : public BsdfBaseNode {
373 public:
374         SHADER_NODE_CLASS(PrincipledBsdfNode)
375
376         bool has_spatial_varying() { return true; }
377         bool has_surface_bssrdf() { return true; }
378         bool has_bssrdf_bump();
379         void compile(SVMCompiler& compiler, ShaderInput *metallic, ShaderInput *subsurface, ShaderInput *subsurface_radius,
380                 ShaderInput *specular, ShaderInput *roughness, ShaderInput *specular_tint, ShaderInput *anisotropic,
381                 ShaderInput *sheen, ShaderInput *sheen_tint, ShaderInput *clearcoat, ShaderInput *clearcoat_roughness,
382                 ShaderInput *ior, ShaderInput *transmission, ShaderInput *anisotropic_rotation, ShaderInput *transmission_roughness);
383
384         float3 base_color;
385         float3 subsurface_color, subsurface_radius;
386         float metallic, subsurface, specular, roughness, specular_tint, anisotropic,
387                 sheen, sheen_tint, clearcoat, clearcoat_roughness, ior, transmission,
388                 anisotropic_rotation, transmission_roughness;
389         float3 normal, clearcoat_normal, tangent;
390         float surface_mix_weight;
391         ClosureType distribution, distribution_orig;
392
393         virtual bool equals(const ShaderNode * /*other*/)
394         {
395                 /* TODO(sergey): With some care BSDF nodes can be de-duplicated. */
396                 return false;
397         }
398
399         ClosureType get_closure_type() { return closure; }
400         bool has_integrator_dependency();
401         void attributes(Shader *shader, AttributeRequestSet *attributes);
402 };
403
404 class TranslucentBsdfNode : public BsdfNode {
405 public:
406         SHADER_NODE_CLASS(TranslucentBsdfNode)
407 };
408
409 class TransparentBsdfNode : public BsdfNode {
410 public:
411         SHADER_NODE_CLASS(TransparentBsdfNode)
412
413         bool has_surface_transparent() { return true; }
414 };
415
416 class VelvetBsdfNode : public BsdfNode {
417 public:
418         SHADER_NODE_CLASS(VelvetBsdfNode)
419
420         float sigma;
421 };
422
423 class GlossyBsdfNode : public BsdfNode {
424 public:
425         SHADER_NODE_CLASS(GlossyBsdfNode)
426
427         void simplify_settings(Scene *scene);
428         bool has_integrator_dependency();
429         ClosureType get_closure_type() { return distribution; }
430
431         float roughness, roughness_orig;
432         ClosureType distribution, distribution_orig;
433 };
434
435 class GlassBsdfNode : public BsdfNode {
436 public:
437         SHADER_NODE_CLASS(GlassBsdfNode)
438
439         void simplify_settings(Scene *scene);
440         bool has_integrator_dependency();
441         ClosureType get_closure_type() { return distribution; }
442
443         float roughness, roughness_orig, IOR;
444         ClosureType distribution, distribution_orig;
445 };
446
447 class RefractionBsdfNode : public BsdfNode {
448 public:
449         SHADER_NODE_CLASS(RefractionBsdfNode)
450
451         void simplify_settings(Scene *scene);
452         bool has_integrator_dependency();
453         ClosureType get_closure_type() { return distribution; }
454
455         float roughness, roughness_orig, IOR;
456         ClosureType distribution, distribution_orig;
457 };
458
459 class ToonBsdfNode : public BsdfNode {
460 public:
461         SHADER_NODE_CLASS(ToonBsdfNode)
462
463         float smooth, size;
464         ClosureType component;
465 };
466
467 class SubsurfaceScatteringNode : public BsdfNode {
468 public:
469         SHADER_NODE_CLASS(SubsurfaceScatteringNode)
470         bool has_surface_bssrdf() { return true; }
471         bool has_bssrdf_bump();
472         ClosureType get_closure_type() { return falloff; }
473
474         float scale;
475         float3 radius;
476         float sharpness;
477         float texture_blur;
478         ClosureType falloff;
479 };
480
481 class EmissionNode : public ShaderNode {
482 public:
483         SHADER_NODE_CLASS(EmissionNode)
484         void constant_fold(const ConstantFolder& folder);
485         virtual ClosureType get_closure_type() { return CLOSURE_EMISSION_ID; }
486
487         bool has_surface_emission() { return true; }
488         bool has_volume_support() { return true; }
489
490         float3 color;
491         float strength;
492         float surface_mix_weight;
493 };
494
495 class BackgroundNode : public ShaderNode {
496 public:
497         SHADER_NODE_CLASS(BackgroundNode)
498         void constant_fold(const ConstantFolder& folder);
499         virtual ClosureType get_closure_type() { return CLOSURE_BACKGROUND_ID; }
500
501         float3 color;
502         float strength;
503         float surface_mix_weight;
504 };
505
506 class HoldoutNode : public ShaderNode {
507 public:
508         SHADER_NODE_CLASS(HoldoutNode)
509         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
510         virtual ClosureType get_closure_type() { return CLOSURE_HOLDOUT_ID; }
511
512         float surface_mix_weight;
513         float volume_mix_weight;
514 };
515
516 class AmbientOcclusionNode : public ShaderNode {
517 public:
518         SHADER_NODE_CLASS(AmbientOcclusionNode)
519
520         bool has_spatial_varying() { return true; }
521         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
522         virtual ClosureType get_closure_type() { return CLOSURE_AMBIENT_OCCLUSION_ID; }
523
524         float3 normal_osl;
525         float3 color;
526         float surface_mix_weight;
527 };
528
529 class VolumeNode : public ShaderNode {
530 public:
531         VolumeNode(const NodeType *node_type);
532         SHADER_NODE_BASE_CLASS(VolumeNode)
533
534         void compile(SVMCompiler& compiler, ShaderInput *param1, ShaderInput *param2);
535         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
536         virtual int get_feature() {
537                 return ShaderNode::get_feature() | NODE_FEATURE_VOLUME;
538         }
539         virtual ClosureType get_closure_type() { return closure; }
540         virtual bool has_volume_support() { return true; }
541
542         float3 color;
543         float density;
544         float volume_mix_weight;
545         ClosureType closure;
546
547         virtual bool equals(const ShaderNode& /*other*/)
548         {
549                 /* TODO(sergey): With some care Volume nodes can be de-duplicated. */
550                 return false;
551         }
552 };
553
554 class AbsorptionVolumeNode : public VolumeNode {
555 public:
556         SHADER_NODE_CLASS(AbsorptionVolumeNode)
557 };
558
559 class ScatterVolumeNode : public VolumeNode {
560 public:
561         SHADER_NODE_CLASS(ScatterVolumeNode)
562
563         float anisotropy;
564 };
565
566 class HairBsdfNode : public BsdfNode {
567 public:
568         SHADER_NODE_CLASS(HairBsdfNode)
569         ClosureType get_closure_type() { return component; }
570
571         ClosureType component;
572         float offset;
573         float roughness_u;
574         float roughness_v;
575         float3 tangent;
576 };
577
578 class GeometryNode : public ShaderNode {
579 public:
580         SHADER_NODE_CLASS(GeometryNode)
581         void attributes(Shader *shader, AttributeRequestSet *attributes);
582         bool has_spatial_varying() { return true; }
583
584         float3 normal_osl;
585 };
586
587 class TextureCoordinateNode : public ShaderNode {
588 public:
589         SHADER_NODE_CLASS(TextureCoordinateNode)
590         void attributes(Shader *shader, AttributeRequestSet *attributes);
591         bool has_spatial_varying() { return true; }
592         bool has_object_dependency() { return use_transform; }
593
594         float3 normal_osl;
595         bool from_dupli;
596         bool use_transform;
597         Transform ob_tfm;
598 };
599
600 class UVMapNode : public ShaderNode {
601 public:
602         SHADER_NODE_CLASS(UVMapNode)
603         void attributes(Shader *shader, AttributeRequestSet *attributes);
604         bool has_spatial_varying() { return true; }
605         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
606
607         ustring attribute;
608         bool from_dupli;
609 };
610
611 class LightPathNode : public ShaderNode {
612 public:
613         SHADER_NODE_CLASS(LightPathNode)
614         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
615 };
616
617 class LightFalloffNode : public ShaderNode {
618 public:
619         SHADER_NODE_CLASS(LightFalloffNode)
620         bool has_spatial_varying() { return true; }
621         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
622
623         float strength;
624         float smooth;
625 };
626
627 class ObjectInfoNode : public ShaderNode {
628 public:
629         SHADER_NODE_CLASS(ObjectInfoNode)
630         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
631 };
632
633 class ParticleInfoNode : public ShaderNode {
634 public:
635         SHADER_NODE_CLASS(ParticleInfoNode)
636         void attributes(Shader *shader, AttributeRequestSet *attributes);
637         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
638 };
639
640 class HairInfoNode : public ShaderNode {
641 public:
642         SHADER_NODE_CLASS(HairInfoNode)
643
644         void attributes(Shader *shader, AttributeRequestSet *attributes);
645         bool has_spatial_varying() { return true; }
646         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
647         virtual int get_feature() {
648                 return ShaderNode::get_feature() | NODE_FEATURE_HAIR;
649         }
650 };
651
652 class ValueNode : public ShaderNode {
653 public:
654         SHADER_NODE_CLASS(ValueNode)
655
656         void constant_fold(const ConstantFolder& folder);
657
658         float value;
659 };
660
661 class ColorNode : public ShaderNode {
662 public:
663         SHADER_NODE_CLASS(ColorNode)
664
665         void constant_fold(const ConstantFolder& folder);
666
667         float3 value;
668 };
669
670 class AddClosureNode : public ShaderNode {
671 public:
672         SHADER_NODE_CLASS(AddClosureNode)
673         void constant_fold(const ConstantFolder& folder);
674 };
675
676 class MixClosureNode : public ShaderNode {
677 public:
678         SHADER_NODE_CLASS(MixClosureNode)
679         void constant_fold(const ConstantFolder& folder);
680
681         float fac;
682 };
683
684 class MixClosureWeightNode : public ShaderNode {
685 public:
686         SHADER_NODE_CLASS(MixClosureWeightNode)
687
688         float weight;
689         float fac;
690 };
691
692 class InvertNode : public ShaderNode {
693 public:
694         SHADER_NODE_CLASS(InvertNode)
695         void constant_fold(const ConstantFolder& folder);
696         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
697
698         float fac;
699         float3 color;
700 };
701
702 class MixNode : public ShaderNode {
703 public:
704         SHADER_NODE_CLASS(MixNode)
705         void constant_fold(const ConstantFolder& folder);
706
707         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
708
709         NodeMix type;
710         bool use_clamp;
711         float3 color1;
712         float3 color2;
713         float fac;
714 };
715
716 class CombineRGBNode : public ShaderNode {
717 public:
718         SHADER_NODE_CLASS(CombineRGBNode)
719         void constant_fold(const ConstantFolder& folder);
720         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
721
722         float r, g, b;
723 };
724
725 class CombineHSVNode : public ShaderNode {
726 public:
727         SHADER_NODE_CLASS(CombineHSVNode)
728         void constant_fold(const ConstantFolder& folder);
729         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
730
731         float h, s, v;
732 };
733
734 class CombineXYZNode : public ShaderNode {
735 public:
736         SHADER_NODE_CLASS(CombineXYZNode)
737         void constant_fold(const ConstantFolder& folder);
738         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
739
740         float x, y, z;
741 };
742
743 class GammaNode : public ShaderNode {
744 public:
745         SHADER_NODE_CLASS(GammaNode)
746         void constant_fold(const ConstantFolder& folder);
747         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
748
749         float3 color;
750         float gamma;
751 };
752
753 class BrightContrastNode : public ShaderNode {
754 public:
755         SHADER_NODE_CLASS(BrightContrastNode)
756         void constant_fold(const ConstantFolder& folder);
757         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
758
759         float3 color;
760         float bright;
761         float contrast;
762 };
763
764 class SeparateRGBNode : public ShaderNode {
765 public:
766         SHADER_NODE_CLASS(SeparateRGBNode)
767         void constant_fold(const ConstantFolder& folder);
768         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
769
770         float3 color;
771 };
772
773 class SeparateHSVNode : public ShaderNode {
774 public:
775         SHADER_NODE_CLASS(SeparateHSVNode)
776         void constant_fold(const ConstantFolder& folder);
777         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
778
779         float3 color;
780 };
781
782 class SeparateXYZNode : public ShaderNode {
783 public:
784         SHADER_NODE_CLASS(SeparateXYZNode)
785         void constant_fold(const ConstantFolder& folder);
786         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
787
788         float3 vector;
789 };
790
791 class HSVNode : public ShaderNode {
792 public:
793         SHADER_NODE_CLASS(HSVNode)
794
795         float hue;
796         float saturation;
797         float value;
798         float fac;
799         float3 color;
800 };
801
802 class AttributeNode : public ShaderNode {
803 public:
804         SHADER_NODE_CLASS(AttributeNode)
805         void attributes(Shader *shader, AttributeRequestSet *attributes);
806         bool has_spatial_varying() { return true; }
807
808         ustring attribute;
809 };
810
811 class CameraNode : public ShaderNode {
812 public:
813         SHADER_NODE_CLASS(CameraNode)
814         bool has_spatial_varying() { return true; }
815         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
816 };
817
818 class FresnelNode : public ShaderNode {
819 public:
820         SHADER_NODE_CLASS(FresnelNode)
821         bool has_spatial_varying() { return true; }
822         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
823
824         float3 normal;
825         float IOR;
826 };
827
828 class LayerWeightNode : public ShaderNode {
829 public:
830         SHADER_NODE_CLASS(LayerWeightNode)
831         bool has_spatial_varying() { return true; }
832         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
833
834         float3 normal;
835         float blend;
836 };
837
838 class WireframeNode : public ShaderNode {
839 public:
840         SHADER_NODE_CLASS(WireframeNode)
841         bool has_spatial_varying() { return true; }
842         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
843
844         float size;
845         bool use_pixel_size;
846 };
847
848 class WavelengthNode : public ShaderNode {
849 public:
850         SHADER_NODE_CLASS(WavelengthNode)
851         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
852
853         float wavelength;
854 };
855
856 class BlackbodyNode : public ShaderNode {
857 public:
858         SHADER_NODE_CLASS(BlackbodyNode)
859         void constant_fold(const ConstantFolder& folder);
860         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
861
862         float temperature;
863 };
864
865 class MathNode : public ShaderNode {
866 public:
867         SHADER_NODE_CLASS(MathNode)
868         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
869         void constant_fold(const ConstantFolder& folder);
870
871         float value1;
872         float value2;
873         NodeMath type;
874         bool use_clamp;
875 };
876
877 class NormalNode : public ShaderNode {
878 public:
879         SHADER_NODE_CLASS(NormalNode)
880         virtual int get_group() { return NODE_GROUP_LEVEL_2; }
881
882         float3 direction;
883         float3 normal;
884 };
885
886 class VectorMathNode : public ShaderNode {
887 public:
888         SHADER_NODE_CLASS(VectorMathNode)
889         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
890         void constant_fold(const ConstantFolder& folder);
891
892         float3 vector1;
893         float3 vector2;
894         NodeVectorMath type;
895 };
896
897 class VectorTransformNode : public ShaderNode {
898 public:
899         SHADER_NODE_CLASS(VectorTransformNode)
900
901         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
902
903         NodeVectorTransformType type;
904         NodeVectorTransformConvertSpace convert_from;
905         NodeVectorTransformConvertSpace convert_to;
906         float3 vector;
907 };
908
909 class BumpNode : public ShaderNode {
910 public:
911         SHADER_NODE_CLASS(BumpNode)
912         void constant_fold(const ConstantFolder& folder);
913         bool has_spatial_varying() { return true; }
914         virtual int get_feature() {
915                 return NODE_FEATURE_BUMP;
916         }
917
918         bool invert;
919         bool use_object_space;
920         float height;
921         float sample_center;
922         float sample_x;
923         float sample_y;
924         float3 normal;
925         float strength;
926         float distance;
927 };
928
929 class CurvesNode : public ShaderNode {
930 public:
931         explicit CurvesNode(const NodeType *node_type);
932         SHADER_NODE_BASE_CLASS(CurvesNode)
933
934         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
935
936         array<float3> curves;
937         float min_x, max_x, fac;
938         float3 value;
939
940 protected:
941         void constant_fold(const ConstantFolder& folder, ShaderInput *value_in);
942         void compile(SVMCompiler& compiler, int type, ShaderInput *value_in, ShaderOutput *value_out);
943         void compile(OSLCompiler& compiler, const char *name);
944 };
945
946 class RGBCurvesNode : public CurvesNode {
947 public:
948         SHADER_NODE_CLASS(RGBCurvesNode)
949         void constant_fold(const ConstantFolder& folder);
950 };
951
952 class VectorCurvesNode : public CurvesNode {
953 public:
954         SHADER_NODE_CLASS(VectorCurvesNode)
955         void constant_fold(const ConstantFolder& folder);
956 };
957
958 class RGBRampNode : public ShaderNode {
959 public:
960         SHADER_NODE_CLASS(RGBRampNode)
961         void constant_fold(const ConstantFolder& folder);
962         virtual int get_group() { return NODE_GROUP_LEVEL_1; }
963
964         array<float3> ramp;
965         array<float> ramp_alpha;
966         float fac;
967         bool interpolate;
968 };
969
970 class SetNormalNode : public ShaderNode {
971 public:
972         SHADER_NODE_CLASS(SetNormalNode)
973         float3 direction;
974 };
975
976 class OSLNode : public ShaderNode {
977 public:
978         static OSLNode *create(size_t num_inputs, const OSLNode *from = NULL);
979         ~OSLNode();
980
981         ShaderNode *clone() const;
982
983         char* input_default_value();
984         void add_input(ustring name, SocketType::Type type);
985         void add_output(ustring name, SocketType::Type type);
986
987         SHADER_NODE_NO_CLONE_CLASS(OSLNode)
988
989         /* ideally we could beter detect this, but we can't query this now */
990         bool has_spatial_varying() { return true; }
991         virtual bool equals(const ShaderNode& /*other*/) { return false; }
992
993         string filepath;
994         string bytecode_hash;
995 };
996
997 class NormalMapNode : public ShaderNode {
998 public:
999         SHADER_NODE_CLASS(NormalMapNode)
1000         void attributes(Shader *shader, AttributeRequestSet *attributes);
1001         bool has_spatial_varying() { return true; }
1002         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
1003
1004         NodeNormalMapSpace space;
1005         ustring attribute;
1006         float strength;
1007         float3 color;
1008         float3 normal_osl;
1009 };
1010
1011 class TangentNode : public ShaderNode {
1012 public:
1013         SHADER_NODE_CLASS(TangentNode)
1014         void attributes(Shader *shader, AttributeRequestSet *attributes);
1015         bool has_spatial_varying() { return true; }
1016         virtual int get_group() { return NODE_GROUP_LEVEL_3; }
1017
1018         NodeTangentDirectionType direction_type;
1019         NodeTangentAxis axis;
1020         ustring attribute;
1021         float3 normal_osl;
1022 };
1023
1024 CCL_NAMESPACE_END
1025
1026 #endif /* __NODES_H__ */
1027