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--build_files/cmake/macros.cmake4
-rw-r--r--build_files/cmake/platform/platform_apple.cmake9
-rw-r--r--intern/cycles/app/cycles_xml.cpp4
-rw-r--r--intern/cycles/cmake/external_libs.cmake2
-rw-r--r--intern/cycles/render/mesh.cpp3
-rw-r--r--intern/cycles/render/mesh_volume.cpp25
-rw-r--r--release/scripts/startup/bl_ui/space_time.py2
-rw-r--r--source/blender/blenkernel/intern/DerivedMesh.c16
-rw-r--r--source/blender/compositor/operations/COM_MapRangeOperation.cpp5
-rw-r--r--source/blender/depsgraph/intern/builder/deg_builder_cycle.cc95
-rw-r--r--source/blender/depsgraph/intern/builder/deg_builder_nodes.cc80
-rw-r--r--source/blender/depsgraph/intern/builder/deg_builder_nodes.h11
-rw-r--r--source/blender/depsgraph/intern/builder/deg_builder_relations.cc21
-rw-r--r--source/blender/depsgraph/intern/depsgraph.cc16
-rw-r--r--source/blender/depsgraph/intern/depsgraph_type_defines.cc1
-rw-r--r--source/blender/depsgraph/intern/depsgraph_types.h1
-rw-r--r--source/blender/editors/space_clip/tracking_ops.c2
-rw-r--r--source/blender/editors/space_sequencer/sequencer_edit.c59
-rw-r--r--source/blender/editors/space_view3d/drawmesh.c1
19 files changed, 268 insertions, 89 deletions
diff --git a/build_files/cmake/macros.cmake b/build_files/cmake/macros.cmake
index e3eb4d9241a..eaf8c2b845b 100644
--- a/build_files/cmake/macros.cmake
+++ b/build_files/cmake/macros.cmake
@@ -1129,7 +1129,9 @@ endmacro()
# External libs may need 'signed char' to be default.
macro(remove_cc_flag_unsigned_char)
- if(CMAKE_C_COMPILER_ID MATCHES "^(GNU|Clang|Intel)$")
+ if(CMAKE_COMPILER_IS_GNUCC OR
+ (CMAKE_C_COMPILER_ID MATCHES "Clang") OR
+ (CMAKE_C_COMPILER_ID MATCHES "Intel"))
remove_cc_flag("-funsigned-char")
elseif(MSVC)
remove_cc_flag("/J")
diff --git a/build_files/cmake/platform/platform_apple.cmake b/build_files/cmake/platform/platform_apple.cmake
index 1435572fa5e..caaf7b96d0e 100644
--- a/build_files/cmake/platform/platform_apple.cmake
+++ b/build_files/cmake/platform/platform_apple.cmake
@@ -29,6 +29,9 @@ endmacro()
if(NOT DEFINED LIBDIR)
set(LIBDIR ${CMAKE_SOURCE_DIR}/../lib/darwin)
+ # Prefer lib directory paths
+ file(GLOB LIB_SUBDIRS ${LIBDIR}/*)
+ set(CMAKE_PREFIX_PATH ${LIB_SUBDIRS})
else()
message(STATUS "Using pre-compiled LIBDIR: ${LIBDIR}")
endif()
@@ -325,8 +328,8 @@ if(WITH_OPENVDB)
endif()
if(WITH_LLVM)
- set(LLVM_ROOT_DIR ${LIBDIR}/llvm CACHE PATH "Path to the LLVM installation")
- set(LLVM_VERSION "3.4" CACHE STRING "Version of LLVM to use")
+ set(LLVM_ROOT_DIR ${LIBDIR}/llvm)
+ set(LLVM_VERSION 3.4)
if(EXISTS "${LLVM_ROOT_DIR}/bin/llvm-config")
set(LLVM_CONFIG "${LLVM_ROOT_DIR}/bin/llvm-config")
else()
@@ -363,7 +366,7 @@ if(WITH_LLVM)
endif()
if(WITH_CYCLES_OSL)
- set(CYCLES_OSL ${LIBDIR}/osl CACHE PATH "Path to OpenShadingLanguage installation")
+ set(CYCLES_OSL ${LIBDIR}/osl)
find_library(OSL_LIB_EXEC NAMES oslexec PATHS ${CYCLES_OSL}/lib)
find_library(OSL_LIB_COMP NAMES oslcomp PATHS ${CYCLES_OSL}/lib)
diff --git a/intern/cycles/app/cycles_xml.cpp b/intern/cycles/app/cycles_xml.cpp
index 2d6e63468af..21ae07e23b8 100644
--- a/intern/cycles/app/cycles_xml.cpp
+++ b/intern/cycles/app/cycles_xml.cpp
@@ -204,7 +204,7 @@ static void xml_read_camera(XMLReadState& state, xml_node node)
cam->matrix = state.tfm;
cam->need_update = true;
- cam->update();
+ cam->update(state.scene);
}
/* Shader */
@@ -515,7 +515,7 @@ static void xml_read_mesh(const XMLReadState& state, xml_node node)
xml_read_float(&sdparams.dicing_rate, node, "dicing_rate");
sdparams.dicing_rate = std::max(0.1f, sdparams.dicing_rate);
- state.scene->camera->update();
+ state.scene->camera->update(state.scene);
sdparams.camera = state.scene->camera;
sdparams.objecttoworld = state.tfm;
}
diff --git a/intern/cycles/cmake/external_libs.cmake b/intern/cycles/cmake/external_libs.cmake
index df88b91f5ac..8d04025e6fd 100644
--- a/intern/cycles/cmake/external_libs.cmake
+++ b/intern/cycles/cmake/external_libs.cmake
@@ -30,7 +30,7 @@ if(NOT CYCLES_STANDALONE_REPOSITORY)
set(GLEW_INCLUDE_DIR "${GLEW_INCLUDE_PATH}")
endif()
-if(WITH_CYCLES_STANDALONE AND WITH_CYCLES_STANDALONE_GUI)
+if(WITH_CYCLES_STANDALONE)
set(CYCLES_APP_GLEW_LIBRARY ${BLENDER_GLEW_LIBRARIES})
endif()
diff --git a/intern/cycles/render/mesh.cpp b/intern/cycles/render/mesh.cpp
index 23b855acdc9..47d24970949 100644
--- a/intern/cycles/render/mesh.cpp
+++ b/intern/cycles/render/mesh.cpp
@@ -561,8 +561,9 @@ void Mesh::clear(bool preserve_voxel_data)
subd_attributes.clear();
attributes.clear(preserve_voxel_data);
+ used_shaders.clear();
+
if(!preserve_voxel_data) {
- used_shaders.clear();
geometry_flags = GEOMETRY_NONE;
}
diff --git a/intern/cycles/render/mesh_volume.cpp b/intern/cycles/render/mesh_volume.cpp
index be43154fd93..f2347c79610 100644
--- a/intern/cycles/render/mesh_volume.cpp
+++ b/intern/cycles/render/mesh_volume.cpp
@@ -393,9 +393,6 @@ void VolumeMeshBuilder::convert_quads_to_tris(const vector<QuadData> &quads,
/* ************************************************************************** */
-/* For debugging: render the created mesh using the default diffuse shader. */
-//#define RENDER_DIFFUSE
-
struct VoxelAttributeGrid {
float *data;
int channels;
@@ -443,6 +440,8 @@ void MeshManager::create_volume_mesh(Scene *scene,
return;
}
+ /* Compute padding. */
+ Shader *volume_shader = NULL;
int pad_size = 0;
foreach(Shader *shader, mesh->used_shaders) {
@@ -450,12 +449,20 @@ void MeshManager::create_volume_mesh(Scene *scene,
continue;
}
+ volume_shader = shader;
+
if(shader->volume_interpolation_method == VOLUME_INTERPOLATION_LINEAR) {
pad_size = max(1, pad_size);
}
else if(shader->volume_interpolation_method == VOLUME_INTERPOLATION_CUBIC) {
pad_size = max(2, pad_size);
}
+
+ break;
+ }
+
+ if(!volume_shader) {
+ return;
}
/* Compute start point and cell size from transform. */
@@ -477,6 +484,7 @@ void MeshManager::create_volume_mesh(Scene *scene,
volume_params.cell_size = cell_size;
volume_params.pad_size = pad_size;
+ /* Build bounding mesh around non-empty volume cells. */
VolumeMeshBuilder builder(&volume_params);
const float isovalue = mesh->volume_isovalue;
@@ -540,26 +548,22 @@ void MeshManager::create_volume_mesh(Scene *scene,
}
}
+ /* Create mesh. */
vector<float3> vertices;
vector<int> indices;
vector<float3> face_normals;
builder.create_mesh(vertices, indices, face_normals);
-#ifdef RENDER_DIFFUSE
- int shader = mesh->used_shaders[0]->id;
-#else
- int shader = mesh->shader[0];
-#endif
-
mesh->clear(true);
mesh->reserve_mesh(vertices.size(), indices.size()/3);
+ mesh->used_shaders.push_back(volume_shader);
for(size_t i = 0; i < vertices.size(); ++i) {
mesh->add_vertex(vertices[i]);
}
for(size_t i = 0; i < indices.size(); i += 3) {
- mesh->add_triangle(indices[i], indices[i + 1], indices[i + 2], shader, false);
+ mesh->add_triangle(indices[i], indices[i + 1], indices[i + 2], 0, false);
}
Attribute *attr_fN = mesh->attributes.add(ATTR_STD_FACE_NORMAL);
@@ -569,6 +573,7 @@ void MeshManager::create_volume_mesh(Scene *scene,
fN[i] = face_normals[i];
}
+ /* Print stats. */
VLOG(1) << "Memory usage volume mesh: "
<< ((vertices.size() + face_normals.size())*sizeof(float3) + indices.size()*sizeof(int))/(1024.0*1024.0)
<< "Mb.";
diff --git a/release/scripts/startup/bl_ui/space_time.py b/release/scripts/startup/bl_ui/space_time.py
index d1202adfce6..9026a93aa99 100644
--- a/release/scripts/startup/bl_ui/space_time.py
+++ b/release/scripts/startup/bl_ui/space_time.py
@@ -119,7 +119,7 @@ class TIME_MT_marker(Menu):
def draw(self, context):
layout = self.layout
- marker_menu_generic(layout, context)
+ marker_menu_generic(layout)
class TIME_MT_view(Menu):
diff --git a/source/blender/blenkernel/intern/DerivedMesh.c b/source/blender/blenkernel/intern/DerivedMesh.c
index 26aecb526d4..15469e3ae4b 100644
--- a/source/blender/blenkernel/intern/DerivedMesh.c
+++ b/source/blender/blenkernel/intern/DerivedMesh.c
@@ -3910,17 +3910,25 @@ void DM_draw_attrib_vertex_uniforms(const DMVertexAttribs *attribs)
{
int i;
if (attribs->totorco) {
- glUniform1i(attribs->orco.gl_info_index, 0);
+ if (attribs->orco.gl_info_index != -1) {
+ glUniform1i(attribs->orco.gl_info_index, 0);
+ }
}
for (i = 0; i < attribs->tottface; i++) {
- glUniform1i(attribs->tface[i].gl_info_index, 0);
+ if (attribs->tface[i].gl_info_index != -1) {
+ glUniform1i(attribs->tface[i].gl_info_index, 0);
+ }
}
for (i = 0; i < attribs->totmcol; i++) {
- glUniform1i(attribs->mcol[i].gl_info_index, GPU_ATTR_INFO_SRGB);
+ if (attribs->mcol[i].gl_info_index != -1) {
+ glUniform1i(attribs->mcol[i].gl_info_index, GPU_ATTR_INFO_SRGB);
+ }
}
for (i = 0; i < attribs->tottang; i++) {
- glUniform1i(attribs->tang[i].gl_info_index, 0);
+ if (attribs->tang[i].gl_info_index != -1) {
+ glUniform1i(attribs->tang[i].gl_info_index, 0);
+ }
}
}
diff --git a/source/blender/compositor/operations/COM_MapRangeOperation.cpp b/source/blender/compositor/operations/COM_MapRangeOperation.cpp
index 7a89ba91b4c..7a38d066122 100644
--- a/source/blender/compositor/operations/COM_MapRangeOperation.cpp
+++ b/source/blender/compositor/operations/COM_MapRangeOperation.cpp
@@ -65,6 +65,11 @@ void MapRangeOperation::executePixelSampled(float output[4], float x, float y, P
dest_min = inputs[3];
dest_max = inputs[4];
+ if (fabsf(source_max - source_min) < 1e-6f) {
+ output[0] = 0.0f;
+ return;
+ }
+
if (value >= -BLENDER_ZMAX && value <= BLENDER_ZMAX) {
value = (value - source_min) / (source_max - source_min);
value = dest_min + value * (dest_max - dest_min);
diff --git a/source/blender/depsgraph/intern/builder/deg_builder_cycle.cc b/source/blender/depsgraph/intern/builder/deg_builder_cycle.cc
index c9fa35bd551..026aa309b02 100644
--- a/source/blender/depsgraph/intern/builder/deg_builder_cycle.cc
+++ b/source/blender/depsgraph/intern/builder/deg_builder_cycle.cc
@@ -46,6 +46,8 @@
namespace DEG {
+namespace {
+
typedef enum eCyclicCheckVisitedState {
/* Not is not visited at all during traversal. */
NODE_NOT_VISITED = 0,
@@ -55,6 +57,30 @@ typedef enum eCyclicCheckVisitedState {
NODE_IN_STACK = 2,
} eCyclicCheckVisitedState;
+struct StackEntry {
+ OperationDepsNode *node;
+ StackEntry *from;
+ DepsRelation *via_relation;
+};
+
+struct CyclesSolverState {
+ CyclesSolverState(Depsgraph *graph)
+ : graph(graph),
+ traversal_stack(BLI_stack_new(sizeof(StackEntry),
+ "DEG detect cycles stack")),
+ num_cycles(0) {
+ }
+ ~CyclesSolverState() {
+ BLI_stack_free(traversal_stack);
+ if (num_cycles != 0) {
+ printf("Detected %d dependency cycles\n", num_cycles);
+ }
+ }
+ Depsgraph *graph;
+ BLI_Stack *traversal_stack;
+ int num_cycles;
+};
+
BLI_INLINE void set_node_visited_state(DepsNode *node,
eCyclicCheckVisitedState state)
{
@@ -76,19 +102,20 @@ BLI_INLINE int get_node_num_visited_children(DepsNode *node)
return node->done >> 2;
}
-void deg_graph_detect_cycles(Depsgraph *graph)
+void schedule_node_to_stack(CyclesSolverState *state, OperationDepsNode *node)
{
- struct StackEntry {
- OperationDepsNode *node;
- StackEntry *from;
- DepsRelation *via_relation;
- };
-
- BLI_Stack *traversal_stack = BLI_stack_new(sizeof(StackEntry),
- "DEG detect cycles stack");
+ StackEntry entry;
+ entry.node = node;
+ entry.from = NULL;
+ entry.via_relation = NULL;
+ BLI_stack_push(state->traversal_stack, &entry);
+ set_node_visited_state(node, NODE_IN_STACK);
+}
- int num_cycles = 0;
- foreach (OperationDepsNode *node, graph->operations) {
+/* Schedule leaf nodes (node without input links) for traversal. */
+void schedule_leaf_nodes(CyclesSolverState *state)
+{
+ foreach (OperationDepsNode *node, state->graph->operations) {
bool has_inlinks = false;
foreach (DepsRelation *rel, node->inlinks) {
if (rel->from->type == DEG_NODE_TYPE_OPERATION) {
@@ -97,18 +124,32 @@ void deg_graph_detect_cycles(Depsgraph *graph)
}
node->done = 0;
if (has_inlinks == false) {
- StackEntry entry;
- entry.node = node;
- entry.from = NULL;
- entry.via_relation = NULL;
- BLI_stack_push(traversal_stack, &entry);
- set_node_visited_state(node, NODE_IN_STACK);
+ schedule_node_to_stack(state, node);
}
else {
set_node_visited_state(node, NODE_NOT_VISITED);
}
}
+}
+
+/* Schedule node which was not checked yet for being belong to
+ * any of dependency cycle.
+ */
+bool schedule_non_checked_node(CyclesSolverState *state)
+{
+ foreach (OperationDepsNode *node, state->graph->operations) {
+ if (get_node_visited_state(node) == NODE_NOT_VISITED) {
+ schedule_node_to_stack(state, node);
+ return true;
+ }
+ }
+ return false;
+}
+/* Solve cycles with all nodes which are scheduled for traversal. */
+void solve_cycles(CyclesSolverState *state)
+{
+ BLI_Stack *traversal_stack = state->traversal_stack;
while (!BLI_stack_is_empty(traversal_stack)) {
StackEntry *entry = (StackEntry *)BLI_stack_peek(traversal_stack);
OperationDepsNode *node = entry->node;
@@ -137,7 +178,7 @@ void deg_graph_detect_cycles(Depsgraph *graph)
}
/* TODO(sergey): So called russian roulette cycle solver. */
rel->flag |= DEPSREL_FLAG_CYCLIC;
- ++num_cycles;
+ ++state->num_cycles;
}
else if (to_state == NODE_NOT_VISITED) {
StackEntry new_entry;
@@ -157,11 +198,23 @@ void deg_graph_detect_cycles(Depsgraph *graph)
BLI_stack_discard(traversal_stack);
}
}
+}
- BLI_stack_free(traversal_stack);
+} // namespace
- if (num_cycles != 0) {
- printf("Detected %d dependency cycles\n", num_cycles);
+void deg_graph_detect_cycles(Depsgraph *graph)
+{
+ CyclesSolverState state(graph);
+ /* First we solve cycles which are reachable from leaf nodes. */
+ schedule_leaf_nodes(&state);
+ solve_cycles(&state);
+ /* We are not done yet. It is possible to have closed loop cycle,
+ * for example A -> B -> C -> A. These nodes were not scheduled
+ * yet (since they all have inlinks), and were not traversed since
+ * nobody else points to them.
+ */
+ while (schedule_non_checked_node(&state)) {
+ solve_cycles(&state);
}
}
diff --git a/source/blender/depsgraph/intern/builder/deg_builder_nodes.cc b/source/blender/depsgraph/intern/builder/deg_builder_nodes.cc
index 7572ee90c0b..0f21c152192 100644
--- a/source/blender/depsgraph/intern/builder/deg_builder_nodes.cc
+++ b/source/blender/depsgraph/intern/builder/deg_builder_nodes.cc
@@ -239,6 +239,22 @@ OperationDepsNode *DepsgraphNodeBuilder::add_operation_node(
name_tag);
}
+OperationDepsNode *DepsgraphNodeBuilder::ensure_operation_node(
+ ID *id,
+ eDepsNode_Type comp_type,
+ const DepsEvalOperationCb& op,
+ eDepsOperation_Code opcode,
+ const char *name,
+ int name_tag)
+{
+ OperationDepsNode *operation =
+ find_operation_node(id, comp_type, opcode, name, name_tag);
+ if (operation != NULL) {
+ return operation;
+ }
+ return add_operation_node(id, comp_type, op, opcode, name, name_tag);
+}
+
bool DepsgraphNodeBuilder::has_operation_node(ID *id,
eDepsNode_Type comp_type,
const char *comp_name,
@@ -516,30 +532,54 @@ void DepsgraphNodeBuilder::build_animdata(ID *id)
* \param id: ID-Block that driver is attached to
* \param fcu: Driver-FCurve
*/
-OperationDepsNode *DepsgraphNodeBuilder::build_driver(ID *id, FCurve *fcu)
+void DepsgraphNodeBuilder::build_driver(ID *id, FCurve *fcurve)
{
/* Create data node for this driver */
- /* TODO(sergey): Avoid creating same operation multiple times,
- * in the future we need to avoid lookup of the operation as well
- * and use some tagging magic instead.
- */
- OperationDepsNode *driver_op = find_operation_node(id,
- DEG_NODE_TYPE_PARAMETERS,
- DEG_OPCODE_DRIVER,
- fcu->rna_path ? fcu->rna_path : "",
- fcu->array_index);
-
- if (driver_op == NULL) {
- driver_op = add_operation_node(id,
- DEG_NODE_TYPE_PARAMETERS,
- function_bind(BKE_animsys_eval_driver, _1, id, fcu),
- DEG_OPCODE_DRIVER,
- fcu->rna_path ? fcu->rna_path : "",
- fcu->array_index);
+ ensure_operation_node(id,
+ DEG_NODE_TYPE_PARAMETERS,
+ function_bind(BKE_animsys_eval_driver, _1, id, fcurve),
+ DEG_OPCODE_DRIVER,
+ fcurve->rna_path ? fcurve->rna_path : "",
+ fcurve->array_index);
+ build_driver_variables(id, fcurve);
+}
+
+void DepsgraphNodeBuilder::build_driver_variables(ID * id, FCurve *fcurve)
+{
+ build_driver_id_property(id, fcurve->rna_path);
+ LISTBASE_FOREACH (DriverVar *, dvar, &fcurve->driver->variables) {
+ DRIVER_TARGETS_USED_LOOPER(dvar)
+ {
+ build_driver_id_property(dtar->id, dtar->rna_path);
+ }
+ DRIVER_TARGETS_LOOPER_END
}
+}
- /* return driver node created */
- return driver_op;
+void DepsgraphNodeBuilder::build_driver_id_property(ID *id,
+ const char *rna_path)
+{
+ if (id == NULL || rna_path == NULL) {
+ return;
+ }
+ PointerRNA id_ptr, ptr;
+ PropertyRNA *prop;
+ RNA_id_pointer_create(id, &id_ptr);
+ if (!RNA_path_resolve_full(&id_ptr, rna_path, &ptr, &prop, NULL)) {
+ return;
+ }
+ if (prop == NULL) {
+ return;
+ }
+ if (!RNA_property_is_idprop(prop)) {
+ return;
+ }
+ const char *prop_identifier = RNA_property_identifier((PropertyRNA *)prop);
+ ensure_operation_node(id,
+ DEG_NODE_TYPE_PARAMETERS,
+ NULL,
+ DEG_OPCODE_ID_PROPERTY,
+ prop_identifier);
}
/* Recursively build graph for world */
diff --git a/source/blender/depsgraph/intern/builder/deg_builder_nodes.h b/source/blender/depsgraph/intern/builder/deg_builder_nodes.h
index 825015194e2..9d47dc6bced 100644
--- a/source/blender/depsgraph/intern/builder/deg_builder_nodes.h
+++ b/source/blender/depsgraph/intern/builder/deg_builder_nodes.h
@@ -99,6 +99,13 @@ struct DepsgraphNodeBuilder {
const char *name = "",
int name_tag = -1);
+ OperationDepsNode *ensure_operation_node(ID *id,
+ eDepsNode_Type comp_type,
+ const DepsEvalOperationCb& op,
+ eDepsOperation_Code opcode,
+ const char *name = "",
+ int name_tag = -1);
+
bool has_operation_node(ID *id,
eDepsNode_Type comp_type,
const char *comp_name,
@@ -130,7 +137,9 @@ struct DepsgraphNodeBuilder {
void build_particles(Object *object);
void build_cloth(Object *object);
void build_animdata(ID *id);
- OperationDepsNode *build_driver(ID *id, FCurve *fcurve);
+ void build_driver(ID *id, FCurve *fcurve);
+ void build_driver_variables(ID *id, FCurve *fcurve);
+ void build_driver_id_property(ID *id, const char *rna_path);
void build_ik_pose(Object *object,
bPoseChannel *pchan,
bConstraint *con);
diff --git a/source/blender/depsgraph/intern/builder/deg_builder_relations.cc b/source/blender/depsgraph/intern/builder/deg_builder_relations.cc
index 0d85b1dfc93..40db9d1b5f1 100644
--- a/source/blender/depsgraph/intern/builder/deg_builder_relations.cc
+++ b/source/blender/depsgraph/intern/builder/deg_builder_relations.cc
@@ -1126,7 +1126,26 @@ void DepsgraphRelationBuilder::build_driver_data(ID *id, FCurve *fcu)
}
else {
RNAPathKey target_key(id, rna_path);
- add_relation(driver_key, target_key, "Driver -> Target");
+ if (RNA_pointer_is_null(&target_key.ptr)) {
+ /* TODO(sergey): This would only mean that driver is broken.
+ * so we can't create relation anyway. However, we need to avoid
+ * adding drivers which are known to be buggy to a dependency
+ * graph, in order to save computational power.
+ */
+ }
+ else {
+ if (target_key.prop != NULL &&
+ RNA_property_is_idprop(target_key.prop))
+ {
+ OperationKey parameters_key(id,
+ DEG_NODE_TYPE_PARAMETERS,
+ DEG_OPCODE_PARAMETERS_EVAL);
+ add_relation(target_key,
+ parameters_key,
+ "Driver Target -> Properties");
+ }
+ add_relation(driver_key, target_key, "Driver -> Target");
+ }
}
}
diff --git a/source/blender/depsgraph/intern/depsgraph.cc b/source/blender/depsgraph/intern/depsgraph.cc
index 841242b995e..2e87786639c 100644
--- a/source/blender/depsgraph/intern/depsgraph.cc
+++ b/source/blender/depsgraph/intern/depsgraph.cc
@@ -214,10 +214,18 @@ static bool pointer_to_component_node_criteria(
}
if (prop != NULL) {
/* All unknown data effectively falls under "parameter evaluation". */
- *type = DEG_NODE_TYPE_PARAMETERS;
- *operation_code = DEG_OPCODE_PARAMETERS_EVAL;
- *operation_name = "";
- *operation_name_tag = -1;
+ if (RNA_property_is_idprop(prop)) {
+ *type = DEG_NODE_TYPE_PARAMETERS;
+ *operation_code = DEG_OPCODE_ID_PROPERTY;
+ *operation_name = RNA_property_identifier((PropertyRNA *)prop);
+ *operation_name_tag = -1;
+ }
+ else {
+ *type = DEG_NODE_TYPE_PARAMETERS;
+ *operation_code = DEG_OPCODE_PARAMETERS_EVAL;
+ *operation_name = "";
+ *operation_name_tag = -1;
+ }
return true;
}
return false;
diff --git a/source/blender/depsgraph/intern/depsgraph_type_defines.cc b/source/blender/depsgraph/intern/depsgraph_type_defines.cc
index 675002d6b90..41c72d11eac 100644
--- a/source/blender/depsgraph/intern/depsgraph_type_defines.cc
+++ b/source/blender/depsgraph/intern/depsgraph_type_defines.cc
@@ -81,6 +81,7 @@ static const char *stringify_opcode(eDepsOperation_Code opcode)
#define STRINGIFY_OPCODE(name) case DEG_OPCODE_##name: return #name
/* Generic Operations. */
STRINGIFY_OPCODE(OPERATION);
+ STRINGIFY_OPCODE(ID_PROPERTY);
STRINGIFY_OPCODE(PARAMETERS_EVAL);
STRINGIFY_OPCODE(PLACEHOLDER);
/* Animation, Drivers, etc. */
diff --git a/source/blender/depsgraph/intern/depsgraph_types.h b/source/blender/depsgraph/intern/depsgraph_types.h
index b2dbe5d2a62..2d0b67f7ee6 100644
--- a/source/blender/depsgraph/intern/depsgraph_types.h
+++ b/source/blender/depsgraph/intern/depsgraph_types.h
@@ -137,6 +137,7 @@ typedef enum eDepsOperation_Code {
DEG_OPCODE_OPERATION = 0,
/* Generic parameters evaluation. */
+ DEG_OPCODE_ID_PROPERTY,
DEG_OPCODE_PARAMETERS_EVAL,
// XXX: Placeholder while porting depsgraph code
diff --git a/source/blender/editors/space_clip/tracking_ops.c b/source/blender/editors/space_clip/tracking_ops.c
index 2ec4f96931f..50f21c8891c 100644
--- a/source/blender/editors/space_clip/tracking_ops.c
+++ b/source/blender/editors/space_clip/tracking_ops.c
@@ -1858,7 +1858,7 @@ static bool is_track_clean(MovieTrackingTrack *track, int frames, int del)
}
}
- if (count == 0) {
+ if (del && count == 0) {
ok = 0;
}
diff --git a/source/blender/editors/space_sequencer/sequencer_edit.c b/source/blender/editors/space_sequencer/sequencer_edit.c
index 29a7e11d859..0895d28fba7 100644
--- a/source/blender/editors/space_sequencer/sequencer_edit.c
+++ b/source/blender/editors/space_sequencer/sequencer_edit.c
@@ -671,6 +671,9 @@ static Sequence *cut_seq_hard(Scene *scene, Sequence *seq, int cutframe)
Sequence *seqn = NULL;
bool skip_dup = false;
+ /* Unlike soft-cut, it's important to use the same value for both strips. */
+ const bool is_end_exact = ((seq->start + seq->len) == cutframe);
+
/* backup values */
ts.start = seq->start;
ts.machine = seq->machine;
@@ -683,7 +686,7 @@ static Sequence *cut_seq_hard(Scene *scene, Sequence *seq, int cutframe)
ts.anim_startofs = seq->anim_startofs;
ts.anim_endofs = seq->anim_endofs;
ts.len = seq->len;
-
+
/* First Strip! */
/* strips with extended stillfames before */
@@ -695,6 +698,8 @@ static Sequence *cut_seq_hard(Scene *scene, Sequence *seq, int cutframe)
BKE_sequence_calc(scene, seq);
}
+ /* Important to offset the start when 'cutframe == seq->start'
+ * because we need at least one frame of content after start/end still have clipped it. */
if ((seq->startstill) && (cutframe <= seq->start)) {
/* don't do funny things with METAs ... */
if (seq->type == SEQ_TYPE_META) {
@@ -709,13 +714,15 @@ static Sequence *cut_seq_hard(Scene *scene, Sequence *seq, int cutframe)
}
}
/* normal strip */
- else if ((cutframe >= seq->start) && (cutframe < (seq->start + seq->len))) {
+ else if ((is_end_exact == false) &&
+ ((cutframe >= seq->start) && (cutframe <= (seq->start + seq->len))))
+ {
seq->endofs = 0;
seq->endstill = 0;
seq->anim_endofs += (seq->start + seq->len) - cutframe;
}
/* strips with extended stillframes after */
- else if (((seq->start + seq->len) == cutframe) ||
+ else if ((is_end_exact == true) ||
(((seq->start + seq->len) < cutframe) && (seq->endstill)))
{
seq->endstill -= seq->enddisp - cutframe;
@@ -735,7 +742,11 @@ static Sequence *cut_seq_hard(Scene *scene, Sequence *seq, int cutframe)
if (seqn) {
seqn->flag |= SELECT;
-
+
+ /* Important not to re-assign this (unlike soft-cut) */
+#if 0
+ is_end_exact = ((seqn->start + seqn->len) == cutframe);
+#endif
/* Second Strip! */
/* strips with extended stillframes before */
if ((seqn->startstill) && (cutframe == seqn->start + 1)) {
@@ -744,9 +755,11 @@ static Sequence *cut_seq_hard(Scene *scene, Sequence *seq, int cutframe)
seqn->anim_endofs = ts.anim_endofs;
seqn->endstill = ts.endstill;
}
-
+
/* normal strip */
- else if ((cutframe >= seqn->start) && (cutframe < (seqn->start + seqn->len))) {
+ else if ((is_end_exact == false) &&
+ ((cutframe >= seqn->start) && (cutframe <= (seqn->start + seqn->len))))
+ {
seqn->start = cutframe;
seqn->startstill = 0;
seqn->startofs = 0;
@@ -755,9 +768,9 @@ static Sequence *cut_seq_hard(Scene *scene, Sequence *seq, int cutframe)
seqn->anim_endofs = ts.anim_endofs;
seqn->endstill = ts.endstill;
}
-
+
/* strips with extended stillframes after */
- else if (((seqn->start + seqn->len) == cutframe) ||
+ else if ((is_end_exact == true) ||
(((seqn->start + seqn->len) < cutframe) && (seqn->endstill)))
{
seqn->start = cutframe;
@@ -766,7 +779,7 @@ static Sequence *cut_seq_hard(Scene *scene, Sequence *seq, int cutframe)
seqn->endstill = ts.enddisp - cutframe - 1;
seqn->startstill = 0;
}
-
+
BKE_sequence_reload_new_file(scene, seqn, false);
BKE_sequence_calc(scene, seqn);
}
@@ -779,6 +792,8 @@ static Sequence *cut_seq_soft(Scene *scene, Sequence *seq, int cutframe)
Sequence *seqn = NULL;
bool skip_dup = false;
+ bool is_end_exact = ((seq->start + seq->len) == cutframe);
+
/* backup values */
ts.start = seq->start;
ts.machine = seq->machine;
@@ -791,10 +806,12 @@ static Sequence *cut_seq_soft(Scene *scene, Sequence *seq, int cutframe)
ts.anim_startofs = seq->anim_startofs;
ts.anim_endofs = seq->anim_endofs;
ts.len = seq->len;
-
+
/* First Strip! */
/* strips with extended stillfames before */
-
+
+ /* Important to offset the start when 'cutframe == seq->start'
+ * because we need at least one frame of content after start/end still have clipped it. */
if ((seq->startstill) && (cutframe <= seq->start)) {
/* don't do funny things with METAs ... */
if (seq->type == SEQ_TYPE_META) {
@@ -809,11 +826,13 @@ static Sequence *cut_seq_soft(Scene *scene, Sequence *seq, int cutframe)
}
}
/* normal strip */
- else if ((cutframe >= seq->start) && (cutframe < (seq->start + seq->len))) {
+ else if ((is_end_exact == false) &&
+ (cutframe >= seq->start) && (cutframe <= (seq->start + seq->len)))
+ {
seq->endofs = (seq->start + seq->len) - cutframe;
}
/* strips with extended stillframes after */
- else if (((seq->start + seq->len) == cutframe) ||
+ else if ((is_end_exact == true) ||
(((seq->start + seq->len) < cutframe) && (seq->endstill)))
{
seq->endstill -= seq->enddisp - cutframe;
@@ -832,7 +851,9 @@ static Sequence *cut_seq_soft(Scene *scene, Sequence *seq, int cutframe)
if (seqn) {
seqn->flag |= SELECT;
-
+
+ is_end_exact = ((seqn->start + seqn->len) == cutframe);
+
/* Second Strip! */
/* strips with extended stillframes before */
if ((seqn->startstill) && (cutframe == seqn->start + 1)) {
@@ -843,15 +864,17 @@ static Sequence *cut_seq_soft(Scene *scene, Sequence *seq, int cutframe)
}
/* normal strip */
- if ((cutframe >= seqn->start) && (cutframe < (seqn->start + seqn->len))) {
+ else if ((is_end_exact == false) &&
+ (cutframe >= seqn->start) && (cutframe <= (seqn->start + seqn->len)))
+ {
seqn->startstill = 0;
seqn->startofs = cutframe - ts.start;
seqn->endofs = ts.endofs;
seqn->endstill = ts.endstill;
}
-
+
/* strips with extended stillframes after */
- else if (((seqn->start + seqn->len) == cutframe) ||
+ else if ((is_end_exact == true) ||
(((seqn->start + seqn->len) < cutframe) && (seqn->endstill)))
{
seqn->start = cutframe - ts.len + 1;
@@ -859,7 +882,7 @@ static Sequence *cut_seq_soft(Scene *scene, Sequence *seq, int cutframe)
seqn->endstill = ts.enddisp - cutframe - 1;
seqn->startstill = 0;
}
-
+
BKE_sequence_calc(scene, seqn);
}
return seqn;
diff --git a/source/blender/editors/space_view3d/drawmesh.c b/source/blender/editors/space_view3d/drawmesh.c
index bbbf8c633bd..b6bcc592cc8 100644
--- a/source/blender/editors/space_view3d/drawmesh.c
+++ b/source/blender/editors/space_view3d/drawmesh.c
@@ -1115,6 +1115,7 @@ static void tex_mat_set_texture_cb(void *userData, int mat_nr, void *attribs)
gattribs->layer[0].type = CD_MTFACE;
gattribs->layer[0].name[0] = '\0';
gattribs->layer[0].gltexco = 1;
+ gattribs->layer[0].glinfoindoex = -1;
gattribs->totlayer = 1;
/* bind material */