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
diff options
context:
space:
mode:
-rw-r--r--intern/cycles/blender/blender_object_cull.cpp2
-rw-r--r--intern/cycles/kernel/CMakeLists.txt1
-rw-r--r--intern/cycles/kernel/geom/geom_primitive.h12
-rw-r--r--intern/cycles/kernel/kernel_camera.h12
-rw-r--r--intern/cycles/kernel/kernel_math.h1
-rw-r--r--intern/cycles/kernel/kernel_types.h21
-rw-r--r--intern/cycles/kernel/osl/osl_services.cpp89
-rw-r--r--intern/cycles/render/camera.cpp57
-rw-r--r--intern/cycles/render/camera.h17
-rw-r--r--intern/cycles/util/CMakeLists.txt1
-rw-r--r--intern/cycles/util/util_projection.h176
-rw-r--r--intern/cycles/util/util_transform.h35
12 files changed, 275 insertions, 149 deletions
diff --git a/intern/cycles/blender/blender_object_cull.cpp b/intern/cycles/blender/blender_object_cull.cpp
index 1d747de647a..bdf7dc469b2 100644
--- a/intern/cycles/blender/blender_object_cull.cpp
+++ b/intern/cycles/blender/blender_object_cull.cpp
@@ -96,7 +96,7 @@ bool BlenderObjectCulling::test(Scene *scene, BL::Object& b_ob, Transform& tfm)
bool BlenderObjectCulling::test_camera(Scene *scene, float3 bb[8])
{
Camera *cam = scene->camera;
- Transform& worldtondc = cam->worldtondc;
+ const ProjectionTransform& worldtondc = cam->worldtondc;
float3 bb_min = make_float3(FLT_MAX, FLT_MAX, FLT_MAX),
bb_max = make_float3(-FLT_MAX, -FLT_MAX, -FLT_MAX);
bool all_behind = true;
diff --git a/intern/cycles/kernel/CMakeLists.txt b/intern/cycles/kernel/CMakeLists.txt
index 50ea03a1f8f..9b7f4e00084 100644
--- a/intern/cycles/kernel/CMakeLists.txt
+++ b/intern/cycles/kernel/CMakeLists.txt
@@ -254,6 +254,7 @@ set(SRC_UTIL_HEADERS
../util/util_math_int3.h
../util/util_math_int4.h
../util/util_math_matrix.h
+ ../util/util_projection.h
../util/util_rect.h
../util/util_static_assert.h
../util/util_transform.h
diff --git a/intern/cycles/kernel/geom/geom_primitive.h b/intern/cycles/kernel/geom/geom_primitive.h
index 60a1e483b84..6a8ea793ff0 100644
--- a/intern/cycles/kernel/geom/geom_primitive.h
+++ b/intern/cycles/kernel/geom/geom_primitive.h
@@ -204,14 +204,14 @@ ccl_device_inline float4 primitive_motion_vector(KernelGlobals *kg, ShaderData *
/* camera motion, for perspective/orthographic motion.pre/post will be a
* world-to-raster matrix, for panorama it's world-to-camera */
if(kernel_data.cam.type != CAMERA_PANORAMA) {
- tfm = kernel_data.cam.worldtoraster;
- motion_center = transform_perspective(&tfm, center);
+ ProjectionTransform projection = kernel_data.cam.worldtoraster;
+ motion_center = transform_perspective(&projection, center);
- tfm = kernel_data.cam.motion.pre;
- motion_pre = transform_perspective(&tfm, motion_pre);
+ projection = kernel_data.cam.perspective_motion.pre;
+ motion_pre = transform_perspective(&projection, motion_pre);
- tfm = kernel_data.cam.motion.post;
- motion_post = transform_perspective(&tfm, motion_post);
+ projection = kernel_data.cam.perspective_motion.post;
+ motion_post = transform_perspective(&projection, motion_post);
}
else {
tfm = kernel_data.cam.worldtocamera;
diff --git a/intern/cycles/kernel/kernel_camera.h b/intern/cycles/kernel/kernel_camera.h
index 66ed9f5fc0f..5b102eabb93 100644
--- a/intern/cycles/kernel/kernel_camera.h
+++ b/intern/cycles/kernel/kernel_camera.h
@@ -42,7 +42,7 @@ ccl_device float2 camera_sample_aperture(ccl_constant KernelCamera *cam, float u
ccl_device void camera_sample_perspective(KernelGlobals *kg, float raster_x, float raster_y, float lens_u, float lens_v, ccl_addr_space Ray *ray)
{
/* create ray form raster position */
- Transform rastertocamera = kernel_data.cam.rastertocamera;
+ ProjectionTransform rastertocamera = kernel_data.cam.rastertocamera;
float3 raster = make_float3(raster_x, raster_y, 0.0f);
float3 Pcamera = transform_perspective(&rastertocamera, raster);
@@ -54,13 +54,13 @@ ccl_device void camera_sample_perspective(KernelGlobals *kg, float raster_x, flo
* interpolated field of view.
*/
if(ray->time < 0.5f) {
- Transform rastertocamera_pre = kernel_data.cam.perspective_motion.pre;
+ ProjectionTransform rastertocamera_pre = kernel_data.cam.perspective_motion.pre;
float3 Pcamera_pre =
transform_perspective(&rastertocamera_pre, raster);
Pcamera = interp(Pcamera_pre, Pcamera, ray->time * 2.0f);
}
else {
- Transform rastertocamera_post = kernel_data.cam.perspective_motion.post;
+ ProjectionTransform rastertocamera_post = kernel_data.cam.perspective_motion.post;
float3 Pcamera_post =
transform_perspective(&rastertocamera_post, raster);
Pcamera = interp(Pcamera, Pcamera_post, (ray->time - 0.5f) * 2.0f);
@@ -169,7 +169,7 @@ ccl_device void camera_sample_perspective(KernelGlobals *kg, float raster_x, flo
ccl_device void camera_sample_orthographic(KernelGlobals *kg, float raster_x, float raster_y, float lens_u, float lens_v, ccl_addr_space Ray *ray)
{
/* create ray form raster position */
- Transform rastertocamera = kernel_data.cam.rastertocamera;
+ ProjectionTransform rastertocamera = kernel_data.cam.rastertocamera;
float3 Pcamera = transform_perspective(&rastertocamera, make_float3(raster_x, raster_y, 0.0f));
float3 P;
@@ -231,7 +231,7 @@ ccl_device_inline void camera_sample_panorama(ccl_constant KernelCamera *cam,
float lens_u, float lens_v,
ccl_addr_space Ray *ray)
{
- Transform rastertocamera = cam->rastertocamera;
+ ProjectionTransform rastertocamera = cam->rastertocamera;
float3 Pcamera = transform_perspective(&rastertocamera, make_float3(raster_x, raster_y, 0.0f));
/* create ray form raster position */
@@ -442,7 +442,7 @@ ccl_device_inline float3 camera_world_to_ndc(KernelGlobals *kg, ShaderData *sd,
if(sd->object == PRIM_NONE && kernel_data.cam.type == CAMERA_PERSPECTIVE)
P += camera_position(kg);
- Transform tfm = kernel_data.cam.worldtondc;
+ ProjectionTransform tfm = kernel_data.cam.worldtondc;
return transform_perspective(&tfm, P);
}
else {
diff --git a/intern/cycles/kernel/kernel_math.h b/intern/cycles/kernel/kernel_math.h
index bd0e23b7705..96391db7649 100644
--- a/intern/cycles/kernel/kernel_math.h
+++ b/intern/cycles/kernel/kernel_math.h
@@ -21,6 +21,7 @@
#include "util/util_math.h"
#include "util/util_math_fast.h"
#include "util/util_math_intersect.h"
+#include "util/util_projection.h"
#include "util/util_texture.h"
#include "util/util_transform.h"
diff --git a/intern/cycles/kernel/kernel_types.h b/intern/cycles/kernel/kernel_types.h
index 2cab63cdc6a..87faa0d0e53 100644
--- a/intern/cycles/kernel/kernel_types.h
+++ b/intern/cycles/kernel/kernel_types.h
@@ -1159,7 +1159,7 @@ typedef struct KernelCamera {
/* matrices */
Transform cameratoworld;
- Transform rastertocamera;
+ ProjectionTransform rastertocamera;
/* differentials */
float4 dx;
@@ -1193,21 +1193,18 @@ typedef struct KernelCamera {
int is_inside_volume;
/* more matrices */
- Transform screentoworld;
- Transform rastertoworld;
- /* work around cuda sm 2.0 crash, this seems to
- * cross some limit in combination with motion
- * Transform ndctoworld; */
- Transform worldtoscreen;
- Transform worldtoraster;
- Transform worldtondc;
+ ProjectionTransform screentoworld;
+ ProjectionTransform rastertoworld;
+ ProjectionTransform ndctoworld;
+ ProjectionTransform worldtoscreen;
+ ProjectionTransform worldtoraster;
+ ProjectionTransform worldtondc;
Transform worldtocamera;
MotionTransform motion;
- /* Denotes changes in the projective matrix, namely in rastertocamera.
- * Used for camera zoom motion blur,
- */
+ /* Stores changes in the projeciton matrix. Use for camera zoom motion
+ * blur and motion pass output for perspective camera. */
PerspectiveMotionTransform perspective_motion;
int shutter_table_offset;
diff --git a/intern/cycles/kernel/osl/osl_services.cpp b/intern/cycles/kernel/osl/osl_services.cpp
index ae4c521659c..dec56c6665b 100644
--- a/intern/cycles/kernel/osl/osl_services.cpp
+++ b/intern/cycles/kernel/osl/osl_services.cpp
@@ -62,11 +62,18 @@ CCL_NAMESPACE_BEGIN
/* RenderServices implementation */
-#define COPY_MATRIX44(m1, m2) { \
- CHECK_TYPE(m1, OSL::Matrix44*); \
- CHECK_TYPE(m2, Transform*); \
- memcpy(m1, m2, sizeof(*m2)); \
-} (void)0
+static void copy_matrix(OSL::Matrix44& m, const Transform& tfm)
+{
+ // TODO: remember when making affine
+ Transform t = transform_transpose(tfm);
+ memcpy(&m, &t, sizeof(m));
+}
+
+static void copy_matrix(OSL::Matrix44& m, const ProjectionTransform& tfm)
+{
+ ProjectionTransform t = projection_transpose(tfm);
+ memcpy(&m, &t, sizeof(m));
+}
/* static ustrings */
ustring OSLRenderServices::u_distance("distance");
@@ -167,14 +174,12 @@ bool OSLRenderServices::get_matrix(OSL::ShaderGlobals *sg, OSL::Matrix44 &result
#else
Transform tfm = object_fetch_transform(kg, object, OBJECT_TRANSFORM);
#endif
- tfm = transform_transpose(tfm);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, tfm);
return true;
}
else if(sd->type == PRIMITIVE_LAMP) {
- Transform tfm = transform_transpose(sd->ob_tfm);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, sd->ob_tfm);
return true;
}
@@ -203,14 +208,12 @@ bool OSLRenderServices::get_inverse_matrix(OSL::ShaderGlobals *sg, OSL::Matrix44
#else
Transform itfm = object_fetch_transform(kg, object, OBJECT_INVERSE_TRANSFORM);
#endif
- itfm = transform_transpose(itfm);
- COPY_MATRIX44(&result, &itfm);
+ copy_matrix(result, itfm);
return true;
}
else if(sd->type == PRIMITIVE_LAMP) {
- Transform tfm = transform_transpose(sd->ob_itfm);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, sd->ob_itfm);
return true;
}
@@ -224,23 +227,19 @@ bool OSLRenderServices::get_matrix(OSL::ShaderGlobals *sg, OSL::Matrix44 &result
KernelGlobals *kg = kernel_globals;
if(from == u_ndc) {
- Transform tfm = transform_transpose(transform_quick_inverse(kernel_data.cam.worldtondc));
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.ndctoworld);
return true;
}
else if(from == u_raster) {
- Transform tfm = transform_transpose(kernel_data.cam.rastertoworld);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.rastertoworld);
return true;
}
else if(from == u_screen) {
- Transform tfm = transform_transpose(kernel_data.cam.screentoworld);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.screentoworld);
return true;
}
else if(from == u_camera) {
- Transform tfm = transform_transpose(kernel_data.cam.cameratoworld);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.cameratoworld);
return true;
}
else if(from == u_world) {
@@ -256,23 +255,19 @@ bool OSLRenderServices::get_inverse_matrix(OSL::ShaderGlobals *sg, OSL::Matrix44
KernelGlobals *kg = kernel_globals;
if(to == u_ndc) {
- Transform tfm = transform_transpose(kernel_data.cam.worldtondc);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.worldtondc);
return true;
}
else if(to == u_raster) {
- Transform tfm = transform_transpose(kernel_data.cam.worldtoraster);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.worldtoraster);
return true;
}
else if(to == u_screen) {
- Transform tfm = transform_transpose(kernel_data.cam.worldtoscreen);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.worldtoscreen);
return true;
}
else if(to == u_camera) {
- Transform tfm = transform_transpose(kernel_data.cam.worldtocamera);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.worldtocamera);
return true;
}
else if(to == u_world) {
@@ -298,14 +293,12 @@ bool OSLRenderServices::get_matrix(OSL::ShaderGlobals *sg, OSL::Matrix44 &result
KernelGlobals *kg = sd->osl_globals;
Transform tfm = object_fetch_transform(kg, object, OBJECT_TRANSFORM);
#endif
- tfm = transform_transpose(tfm);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, tfm);
return true;
}
else if(sd->type == PRIMITIVE_LAMP) {
- Transform tfm = transform_transpose(sd->ob_tfm);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, sd->ob_tfm);
return true;
}
@@ -329,14 +322,12 @@ bool OSLRenderServices::get_inverse_matrix(OSL::ShaderGlobals *sg, OSL::Matrix44
KernelGlobals *kg = sd->osl_globals;
Transform tfm = object_fetch_transform(kg, object, OBJECT_INVERSE_TRANSFORM);
#endif
- tfm = transform_transpose(tfm);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, tfm);
return true;
}
else if(sd->type == PRIMITIVE_LAMP) {
- Transform tfm = transform_transpose(sd->ob_itfm);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, sd->ob_itfm);
return true;
}
@@ -350,23 +341,19 @@ bool OSLRenderServices::get_matrix(OSL::ShaderGlobals *sg, OSL::Matrix44 &result
KernelGlobals *kg = kernel_globals;
if(from == u_ndc) {
- Transform tfm = transform_transpose(transform_quick_inverse(kernel_data.cam.worldtondc));
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.ndctoworld);
return true;
}
else if(from == u_raster) {
- Transform tfm = transform_transpose(kernel_data.cam.rastertoworld);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.rastertoworld);
return true;
}
else if(from == u_screen) {
- Transform tfm = transform_transpose(kernel_data.cam.screentoworld);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.screentoworld);
return true;
}
else if(from == u_camera) {
- Transform tfm = transform_transpose(kernel_data.cam.cameratoworld);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.cameratoworld);
return true;
}
@@ -378,23 +365,19 @@ bool OSLRenderServices::get_inverse_matrix(OSL::ShaderGlobals *sg, OSL::Matrix44
KernelGlobals *kg = kernel_globals;
if(to == u_ndc) {
- Transform tfm = transform_transpose(kernel_data.cam.worldtondc);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.worldtondc);
return true;
}
else if(to == u_raster) {
- Transform tfm = transform_transpose(kernel_data.cam.worldtoraster);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.worldtoraster);
return true;
}
else if(to == u_screen) {
- Transform tfm = transform_transpose(kernel_data.cam.worldtoscreen);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.worldtoscreen);
return true;
}
else if(to == u_camera) {
- Transform tfm = transform_transpose(kernel_data.cam.worldtocamera);
- COPY_MATRIX44(&result, &tfm);
+ copy_matrix(result, kernel_data.cam.worldtocamera);
return true;
}
diff --git a/intern/cycles/render/camera.cpp b/intern/cycles/render/camera.cpp
index a2fda12ec85..e6585b2de55 100644
--- a/intern/cycles/render/camera.cpp
+++ b/intern/cycles/render/camera.cpp
@@ -163,12 +163,12 @@ Camera::Camera()
compute_auto_viewplane();
- screentoworld = transform_identity();
- rastertoworld = transform_identity();
- ndctoworld = transform_identity();
- rastertocamera = transform_identity();
+ screentoworld = projection_identity();
+ rastertoworld = projection_identity();
+ ndctoworld = projection_identity();
+ rastertocamera = projection_identity();
cameratoworld = transform_identity();
- worldtoraster = transform_identity();
+ worldtoraster = projection_identity();
dx = make_float3(0.0f, 0.0f, 0.0f);
dy = make_float3(0.0f, 0.0f, 0.0f);
@@ -241,18 +241,18 @@ void Camera::update(Scene *scene)
Transform full_rastertoscreen = transform_inverse(full_screentoraster);
/* screen to camera */
- Transform cameratoscreen;
+ ProjectionTransform cameratoscreen;
if(type == CAMERA_PERSPECTIVE)
- cameratoscreen = transform_perspective(fov, nearclip, farclip);
+ cameratoscreen = projection_perspective(fov, nearclip, farclip);
else if(type == CAMERA_ORTHOGRAPHIC)
- cameratoscreen = transform_orthographic(nearclip, farclip);
+ cameratoscreen = projection_orthographic(nearclip, farclip);
else
- cameratoscreen = transform_identity();
+ cameratoscreen = projection_identity();
- Transform screentocamera = transform_inverse(cameratoscreen);
+ ProjectionTransform screentocamera = projection_inverse(cameratoscreen);
rastertocamera = screentocamera * rastertoscreen;
- Transform full_rastertocamera = screentocamera * full_rastertoscreen;
+ ProjectionTransform full_rastertocamera = screentocamera * full_rastertoscreen;
cameratoraster = screentoraster * cameratoscreen;
cameratoworld = matrix;
@@ -270,10 +270,10 @@ void Camera::update(Scene *scene)
/* differentials */
if(type == CAMERA_ORTHOGRAPHIC) {
- dx = transform_direction(&rastertocamera, make_float3(1, 0, 0));
- dy = transform_direction(&rastertocamera, make_float3(0, 1, 0));
- full_dx = transform_direction(&full_rastertocamera, make_float3(1, 0, 0));
- full_dy = transform_direction(&full_rastertocamera, make_float3(0, 1, 0));
+ dx = transform_perspective_direction(&rastertocamera, make_float3(1, 0, 0));
+ dy = transform_perspective_direction(&rastertocamera, make_float3(0, 1, 0));
+ full_dx = transform_perspective_direction(&full_rastertocamera, make_float3(1, 0, 0));
+ full_dy = transform_perspective_direction(&full_rastertocamera, make_float3(0, 1, 0));
}
else if(type == CAMERA_PERSPECTIVE) {
dx = transform_perspective(&rastertocamera, make_float3(1, 0, 0)) -
@@ -307,14 +307,14 @@ void Camera::update(Scene *scene)
/* TODO(sergey): Move to an utility function and de-duplicate with
* calculation above.
*/
- Transform screentocamera_pre =
- transform_inverse(transform_perspective(fov_pre,
- nearclip,
- farclip));
- Transform screentocamera_post =
- transform_inverse(transform_perspective(fov_post,
- nearclip,
- farclip));
+ ProjectionTransform screentocamera_pre =
+ projection_inverse(projection_perspective(fov_pre,
+ nearclip,
+ farclip));
+ ProjectionTransform screentocamera_post =
+ projection_inverse(projection_perspective(fov_post,
+ nearclip,
+ farclip));
perspective_motion.pre = screentocamera_pre * rastertoscreen;
perspective_motion.post = screentocamera_post * rastertoscreen;
}
@@ -331,6 +331,7 @@ void Camera::update(Scene *scene)
kcam->worldtoscreen = worldtoscreen;
kcam->worldtoraster = worldtoraster;
kcam->worldtondc = worldtondc;
+ kcam->ndctoworld = ndctoworld;
/* camera motion */
kcam->have_motion = 0;
@@ -350,12 +351,12 @@ void Camera::update(Scene *scene)
}
else {
if(use_motion) {
- kcam->motion.pre = cameratoraster * transform_inverse(motion.pre);
- kcam->motion.post = cameratoraster * transform_inverse(motion.post);
+ kcam->perspective_motion.pre = cameratoraster * transform_inverse(motion.pre);
+ kcam->perspective_motion.post = cameratoraster * transform_inverse(motion.post);
}
else {
- kcam->motion.pre = worldtoraster;
- kcam->motion.post = worldtoraster;
+ kcam->perspective_motion.pre = worldtoraster;
+ kcam->perspective_motion.post = worldtoraster;
}
}
}
@@ -606,7 +607,7 @@ float Camera::world_to_raster_size(float3 P)
res = min(len(full_dx), len(full_dy));
if(offscreen_dicing_scale > 1.0f) {
- float3 p = transform_perspective(&worldtocamera, P);
+ float3 p = transform_point(&worldtocamera, P);
float3 v = transform_perspective(&rastertocamera, make_float3(width, height, 0.0f));
/* Create point clamped to frustum */
diff --git a/intern/cycles/render/camera.h b/intern/cycles/render/camera.h
index 4ec0fe3bc6e..aa4e53a347b 100644
--- a/intern/cycles/render/camera.h
+++ b/intern/cycles/render/camera.h
@@ -22,6 +22,7 @@
#include "graph/node.h"
#include "util/util_boundbox.h"
+#include "util/util_projection.h"
#include "util/util_transform.h"
#include "util/util_types.h"
@@ -146,18 +147,18 @@ public:
PerspectiveMotionTransform perspective_motion;
/* computed camera parameters */
- Transform screentoworld;
- Transform rastertoworld;
- Transform ndctoworld;
+ ProjectionTransform screentoworld;
+ ProjectionTransform rastertoworld;
+ ProjectionTransform ndctoworld;
Transform cameratoworld;
- Transform worldtoraster;
- Transform worldtoscreen;
- Transform worldtondc;
+ ProjectionTransform worldtoraster;
+ ProjectionTransform worldtoscreen;
+ ProjectionTransform worldtondc;
Transform worldtocamera;
- Transform rastertocamera;
- Transform cameratoraster;
+ ProjectionTransform rastertocamera;
+ ProjectionTransform cameratoraster;
float3 dx;
float3 dy;
diff --git a/intern/cycles/util/CMakeLists.txt b/intern/cycles/util/CMakeLists.txt
index 66c4f22a7e2..24043e2231b 100644
--- a/intern/cycles/util/CMakeLists.txt
+++ b/intern/cycles/util/CMakeLists.txt
@@ -67,6 +67,7 @@ set(SRC_HEADERS
util_param.h
util_path.h
util_progress.h
+ util_projection.h
util_queue.h
util_rect.h
util_set.h
diff --git a/intern/cycles/util/util_projection.h b/intern/cycles/util/util_projection.h
new file mode 100644
index 00000000000..0b8ff032120
--- /dev/null
+++ b/intern/cycles/util/util_projection.h
@@ -0,0 +1,176 @@
+/*
+ * Copyright 2011-2018 Blender Foundation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef __UTIL_PROJECTION_H__
+#define __UTIL_PROJECTION_H__
+
+#include "util/util_transform.h"
+
+CCL_NAMESPACE_BEGIN
+
+/* Data Types */
+
+typedef struct ProjectionTransform {
+ float4 x, y, z, w; /* rows */
+
+#ifndef __KERNEL_GPU__
+ ProjectionTransform()
+ {
+ }
+
+ explicit ProjectionTransform(const Transform& tfm)
+ : x(tfm.x),
+ y(tfm.y),
+ z(tfm.z),
+ w(tfm.w)
+ {
+ }
+#endif
+} ProjectionTransform;
+
+typedef struct PerspectiveMotionTransform {
+ ProjectionTransform pre;
+ ProjectionTransform post;
+} PerspectiveMotionTransform;
+
+/* Functions */
+
+ccl_device_inline float3 transform_perspective(const ProjectionTransform *t, const float3 a)
+{
+ float4 b = make_float4(a.x, a.y, a.z, 1.0f);
+ float3 c = make_float3(dot(t->x, b), dot(t->y, b), dot(t->z, b));
+ float w = dot(t->w, b);
+
+ return (w != 0.0f)? c/w: make_float3(0.0f, 0.0f, 0.0f);
+}
+
+ccl_device_inline float3 transform_perspective_direction(const ProjectionTransform *t, const float3 a)
+{
+ float3 c = make_float3(
+ a.x*t->x.x + a.y*t->x.y + a.z*t->x.z,
+ a.x*t->y.x + a.y*t->y.y + a.z*t->y.z,
+ a.x*t->z.x + a.y*t->z.y + a.z*t->z.z);
+
+ return c;
+}
+
+#ifndef __KERNEL_GPU__
+
+ccl_device_inline ProjectionTransform projection_transpose(const ProjectionTransform& a)
+{
+ ProjectionTransform t;
+
+ t.x.x = a.x.x; t.x.y = a.y.x; t.x.z = a.z.x; t.x.w = a.w.x;
+ t.y.x = a.x.y; t.y.y = a.y.y; t.y.z = a.z.y; t.y.w = a.w.y;
+ t.z.x = a.x.z; t.z.y = a.y.z; t.z.z = a.z.z; t.z.w = a.w.z;
+ t.w.x = a.x.w; t.w.y = a.y.w; t.w.z = a.z.w; t.w.w = a.w.w;
+
+ return t;
+}
+
+ccl_device_inline ProjectionTransform projection_inverse(const ProjectionTransform& a)
+{
+ Transform t = {a.x, a.y, a.z, a.w};
+ t = transform_inverse(t);
+ return ProjectionTransform(t);
+}
+
+ccl_device_inline ProjectionTransform make_projection(
+ float a, float b, float c, float d,
+ float e, float f, float g, float h,
+ float i, float j, float k, float l,
+ float m, float n, float o, float p)
+{
+ ProjectionTransform t;
+
+ t.x.x = a; t.x.y = b; t.x.z = c; t.x.w = d;
+ t.y.x = e; t.y.y = f; t.y.z = g; t.y.w = h;
+ t.z.x = i; t.z.y = j; t.z.z = k; t.z.w = l;
+ t.w.x = m; t.w.y = n; t.w.z = o; t.w.w = p;
+
+ return t;
+}
+ccl_device_inline ProjectionTransform projection_identity()
+{
+ return make_projection(
+ 1.0f, 0.0f, 0.0f, 0.0f,
+ 0.0f, 1.0f, 0.0f, 0.0f,
+ 0.0f, 0.0f, 1.0f, 0.0f,
+ 0.0f, 0.0f, 0.0f, 1.0f);
+}
+
+ccl_device_inline ProjectionTransform operator*(const ProjectionTransform& a, const ProjectionTransform& b)
+{
+ ProjectionTransform c = projection_transpose(b);
+ ProjectionTransform t;
+
+ t.x = make_float4(dot(a.x, c.x), dot(a.x, c.y), dot(a.x, c.z), dot(a.x, c.w));
+ t.y = make_float4(dot(a.y, c.x), dot(a.y, c.y), dot(a.y, c.z), dot(a.y, c.w));
+ t.z = make_float4(dot(a.z, c.x), dot(a.z, c.y), dot(a.z, c.z), dot(a.z, c.w));
+ t.w = make_float4(dot(a.w, c.x), dot(a.w, c.y), dot(a.w, c.z), dot(a.w, c.w));
+
+ return t;
+}
+
+ccl_device_inline ProjectionTransform operator*(const ProjectionTransform& a, const Transform& b)
+{
+ return a * ProjectionTransform(b);
+}
+
+ccl_device_inline ProjectionTransform operator*(const Transform& a, const ProjectionTransform& b)
+{
+ return ProjectionTransform(a) * b;
+}
+
+ccl_device_inline void print_projection(const char *label, const ProjectionTransform& t)
+{
+ print_float4(label, t.x);
+ print_float4(label, t.y);
+ print_float4(label, t.z);
+ print_float4(label, t.w);
+ printf("\n");
+}
+
+ccl_device_inline ProjectionTransform projection_perspective(float fov, float n, float f)
+{
+ ProjectionTransform persp = make_projection(
+ 1, 0, 0, 0,
+ 0, 1, 0, 0,
+ 0, 0, f / (f - n), -f*n / (f - n),
+ 0, 0, 1, 0);
+
+ float inv_angle = 1.0f/tanf(0.5f*fov);
+
+ Transform scale = transform_scale(inv_angle, inv_angle, 1);
+
+ return scale * persp;
+}
+
+ccl_device_inline ProjectionTransform projection_orthographic(float znear, float zfar)
+{
+ Transform t =
+ transform_scale(1.0f, 1.0f, 1.0f / (zfar-znear)) *
+ transform_translate(0.0f, 0.0f, -znear);
+
+ return ProjectionTransform(t);
+}
+
+#endif /* __KERNEL_GPU__ */
+
+CCL_NAMESPACE_END
+
+#endif /* __UTIL_PROJECTION_H__ */
+
diff --git a/intern/cycles/util/util_transform.h b/intern/cycles/util/util_transform.h
index 1efe001f6a8..52022292d0b 100644
--- a/intern/cycles/util/util_transform.h
+++ b/intern/cycles/util/util_transform.h
@@ -47,22 +47,8 @@ typedef struct ccl_may_alias MotionTransform {
Transform post;
} MotionTransform;
-typedef struct PerspectiveMotionTransform {
- Transform pre;
- Transform post;
-} PerspectiveMotionTransform;
-
/* Functions */
-ccl_device_inline float3 transform_perspective(const Transform *t, const float3 a)
-{
- float4 b = make_float4(a.x, a.y, a.z, 1.0f);
- float3 c = make_float3(dot(t->x, b), dot(t->y, b), dot(t->z, b));
- float w = dot(t->w, b);
-
- return (w != 0.0f)? c/w: make_float3(0.0f, 0.0f, 0.0f);
-}
-
ccl_device_inline float3 transform_point(const Transform *t, const float3 a)
{
/* TODO(sergey): Disabled for now, causes crashes in certain cases. */
@@ -221,21 +207,6 @@ ccl_device_inline Transform transform_scale(float x, float y, float z)
return transform_scale(make_float3(x, y, z));
}
-ccl_device_inline Transform transform_perspective(float fov, float n, float f)
-{
- Transform persp = make_transform(
- 1, 0, 0, 0,
- 0, 1, 0, 0,
- 0, 0, f / (f - n), -f*n / (f - n),
- 0, 0, 1, 0);
-
- float inv_angle = 1.0f/tanf(0.5f*fov);
-
- Transform scale = transform_scale(inv_angle, inv_angle, 1);
-
- return scale * persp;
-}
-
ccl_device_inline Transform transform_rotate(float angle, float3 axis)
{
float s = sinf(angle);
@@ -272,12 +243,6 @@ ccl_device_inline Transform transform_euler(float3 euler)
transform_rotate(euler.x, make_float3(1.0f, 0.0f, 0.0f));
}
-ccl_device_inline Transform transform_orthographic(float znear, float zfar)
-{
- return transform_scale(1.0f, 1.0f, 1.0f / (zfar-znear)) *
- transform_translate(0.0f, 0.0f, -znear);
-}
-
ccl_device_inline Transform transform_identity()
{
return transform_scale(1.0f, 1.0f, 1.0f);