Fix T78447: Cycles vertex color node not working with hair

This commit is contained in:
Brecht Van Lommel 2020-06-30 14:07:49 +02:00
parent 8aaca88402
commit 4e9ed1dae9
Notes: blender-bot 2023-02-13 21:56:30 +01:00
Referenced by issue #78447, Vertex Paint not showing on hair in Cycles and Viewport Vertex Color missing
4 changed files with 70 additions and 5 deletions

View File

@ -262,7 +262,7 @@ static bool ObtainCacheParticleVcol(Hair *hair,
BL::Mesh::vertex_colors_iterator l;
b_mesh->vertex_colors.begin(l);
float3 vcol = make_float3(0.0f, 0.0f, 0.0f);
float4 vcol = make_float4(0.0f, 0.0f, 0.0f, 1.0f);
if (b_mesh->vertex_colors.length())
b_psys.mcol_on_emitter(psmd, *b_pa, pa_no, vcol_num, &vcol.x);
CData->curve_vcol.push_back_slow(vcol);
@ -578,16 +578,16 @@ void BlenderSync::sync_particle_hair(
ObtainCacheParticleVcol(hair, &b_mesh, &b_ob, &CData, !preview, vcol_num);
Attribute *attr_vcol = hair->attributes.add(
ustring(l->name().c_str()), TypeDesc::TypeColor, ATTR_ELEMENT_CURVE);
ustring(l->name().c_str()), TypeRGBA, ATTR_ELEMENT_CURVE);
float3 *fdata = attr_vcol->data_float3();
float4 *fdata = attr_vcol->data_float4();
if (fdata) {
size_t i = 0;
/* Encode vertex color using the sRGB curve. */
for (size_t curve = 0; curve < CData.curve_vcol.size(); curve++) {
fdata[i++] = color_srgb_to_linear_v3(CData.curve_vcol[curve]);
fdata[i++] = color_srgb_to_linear_v4(CData.curve_vcol[curve]);
}
}
}

View File

@ -198,6 +198,66 @@ ccl_device float3 curve_attribute_float3(KernelGlobals *kg,
}
}
ccl_device float4 curve_attribute_float4(KernelGlobals *kg,
const ShaderData *sd,
const AttributeDescriptor desc,
float4 *dx,
float4 *dy)
{
if (desc.element == ATTR_ELEMENT_CURVE) {
/* idea: we can't derive any useful differentials here, but for tiled
* mipmap image caching it would be useful to avoid reading the highest
* detail level always. maybe a derivative based on the hair density
* could be computed somehow? */
# ifdef __RAY_DIFFERENTIALS__
if (dx)
*dx = make_float4(0.0f, 0.0f, 0.0f, 0.0f);
if (dy)
*dy = make_float4(0.0f, 0.0f, 0.0f, 0.0f);
# endif
return kernel_tex_fetch(__attributes_float3, desc.offset + sd->prim);
}
else if (desc.element == ATTR_ELEMENT_CURVE_KEY ||
desc.element == ATTR_ELEMENT_CURVE_KEY_MOTION) {
float4 curvedata = kernel_tex_fetch(__curves, sd->prim);
int k0 = __float_as_int(curvedata.x) + PRIMITIVE_UNPACK_SEGMENT(sd->type);
int k1 = k0 + 1;
float4 f0 = kernel_tex_fetch(__attributes_float3, desc.offset + k0);
float4 f1 = kernel_tex_fetch(__attributes_float3, desc.offset + k1);
# ifdef __RAY_DIFFERENTIALS__
if (dx)
*dx = sd->du.dx * (f1 - f0);
if (dy)
*dy = make_float4(0.0f, 0.0f, 0.0f, 0.0f);
# endif
return (1.0f - sd->u) * f0 + sd->u * f1;
}
else if (desc.element == ATTR_ELEMENT_OBJECT || desc.element == ATTR_ELEMENT_MESH) {
# ifdef __RAY_DIFFERENTIALS__
if (dx)
*dx = make_float4(0.0f, 0.0f, 0.0f, 0.0f);
if (dy)
*dy = make_float4(0.0f, 0.0f, 0.0f, 0.0f);
# endif
return kernel_tex_fetch(__attributes_float3, desc.offset);
}
else {
# ifdef __RAY_DIFFERENTIALS__
if (dx)
*dx = make_float4(0.0f, 0.0f, 0.0f, 0.0f);
if (dy)
*dy = make_float4(0.0f, 0.0f, 0.0f, 0.0f);
# endif
return make_float4(0.0f, 0.0f, 0.0f, 0.0f);
}
}
/* Curve thickness */
ccl_device float curve_thickness(KernelGlobals *kg, ShaderData *sd)

View File

@ -174,6 +174,11 @@ ccl_device_inline float4 primitive_attribute_float4(KernelGlobals *kg,
else
return subd_triangle_attribute_float4(kg, sd, desc, dx, dy);
}
#ifdef __HAIR__
else if (sd->type & PRIMITIVE_ALL_CURVE) {
return curve_attribute_float4(kg, sd, desc, dx, dy);
}
#endif
else {
if (dx)
*dx = make_float4(0.0f, 0.0f, 0.0f, 0.0f);

View File

@ -50,7 +50,7 @@ class ParticleCurveData {
array<int> curve_keynum;
array<float> curve_length;
array<float2> curve_uv;
array<float3> curve_vcol;
array<float4> curve_vcol;
array<float3> curvekey_co;
array<float> curvekey_time;