Browse Source

shader: Add missing support for p3d_Fog, p3d_Color and p3d_ClipPlane[]

rdb 5 years ago
parent
commit
e5fc7fffc2
3 changed files with 147 additions and 1 deletions
  1. 118 1
      panda/src/gobj/shader.cxx
  2. 26 0
      panda/src/gobj/shaderType.cxx
  3. 3 0
      panda/src/gobj/shaderType.h

+ 118 - 1
panda/src/gobj/shader.cxx

@@ -1415,10 +1415,58 @@ bind_parameter(const Parameter &param) {
       bind._arg[0] = nullptr;
       bind._arg[0] = nullptr;
       bind._part[1] = SMO_identity;
       bind._part[1] = SMO_identity;
       bind._arg[1] = nullptr;
       bind._arg[1] = nullptr;
-      bind._piece = SMP_row3;
+
+      if (type->as_vector()->get_num_components() == 3) {
+        bind._piece = Shader::SMP_row3x3;
+      } else {
+        bind._piece = Shader::SMP_row3;
+      }
+      cp_add_mat_spec(bind);
+      return true;
+    }
+    if (pieces[1] == "Color") {
+      if (!expect_float_vector(name, type, 3, 4)) {
+        return false;
+      }
+      ShaderMatSpec bind;
+      bind._id = param;
+      bind._func = Shader::SMF_first;
+      bind._part[0] = Shader::SMO_attr_color;
+      bind._arg[0] = nullptr;
+      bind._part[1] = Shader::SMO_identity;
+      bind._arg[1] = nullptr;
+
+      if (type->as_vector()->get_num_components() == 3) {
+        bind._piece = Shader::SMP_row3x3;
+      } else {
+        bind._piece = Shader::SMP_row3;
+      }
       cp_add_mat_spec(bind);
       cp_add_mat_spec(bind);
       return true;
       return true;
     }
     }
