From 49df707496e505c8a8b21c1ea36b479e950cc66c Mon Sep 17 00:00:00 2001 From: Thomas Dinges Date: Fri, 13 Jun 2014 21:27:21 +0200 Subject: Cycles: Calculate face normal on the fly. Instead of pre-calculation and storage, we now calculate the face normal during render. This gives a small slowdown (~1%) but decreases memory usage, which is especially important for GPUs, where you have limited VRAM. Part of my GSoC 2014. --- intern/cycles/kernel/geom/geom_bvh_shadow.h | 3 +-- intern/cycles/kernel/geom/geom_motion_triangle.h | 3 +-- intern/cycles/kernel/geom/geom_triangle.h | 22 +++++++++++++++++++--- 3 files changed, 21 insertions(+), 7 deletions(-) (limited to 'intern/cycles/kernel/geom') diff --git a/intern/cycles/kernel/geom/geom_bvh_shadow.h b/intern/cycles/kernel/geom/geom_bvh_shadow.h index 48876da049e..1f6e4942fab 100644 --- a/intern/cycles/kernel/geom/geom_bvh_shadow.h +++ b/intern/cycles/kernel/geom/geom_bvh_shadow.h @@ -252,8 +252,7 @@ ccl_device bool BVH_FUNCTION_NAME if(kernel_tex_fetch(__prim_type, isect_array->prim) & PRIMITIVE_ALL_TRIANGLE) #endif { - float4 Ns = kernel_tex_fetch(__tri_normal, prim); - shader = __float_as_int(Ns.w); + shader = __float_as_int(kernel_tex_fetch(__tri_shader, prim)); } #ifdef __HAIR__ else { diff --git a/intern/cycles/kernel/geom/geom_motion_triangle.h b/intern/cycles/kernel/geom/geom_motion_triangle.h index 73fcf1adda6..5ab0b731bdd 100644 --- a/intern/cycles/kernel/geom/geom_motion_triangle.h +++ b/intern/cycles/kernel/geom/geom_motion_triangle.h @@ -233,8 +233,7 @@ ccl_device_inline float3 motion_triangle_refine_subsurface(KernelGlobals *kg, Sh ccl_device_noinline void motion_triangle_shader_setup(KernelGlobals *kg, ShaderData *sd, const Intersection *isect, const Ray *ray, bool subsurface) { /* get shader */ - float4 Ns = kernel_tex_fetch(__tri_normal, sd->prim); - sd->shader = __float_as_int(Ns.w); + sd->shader = __float_as_int(kernel_tex_fetch(__tri_shader, sd->prim)); /* get motion info */ int numsteps, numverts; diff --git a/intern/cycles/kernel/geom/geom_triangle.h b/intern/cycles/kernel/geom/geom_triangle.h index 355e36fef0c..4ee5d5aa6d5 100644 --- a/intern/cycles/kernel/geom/geom_triangle.h +++ b/intern/cycles/kernel/geom/geom_triangle.h @@ -116,6 +116,20 @@ ccl_device_inline float3 triangle_refine_subsurface(KernelGlobals *kg, ShaderDat #endif } +/* normal on triangle */ +ccl_device_inline float3 triangle_normal(KernelGlobals *kg, int prim) +{ + /* load triangle vertices */ + float3 tri_vindex = float4_to_float3(kernel_tex_fetch(__tri_vindex, prim)); + + float3 v0 = float4_to_float3(kernel_tex_fetch(__tri_verts, __float_as_int(tri_vindex.x))); + float3 v1 = float4_to_float3(kernel_tex_fetch(__tri_verts, __float_as_int(tri_vindex.y))); + float3 v2 = float4_to_float3(kernel_tex_fetch(__tri_verts, __float_as_int(tri_vindex.z))); + + /* return normal */ + return normalize(cross(v1 - v0, v2 - v0)); +} + /* point and normal on triangle */ ccl_device_inline void triangle_point_normal(KernelGlobals *kg, int prim, float u, float v, float3 *P, float3 *Ng, int *shader) { @@ -130,9 +144,11 @@ ccl_device_inline void triangle_point_normal(KernelGlobals *kg, int prim, float float t = 1.0f - u - v; *P = (u*v0 + v*v1 + t*v2); - float4 Nm = kernel_tex_fetch(__tri_normal, prim); - *Ng = make_float3(Nm.x, Nm.y, Nm.z); - *shader = __float_as_int(Nm.w); + /* compute normal */ + *Ng = normalize(cross(v1 - v0, v2 - v0)); + + /* shader`*/ + *shader = __float_as_int(kernel_tex_fetch(__tri_shader, prim)); } /* Triangle vertex locations */ -- cgit v1.2.3