Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/intern
diff options
context:
space:
mode:
authorBrecht Van Lommel <brecht@blender.org>2022-05-27 16:45:29 +0300
committerBrecht Van Lommel <brecht@blender.org>2022-05-27 17:55:49 +0300
commit3a4f2131c2d2bc30aec6e74bdfe985c1ec498768 (patch)
tree63733557bc341437d0bbfa82f7edb5bc515ea98d /intern
parentbf6aa5d63d2d775b948966965f01e400650730ea (diff)
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.
Diffstat (limited to 'intern')
-rw-r--r--intern/cycles/blender/mesh.cpp234
1 files changed, 100 insertions, 134 deletions
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_attribute(b_mesh, data, b_domain, [&](int i) {
+ fill_generic_attribute(b_mesh, data, b_domain, subdivision, [&](int i) {
BL::Array<float, 2> v = b_float2_attribute.data[i].vector();
return make_float2(v[0], v[1]);
});
@@ -503,69 +534,6 @@ static void attr_create_generic(Scene *scene,
}
}
-/* Create vertex color attributes. */
-static void attr_create_vertex_color(Scene *scene, Mesh *mesh, BL::Mesh &b_mesh, bool subdivision)
-{
- for (BL::MeshLoopColorLayer &l : b_mesh.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;
- }
-
- Attribute *vcol_attr = NULL;
-
- if (subdivision) {
- if (active_render) {
- vcol_attr = mesh->subd_attributes.add(vcol_std, vcol_name);
- }
- else {
- vcol_attr = mesh->subd_attributes.add(vcol_name, TypeRGBA, ATTR_ELEMENT_CORNER_BYTE);
- }
-
- uchar4 *cdata = vcol_attr->data_uchar4();
-
- for (BL::MeshPolygon &p : b_mesh.polygons) {
- int n = p.loop_total();
- for (int i = 0; i < n; i++) {
- float4 color = get_float4(l.data[p.loop_start() + i].color());
- /* Compress/encode vertex color using the sRGB curve. */
- *(cdata++) = color_float4_to_uchar4(color);
- }
- }
- }
- else {
- if (active_render) {
- vcol_attr = mesh->attributes.add(vcol_std, vcol_name);
- }
- else {
- vcol_attr = mesh->attributes.add(vcol_name, TypeRGBA, ATTR_ELEMENT_CORNER_BYTE);
- }
-
- uchar4 *cdata = vcol_attr->data_uchar4();
-
- for (BL::MeshLoopTriangle &t : b_mesh.loop_triangles) {
- int3 li = get_int3(t.loops());
- float4 c1 = get_float4(l.data[li[0]].color());
- float4 c2 = get_float4(l.data[li[1]].color());
- float4 c3 = get_float4(l.data[li[2]].color());
-
- /* Compress/encode vertex color using the sRGB curve. */
- cdata[0] = color_float4_to_uchar4(c1);
- cdata[1] = color_float4_to_uchar4(c2);
- cdata[2] = color_float4_to_uchar4(c3);
-
- cdata += 3;
- }
- }
- }
-}
-
/* Create uv map attributes. */
static void attr_create_uv_map(Scene *scene, Mesh *mesh, BL::Mesh &b_mesh)
{
@@ -1029,8 +997,6 @@ static void create_mesh(Scene *scene,
* The calculate functions will check whether they're needed or not.
*/
attr_create_pointiness(scene, mesh, b_mesh, subdivision);
- attr_create_vertex_color(scene, mesh, b_mesh, subdivision);
- attr_create_sculpt_vertex_color(scene, mesh, b_mesh, subdivision);
attr_create_random_per_island(scene, mesh, b_mesh, subdivision);
attr_create_generic(scene, mesh, b_mesh, subdivision, need_motion, motion_scale);