+    if (pieces[1] == "ClipPlane") {
+      const ::ShaderType *element_type;
+      uint32_t num_elements;
+      type->unwrap_array(element_type, num_elements);
+      if (!expect_float_vector(name, element_type, 4, 4)) {
+        return false;
+      }
+      Shader::ShaderMatSpec bind;
+      bind._id = param;
+      bind._piece = Shader::SMP_row3;
+      bind._func = Shader::SMF_first;
+      bind._part[0] = Shader::SMO_apiview_clipplane_i;
+      bind._arg[0] = nullptr;
+      bind._part[1] = Shader::SMO_identity;
+      bind._arg[1] = nullptr;
+
+      for (uint32_t i = 0; i < num_elements; ++i) {
+        bind._index = i;
+        cp_add_mat_spec(bind);
+        ++bind._id._location;
+      }
+      return true;
+    }
     if (pieces[1] == "TexAlphaOnly") {
     if (pieces[1] == "TexAlphaOnly") {
       ShaderMatSpec bind;
       ShaderMatSpec bind;
       bind._id = param;
       bind._id = param;
@@ -1432,6 +1480,75 @@ bind_parameter(const Parameter &param) {
       cp_add_mat_spec(bind);
       cp_add_mat_spec(bind);
       return true;
       return true;
     }
     }
+    if (pieces[1] == "Fog") {
+      ShaderMatSpec bind;
+      bind._id = param;
+      bind._func = SMF_first;
+      bind._arg[0] = nullptr;
+      bind._part[1] = SMO_identity;
+      bind._arg[1] = nullptr;
+
+      const ::ShaderType::Struct *struct_type = type->as_struct();
+      if (struct_type == nullptr) {
+        return report_parameter_error(name, type, "expected struct");
+      }
+
+      bool success = true;
+      for (size_t i = 0; i < struct_type->get_num_members(); ++i) {
+        const ::ShaderType::Struct::Member &member = struct_type->get_member(i);
+
+        CPT(InternalName) fqname = ((InternalName *)name.p())->append(member.name);
+        bind._id._location = param._location + i;
+        bind._id._name = fqname->get_name();
+        bind._id._type = member.type;
+
+        if (member.name == "color") {
+          if (expect_float_vector(fqname, member.type, 3, 4)) {
+            bind._part[0] = SMO_attr_fogcolor;
+            if (member.type->as_vector()->get_num_components() == 3) {
+              bind._piece = Shader::SMP_row3x3;
+            } else {
+              bind._piece = Shader::SMP_row3;
+            }
+            cp_add_mat_spec(bind);
+            continue;
+          }
+        } else if (member.name == "density") {
+          if (expect_float_vector(fqname, member.type, 1, 1)) {
+            bind._part[0] = SMO_attr_fog;
+            bind._piece = SMP_row3x1;
+            cp_add_mat_spec(bind);
+            continue;
+          }
+        } else if (member.name == "start") {
+          if (expect_float_vector(fqname, member.type, 1, 1)) {
+            bind._part[0] = SMO_attr_fog;
+            bind._piece = SMP_cell13;
+            cp_add_mat_spec(bind);
+            continue;
+          }
+        } else if (member.name == "end") {
+          if (expect_float_vector(fqname, member.type, 1, 1)) {
+            bind._part[0] = SMO_attr_fog;
+            bind._piece = SMP_cell14;
+            cp_add_mat_spec(bind);
+            continue;
+          }
+        } else if (member.name == "scale") {
+          if (expect_float_vector(fqname, member.type, 1, 1)) {
+            bind._part[0] = SMO_attr_fog;
+            bind._piece = SMP_cell15;
+            cp_add_mat_spec(bind);
+            continue;
+          }
+        } else {
+          report_parameter_error(fqname, member.type, "unrecognized fog attribute");
+        }
+        success = false;
+      }
+
+      return success;
+    }
     if (pieces[1] == "LightModel") {
     if (pieces[1] == "LightModel") {
       const ::ShaderType::Struct *struct_type = type->as_struct();
       const ::ShaderType::Struct *struct_type = type->as_struct();
       if (struct_type == nullptr || struct_type->get_num_members() > 1) {
       if (struct_type == nullptr || struct_type->get_num_members() > 1) {

+ 26 - 0
panda/src/gobj/shaderType.cxx

@@ -35,6 +35,19 @@ const ShaderType::Scalar *ShaderType::float_type;
 const ShaderType::Scalar *ShaderType::double_type;
 const ShaderType::Scalar *ShaderType::double_type;
 const ShaderType::Sampler *ShaderType::sampler_type;
 const ShaderType::Sampler *ShaderType::sampler_type;
 
 
+/**
+ * If this type is an array, puts the element type in the first argument and the
+ * number of elements in the second argument, and returns true.  If not, puts
+ * the current type in the first argument, and 1 in the second argument, and
+ * returns false.
+ */
+bool ShaderType::
+unwrap_array(const ShaderType *&element_type, uint32_t &num_elements) const {
+  element_type = this;
+  num_elements = 1;
+  return false;
+}
+
 /**
 /**
  *
  *
  */
  */
@@ -399,6 +412,19 @@ get_num_parameter_locations() const {
   return total;
   return total;
 }
 }
 
 
+/**
+ * If this type is an array, puts the element type in the first argument and the
+ * number of elements in the second argument, and returns true.  If not, puts
+ * the current type in the first argument, and 1 in the second argument, and
+ * returns false.
+ */
+bool ShaderType::Array::
+unwrap_array(const ShaderType *&element_type, uint32_t &num_elements) const {
+  element_type = _element_type;
+  num_elements = _num_elements;
+  return true;
+}
+
 /**
 /**
  * Returns true if this type contains the given scalar type.
  * Returns true if this type contains the given scalar type.
  */
  */

+ 3 - 0
panda/src/gobj/shaderType.h

@@ -72,6 +72,7 @@ PUBLISHED:
 
 
 public:
 public:
   virtual bool is_aggregate_type() const { return false; }
   virtual bool is_aggregate_type() const { return false; }
+  virtual bool unwrap_array(const ShaderType *&element_type, uint32_t &num_elements) const;
   virtual bool contains_scalar_type(ScalarType type) const { return false; }
   virtual bool contains_scalar_type(ScalarType type) const { return false; }
   virtual bool as_scalar_type(ScalarType &type,
   virtual bool as_scalar_type(ScalarType &type,
                               uint32_t &num_elements,
                               uint32_t &num_elements,
@@ -293,6 +294,8 @@ public:
   INLINE const ShaderType *get_element_type() const;
   INLINE const ShaderType *get_element_type() const;
   INLINE uint32_t get_num_elements() const;
   INLINE uint32_t get_num_elements() const;
 
 
+  virtual bool unwrap_array(const ShaderType *&element_type, uint32_t &num_elements) const override;
+
   virtual bool contains_scalar_type(ScalarType type) const override;
   virtual bool contains_scalar_type(ScalarType type) const override;
   virtual bool as_scalar_type(ScalarType &type, uint32_t &num_elements,
   virtual bool as_scalar_type(ScalarType &type, uint32_t &num_elements,
                               uint32_t &num_rows, uint32_t &num_columns) const override;
                               uint32_t &num_rows, uint32_t &num_columns) const override;