[Bf-blender-cvs] [8f71a84496a] master: Cycles/Eevee: add Emission and Alpha inputs to Principled BSDF

Brecht Van Lommel noreply at git.blender.org
Mon May 13 16:33:30 CEST 2019


Commit: 8f71a84496a95528303fbe0bb7c1406060353425
Author: Brecht Van Lommel
Date:   Sun May 12 14:39:30 2019 +0200
Branches: master
https://developer.blender.org/rB8f71a84496a95528303fbe0bb7c1406060353425

Cycles/Eevee: add Emission and Alpha inputs to Principled BSDF

This makes it easier to set up materials with emission and transparency.
Importers/exporters and add-ons are recommended to now use these rather than
creating separate transparent BSDF and emission nodes.

===================================================================

M	intern/cycles/render/graph.cpp
M	intern/cycles/render/graph.h
M	intern/cycles/render/nodes.cpp
M	intern/cycles/render/nodes.h
M	source/blender/gpu/shaders/gpu_shader_material.glsl
M	source/blender/nodes/shader/nodes/node_shader_bsdf_principled.c

===================================================================

diff --git a/intern/cycles/render/graph.cpp b/intern/cycles/render/graph.cpp
index e5fd39f08b7..9203c4468d2 100644
--- a/intern/cycles/render/graph.cpp
+++ b/intern/cycles/render/graph.cpp
@@ -127,6 +127,12 @@ ShaderOutput *ShaderNode::output(ustring name)
   return NULL;
 }
 
