Fix #32900: object motion blur not working on the GPU. To make this work I disabled...
authorBrecht Van Lommel <brechtvanlommel@pandora.be>
Thu, 29 Nov 2012 00:43:50 +0000 (00:43 +0000)
committerBrecht Van Lommel <brechtvanlommel@pandora.be>
Thu, 29 Nov 2012 00:43:50 +0000 (00:43 +0000)
blurring of scale animation, probably not a big loss in practice since it's not so common
to animate this, can be added back later.

intern/cycles/kernel/kernel_camera.h
intern/cycles/kernel/kernel_object.h
intern/cycles/kernel/kernel_types.h
intern/cycles/render/camera.cpp
intern/cycles/render/object.cpp
intern/cycles/util/util_transform.cpp
intern/cycles/util/util_transform.h

index abc63d99c74ae7de04ae324abfe43c3fb365f5f4..97d37a8b3f4a3033704aaeca9505c8fb00a3a214 100644 (file)
@@ -65,7 +65,7 @@ __device void camera_sample_perspective(KernelGlobals *kg, float raster_x, float
 
 #ifdef __CAMERA_MOTION__
        if(kernel_data.cam.have_motion)
-               transform_motion_interpolate(&cameratoworld, &kernel_data.cam.motion, ray->time);
+               transform_motion_interpolate(&cameratoworld, (const DecompMotionTransform*)&kernel_data.cam.motion, ray->time);
 #endif
 
        ray->P = transform_point(&cameratoworld, ray->P);
@@ -108,7 +108,7 @@ __device void camera_sample_orthographic(KernelGlobals *kg, float raster_x, floa
 
 #ifdef __CAMERA_MOTION__
        if(kernel_data.cam.have_motion)
-               transform_motion_interpolate(&cameratoworld, &kernel_data.cam.motion, ray->time);
+               transform_motion_interpolate(&cameratoworld, (const DecompMotionTransform*)&kernel_data.cam.motion, ray->time);
 #endif
 
        ray->P = transform_point(&cameratoworld, ray->P);
@@ -182,7 +182,7 @@ __device void camera_sample_panorama(KernelGlobals *kg, float raster_x, float ra
 
 #ifdef __CAMERA_MOTION__
        if(kernel_data.cam.have_motion)
-               transform_motion_interpolate(&cameratoworld, &kernel_data.cam.motion, ray->time);
+               transform_motion_interpolate(&cameratoworld, (const DecompMotionTransform*)&kernel_data.cam.motion, ray->time);
 #endif
 
        ray->P = transform_point(&cameratoworld, ray->P);
index 112bfbb86b5ae27ebc59b3697413da1ee87e2565..2b38544e527198c5338ee853b7e460f7c2963802 100644 (file)
@@ -23,9 +23,8 @@ enum ObjectTransform {
        OBJECT_INVERSE_TRANSFORM = 3,
        OBJECT_PROPERTIES = 6,
        OBJECT_TRANSFORM_MOTION_PRE = 8,
-       OBJECT_TRANSFORM_MOTION_MID = 12,
-       OBJECT_TRANSFORM_MOTION_POST = 16,
-       OBJECT_DUPLI = 20
+       OBJECT_TRANSFORM_MOTION_POST = 12,
+       OBJECT_DUPLI = 16
 };
 
 __device_inline Transform object_fetch_transform(KernelGlobals *kg, int object, enum ObjectTransform type)
@@ -44,24 +43,19 @@ __device_inline Transform object_fetch_transform(KernelGlobals *kg, int object,
 #ifdef __OBJECT_MOTION__
 __device_inline Transform object_fetch_transform_motion(KernelGlobals *kg, int object, float time)
 {
-       MotionTransform motion;
+       DecompMotionTransform motion;
 
        int offset = object*OBJECT_SIZE + (int)OBJECT_TRANSFORM_MOTION_PRE;
 
-       motion.pre.x = kernel_tex_fetch(__objects, offset + 0);
-       motion.pre.y = kernel_tex_fetch(__objects, offset + 1);
-       motion.pre.z = kernel_tex_fetch(__objects, offset + 2);
-       motion.pre.w = kernel_tex_fetch(__objects, offset + 3);
+       motion.mid.x = kernel_tex_fetch(__objects, offset + 0);
+       motion.mid.y = kernel_tex_fetch(__objects, offset + 1);
+       motion.mid.z = kernel_tex_fetch(__objects, offset + 2);
+       motion.mid.w = kernel_tex_fetch(__objects, offset + 3);
 
-       motion.mid.x = kernel_tex_fetch(__objects, offset + 4);
-       motion.mid.y = kernel_tex_fetch(__objects, offset + 5);
-       motion.mid.z = kernel_tex_fetch(__objects, offset + 6);
-       motion.mid.w = kernel_tex_fetch(__objects, offset + 7);
-
-       motion.post.x = kernel_tex_fetch(__objects, offset + 8);
-       motion.post.y = kernel_tex_fetch(__objects, offset + 9);
-       motion.post.z = kernel_tex_fetch(__objects, offset + 10);
-       motion.post.w = kernel_tex_fetch(__objects, offset + 11);
+       motion.pre_x = kernel_tex_fetch(__objects, offset + 4);
+       motion.pre_y = kernel_tex_fetch(__objects, offset + 5);
+       motion.post_x = kernel_tex_fetch(__objects, offset + 6);
+       motion.post_y = kernel_tex_fetch(__objects, offset + 7);
 
        Transform tfm;
        transform_motion_interpolate(&tfm, &motion, time);
index 977fb8c4fd4bb52ef238396c400627d8a10152d6..a7bf6b28e7e56655324381b80bde29d2ee40ae6c 100644 (file)
@@ -29,7 +29,7 @@
 CCL_NAMESPACE_BEGIN
 
 /* constants */
-#define OBJECT_SIZE            22
+#define OBJECT_SIZE            18
 #define LIGHT_SIZE                     4
 #define FILTER_TABLE_SIZE      256
 #define RAMP_TABLE_SIZE                256
@@ -112,13 +112,9 @@ CCL_NAMESPACE_BEGIN
 #define __AO__
 #define __CAMERA_MOTION__
 #define __ANISOTROPIC__
-
-#ifndef __KERNEL_CUDA__
 #define __OBJECT_MOTION__
 #endif
 
-#endif
-
 //#define __SOBOL_FULL_SCREEN__
 
 /* Shader Evaluation */
index 32c273c12485155c587856a3167ed9c7ff6e740e..a78ede979b23cfa1d5b735c559259311c5f4b3e6 100644 (file)
@@ -202,7 +202,7 @@ void Camera::device_update(Device *device, DeviceScene *dscene, Scene *scene)
 #ifdef __CAMERA_MOTION__
        else if(need_motion == Scene::MOTION_BLUR) {
                if(use_motion) {
-                       transform_motion_decompose(&kcam->motion, &motion, &matrix);
+                       transform_motion_decompose((DecompMotionTransform*)&kcam->motion, &motion, &matrix);
                        kcam->have_motion = 1;
                }
        }
index 25b4d1f08cc7f874fd35b155d11edcff04c3e64d..d08cb07fc3c3377c4546ed24bc83120171f7d201 100644 (file)
@@ -56,7 +56,7 @@ void Object::compute_bounds(bool motion_blur, float shuttertime)
        BoundBox mbounds = mesh->bounds;
 
        if(motion_blur && use_motion) {
-               MotionTransform decomp;
+               DecompMotionTransform decomp;
                transform_motion_decompose(&decomp, &motion, &tfm);
 
                bounds = BoundBox::empty;
@@ -222,29 +222,29 @@ void ObjectManager::device_update_transforms(Device *device, DeviceScene *dscene
                                mtfm_post = mtfm_post * itfm;
 
                        memcpy(&objects[offset+8], &mtfm_pre, sizeof(float4)*4);
-                       memcpy(&objects[offset+16], &mtfm_post, sizeof(float4)*4);
+                       memcpy(&objects[offset+12], &mtfm_post, sizeof(float4)*4);
                }
 #ifdef __OBJECT_MOTION__
                else if(need_motion == Scene::MOTION_BLUR) {
                        if(ob->use_motion) {
                                /* decompose transformations for interpolation */
-                               MotionTransform decomp;
+                               DecompMotionTransform decomp;
 
                                transform_motion_decompose(&decomp, &ob->motion, &ob->tfm);
-                               memcpy(&objects[offset+8], &decomp, sizeof(float4)*12);
+                               memcpy(&objects[offset+8], &decomp, sizeof(float4)*8);
                                flag |= SD_OBJECT_MOTION;
                                have_motion = true;
                        }
                        else {
                                float4 no_motion = make_float4(FLT_MAX);
-                               memcpy(&objects[offset+8], &no_motion, sizeof(float4)*12);
+                               memcpy(&objects[offset+8], &no_motion, sizeof(float4)*8);
                        }
                }
 #endif
 
                /* dupli object coords */
-               objects[offset+20] = make_float4(ob->dupli_generated[0], ob->dupli_generated[1], ob->dupli_generated[2], 0.0f);
-               objects[offset+21] = make_float4(ob->dupli_uv[0], ob->dupli_uv[1], 0.0f, 0.0f);
+               objects[offset+16] = make_float4(ob->dupli_generated[0], ob->dupli_generated[1], ob->dupli_generated[2], 0.0f);
+               objects[offset+17] = make_float4(ob->dupli_uv[0], ob->dupli_uv[1], 0.0f, 0.0f);
 
                /* object flag */
                if(ob->use_holdout)
index 4eee024990f6eb827b897027eb69c9f9dabff643..ca19146e1252a3fe35045a8a140cb040e5fbf857 100644 (file)
@@ -246,18 +246,30 @@ static void transform_decompose(Transform *decomp, const Transform *tfm)
        decomp->w = make_float4(scale.y.z, scale.z.x, scale.z.y, scale.z.z);
 }
 
-void transform_motion_decompose(MotionTransform *decomp, const MotionTransform *motion, const Transform *mid)
+void transform_motion_decompose(DecompMotionTransform *decomp, const MotionTransform *motion, const Transform *mid)
 {
-       transform_decompose(&decomp->pre, &motion->pre);
+       Transform pre, post;
+
+       transform_decompose(&pre, &motion->pre);
        transform_decompose(&decomp->mid, mid);
-       transform_decompose(&decomp->post, &motion->post);
+       transform_decompose(&post, &motion->post);
 
        /* ensure rotation around shortest angle, negated quaternions are the same
         * but this means we don't have to do the check in quat_interpolate */
-       if(dot(decomp->mid.x, decomp->post.x) < 0.0f)
+       if(dot(decomp->mid.x, post.x) < 0.0f)
                decomp->mid.x = -decomp->mid.x;
-       if(dot(decomp->pre.x, decomp->mid.x) < 0.0f)
-               decomp->pre.x = -decomp->pre.x;
+       if(dot(pre.x, decomp->mid.x) < 0.0f)
+               pre.x = -pre.x;
+       
+       /* drop scale of pre/post */
+       pre.y.w = decomp->mid.y.w;
+       post.y.w = decomp->mid.y.w;
+
+       /* store translation/rotation part of pre/post */
+       decomp->pre_x = pre.x;
+       decomp->pre_y = pre.y;
+       decomp->post_x = post.x;
+       decomp->post_y = post.y;
 }
 
 CCL_NAMESPACE_END
index 65162ebf4e6c8a17f49d56b9c49d4fa243736515..dbf88cb67a0c8ecd31273dd4bc81e3eaede9761d 100644 (file)
@@ -41,7 +41,9 @@ typedef struct Transform {
 
 /* transform decomposed in rotation/translation/scale. we use the same data
  * structure as Transform, and tightly pack decomposition into it. first the
- * rotation (4), then translation (3), then 3x3 scale matrix (9) */
+ * rotation (4), then translation (3), then 3x3 scale matrix (9).
+ *
+ * For the DecompMotionTransform we drop scale from pre/post. */
 
 typedef struct MotionTransform {
        Transform pre;
@@ -49,6 +51,12 @@ typedef struct MotionTransform {
        Transform post;
 } MotionTransform;
 
+typedef struct DecompMotionTransform {
+       Transform mid;
+       float4 pre_x, pre_y;
+       float4 post_x, post_y;
+} DecompMotionTransform;
+
 /* Functions */
 
 __device_inline float3 transform_perspective(const Transform *t, const float3 a)
@@ -384,7 +392,7 @@ __device_inline void transform_compose(Transform *tfm, const Transform *decomp)
 /* Disabled for now, need arc-length parametrization for constant speed motion.
  * #define CURVED_MOTION_INTERPOLATE */
 
-__device void transform_motion_interpolate(Transform *tfm, const MotionTransform *motion, float t)
+__device void transform_motion_interpolate(Transform *tfm, const DecompMotionTransform *motion, float t)
 {
        /* possible optimization: is it worth it adding a check to skip scaling?
         * it's probably quite uncommon to have scaling objects. or can we skip
@@ -393,9 +401,9 @@ __device void transform_motion_interpolate(Transform *tfm, const MotionTransform
 
 #ifdef CURVED_MOTION_INTERPOLATE
        /* 3 point bezier curve interpolation for position */
-       float3 Ppre = float4_to_float3(motion->pre.y);
+       float3 Ppre = float4_to_float3(motion->pre_y);
        float3 Pmid = float4_to_float3(motion->mid.y);
-       float3 Ppost = float4_to_float3(motion->post.y);
+       float3 Ppost = float4_to_float3(motion->post_y);
 
        float3 Pcontrol = 2.0f*Pmid - 0.5f*(Ppre + Ppost);
        float3 P = Ppre*t*t + Pcontrol*2.0f*t*(1.0f - t) + Ppost*(1.0f - t)*(1.0f - t);
@@ -409,28 +417,27 @@ __device void transform_motion_interpolate(Transform *tfm, const MotionTransform
        if(t < 0.5f) {
                t *= 2.0f;
 
-               decomp.x = quat_interpolate(motion->pre.x, motion->mid.x, t);
+               decomp.x = quat_interpolate(motion->pre_x, motion->mid.x, t);
 #ifdef CURVED_MOTION_INTERPOLATE
-               decomp.y.w = (1.0f - t)*motion->pre.y.w + t*motion->mid.y.w;
+               decomp.y.w = (1.0f - t)*motion->pre_y.w + t*motion->mid.y.w;
 #else
-               decomp.y = (1.0f - t)*motion->pre.y + t*motion->mid.y;
+               decomp.y = (1.0f - t)*motion->pre_y + t*motion->mid.y;
 #endif
-               decomp.z = (1.0f - t)*motion->pre.z + t*motion->mid.z;
-               decomp.w = (1.0f - t)*motion->pre.w + t*motion->mid.w;
        }
        else {
                t = (t - 0.5f)*2.0f;
 
-               decomp.x = quat_interpolate(motion->mid.x, motion->post.x, t);
+               decomp.x = quat_interpolate(motion->mid.x, motion->post_x, t);
 #ifdef CURVED_MOTION_INTERPOLATE
-               decomp.y.w = (1.0f - t)*motion->mid.y.w + t*motion->post.y.w;
+               decomp.y.w = (1.0f - t)*motion->mid.y.w + t*motion->post_y.w;
 #else
-               decomp.y = (1.0f - t)*motion->mid.y + t*motion->post.y;
+               decomp.y = (1.0f - t)*motion->mid.y + t*motion->post_y;
 #endif
-               decomp.z = (1.0f - t)*motion->mid.z + t*motion->post.z;
-               decomp.w = (1.0f - t)*motion->mid.w + t*motion->post.w;
        }
 
+       decomp.z = motion->mid.z;
+       decomp.w = motion->mid.w;
+
        /* compose rotation, translation, scale into matrix */
        transform_compose(tfm, &decomp);
 }
@@ -442,7 +449,7 @@ __device_inline bool operator==(const MotionTransform& A, const MotionTransform&
        return (A.pre == B.pre && A.post == B.post);
 }
 
-void transform_motion_decompose(MotionTransform *decomp, const MotionTransform *motion, const Transform *mid);
+void transform_motion_decompose(DecompMotionTransform *decomp, const MotionTransform *motion, const Transform *mid);
 
 #endif