[Bf-blender-cvs] [3a4f2131c2d] blender-v3.2-release: Fix Cycles not rendering byte precision vertex domain colors

Brecht Van Lommel noreply at git.blender.org
Fri May 27 17:02:33 CEST 2022


Commit: 3a4f2131c2d2bc30aec6e74bdfe985c1ec498768
Author: Brecht Van Lommel
Date:   Fri May 27 15:45:29 2022 +0200
Branches: blender-v3.2-release
https://developer.blender.org/rB3a4f2131c2d2bc30aec6e74bdfe985c1ec498768

Fix Cycles not rendering byte precision vertex domain colors

Code was not yet updated to use generic attributes for vertex colors. This also
makes generic attributes work for adaptive subdivision.

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

M	intern/cycles/blender/mesh.cpp

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

diff --git a/intern/cycles/blender/mesh.cpp b/intern/cycles/blender/mesh.cpp
index de67e27923d..635421d3d61 100644
--- a/intern/cycles/blender/mesh.cpp
+++ b/intern/cycles/blender/mesh.cpp
@@ -267,75 +267,62 @@ static void mikk_compute_tangents(
   genTangSpaceDefault(&context);
 }
 
-/* Create sculpt vertex color attributes. */
-static void attr_create_sculpt_vertex_color(Scene *scene,
-                                            Mesh *mesh,
-                                            BL::Mesh &b_mesh,
-                                            bool subdivision)
-{
-  for (BL::MeshVertColorLayer &l : b_mesh.sculpt_vertex_colors) {
-    const bool active_render = l.active_render();
-    AttributeStandard vcol_std = (active_render) ? ATTR_STD_VERTEX_COLOR : ATTR_STD_NONE;
-    ustring vcol_name = ustring(l.name().c_str());
-
-    const bool need_vcol = mesh->need_attribute(scene, vcol_name) ||
-                           mesh->need_attribute(scene, vcol_std);
-
-    if (!need_vcol) {
-      continue;
-    }
-
-    AttributeSet &attributes = (subdivision) ? mesh->subd_attributes : mesh->attributes;
-    Attribute *vcol_attr = attributes.add(vcol_name, TypeRGBA, ATTR_ELEMENT_VERTEX);
-    vcol_attr->std = vcol_std;
-
-    float4 *cdata = vcol_attr->data_float4();
-    int numverts = b_mesh.vertices.length();
-
-    for (int i = 0; i < numverts; i++) {
-      *(cdata++) = get_float4(l.data[i].color());
-    }
-  }
-}
-
 template<typename TypeInCycles, typename GetValueAtIndex>
 static void fill_generic_attribute(BL::Mesh &b_mesh,
                                    TypeInCycles *data,
                                    const BL::Attribute::domain_enum b_domain,
+                                   const bool subdivision,
                                    const GetValueAtIndex &get_value_at_index)
 {
   switch (b_domain) {
     case BL::Attribute::domain_CORNER: {
-      for (BL::MeshLoopTriangle &t : b_mesh.loop_triangles) {
-        const int index = t.index() * 3;
-        BL::Array<int, 3> loops = t.loops();
-        data[index] = get_value_at_index(loops[0]);
-        data[index + 1] = get_value_at_index(loops[1]);
-        data[index + 2] = get_value_at_index(loops[2]);
+      if (subdivision) {
+        for (BL::MeshPolygon &p : b_mesh.polygons) {
+          int n = p.loop_total();
+          for (int i = 0; i < n; i++) {
+            *data = get_value_at_index(p.loop_start() + i);
+            data++;
+          }
+        }
+      }
+      else {
+        for (BL::MeshLoopTriangle &t : b_mesh.loop_triangles) {
+          const int index = t.index() * 3;
+          BL::Array<int, 3> loops = t.loops();
+          data[index] = get_value_at_index(loops[0]);
+          data[index + 1] = get_value_at_index(loops[1]);
+          data[index + 2] = get_value_at_index(loops[2]);
+        }
       }
       break;
     }
     case BL::Attribute::domain_EDGE: {
-      /* Averge edge attributes at vertices. */
-      const size_t num_verts = b_mesh.vertices.length();
-      vector<int> count(num_verts, 0);
-
-      for (BL::MeshEdge &e : b_mesh.edges) {
-        BL::Array<int, 2> vertices = e.vertices();
-        TypeInCycles value = get_value_at_index(e.index());
-
-        data[vertices[0]] += value;
-        data[vertices[1]] += value;
-        count[vertices[0]]++;
-        count[vertices[1]]++;
+      if constexpr (std::is_same_v<TypeInCycles, uchar4>) {
+        /* uchar4 edge attributes do not exist, and averaging in place
+         * would not work. */
+        assert(0);
       }
+      else {
+        /* Averge edge attributes at vertices. */
+        const size_t num_verts = b_mesh.vertices.length();
+        vector<int> count(num_verts, 0);
+
+        for (BL::MeshEdge &e : b_mesh.edges) {
+          BL::Array<int, 2> vertices = e.vertices();
+          TypeInCycles value = get_value_at_index(e.index());
+
+          data[vertices[0]] += value;
+          data[vertices[1]] += value;
+          count[vertices[0]]++;
+          count[vertices[1]]++;
+        }
 
-      for (size_t i = 0; i < num_verts; i++) {
-        if (count[i] > 1) {
-          data[i] /= (float)count[i];
+        for (size_t i = 0; i < num_verts; i++) {
+          if (count[i] > 1) {
+            data[i] /= (float)count[i];
+          }
         }
       }
-
       break;
     }
     case BL::Attribute::domain_POINT: {
@@ -346,8 +333,16 @@ static void fill_generic_attribute(BL::Mesh &b_mesh,
       break;
     }
     case BL::Attribute::domain_FACE: {
-      for (BL::MeshLoopTriangle &t : b_mesh.loop_triangles) {
-        data[t.index()] = get_value_at_index(t.polygon_index());
+      if (subdivision) {
+        const int num_polygons = b_mesh.polygons.length();
+        for (int i = 0; i < num_polygons; i++) {
+          data[i] = get_value_at_index(i);
+        }
+      }
+      else {
+        for (BL::MeshLoopTriangle &t : b_mesh.loop_triangles) {
+          data[t.index()] = get_value_at_index(t.polygon_index());
+        }
       }
       break;
     }
@@ -395,21 +390,22 @@ static void attr_create_generic(Scene *scene,
                                 const bool need_motion,
                                 const float motion_scale)
 {
-  if (subdivision) {
-    /* TODO: Handle subdivision correctly. */
-    return;
-  }
-  AttributeSet &attributes = mesh->attributes;
+  AttributeSet &attributes = (subdivision) ? mesh->subd_attributes : mesh->attributes;
   static const ustring u_velocity("velocity");
 
+  int attribute_index = 0;
+  int render_color_index = b_mesh.attributes.render_color_index();
+
   for (BL::Attribute &b_attribute : b_mesh.attributes) {
     const ustring name{b_attribute.name().c_str()};
+    const bool is_render_color = (attribute_index++ == render_color_index);
 
     if (need_motion && name == u_velocity) {
       attr_create_motion(mesh, b_attribute, motion_scale);
     }
 
-    if (!mesh->need_attribute(scene, name)) {
+    if (!(mesh->need_attribute(scene, name) ||
+          (is_render_color && mesh->need_attribute(scene, ATTR_STD_VERTEX_COLOR)))) {
       continue;
     }
     if (attributes.find(name)) {
@@ -445,15 +441,16 @@ static void attr_create_generic(Scene *scene,
         BL::FloatAttribute b_float_attribute{b_attribute};
         Attribute *attr = attributes.add(name, TypeFloat, element);
         float *data = attr->data_float();
-        fill_generic_attribute(
-            b_mesh, data, b_domain, [&](int i) { return b_float_attribute.data[i].value(); });
+        fill_generic_attribute(b_mesh, data, b_domain, subdivision, [&](int i) {
+          return b_float_attribute.data[i].value();
+        });
         break;
       }
       case BL::Attribute::data_type_BOOLEAN: {
         BL::BoolAttribute b_bool_attribute{b_attribute};
         Attribute *attr = attributes.add(name, TypeFloat, element);
         float *data = attr->data_float();
-        fill_generic_attribute(b_mesh, data, b_domain, [&](int i) {
+        fill_generic_attribute(b_mesh, data, b_domain, subdivision, [&](int i) {
           return (float)b_bool_attribute.data[i].value();
         });
         break;
@@ -462,25 +459,59 @@ static void attr_create_generic(Scene *scene,
         BL::IntAttribute b_int_attribute{b_attribute};
         Attribute *attr = attributes.add(name, TypeFloat, element);
         float *data = attr->data_float();
-        fill_generic_attribute(
-            b_mesh, data, b_domain, [&](int i) { return (float)b_int_attribute.data[i].value(); });
+        fill_generic_attribute(b_mesh, data, b_domain, subdivision, [&](int i) {
+          return (float)b_int_attribute.data[i].value();
+        });
         break;
       }
       case BL::Attribute::data_type_FLOAT_VECTOR: {
         BL::FloatVectorAttribute b_vector_attribute{b_attribute};
         Attribute *attr = attributes.add(name, TypeVector, element);
         float3 *data = attr->data_float3();
-        fill_generic_attribute(b_mesh, data, b_domain, [&](int i) {
+        fill_generic_attribute(b_mesh, data, b_domain, subdivision, [&](int i) {
           BL::Array<float, 3> v = b_vector_attribute.data[i].vector();
           return make_float3(v[0], v[1], v[2]);
         });
         break;
       }
+      case BL::Attribute::data_type_BYTE_COLOR: {
+        BL::ByteColorAttribute b_color_attribute{b_attribute};
+
+        if (element == ATTR_ELEMENT_CORNER) {
+          element = ATTR_ELEMENT_CORNER_BYTE;
+        }
+        Attribute *attr = attributes.add(name, TypeRGBA, element);
+        if (is_render_color) {
+          attr->std = ATTR_STD_VERTEX_COLOR;
+        }
+
+        if (element == ATTR_ELEMENT_CORNER_BYTE) {
+          uchar4 *data = attr->data_uchar4();
+          fill_generic_attribute(b_mesh, data, b_domain, subdivision, [&](int i) {
+            /* Compress/encode vertex color using the sRGB curve. */
+            const float4 c = get_float4(b_color_attribute.data[i].color());
+            return color_float4_to_uchar4(color_linear_to_srgb_v4(c));
+          });
+        }
+        else {
+          float4 *data = attr->data_float4();
+          fill_generic_attribute(b_mesh, data, b_domain, subdivision, [&](int i) {
+            BL::Array<float, 4> v = b_color_attribute.data[i].color();
+            return make_float4(v[0], v[1], v[2], v[3]);
+          });
+        }
+        break;
+      }
       case BL::Attribute::data_type_FLOAT_COLOR: {
         BL::FloatColorAttribute b_color_attribute{b_attribute};
+
         Attribute *attr = attributes.add(name, TypeRGBA, element);
+        if (is_render_color) {
+          attr->std = ATTR_STD_VERTEX_COLOR;
+        }
+
         float4 *data = attr->data_float4();
-        fill_generic_attribute(b_mesh, data, b_domain, [&](int i) {
+        fill_generic_attribute(b_mesh, data, b_domain, subdivision, [&](int i) {
           BL::Array<float, 4> v = b_color_attribute.data[i].color();
           return make_float4(v[0], v[1], v[2], v[3]);
         });
@@ -490,7 +521,7 @@ static void attr_create_generic(Scene *scene,
         BL::Float2Attribute b_float2_attribute{b_attribute};
         Attribute *attr = attributes.add(name, TypeFloat2, element);
         float2 *data = attr->data_float2();
-        fill_generic_at

@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list