Blender V2.61 - r43446

graph.h

Go to the documentation of this file.
00001 /*
00002  * Copyright 2011, Blender Foundation.
00003  *
00004  * This program is free software; you can redistribute it and/or
00005  * modify it under the terms of the GNU General Public License
00006  * as published by the Free Software Foundation; either version 2
00007  * of the License, or (at your option) any later version.
00008  *
00009  * This program is distributed in the hope that it will be useful,
00010  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00011  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00012  * GNU General Public License for more details.
00013  *
00014  * You should have received a copy of the GNU General Public License
00015  * along with this program; if not, write to the Free Software Foundation,
00016  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
00017  */
00018 
00019 #ifndef __GRAPH_H__
00020 #define __GRAPH_H__
00021 
00022 #include "kernel_types.h"
00023 
00024 #include "util_list.h"
00025 #include "util_map.h"
00026 #include "util_param.h"
00027 #include "util_set.h"
00028 #include "util_types.h"
00029 #include "util_vector.h"
00030 
00031 CCL_NAMESPACE_BEGIN
00032 
00033 class AttributeRequestSet;
00034 class ShaderInput;
00035 class ShaderOutput;
00036 class ShaderNode;
00037 class ShaderGraph;
00038 class SVMCompiler;
00039 class OSLCompiler;
00040 
00041 /* Socket Type
00042  *
00043  * Data type for inputs and outputs */
00044 
00045 enum ShaderSocketType {
00046     SHADER_SOCKET_FLOAT,
00047     SHADER_SOCKET_COLOR,
00048     SHADER_SOCKET_VECTOR,
00049     SHADER_SOCKET_POINT,
00050     SHADER_SOCKET_NORMAL,
00051     SHADER_SOCKET_CLOSURE
00052 };
00053 
00054 /* Bump
00055  *
00056  * For bump mapping, a node may be evaluated multiple times, using different
00057  * samples to reconstruct the normal, this indicates the sample position */
00058 
00059 enum ShaderBump {
00060     SHADER_BUMP_NONE,
00061     SHADER_BUMP_CENTER,
00062     SHADER_BUMP_DX,
00063     SHADER_BUMP_DY
00064 };
00065 
00066 /* Enum
00067  *
00068  * Utility class for enum values. */
00069 
00070 class ShaderEnum {
00071 public:
00072     bool empty() const { return left.empty(); }
00073     void insert(const char *x, int y) {
00074         left[ustring(x)] = y;
00075         right[y] = ustring(x);
00076     }
00077 
00078     bool exists(ustring x) { return left.find(x) != left.end(); }
00079     bool exists(int y) { return right.find(y) != right.end(); }
00080 
00081     int operator[](const char *x) { return left[ustring(x)]; }
00082     int operator[](ustring x) { return left[x]; }
00083     ustring operator[](int y) { return right[y]; }
00084 
00085 protected:
00086     map<ustring, int> left;
00087     map<int, ustring> right;
00088 };
00089 
00090 /* Input
00091  *
00092  * Input socket for a shader node. May be linked to an output or not. If not
00093  * linked, it will either get a fixed default value, or e.g. a texture
00094  * coordinate. */
00095 
00096 class ShaderInput {
00097 public:
00098     enum DefaultValue {
00099         TEXTURE_GENERATED,
00100         TEXTURE_UV,
00101         INCOMING,
00102         NORMAL,
00103         POSITION,
00104         NONE
00105     };
00106 
00107     ShaderInput(ShaderNode *parent, const char *name, ShaderSocketType type);
00108     void set(const float3& v) { value = v; }
00109     void set(float f) { value = make_float3(f, 0, 0); }
00110 
00111     const char *name;
00112     ShaderSocketType type;
00113 
00114     ShaderNode *parent;
00115     ShaderOutput *link;
00116 
00117     DefaultValue default_value;
00118     float3 value;
00119 
00120     int stack_offset; /* for SVM compiler */
00121     bool osl_only;
00122 };
00123 
00124 /* Output
00125  *
00126  * Output socket for a shader node. */
00127 
00128 class ShaderOutput {
00129 public:
00130     ShaderOutput(ShaderNode *parent, const char *name, ShaderSocketType type);
00131 
00132     const char *name;
00133     ShaderNode *parent;
00134     ShaderSocketType type;
00135 
00136     vector<ShaderInput*> links;
00137 
00138     int stack_offset; /* for SVM compiler */
00139 };
00140 
00141 /* Node
00142  *
00143  * Shader node in graph, with input and output sockets. This is the virtual
00144  * base class for all node types. */
00145 
00146 class ShaderNode {
00147 public:
00148     ShaderNode(const char *name);
00149     virtual ~ShaderNode();
00150 
00151     ShaderInput *input(const char *name);
00152     ShaderOutput *output(const char *name);
00153 
00154     ShaderInput *add_input(const char *name, ShaderSocketType type, float value=0.0f);
00155     ShaderInput *add_input(const char *name, ShaderSocketType type, float3 value);
00156     ShaderInput *add_input(const char *name, ShaderSocketType type, ShaderInput::DefaultValue value, bool osl_only=false);
00157     ShaderOutput *add_output(const char *name, ShaderSocketType type);
00158 
00159     virtual ShaderNode *clone() const = 0;
00160     virtual void attributes(AttributeRequestSet *attributes);
00161     virtual void compile(SVMCompiler& compiler) = 0;
00162     virtual void compile(OSLCompiler& compiler) = 0;
00163 
00164     vector<ShaderInput*> inputs;
00165     vector<ShaderOutput*> outputs;
00166 
00167     ustring name; /* name, not required to be unique */
00168     int id; /* index in graph node array */
00169     ShaderBump bump; /* for bump mapping utility */
00170 };
00171 
00172 
00173 /* Node definition utility macros */
00174 
00175 #define SHADER_NODE_CLASS(type) \
00176     type(); \
00177     virtual ShaderNode *clone() const { return new type(*this); } \
00178     virtual void compile(SVMCompiler& compiler); \
00179     virtual void compile(OSLCompiler& compiler); \
00180 
00181 #define SHADER_NODE_NO_CLONE_CLASS(type) \
00182     type(); \
00183     virtual void compile(SVMCompiler& compiler); \
00184     virtual void compile(OSLCompiler& compiler); \
00185 
00186 #define SHADER_NODE_BASE_CLASS(type) \
00187     virtual ShaderNode *clone() const { return new type(*this); } \
00188     virtual void compile(SVMCompiler& compiler); \
00189     virtual void compile(OSLCompiler& compiler); \
00190 
00191 /* Graph
00192  *
00193  * Shader graph of nodes. Also does graph manipulations for default inputs,
00194  * bump mapping from displacement, and possibly other things in the future. */
00195 
00196 class ShaderGraph {
00197 public:
00198     list<ShaderNode*> nodes;
00199     bool finalized;
00200 
00201     ShaderGraph();
00202     ~ShaderGraph();
00203 
00204     ShaderGraph *copy();
00205 
00206     ShaderNode *add(ShaderNode *node);
00207     ShaderNode *output();
00208 
00209     void connect(ShaderOutput *from, ShaderInput *to);
00210     void disconnect(ShaderInput *to);
00211 
00212     void finalize(bool do_bump = false, bool do_osl = false);
00213 
00214 protected:
00215     typedef pair<ShaderNode* const, ShaderNode*> NodePair;
00216 
00217     void find_dependencies(set<ShaderNode*>& dependencies, ShaderInput *input);
00218     void copy_nodes(set<ShaderNode*>& nodes, map<ShaderNode*, ShaderNode*>& nnodemap);
00219 
00220     void remove_proxy_nodes(vector<bool>& removed);
00221     void break_cycles(ShaderNode *node, vector<bool>& visited, vector<bool>& on_stack);
00222     void clean();
00223     void bump_from_displacement();
00224     void default_inputs(bool do_osl);
00225 };
00226 
00227 CCL_NAMESPACE_END
00228 
00229 #endif /* __GRAPH_H__ */
00230