diff options
author | Stefan Werner <stefan.werner@tangent-animation.com> | 2019-03-05 17:06:09 +0300 |
---|---|---|
committer | Stefan Werner <stefan.werner@tangent-animation.com> | 2019-03-05 17:06:09 +0300 |
commit | c891fb2fbe99362ac8f3ff0821b32b84566f8f1c (patch) | |
tree | e410c45d5413058780cc6ae6b1a5033c80386c22 /intern | |
parent | cb7e66737d2d2d0628dda49ddb7d5541915d017b (diff) | |
parent | db7f9a70b0addd17a2f8a8d87c0b4d77d78b536e (diff) |
Merge branch 'blender2.7'
Diffstat (limited to 'intern')
-rw-r--r-- | intern/cycles/blender/blender_mesh.cpp | 18 | ||||
-rw-r--r-- | intern/cycles/kernel/geom/geom_curve.h | 39 | ||||
-rw-r--r-- | intern/cycles/kernel/geom/geom_patch.h | 27 | ||||
-rw-r--r-- | intern/cycles/kernel/geom/geom_primitive.h | 54 | ||||
-rw-r--r-- | intern/cycles/kernel/geom/geom_subd_triangle.h | 122 | ||||
-rw-r--r-- | intern/cycles/kernel/geom/geom_triangle.h | 47 | ||||
-rw-r--r-- | intern/cycles/kernel/kernel_textures.h | 1 | ||||
-rw-r--r-- | intern/cycles/kernel/osl/osl_services.cpp | 44 | ||||
-rw-r--r-- | intern/cycles/kernel/svm/svm_attribute.h | 47 | ||||
-rw-r--r-- | intern/cycles/kernel/svm/svm_tex_coord.h | 10 | ||||
-rw-r--r-- | intern/cycles/kernel/svm/svm_types.h | 1 | ||||
-rw-r--r-- | intern/cycles/render/attribute.cpp | 5 | ||||
-rw-r--r-- | intern/cycles/render/attribute.h | 3 | ||||
-rw-r--r-- | intern/cycles/render/mesh.cpp | 37 | ||||
-rw-r--r-- | intern/cycles/render/mesh_subdivision.cpp | 7 | ||||
-rw-r--r-- | intern/cycles/render/nodes.cpp | 2 | ||||
-rw-r--r-- | intern/cycles/render/scene.cpp | 1 | ||||
-rw-r--r-- | intern/cycles/render/scene.h | 1 | ||||
-rw-r--r-- | intern/cycles/util/util_math_float2.h | 6 | ||||
-rw-r--r-- | intern/cycles/util/util_param.h | 2 |
20 files changed, 452 insertions, 22 deletions
diff --git a/intern/cycles/blender/blender_mesh.cpp b/intern/cycles/blender/blender_mesh.cpp index 8e81e3ac121..fa61caf2e5b 100644 --- a/intern/cycles/blender/blender_mesh.cpp +++ b/intern/cycles/blender/blender_mesh.cpp @@ -66,7 +66,7 @@ struct MikkUserData { else { Attribute *attr_uv = attributes.find(ustring(layer_name)); if(attr_uv != NULL) { - texface = attr_uv->data_float3(); + texface = attr_uv->data_float2(); } } } @@ -75,7 +75,7 @@ struct MikkUserData { int num_faces; float3 *vertex_normal; - float3 *texface; + float2 *texface; float3 *orco; float3 orco_loc, orco_size; @@ -150,7 +150,7 @@ static void mikk_get_texture_coordinate(const SMikkTSpaceContext *context, const Mesh *mesh = userdata->mesh; if(userdata->texface != NULL) { const int corner_index = mikk_corner_index(mesh, face_num, vert_num); - float3 tfuv = userdata->texface[corner_index]; + float2 tfuv = userdata->texface[corner_index]; uv[0] = tfuv.x; uv[1] = tfuv.y; } @@ -435,13 +435,13 @@ static void attr_create_uv_map(Scene *scene, } BL::Mesh::loop_triangles_iterator t; - float3 *fdata = uv_attr->data_float3(); + float2 *fdata = uv_attr->data_float2(); for(b_mesh.loop_triangles.begin(t); t != b_mesh.loop_triangles.end(); ++t) { int3 li = get_int3(t->loops()); - fdata[0] = get_float3(l->data[li[0]].uv()); - fdata[1] = get_float3(l->data[li[1]].uv()); - fdata[2] = get_float3(l->data[li[2]].uv()); + fdata[0] = get_float2(l->data[li[0]].uv()); + fdata[1] = get_float2(l->data[li[1]].uv()); + fdata[2] = get_float2(l->data[li[2]].uv()); fdata += 3; } } @@ -516,12 +516,12 @@ static void attr_create_subd_uv_map(Scene *scene, } BL::Mesh::polygons_iterator p; - float3 *fdata = uv_attr->data_float3(); + float2 *fdata = uv_attr->data_float2(); for(b_mesh.polygons.begin(p); p != b_mesh.polygons.end(); ++p) { int n = p->loop_total(); for(int j = 0; j < n; j++) { - *(fdata++) = get_float3(l->data[p->loop_start() + j].uv()); + *(fdata++) = get_float2(l->data[p->loop_start() + j].uv()); } } } diff --git a/intern/cycles/kernel/geom/geom_curve.h b/intern/cycles/kernel/geom/geom_curve.h index dea0c742ed7..9b60cf6d56b 100644 --- a/intern/cycles/kernel/geom/geom_curve.h +++ b/intern/cycles/kernel/geom/geom_curve.h @@ -87,6 +87,45 @@ ccl_device float curve_attribute_float(KernelGlobals *kg, const ShaderData *sd, } } +ccl_device float2 curve_attribute_float2(KernelGlobals *kg, const ShaderData *sd, const AttributeDescriptor desc, float2 *dx, float2 *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_float2(0.0f, 0.0f); + if(dy) *dy = make_float2(0.0f, 0.0f); +#endif + + return kernel_tex_fetch(__attributes_float2, 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; + + float2 f0 = kernel_tex_fetch(__attributes_float2, desc.offset + k0); + float2 f1 = kernel_tex_fetch(__attributes_float2, desc.offset + k1); + +#ifdef __RAY_DIFFERENTIALS__ + if(dx) *dx = sd->du.dx*(f1 - f0); + if(dy) *dy = make_float2(0.0f, 0.0f); +#endif + + return (1.0f - sd->u)*f0 + sd->u*f1; + } + else { +#ifdef __RAY_DIFFERENTIALS__ + if(dx) *dx = make_float2(0.0f, 0.0f); + if(dy) *dy = make_float2(0.0f, 0.0f); +#endif + + return make_float2(0.0f, 0.0f); + } +} + ccl_device float3 curve_attribute_float3(KernelGlobals *kg, const ShaderData *sd, const AttributeDescriptor desc, float3 *dx, float3 *dy) { if(desc.element == ATTR_ELEMENT_CURVE) { diff --git a/intern/cycles/kernel/geom/geom_patch.h b/intern/cycles/kernel/geom/geom_patch.h index 0143b384aa2..edb82172959 100644 --- a/intern/cycles/kernel/geom/geom_patch.h +++ b/intern/cycles/kernel/geom/geom_patch.h @@ -284,6 +284,33 @@ ccl_device float patch_eval_float(KernelGlobals *kg, const ShaderData *sd, int o return val; } +ccl_device float2 patch_eval_float2(KernelGlobals *kg, const ShaderData *sd, int offset, + int patch, float u, float v, int channel, + float2 *du, float2 *dv) +{ + int indices[PATCH_MAX_CONTROL_VERTS]; + float weights[PATCH_MAX_CONTROL_VERTS]; + float weights_du[PATCH_MAX_CONTROL_VERTS]; + float weights_dv[PATCH_MAX_CONTROL_VERTS]; + + int num_control = patch_eval_control_verts(kg, sd->object, patch, u, v, channel, + indices, weights, weights_du, weights_dv); + + float2 val = make_float2(0.0f, 0.0f); + if(du) *du = make_float2(0.0f, 0.0f); + if(dv) *dv = make_float2(0.0f, 0.0f); + + for(int i = 0; i < num_control; i++) { + float2 v = kernel_tex_fetch(__attributes_float2, offset + indices[i]); + + val += v * weights[i]; + if(du) *du += v * weights_du[i]; + if(dv) *dv += v * weights_dv[i]; + } + + return val; +} + ccl_device float3 patch_eval_float3(KernelGlobals *kg, const ShaderData *sd, int offset, int patch, float u, float v, int channel, float3 *du, float3 *dv) diff --git a/intern/cycles/kernel/geom/geom_primitive.h b/intern/cycles/kernel/geom/geom_primitive.h index e3e2648e9ec..c9b1995ee05 100644 --- a/intern/cycles/kernel/geom/geom_primitive.h +++ b/intern/cycles/kernel/geom/geom_primitive.h @@ -89,6 +89,37 @@ ccl_device_inline float primitive_volume_attribute_float(KernelGlobals *kg, } #endif +ccl_device_inline float2 primitive_attribute_float2(KernelGlobals *kg, + const ShaderData *sd, + const AttributeDescriptor desc, + float2 *dx, float2 *dy) +{ + if(sd->type & PRIMITIVE_ALL_TRIANGLE) { + if(subd_triangle_patch(kg, sd) == ~0) + return triangle_attribute_float2(kg, sd, desc, dx, dy); + else + return subd_triangle_attribute_float2(kg, sd, desc, dx, dy); + } +#ifdef __HAIR__ + else if(sd->type & PRIMITIVE_ALL_CURVE) { + return curve_attribute_float2(kg, sd, desc, dx, dy); + } +#endif +#ifdef __VOLUME__ + else if(sd->object != OBJECT_NONE && desc.element == ATTR_ELEMENT_VOXEL) { + kernel_assert(0); + if(dx) *dx = make_float2(0.0f, 0.0f); + if(dy) *dy = make_float2(0.0f, 0.0f); + return make_float2(0.0f, 0.0f); + } +#endif + else { + if(dx) *dx = make_float2(0.0f, 0.0f); + if(dy) *dy = make_float2(0.0f, 0.0f); + return make_float2(0.0f, 0.0f); + } +} + ccl_device_inline float3 primitive_attribute_float3(KernelGlobals *kg, const ShaderData *sd, const AttributeDescriptor desc, @@ -119,6 +150,29 @@ ccl_device_inline float3 primitive_attribute_float3(KernelGlobals *kg, } } +ccl_device_inline float2 primitive_surface_attribute_float2(KernelGlobals *kg, + const ShaderData *sd, + const AttributeDescriptor desc, + float2 *dx, float2 *dy) +{ + if(sd->type & PRIMITIVE_ALL_TRIANGLE) { + if(subd_triangle_patch(kg, sd) == ~0) + return triangle_attribute_float2(kg, sd, desc, dx, dy); + else + return subd_triangle_attribute_float2(kg, sd, desc, dx, dy); + } +#ifdef __HAIR__ + else if(sd->type & PRIMITIVE_ALL_CURVE) { + return curve_attribute_float2(kg, sd, desc, dx, dy); + } +#endif + else { + if(dx) *dx = make_float2(0.0f, 0.0f); + if(dy) *dy = make_float2(0.0f, 0.0f); + return make_float2(0.0f, 0.0f); + } +} + ccl_device_inline float3 primitive_surface_attribute_float3(KernelGlobals *kg, const ShaderData *sd, const AttributeDescriptor desc, diff --git a/intern/cycles/kernel/geom/geom_subd_triangle.h b/intern/cycles/kernel/geom/geom_subd_triangle.h index 8c0d0a9770e..251e070c21f 100644 --- a/intern/cycles/kernel/geom/geom_subd_triangle.h +++ b/intern/cycles/kernel/geom/geom_subd_triangle.h @@ -216,6 +216,128 @@ ccl_device_noinline float subd_triangle_attribute_float(KernelGlobals *kg, const } } +ccl_device_noinline float2 subd_triangle_attribute_float2(KernelGlobals *kg, const ShaderData *sd, const AttributeDescriptor desc, float2 *dx, float2 *dy) +{ + int patch = subd_triangle_patch(kg, sd); + +#ifdef __PATCH_EVAL__ + if(desc.flags & ATTR_SUBDIVIDED) { + float2 uv[3]; + subd_triangle_patch_uv(kg, sd, uv); + + float2 dpdu = uv[0] - uv[2]; + float2 dpdv = uv[1] - uv[2]; + + /* p is [s, t] */ + float2 p = dpdu * sd->u + dpdv * sd->v + uv[2]; + + float2 a, dads, dadt; + + a = patch_eval_float2(kg, sd, desc.offset, patch, p.x, p.y, 0, &dads, &dadt); + +#ifdef __RAY_DIFFERENTIALS__ + if(dx || dy) { + float dsdu = dpdu.x; + float dtdu = dpdu.y; + float dsdv = dpdv.x; + float dtdv = dpdv.y; + + if(dx) { + float dudx = sd->du.dx; + float dvdx = sd->dv.dx; + + float dsdx = dsdu*dudx + dsdv*dvdx; + float dtdx = dtdu*dudx + dtdv*dvdx; + + *dx = dads*dsdx + dadt*dtdx; + } + if(dy) { + float dudy = sd->du.dy; + float dvdy = sd->dv.dy; + + float dsdy = dsdu*dudy + dsdv*dvdy; + float dtdy = dtdu*dudy + dtdv*dvdy; + + *dy = dads*dsdy + dadt*dtdy; + } + } +#endif + + return a; + } + else +#endif /* __PATCH_EVAL__ */ + if(desc.element == ATTR_ELEMENT_FACE) { + if(dx) *dx = make_float2(0.0f, 0.0f); + if(dy) *dy = make_float2(0.0f, 0.0f); + + return kernel_tex_fetch(__attributes_float2, desc.offset + subd_triangle_patch_face(kg, patch)); + } + else if(desc.element == ATTR_ELEMENT_VERTEX || desc.element == ATTR_ELEMENT_VERTEX_MOTION) { + float2 uv[3]; + subd_triangle_patch_uv(kg, sd, uv); + + uint4 v = subd_triangle_patch_indices(kg, patch); + + float2 f0 = kernel_tex_fetch(__attributes_float2, desc.offset + v.x); + float2 f1 = kernel_tex_fetch(__attributes_float2, desc.offset + v.y); + float2 f2 = kernel_tex_fetch(__attributes_float2, desc.offset + v.z); + float2 f3 = kernel_tex_fetch(__attributes_float2, desc.offset + v.w); + + if(subd_triangle_patch_num_corners(kg, patch) != 4) { + f1 = (f1+f0)*0.5f; + f3 = (f3+f0)*0.5f; + } + + float2 a = mix(mix(f0, f1, uv[0].x), mix(f3, f2, uv[0].x), uv[0].y); + float2 b = mix(mix(f0, f1, uv[1].x), mix(f3, f2, uv[1].x), uv[1].y); + float2 c = mix(mix(f0, f1, uv[2].x), mix(f3, f2, uv[2].x), uv[2].y); + +#ifdef __RAY_DIFFERENTIALS__ + if(dx) *dx = sd->du.dx*a + sd->dv.dx*b - (sd->du.dx + sd->dv.dx)*c; + if(dy) *dy = sd->du.dy*a + sd->dv.dy*b - (sd->du.dy + sd->dv.dy)*c; +#endif + + return sd->u*a + sd->v*b + (1.0f - sd->u - sd->v)*c; + } + else if(desc.element == ATTR_ELEMENT_CORNER) { + float2 uv[3]; + subd_triangle_patch_uv(kg, sd, uv); + + int corners[4]; + subd_triangle_patch_corners(kg, patch, corners); + + float2 f0, f1, f2, f3; + + f0 = kernel_tex_fetch(__attributes_float2, corners[0] + desc.offset); + f1 = kernel_tex_fetch(__attributes_float2, corners[1] + desc.offset); + f2 = kernel_tex_fetch(__attributes_float2, corners[2] + desc.offset); + f3 = kernel_tex_fetch(__attributes_float2, corners[3] + desc.offset); + + if(subd_triangle_patch_num_corners(kg, patch) != 4) { + f1 = (f1+f0)*0.5f; + f3 = (f3+f0)*0.5f; + } + + float2 a = mix(mix(f0, f1, uv[0].x), mix(f3, f2, uv[0].x), uv[0].y); + float2 b = mix(mix(f0, f1, uv[1].x), mix(f3, f2, uv[1].x), uv[1].y); + float2 c = mix(mix(f0, f1, uv[2].x), mix(f3, f2, uv[2].x), uv[2].y); + +#ifdef __RAY_DIFFERENTIALS__ + if(dx) *dx = sd->du.dx*a + sd->dv.dx*b - (sd->du.dx + sd->dv.dx)*c; + if(dy) *dy = sd->du.dy*a + sd->dv.dy*b - (sd->du.dy + sd->dv.dy)*c; +#endif + + return sd->u*a + sd->v*b + (1.0f - sd->u - sd->v)*c; + } + else { + if(dx) *dx = make_float2(0.0f, 0.0f); + if(dy) *dy = make_float2(0.0f, 0.0f); + + return make_float2(0.0f, 0.0f); + } +} + ccl_device_noinline float3 subd_triangle_attribute_float3(KernelGlobals *kg, const ShaderData *sd, const AttributeDescriptor desc, float3 *dx, float3 *dy) { int patch = subd_triangle_patch(kg, sd); diff --git a/intern/cycles/kernel/geom/geom_triangle.h b/intern/cycles/kernel/geom/geom_triangle.h index 105aee8da15..300227c38e6 100644 --- a/intern/cycles/kernel/geom/geom_triangle.h +++ b/intern/cycles/kernel/geom/geom_triangle.h @@ -149,6 +149,53 @@ ccl_device float triangle_attribute_float(KernelGlobals *kg, const ShaderData *s } } +ccl_device float2 triangle_attribute_float2(KernelGlobals *kg, const ShaderData *sd, const AttributeDescriptor desc, float2 *dx, float2 *dy) +{ + if(desc.element == ATTR_ELEMENT_FACE) { + if(dx) *dx = make_float2(0.0f, 0.0f); + if(dy) *dy = make_float2(0.0f, 0.0f); + + return kernel_tex_fetch(__attributes_float2, desc.offset + sd->prim); + } + else if(desc.element == ATTR_ELEMENT_VERTEX || desc.element == ATTR_ELEMENT_VERTEX_MOTION) { + uint4 tri_vindex = kernel_tex_fetch(__tri_vindex, sd->prim); + + float2 f0 = kernel_tex_fetch(__attributes_float2, desc.offset + tri_vindex.x); + float2 f1 = kernel_tex_fetch(__attributes_float2, desc.offset + tri_vindex.y); + float2 f2 = kernel_tex_fetch(__attributes_float2, desc.offset + tri_vindex.z); + +#ifdef __RAY_DIFFERENTIALS__ + if(dx) *dx = sd->du.dx*f0 + sd->dv.dx*f1 - (sd->du.dx + sd->dv.dx)*f2; + if(dy) *dy = sd->du.dy*f0 + sd->dv.dy*f1 - (sd->du.dy + sd->dv.dy)*f2; +#endif + + return sd->u*f0 + sd->v*f1 + (1.0f - sd->u - sd->v)*f2; + } + else if(desc.element == ATTR_ELEMENT_CORNER) { + int tri = desc.offset + sd->prim*3; + float2 f0, f1, f2; + + if(desc.element == ATTR_ELEMENT_CORNER) { + f0 = kernel_tex_fetch(__attributes_float2, tri + 0); + f1 = kernel_tex_fetch(__attributes_float2, tri + 1); + f2 = kernel_tex_fetch(__attributes_float2, tri + 2); + } + +#ifdef __RAY_DIFFERENTIALS__ + if(dx) *dx = sd->du.dx*f0 + sd->dv.dx*f1 - (sd->du.dx + sd->dv.dx)*f2; + if(dy) *dy = sd->du.dy*f0 + sd->dv.dy*f1 - (sd->du.dy + sd->dv.dy)*f2; +#endif + + return sd->u*f0 + sd->v*f1 + (1.0f - sd->u - sd->v)*f2; + } + else { + if(dx) *dx = make_float2(0.0f, 0.0f); + if(dy) *dy = make_float2(0.0f, 0.0f); + + return make_float2(0.0f, 0.0f); + } +} + ccl_device float3 triangle_attribute_float3(KernelGlobals *kg, const ShaderData *sd, const AttributeDescriptor desc, float3 *dx, float3 *dy) { if(desc.element == ATTR_ELEMENT_FACE) { diff --git a/intern/cycles/kernel/kernel_textures.h b/intern/cycles/kernel/kernel_textures.h index e83727ec64e..9eaa6b5516e 100644 --- a/intern/cycles/kernel/kernel_textures.h +++ b/intern/cycles/kernel/kernel_textures.h @@ -56,6 +56,7 @@ KERNEL_TEX(uint, __patches) /* attributes */ KERNEL_TEX(uint4, __attributes_map) KERNEL_TEX(float, __attributes_float) +KERNEL_TEX(float2, __attributes_float2) KERNEL_TEX(float4, __attributes_float3) KERNEL_TEX(uchar4, __attributes_uchar4) diff --git a/intern/cycles/kernel/osl/osl_services.cpp b/intern/cycles/kernel/osl/osl_services.cpp index 5436a66c9d4..6464d382634 100644 --- a/intern/cycles/kernel/osl/osl_services.cpp +++ b/intern/cycles/kernel/osl/osl_services.cpp @@ -392,6 +392,44 @@ bool OSLRenderServices::get_array_attribute(OSL::ShaderGlobals *sg, bool derivat return false; } +static bool set_attribute_float2(float2 f[3], TypeDesc type, bool derivatives, void *val) +{ + if(type == TypeDesc::TypePoint || type == TypeDesc::TypeVector || + type == TypeDesc::TypeNormal || type == TypeDesc::TypeColor) + { + float *fval = (float *)val; + + fval[0] = f[0].x; + fval[1] = f[0].y; + fval[2] = 0.0f; + + if(derivatives) { + fval[3] = f[1].x; + fval[4] = f[1].y; + fval[5] = 0.0f; + + fval[6] = f[2].x; + fval[7] = f[2].y; + fval[8] = 0.0f; + } + + return true; + } + else if(type == TypeDesc::TypeFloat) { + float *fval = (float *)val; + fval[0] = average(f[0]); + + if(derivatives) { + fval[1] = average(f[1]); + fval[2] = average(f[2]); + } + + return true; + } + + return false; +} + static bool set_attribute_float3(float3 f[3], TypeDesc type, bool derivatives, void *val) { if(type == TypeDesc::TypePoint || type == TypeDesc::TypeVector || @@ -572,6 +610,12 @@ static bool get_primitive_attribute(KernelGlobals *kg, const ShaderData *sd, con (derivatives) ? &fval[1] : NULL, (derivatives) ? &fval[2] : NULL); return set_attribute_float3(fval, type, derivatives, val); } + else if(attr.type == TypeFloat2) { + float2 fval[2]; + fval[0] = primitive_attribute_float2(kg, sd, attr.desc, + (derivatives) ? &fval[1] : NULL, (derivatives) ? &fval[2] : NULL); + return set_attribute_float2(fval, type, derivatives, val); + } else if(attr.type == TypeDesc::TypeFloat) { float fval[3]; fval[0] = primitive_attribute_float(kg, sd, attr.desc, diff --git a/intern/cycles/kernel/svm/svm_attribute.h b/intern/cycles/kernel/svm/svm_attribute.h index ef6f7d7cbb5..c2366df71d0 100644 --- a/intern/cycles/kernel/svm/svm_attribute.h +++ b/intern/cycles/kernel/svm/svm_attribute.h @@ -52,18 +52,27 @@ ccl_device void svm_node_attr(KernelGlobals *kg, ShaderData *sd, float *stack, u AttributeDescriptor desc = svm_node_attr_init(kg, sd, node, &type, &out_offset); /* fetch and store attribute */ - if (desc.type == NODE_ATTR_FLOAT) { + if(desc.type == NODE_ATTR_FLOAT) { float f = primitive_attribute_float(kg, sd, desc, NULL, NULL); - if (type == NODE_ATTR_FLOAT) { + if(type == NODE_ATTR_FLOAT) { stack_store_float(stack, out_offset, f); } else { stack_store_float3(stack, out_offset, make_float3(f, f, f)); } } + else if(desc.type == NODE_ATTR_FLOAT2) { + float2 f = primitive_attribute_float2(kg, sd, desc, NULL, NULL); + if(type == NODE_ATTR_FLOAT) { + stack_store_float(stack, out_offset, f.x); + } + else { + stack_store_float3(stack, out_offset, make_float3(f.x, f.y, 0.0f)); + } + } else { float3 f = primitive_attribute_float3(kg, sd, desc, NULL, NULL); - if (type == NODE_ATTR_FLOAT) { + if(type == NODE_ATTR_FLOAT) { stack_store_float(stack, out_offset, average(f)); } else { @@ -84,20 +93,30 @@ void svm_node_attr_bump_dx(KernelGlobals *kg, ShaderData *sd, float *stack, uint AttributeDescriptor desc = svm_node_attr_init(kg, sd, node, &type, &out_offset); /* fetch and store attribute */ - if (desc.type == NODE_ATTR_FLOAT) { + if(desc.type == NODE_ATTR_FLOAT) { float dx; float f = primitive_surface_attribute_float(kg, sd, desc, &dx, NULL); - if (type == NODE_ATTR_FLOAT) { + if(type == NODE_ATTR_FLOAT) { stack_store_float(stack, out_offset, f+dx); } else { stack_store_float3(stack, out_offset, make_float3(f+dx, f+dx, f+dx)); } } + else if(desc.type == NODE_ATTR_FLOAT2) { + float2 dx; + float2 f = primitive_attribute_float2(kg, sd, desc, &dx, NULL); + if (type == NODE_ATTR_FLOAT) { + stack_store_float(stack, out_offset, f.x + dx.x); + } + else { + stack_store_float3(stack, out_offset, make_float3(f.x+dx.x, f.y+dx.y, 0.0f)); + } + } else { float3 dx; float3 f = primitive_surface_attribute_float3(kg, sd, desc, &dx, NULL); - if (type == NODE_ATTR_FLOAT) { + if(type == NODE_ATTR_FLOAT) { stack_store_float(stack, out_offset, average(f+dx)); } else { @@ -121,20 +140,30 @@ void svm_node_attr_bump_dy(KernelGlobals *kg, AttributeDescriptor desc = svm_node_attr_init(kg, sd, node, &type, &out_offset); /* fetch and store attribute */ - if (desc.type == NODE_ATTR_FLOAT) { + if(desc.type == NODE_ATTR_FLOAT) { float dy; float f = primitive_surface_attribute_float(kg, sd, desc, NULL, &dy); - if (type == NODE_ATTR_FLOAT) { + if(type == NODE_ATTR_FLOAT) { stack_store_float(stack, out_offset, f+dy); } else { stack_store_float3(stack, out_offset, make_float3(f+dy, f+dy, f+dy)); } } + else if(desc.type == NODE_ATTR_FLOAT2) { + float2 dy; + float2 f = primitive_attribute_float2(kg, sd, desc, NULL, &dy); + if(type == NODE_ATTR_FLOAT) { + stack_store_float(stack, out_offset, f.x + dy.x); + } + else { + stack_store_float3(stack, out_offset, make_float3(f.x+dy.x, f.y+dy.y, 0.0f)); + } + } else { float3 dy; float3 f = primitive_surface_attribute_float3(kg, sd, desc, NULL, &dy); - if (type == NODE_ATTR_FLOAT) { + if(type == NODE_ATTR_FLOAT) { stack_store_float(stack, out_offset, average(f+dy)); } else { diff --git a/intern/cycles/kernel/svm/svm_tex_coord.h b/intern/cycles/kernel/svm/svm_tex_coord.h index 72871254f0d..fe61292d0b0 100644 --- a/intern/cycles/kernel/svm/svm_tex_coord.h +++ b/intern/cycles/kernel/svm/svm_tex_coord.h @@ -363,7 +363,15 @@ ccl_device void svm_node_tangent(KernelGlobals *kg, ShaderData *sd, float *stack float3 attribute_value; const AttributeDescriptor desc = find_attribute(kg, sd, node.z); if (desc.offset != ATTR_STD_NOT_FOUND) { - attribute_value = primitive_surface_attribute_float3(kg, sd, desc, NULL, NULL); + if(desc.type == NODE_ATTR_FLOAT2) { + float2 value = primitive_surface_attribute_float2(kg, sd, desc, NULL, NULL); + attribute_value.x = value.x; + attribute_value.y = value.y; + attribute_value.z = 0.0f; + } + else { + attribute_value = primitive_surface_attribute_float3(kg, sd, desc, NULL, NULL); + } } diff --git a/intern/cycles/kernel/svm/svm_types.h b/intern/cycles/kernel/svm/svm_types.h index 0f1dfa4936b..8b15d7bf9f4 100644 --- a/intern/cycles/kernel/svm/svm_types.h +++ b/intern/cycles/kernel/svm/svm_types.h @@ -141,6 +141,7 @@ typedef enum ShaderNodeType { typedef enum NodeAttributeType { NODE_ATTR_FLOAT = 0, + NODE_ATTR_FLOAT2, NODE_ATTR_FLOAT3, NODE_ATTR_MATRIX } NodeAttributeType; diff --git a/intern/cycles/render/attribute.cpp b/intern/cycles/render/attribute.cpp index ca167a7c722..70f75a4b573 100644 --- a/intern/cycles/render/attribute.cpp +++ b/intern/cycles/render/attribute.cpp @@ -48,7 +48,8 @@ void Attribute::set(ustring name_, TypeDesc type_, AttributeElement element_) /* string and matrix not supported! */ assert(type == TypeDesc::TypeFloat || type == TypeDesc::TypeColor || type == TypeDesc::TypePoint || type == TypeDesc::TypeVector || - type == TypeDesc::TypeNormal || type == TypeDesc::TypeMatrix); + type == TypeDesc::TypeNormal || type == TypeDesc::TypeMatrix || + type == TypeFloat2); } void Attribute::resize(Mesh *mesh, AttributePrimitive prim, bool reserve_only) @@ -400,7 +401,7 @@ Attribute *AttributeSet::add(AttributeStandard std, ustring name) attr = add(name, TypeDesc::TypeNormal, ATTR_ELEMENT_FACE); break; case ATTR_STD_UV: - attr = add(name, TypeDesc::TypePoint, ATTR_ELEMENT_CORNER); + attr = add(name, TypeFloat2, ATTR_ELEMENT_CORNER); break; case ATTR_STD_UV_TANGENT: attr = add(name, TypeDesc::TypeVector, ATTR_ELEMENT_CORNER); diff --git a/intern/cycles/render/attribute.h b/intern/cycles/render/attribute.h index e7438f4513d..9a92d98b713 100644 --- a/intern/cycles/render/attribute.h +++ b/intern/cycles/render/attribute.h @@ -67,6 +67,7 @@ public: size_t buffer_size(Mesh *mesh, AttributePrimitive prim) const; char *data() { return (buffer.size())? &buffer[0]: NULL; }; + float2 *data_float2() { return (float2*)data(); } float3 *data_float3() { return (float3*)data(); } float4 *data_float4() { return (float4*)data(); } float *data_float() { return (float*)data(); } @@ -75,6 +76,7 @@ public: VoxelAttribute *data_voxel() { return ( VoxelAttribute*)data(); } const char *data() const { return (buffer.size())? &buffer[0]: NULL; } + const float2 *data_float2() const { return (const float2*)data(); } const float3 *data_float3() const { return (const float3*)data(); } const float4 *data_float4() const { return (const float4*)data(); } const float *data_float() const { return (const float*)data(); } @@ -85,6 +87,7 @@ public: void add_with_weight(void* dst, void* src, float weight); void add(const float& f); + void add(const float2& f); void add(const float3& f); void add(const uchar4& f); void add(const Transform& f); diff --git a/intern/cycles/render/mesh.cpp b/intern/cycles/render/mesh.cpp index 955fa390e06..f0b06a1e14a 100644 --- a/intern/cycles/render/mesh.cpp +++ b/intern/cycles/render/mesh.cpp @@ -1209,6 +1209,8 @@ void MeshManager::update_osl_attributes(Device *device, Scene *scene, vector<Att osl_attr.type = TypeDesc::TypeFloat; else if(req.triangle_type == TypeDesc::TypeMatrix) osl_attr.type = TypeDesc::TypeMatrix; + else if(req.triangle_type == TypeFloat2) + osl_attr.type = TypeFloat2; else osl_attr.type = TypeDesc::TypeColor; @@ -1318,6 +1320,8 @@ void MeshManager::update_svm_attributes(Device *, DeviceScene *dscene, Scene *sc attr_map[index].w = NODE_ATTR_FLOAT; else if(req.triangle_type == TypeDesc::TypeMatrix) attr_map[index].w = NODE_ATTR_MATRIX; + else if(req.triangle_type == TypeFloat2) + attr_map[index].w = NODE_ATTR_FLOAT2; else attr_map[index].w = NODE_ATTR_FLOAT3; @@ -1335,6 +1339,8 @@ void MeshManager::update_svm_attributes(Device *, DeviceScene *dscene, Scene *sc attr_map[index].w = NODE_ATTR_FLOAT; else if(req.curve_type == TypeDesc::TypeMatrix) attr_map[index].w = NODE_ATTR_MATRIX; + else if(req.curve_type == TypeFloat2) + attr_map[index].w = NODE_ATTR_FLOAT2; else attr_map[index].w = NODE_ATTR_FLOAT3; @@ -1352,6 +1358,8 @@ void MeshManager::update_svm_attributes(Device *, DeviceScene *dscene, Scene *sc attr_map[index].w = NODE_ATTR_FLOAT; else if(req.subd_type == TypeDesc::TypeMatrix) attr_map[index].w = NODE_ATTR_MATRIX; + else if(req.subd_type == TypeFloat2) + attr_map[index].w = NODE_ATTR_FLOAT2; else attr_map[index].w = NODE_ATTR_FLOAT3; @@ -1380,6 +1388,7 @@ static void update_attribute_element_size(Mesh *mesh, Attribute *mattr, AttributePrimitive prim, size_t *attr_float_size, + size_t *attr_float2_size, size_t *attr_float3_size, size_t *attr_uchar4_size) { @@ -1395,6 +1404,9 @@ static void update_attribute_element_size(Mesh *mesh, else if(mattr->type == TypeDesc::TypeFloat) { *attr_float_size += size; } + else if(mattr->type == TypeFloat2) { + *attr_float2_size += size; + } else if(mattr->type == TypeDesc::TypeMatrix) { *attr_float3_size += size * 4; } @@ -1407,6 +1419,8 @@ static void update_attribute_element_size(Mesh *mesh, static void update_attribute_element_offset(Mesh *mesh, device_vector<float>& attr_float, size_t& attr_float_offset, + device_vector<float2>& attr_float2, + size_t& attr_float2_offset, device_vector<float4>& attr_float3, size_t& attr_float3_offset, device_vector<uchar4>& attr_uchar4, @@ -1453,6 +1467,16 @@ static void update_attribute_element_offset(Mesh *mesh, } attr_float_offset += size; } + else if(mattr->type == TypeFloat2) { + float2 *data = mattr->data_float2(); + offset = attr_float2_offset; + + assert(attr_float2.size() >= offset + size); + for(size_t k = 0; k < size; k++) { + attr_float2[offset+k] = data[k]; + } + attr_float2_offset += size; + } else if(mattr->type == TypeDesc::TypeMatrix) { Transform *tfm = mattr->data_transform(); offset = attr_float3_offset; @@ -1537,6 +1561,7 @@ void MeshManager::device_update_attributes(Device *device, DeviceScene *dscene, * take 2x of overall attribute memory usage. */ size_t attr_float_size = 0; + size_t attr_float2_size = 0; size_t attr_float3_size = 0; size_t attr_uchar4_size = 0; for(size_t i = 0; i < scene->meshes.size(); i++) { @@ -1551,28 +1576,33 @@ void MeshManager::device_update_attributes(Device *device, DeviceScene *dscene, triangle_mattr, ATTR_PRIM_TRIANGLE, &attr_float_size, + &attr_float2_size, &attr_float3_size, &attr_uchar4_size); update_attribute_element_size(mesh, curve_mattr, ATTR_PRIM_CURVE, &attr_float_size, + &attr_float2_size, &attr_float3_size, &attr_uchar4_size); update_attribute_element_size(mesh, subd_mattr, ATTR_PRIM_SUBD, &attr_float_size, + &attr_float2_size, &attr_float3_size, &attr_uchar4_size); } } dscene->attributes_float.alloc(attr_float_size); + dscene->attributes_float2.alloc(attr_float2_size); dscene->attributes_float3.alloc(attr_float3_size); dscene->attributes_uchar4.alloc(attr_uchar4_size); size_t attr_float_offset = 0; + size_t attr_float2_offset = 0; size_t attr_float3_offset = 0; size_t attr_uchar4_offset = 0; @@ -1590,6 +1620,7 @@ void MeshManager::device_update_attributes(Device *device, DeviceScene *dscene, update_attribute_element_offset(mesh, dscene->attributes_float, attr_float_offset, + dscene->attributes_float2, attr_float2_offset, dscene->attributes_float3, attr_float3_offset, dscene->attributes_uchar4, attr_uchar4_offset, triangle_mattr, @@ -1599,6 +1630,7 @@ void MeshManager::device_update_attributes(Device *device, DeviceScene *dscene, update_attribute_element_offset(mesh, dscene->attributes_float, attr_float_offset, + dscene->attributes_float2, attr_float2_offset, dscene->attributes_float3, attr_float3_offset, dscene->attributes_uchar4, attr_uchar4_offset, curve_mattr, @@ -1608,6 +1640,7 @@ void MeshManager::device_update_attributes(Device *device, DeviceScene *dscene, update_attribute_element_offset(mesh, dscene->attributes_float, attr_float_offset, + dscene->attributes_float2, attr_float2_offset, dscene->attributes_float3, attr_float3_offset, dscene->attributes_uchar4, attr_uchar4_offset, subd_mattr, @@ -1633,6 +1666,9 @@ void MeshManager::device_update_attributes(Device *device, DeviceScene *dscene, if(dscene->attributes_float.size()) { dscene->attributes_float.copy_to_device(); } + if(dscene->attributes_float2.size()) { + dscene->attributes_float2.copy_to_device(); + } if(dscene->attributes_float3.size()) { dscene->attributes_float3.copy_to_device(); } @@ -2265,6 +2301,7 @@ void MeshManager::device_free(Device *device, DeviceScene *dscene) dscene->patches.free(); dscene->attributes_map.free(); dscene->attributes_float.free(); + dscene->attributes_float2.free(); dscene->attributes_float3.free(); dscene->attributes_uchar4.free(); diff --git a/intern/cycles/render/mesh_subdivision.cpp b/intern/cycles/render/mesh_subdivision.cpp index 13fda99e9cc..95cc6f1fca1 100644 --- a/intern/cycles/render/mesh_subdivision.cpp +++ b/intern/cycles/render/mesh_subdivision.cpp @@ -231,6 +231,9 @@ public: if(attr.same_storage(attr.type, TypeDesc::TypeFloat)) { primvar_refiner.Interpolate(i+1, (OsdValue<float>*)src, (OsdValue<float>*&)dest); } + else if(attr.same_storage(attr.type, TypeFloat2)) { + primvar_refiner.Interpolate(i+1, (OsdValue<float2>*)src, (OsdValue<float2>*&)dest); + } else { primvar_refiner.Interpolate(i+1, (OsdValue<float4>*)src, (OsdValue<float4>*&)dest); } @@ -243,6 +246,10 @@ public: patch_table->ComputeLocalPointValues((OsdValue<float>*)&attr.buffer[0], (OsdValue<float>*)&attr.buffer[num_refiner_verts * attr.data_sizeof()]); } + else if(attr.same_storage(attr.type, TypeFloat2)) { + patch_table->ComputeLocalPointValues((OsdValue<float2>*)&attr.buffer[0], + (OsdValue<float2>*)&attr.buffer[num_refiner_verts * attr.data_sizeof()]); + } else { patch_table->ComputeLocalPointValues((OsdValue<float4>*)&attr.buffer[0], (OsdValue<float4>*)&attr.buffer[num_refiner_verts * attr.data_sizeof()]); diff --git a/intern/cycles/render/nodes.cpp b/intern/cycles/render/nodes.cpp index b70bad810de..fcdfb62785a 100644 --- a/intern/cycles/render/nodes.cpp +++ b/intern/cycles/render/nodes.cpp @@ -3480,7 +3480,7 @@ void TextureCoordinateNode::compile(SVMCompiler& compiler) } else { int attr = compiler.attribute(ATTR_STD_UV); - compiler.add_node(attr_node, attr, compiler.stack_assign(out), NODE_ATTR_FLOAT3); + compiler.add_node(attr_node, attr, compiler.stack_assign(out), NODE_ATTR_FLOAT2); } } diff --git a/intern/cycles/render/scene.cpp b/intern/cycles/render/scene.cpp index 23233b4e29e..1f551f206ef 100644 --- a/intern/cycles/render/scene.cpp +++ b/intern/cycles/render/scene.cpp @@ -66,6 +66,7 @@ DeviceScene::DeviceScene(Device *device) camera_motion(device, "__camera_motion", MEM_TEXTURE), attributes_map(device, "__attributes_map", MEM_TEXTURE), attributes_float(device, "__attributes_float", MEM_TEXTURE), + attributes_float2(device, "__attributes_float2", MEM_TEXTURE), attributes_float3(device, "__attributes_float3", MEM_TEXTURE), attributes_uchar4(device, "__attributes_uchar4", MEM_TEXTURE), light_distribution(device, "__light_distribution", MEM_TEXTURE), diff --git a/intern/cycles/render/scene.h b/intern/cycles/render/scene.h index 69cbfe9a324..e43800fe5c4 100644 --- a/intern/cycles/render/scene.h +++ b/intern/cycles/render/scene.h @@ -98,6 +98,7 @@ public: /* attributes */ device_vector<uint4> attributes_map; device_vector<float> attributes_float; + device_vector<float2> attributes_float2; device_vector<float4> attributes_float3; device_vector<uchar4> attributes_uchar4; diff --git a/intern/cycles/util/util_math_float2.h b/intern/cycles/util/util_math_float2.h index e937509367f..6fe8e3b4115 100644 --- a/intern/cycles/util/util_math_float2.h +++ b/intern/cycles/util/util_math_float2.h @@ -220,6 +220,12 @@ ccl_device_inline float2 interp(const float2& a, const float2& b, float t) { return a + t*(b - a); } + +ccl_device_inline float2 mix(const float2& a, const float2& b, float t) +{ + return a + t*(b - a); +} + #endif /* !__KERNEL_OPENCL__ */ CCL_NAMESPACE_END diff --git a/intern/cycles/util/util_param.h b/intern/cycles/util/util_param.h index 4453c66aae2..03815486429 100644 --- a/intern/cycles/util/util_param.h +++ b/intern/cycles/util/util_param.h @@ -28,6 +28,8 @@ CCL_NAMESPACE_BEGIN OIIO_NAMESPACE_USING +static constexpr TypeDesc TypeFloat2(TypeDesc::FLOAT, TypeDesc::VEC2); + CCL_NAMESPACE_END #endif /* __UTIL_PARAM_H__ */ |