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.cpp12
-rw-r--r--intern/cycles/kernel/kernel_random.h7
-rw-r--r--intern/cycles/render/mesh.cpp14
-rw-r--r--intern/cycles/render/mesh.h1
-rw-r--r--intern/cycles/render/object.cpp11
-rw-r--r--intern/cycles/util/util_transform.h9
6 files changed, 45 insertions, 9 deletions
diff --git a/intern/cycles/blender/blender_object.cpp b/intern/cycles/blender/blender_object.cpp
index 0edac820e94..abadee9328e 100644
--- a/intern/cycles/blender/blender_object.cpp
+++ b/intern/cycles/blender/blender_object.cpp
@@ -171,8 +171,14 @@ void BlenderSync::sync_object(BL::Object b_parent, int b_index, BL::Object b_ob,
Object *object;
bool object_updated = false;
+ if(object_map.sync(&object, b_ob, b_parent, key))
+ object_updated = true;
+
+ /* mesh sync */
+ object->mesh = sync_mesh(b_ob, object_updated);
+
/* object sync */
- if(object_map.sync(&object, b_ob, b_parent, key)) {
+ if(object_updated || (object->mesh && object->mesh->need_update)) {
object->name = b_ob.name().c_str();
object->tfm = tfm;
@@ -181,11 +187,7 @@ void BlenderSync::sync_object(BL::Object b_parent, int b_index, BL::Object b_ob,
object->visibility &= object_ray_visibility(b_parent);
object->tag_update(scene);
- object_updated = true;
}
-
- /* mesh sync */
- object->mesh = sync_mesh(b_ob, object_updated);
}
/* Object Loop */
diff --git a/intern/cycles/kernel/kernel_random.h b/intern/cycles/kernel/kernel_random.h
index df876e6f726..ba97ab3e3b6 100644
--- a/intern/cycles/kernel/kernel_random.h
+++ b/intern/cycles/kernel/kernel_random.h
@@ -22,6 +22,11 @@ typedef uint RNG;
#ifdef __SOBOL__
+/* skip initial numbers that are not as well distributed, especially the
+ first sequence is just 0 everywhere, which can be problematic for e.g.
+ path termination */
+#define SOBOL_SKIP 64
+
/* High Dimensional Sobol */
/* van der corput radical inverse */
@@ -103,7 +108,7 @@ __device_inline float path_rng(KernelGlobals *kg, RNG *rng, int sample, int dime
return r;
#else
/* compute sobol sequence value using direction vectors */
- uint result = sobol_dimension(kg, sample, dimension);
+ uint result = sobol_dimension(kg, sample + SOBOL_SKIP, dimension);
float r = (float)result * (1.0f/(float)0xFFFFFFFF);
/* Cranly-Patterson rotation using rng seed */
diff --git a/intern/cycles/render/mesh.cpp b/intern/cycles/render/mesh.cpp
index 2fef54605a1..19992771c1d 100644
--- a/intern/cycles/render/mesh.cpp
+++ b/intern/cycles/render/mesh.cpp
@@ -42,6 +42,7 @@ Mesh::Mesh()
{
need_update = true;
transform_applied = false;
+ transform_negative_scaled = false;
displacement_method = DISPLACE_BUMP;
bvh = NULL;
@@ -75,6 +76,9 @@ void Mesh::clear()
attributes.clear();
used_shaders.clear();
+
+ transform_applied = false;
+ transform_negative_scaled = false;
}
void Mesh::add_triangle(int v0, int v1, int v2, int shader_, bool smooth_)
@@ -116,6 +120,7 @@ void Mesh::add_face_normals()
/* compute face normals */
size_t triangles_size = triangles.size();
+ bool flip = transform_negative_scaled;
if(triangles_size) {
float3 *verts_ptr = &verts[0];
@@ -128,6 +133,9 @@ void Mesh::add_face_normals()
float3 v2 = verts_ptr[t.v[2]];
fN[i] = normalize(cross(v1 - v0, v2 - v0));
+
+ if(flip)
+ fN[i] = -fN[i];
}
}
}
@@ -150,6 +158,7 @@ void Mesh::add_vertex_normals()
size_t verts_size = verts.size();
size_t triangles_size = triangles.size();
+ bool flip = transform_negative_scaled;
if(triangles_size) {
Triangle *triangles_ptr = &triangles[0];
@@ -159,8 +168,11 @@ void Mesh::add_vertex_normals()
vN[triangles_ptr[i].v[j]] += fN[i];
}
- for(size_t i = 0; i < verts_size; i++)
+ for(size_t i = 0; i < verts_size; i++) {
vN[i] = normalize(vN[i]);
+ if(flip)
+ vN[i] = -vN[i];
+ }
}
void Mesh::pack_normals(Scene *scene, float4 *normal, float4 *vnormal)
diff --git a/intern/cycles/render/mesh.h b/intern/cycles/render/mesh.h
index 367896697ed..585203484c7 100644
--- a/intern/cycles/render/mesh.h
+++ b/intern/cycles/render/mesh.h
@@ -70,6 +70,7 @@ public:
BoundBox bounds;
bool transform_applied;
+ bool transform_negative_scaled;
DisplacementMethod displacement_method;
/* Update Flags */
diff --git a/intern/cycles/render/object.cpp b/intern/cycles/render/object.cpp
index b91531ac462..3a9f0add735 100644
--- a/intern/cycles/render/object.cpp
+++ b/intern/cycles/render/object.cpp
@@ -60,6 +60,11 @@ void Object::apply_transform()
Transform ntfm = transform_transpose(transform_inverse(tfm));
+ /* we keep normals pointing in same direction on negative scale, notify
+ mesh about this in it (re)calculates normals */
+ if(transform_negative_scale(tfm))
+ mesh->transform_negative_scaled = true;
+
if(attr_fN) {
float3 *fN = attr_fN->data_float3();
@@ -232,8 +237,10 @@ void ObjectManager::apply_static_transforms(Scene *scene, Progress& progress)
/* apply transforms for objects with single user meshes */
foreach(Object *object, scene->objects) {
if(mesh_users[object->mesh] == 1) {
- object->apply_transform();
- object->mesh->transform_applied = true;
+ if(!object->mesh->transform_applied) {
+ object->apply_transform();
+ object->mesh->transform_applied = true;
+ }
if(progress.get_cancel()) return;
}
diff --git a/intern/cycles/util/util_transform.h b/intern/cycles/util/util_transform.h
index c43736fb2e4..8f4e2b46616 100644
--- a/intern/cycles/util/util_transform.h
+++ b/intern/cycles/util/util_transform.h
@@ -234,6 +234,15 @@ __device_inline bool transform_uniform_scale(const Transform& tfm, float& scale)
return false;
}
+__device_inline bool transform_negative_scale(const Transform& tfm)
+{
+ float3 c0 = transform_get_column(&tfm, 0);
+ float3 c1 = transform_get_column(&tfm, 1);
+ float3 c2 = transform_get_column(&tfm, 2);
+
+ return (dot(cross(c0, c1), c2) < 0.0f);
+}
+
#endif
CCL_NAMESPACE_END