+void ShaderNode::remove_input(ShaderInput *input)
+{
+  assert(input->link == NULL);
+  inputs.erase(remove(inputs.begin(), inputs.end(), input), inputs.end());
+}
+
 void ShaderNode::attributes(Shader *shader, AttributeRequestSet *attributes)
 {
   foreach (ShaderInput *input, inputs) {
@@ -297,6 +303,28 @@ void ShaderGraph::disconnect(ShaderInput *to)
   from->links.erase(remove(from->links.begin(), from->links.end(), to), from->links.end());
 }
 
+void ShaderGraph::relink(ShaderInput *from, ShaderInput *to)
+{
+  ShaderOutput *out = from->link;
+  if (out) {
+    disconnect(from);
+    connect(out, to);
+  }
+  to->parent->copy_value(to->socket_type, *(from->parent), from->socket_type);
+}
+
+void ShaderGraph::relink(ShaderOutput *from, ShaderOutput *to)
+{
+  /* Copy because disconnect modifies this list. */
+  vector<ShaderInput *> outputs = from->links;
+
+  foreach (ShaderInput *sock, outputs) {
+    disconnect(sock);
+    if (to)
+      connect(to, sock);
+  }
+}
+
 void ShaderGraph::relink(ShaderNode *node, ShaderOutput *from, ShaderOutput *to)
 {
   simplified = false;
@@ -320,6 +348,7 @@ void ShaderGraph::relink(ShaderNode *node, ShaderOutput *from, ShaderOutput *to)
 void ShaderGraph::simplify(Scene *scene)
 {
   if (!simplified) {
+    expand();
     default_inputs(scene->shader_manager->use_osl());
     clean(scene);
     refine_bump_nodes();
@@ -780,6 +809,14 @@ void ShaderGraph::clean(Scene *scene)
   nodes = newnodes;
 }
 
+void ShaderGraph::expand()
+{
+  /* Call expand on all nodes, to generate additional nodes. */
+  foreach (ShaderNode *node, nodes) {
+    node->expand(this);
+  }
+}
+
 void ShaderGraph::default_inputs(bool do_osl)
 {
   /* nodes can specify default texture coordinates, for now we give
diff --git a/intern/cycles/render/graph.h b/intern/cycles/render/graph.h
index b1aa5cf3168..cade04de374 100644
--- a/intern/cycles/render/graph.h
+++ b/intern/cycles/render/graph.h
@@ -147,6 +147,7 @@ class ShaderNode : public Node {
   virtual ~ShaderNode();
 
   void create_inputs_outputs(const NodeType *type);
+  void remove_input(ShaderInput *input);
 
   ShaderInput *input(const char *name);
   ShaderOutput *output(const char *name);
@@ -158,6 +159,11 @@ class ShaderNode : public Node {
   virtual void compile(SVMCompiler &compiler) = 0;
   virtual void compile(OSLCompiler &compiler) = 0;
 
+  /* Expand node into additional nodes. */
+  virtual void expand(ShaderGraph * /* graph */)
+  {
+  }
+
   /* ** Node optimization ** */
   /* Check whether the node can be replaced with single constant. */
   virtual void constant_fold(const ConstantFolder & /*folder*/)
@@ -322,6 +328,8 @@ class ShaderGraph {
   void connect(ShaderOutput *from, ShaderInput *to);
   void disconnect(ShaderOutput *from);
   void disconnect(ShaderInput *to);
+  void relink(ShaderInput *from, ShaderInput *to);
+  void relink(ShaderOutput *from, ShaderOutput *to);
   void relink(ShaderNode *node, ShaderOutput *from, ShaderOutput *to);
 
   void remove_proxy_nodes();
@@ -346,6 +354,7 @@ class ShaderGraph {
   void break_cycles(ShaderNode *node, vector<bool> &visited, vector<bool> &on_stack);
   void bump_from_displacement(bool use_object_space);
   void refine_bump_nodes();
+  void expand();
   void default_inputs(bool do_osl);
   void transform_multi_closure(ShaderNode *node, ShaderOutput *weight_out, bool volume);
 
diff --git a/intern/cycles/render/nodes.cpp b/intern/cycles/render/nodes.cpp
index 6e86643cc2b..86cc2030d1b 100644
--- a/intern/cycles/render/nodes.cpp
+++ b/intern/cycles/render/nodes.cpp
@@ -2427,6 +2427,8 @@ NODE_DEFINE(PrincipledBsdfNode)
   SOCKET_IN_FLOAT(transmission, "Transmission", 0.0f);
   SOCKET_IN_FLOAT(transmission_roughness, "Transmission Roughness", 0.0f);
   SOCKET_IN_FLOAT(anisotropic_rotation, "Anisotropic Rotation", 0.0f);
+  SOCKET_IN_COLOR(emission, "Emission", make_float3(0.0f, 0.0f, 0.0f));
+  SOCKET_IN_FLOAT(alpha, "Alpha", 1.0f);
   SOCKET_IN_NORMAL(normal, "Normal", make_float3(0.0f, 0.0f, 0.0f), SocketType::LINK_NORMAL);
   SOCKET_IN_NORMAL(clearcoat_normal,
                    "Clearcoat Normal",
@@ -2447,6 +2449,48 @@ PrincipledBsdfNode::PrincipledBsdfNode() : BsdfBaseNode(node_type)
   distribution_orig = NBUILTIN_CLOSURES;
 }
 
+void PrincipledBsdfNode::expand(ShaderGraph *graph)
+{
+  ShaderOutput *principled_out = output("BSDF");
+
+  ShaderInput *emission_in = input("Emission");
+  if (emission_in->link || emission != make_float3(0.0f, 0.0f, 0.0f)) {
+    /* Create add closure and emission. */
+    AddClosureNode *add = new AddClosureNode();
+    EmissionNode *emission_node = new EmissionNode();
+    ShaderOutput *new_out = add->output("Closure");
+
+    graph->add(add);
+    graph->add(emission_node);
+
+    emission_node->strength = 1.0f;
+    graph->relink(emission_in, emission_node->input("Color"));
+    graph->relink(principled_out, new_out);
+    graph->connect(emission_node->output("Emission"), add->input("Closure1"));
+    graph->connect(principled_out, add->input("Closure2"));
+
+    principled_out = new_out;
+  }
+
+  ShaderInput *alpha_in = input("Alpha");
+  if (alpha_in->link || alpha != 1.0f) {
+    /* Create mix and transparent BSDF for alpha transparency. */
+    MixClosureNode *mix = new MixClosureNode();
+    TransparentBsdfNode *transparent = new TransparentBsdfNode();
+
+    graph->add(mix);
+    graph->add(transparent);
+
+    graph->relink(alpha_in, mix->input("Fac"));
+    graph->relink(principled_out, mix->output("Closure"));
+    graph->connect(transparent->output("BSDF"), mix->input("Closure1"));
+    graph->connect(principled_out, mix->input("Closure2"));
+  }
+
+  remove_input(emission_in);
+  remove_input(alpha_in);
+}
+
 bool PrincipledBsdfNode::has_surface_bssrdf()
 {
   ShaderInput *subsurface_in = input("Subsurface");
@@ -2627,7 +2671,7 @@ NODE_DEFINE(TransparentBsdfNode)
 {
   NodeType *type = NodeType::add("transparent_bsdf", create, NodeType::SHADER);
 
-  SOCKET_IN_COLOR(color, "Color", make_float3(0.8f, 0.8f, 0.8f));
+  SOCKET_IN_COLOR(color, "Color", make_float3(1.0f, 1.0f, 1.0f));
   SOCKET_IN_FLOAT(surface_mix_weight, "SurfaceMixWeight", 0.0f, SocketType::SVM_INTERNAL);
 
   SOCKET_OUT_CLOSURE(BSDF, "BSDF");
diff --git a/intern/cycles/render/nodes.h b/intern/cycles/render/nodes.h
index 88fa728ecd1..3dd84ad8dca 100644
--- a/intern/cycles/render/nodes.h
+++ b/intern/cycles/render/nodes.h
@@ -487,6 +487,7 @@ class PrincipledBsdfNode : public BsdfBaseNode {
  public:
   SHADER_NODE_CLASS(PrincipledBsdfNode)
 
+  void expand(ShaderGraph *graph);
   bool has_surface_bssrdf();
   bool has_bssrdf_bump();
   void compile(SVMCompiler &compiler,
@@ -515,6 +516,8 @@ class PrincipledBsdfNode : public BsdfBaseNode {
   float surface_mix_weight;
   ClosureType distribution, distribution_orig;
   ClosureType subsurface_method;
+  float3 emission;
+  float alpha;
 
   bool has_integrator_dependency();
   void attributes(Shader *shader, AttributeRequestSet *attributes);
diff --git a/source/blender/gpu/shaders/gpu_shader_material.glsl b/source/blender/gpu/shaders/gpu_shader_material.glsl
index 5596940cbf6..768f5ddb057 100644
--- a/source/blender/gpu/shaders/gpu_shader_material.glsl
+++ b/source/blender/gpu/shaders/gpu_shader_material.glsl
@@ -1242,6 +1242,8 @@ void node_bsdf_principled(vec4 base_color,
                           float ior,
                           float transmission,
                           float transmission_roughness,
+                          vec4 emission,
+                          float alpha,
                           vec3 N,
                           vec3 CN,
                           vec3 T,
@@ -1321,6 +1323,8 @@ void node_bsdf_principled(vec4 base_color,
 #    endif
   result.sss_data.rgb *= (1.0 - transmission);
 #  endif
+  result.radiance += emission.rgb;
+  result.opacity = alpha;
 }
 
 void node_bsdf_principled_dielectric(vec4 base_color,
@@ -1340,6 +1344,8 @@ void node_bsdf_principled_dielectric(vec4 base_color,
                                      float ior,
                                      float transmission,
                                      float transmission_roughness,
+                                     vec4 emission,
+                                     float alpha,
                                      vec3 N,
                                      vec3 CN,
                                      vec3 T,
@@ -1369,6 +1375,8 @@ void node_bsdf_principled_dielectric(vec4 base_color,
   result.ssr_data = vec4(ssr_spec, roughness);
   result.ssr_normal = normal_encode(vN, viewCameraVec);
   result.ssr_id = int(ssr_id);
+  result.radiance += emission.rgb;
+  result.opacity = alpha;
 }
 
 void node_bsdf_principled_metallic(vec4 base_color,
@@ -1388,6 +1396,8 @@ void node_bsdf_principled_metallic(vec4 base_color,
                                    float ior,
                                    float transmission,
                                    float transmission_roughness,
+                                   vec4 emission,
+                                   float alpha,
                                    vec3 N,
                                    vec3 CN,
                                    vec3 T,
@@ -1408,6 +1418,8 @@ void node_bsdf_principled_metallic(vec4 base_color,
   result.ssr_data = vec4(ssr_spec, roughness);
   result.ssr_normal = normal_encode(vN, viewCameraVec);
   result.ssr_id = int(ssr_id);
+  result.radiance += emission.rgb;
+  result.opacity = alpha;
 }
 
 void node_bsdf_principled_clearcoat(vec4 base_color,
@@ -1427,6 +1439,8 @@ void node_bsdf_principled_clearcoat(vec4 base_color,
                                     float ior,
                                     float transmission,
                                     float transmission_roughness,
+                                    vec4 emission,
+                                    float alpha,
                                     vec3 N,
                                     vec3 

@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list