From c2b0d8b6d6c771da70b8fd9da5ac9cc53d04184d Mon Sep 17 00:00:00 2001 From: Sergey Sharybin Date: Mon, 10 Dec 2018 15:09:46 +0100 Subject: Fix T57633: Particle texture update problem Textures are now hooked up to the RESET operation of particle settings, which ensures particles being re-distributed when texture is changed. This is limited to a direct user modifications, which matches old behavior in 2.79. --- .../depsgraph/intern/builder/deg_builder_nodes.cc | 71 +++++++++++++------- .../depsgraph/intern/builder/deg_builder_nodes.h | 2 +- .../intern/builder/deg_builder_relations.cc | 77 +++++++++++++++++----- .../intern/builder/deg_builder_relations.h | 8 +-- .../intern/debug/deg_debug_relations_graphviz.cc | 3 +- source/blender/depsgraph/intern/depsgraph_tag.cc | 4 +- .../depsgraph/intern/depsgraph_type_defines.cc | 11 +++- source/blender/depsgraph/intern/depsgraph_types.h | 13 ++-- .../depsgraph/intern/nodes/deg_node_component.cc | 6 +- .../depsgraph/intern/nodes/deg_node_component.h | 1 + 10 files changed, 139 insertions(+), 57 deletions(-) (limited to 'source/blender/depsgraph') diff --git a/source/blender/depsgraph/intern/builder/deg_builder_nodes.cc b/source/blender/depsgraph/intern/builder/deg_builder_nodes.cc index 3fcaa12f036..d65acbcad1d 100644 --- a/source/blender/depsgraph/intern/builder/deg_builder_nodes.cc +++ b/source/blender/depsgraph/intern/builder/deg_builder_nodes.cc @@ -640,7 +640,7 @@ void DepsgraphNodeBuilder::build_object(int base_index, build_animdata(&object->id); /* Particle systems. */ if (object->particlesystem.first != NULL) { - build_particles(object, is_visible); + build_particle_systems(object, is_visible); } /* Proxy object to copy from. */ if (object->proxy_from != NULL) { @@ -1109,8 +1109,8 @@ void DepsgraphNodeBuilder::build_rigidbody(Scene *scene) } } -void DepsgraphNodeBuilder::build_particles(Object *object, - bool is_object_visible) +void DepsgraphNodeBuilder::build_particle_systems(Object *object, + bool is_object_visible) { /** * Particle Systems Nodes @@ -1128,25 +1128,22 @@ void DepsgraphNodeBuilder::build_particles(Object *object, */ /* Component for all particle systems. */ ComponentDepsNode *psys_comp = - add_component_node(&object->id, DEG_NODE_TYPE_EVAL_PARTICLES); + add_component_node(&object->id, DEG_NODE_TYPE_PARTICLE_SYSTEM); - /* TODO(sergey): Need to get COW of PSYS. */ - Scene *scene_cow = get_cow_datablock(scene_); Object *ob_cow = get_cow_datablock(object); - - add_operation_node(psys_comp, - function_bind(BKE_particle_system_eval_init, - _1, - scene_cow, - ob_cow), - DEG_OPCODE_PARTICLE_SYSTEM_EVAL_INIT); + OperationDepsNode *op_node; + op_node = add_operation_node(psys_comp, + function_bind(BKE_particle_system_eval_init, + _1, + ob_cow), + DEG_OPCODE_PARTICLE_SYSTEM_INIT); + op_node->set_as_entry(); /* Build all particle systems. */ LISTBASE_FOREACH (ParticleSystem *, psys, &object->particlesystem) { ParticleSettings *part = psys->part; /* Build particle settings operations. * - * NOTE: The call itself ensures settings are only build once. - */ + * NOTE: The call itself ensures settings are only build once. */ build_particle_settings(part); /* Particle system evaluation. */ add_operation_node(psys_comp, @@ -1170,19 +1167,49 @@ void DepsgraphNodeBuilder::build_particles(Object *object, break; } } + op_node = add_operation_node(psys_comp, + NULL, + DEG_OPCODE_PARTICLE_SYSTEM_DONE); + op_node->set_as_exit(); } -void DepsgraphNodeBuilder::build_particle_settings(ParticleSettings *part) { - if (built_map_.checkIsBuiltAndTag(part)) { +void DepsgraphNodeBuilder::build_particle_settings( + ParticleSettings *particle_settings) { + if (built_map_.checkIsBuiltAndTag(particle_settings)) { return; } + /* Make sure we've got proper copied ID pointer. */ + add_id_node(&particle_settings->id); + ParticleSettings *particle_settings_cow = + get_cow_datablock(particle_settings); /* Animation data. */ - build_animdata(&part->id); + build_animdata(&particle_settings->id); /* Parameters change. */ - add_operation_node(&part->id, - DEG_NODE_TYPE_PARAMETERS, - NULL, - DEG_OPCODE_PARTICLE_SETTINGS_EVAL); + OperationDepsNode *op_node; + op_node = add_operation_node(&particle_settings->id, + DEG_NODE_TYPE_PARTICLE_SETTINGS, + NULL, + DEG_OPCODE_PARTICLE_SETTINGS_INIT); + op_node->set_as_entry(); + add_operation_node(&particle_settings->id, + DEG_NODE_TYPE_PARTICLE_SETTINGS, + function_bind(BKE_particle_settings_eval_reset, + _1, + particle_settings_cow), + DEG_OPCODE_PARTICLE_SETTINGS_RESET); + op_node = add_operation_node(&particle_settings->id, + DEG_NODE_TYPE_PARTICLE_SETTINGS, + NULL, + DEG_OPCODE_PARTICLE_SETTINGS_EVAL); + op_node->set_as_exit(); + /* Texture slots. */ + for (int mtex_index = 0; mtex_index < MAX_MTEX; ++mtex_index) { + MTex *mtex = particle_settings->mtex[mtex_index]; + if (mtex == NULL || mtex->tex == NULL) { + continue; + } + build_texture(mtex->tex); + } } /* Shapekeys */ diff --git a/source/blender/depsgraph/intern/builder/deg_builder_nodes.h b/source/blender/depsgraph/intern/builder/deg_builder_nodes.h index cdf1f6ed03d..3357f6cb0a2 100644 --- a/source/blender/depsgraph/intern/builder/deg_builder_nodes.h +++ b/source/blender/depsgraph/intern/builder/deg_builder_nodes.h @@ -190,7 +190,7 @@ struct DepsgraphNodeBuilder { int pchan_index, bool is_object_visible); void build_rigidbody(Scene *scene); - void build_particles(Object *object, bool is_object_visible); + void build_particle_systems(Object *object, bool is_object_visible); void build_particle_settings(ParticleSettings *part); void build_animdata(ID *id); void build_animdata_nlastrip_targets(ListBase *strips); diff --git a/source/blender/depsgraph/intern/builder/deg_builder_relations.cc b/source/blender/depsgraph/intern/builder/deg_builder_relations.cc index f66a0a8963a..1d5ff8cd3e5 100644 --- a/source/blender/depsgraph/intern/builder/deg_builder_relations.cc +++ b/source/blender/depsgraph/intern/builder/deg_builder_relations.cc @@ -410,7 +410,8 @@ void DepsgraphRelationBuilder::add_forcefield_relations( } if (relation->psys) { if (relation->ob != object) { - ComponentKey eff_key(&relation->ob->id, DEG_NODE_TYPE_EVAL_PARTICLES); + ComponentKey eff_key(&relation->ob->id, + DEG_NODE_TYPE_PARTICLE_SYSTEM); add_relation(eff_key, key, name); /* TODO: remove this when/if EVAL_PARTICLES is sufficient * for up to date particles. @@ -420,7 +421,7 @@ void DepsgraphRelationBuilder::add_forcefield_relations( } else if (relation->psys != psys) { OperationKey eff_key(&relation->ob->id, - DEG_NODE_TYPE_EVAL_PARTICLES, + DEG_NODE_TYPE_PARTICLE_SYSTEM, DEG_OPCODE_PARTICLE_SYSTEM_EVAL, relation->psys->name); add_relation(eff_key, key, name); @@ -661,7 +662,7 @@ void DepsgraphRelationBuilder::build_object(Base *base, Object *object) build_object_data(object); /* Particle systems. */ if (object->particlesystem.first != NULL) { - build_particles(object); + build_particle_systems(object); } /* Proxy object to copy from. */ if (object->proxy_from != NULL) { @@ -1692,16 +1693,21 @@ void DepsgraphRelationBuilder::build_rigidbody(Scene *scene) } } -void DepsgraphRelationBuilder::build_particles(Object *object) +void DepsgraphRelationBuilder::build_particle_systems(Object *object) { TimeSourceKey time_src_key; OperationKey obdata_ubereval_key(&object->id, DEG_NODE_TYPE_GEOMETRY, DEG_OPCODE_GEOMETRY_UBEREVAL); OperationKey eval_init_key(&object->id, - DEG_NODE_TYPE_EVAL_PARTICLES, - DEG_OPCODE_PARTICLE_SYSTEM_EVAL_INIT); - + DEG_NODE_TYPE_PARTICLE_SYSTEM, + DEG_OPCODE_PARTICLE_SYSTEM_INIT); + OperationKey eval_done_key(&object->id, + DEG_NODE_TYPE_PARTICLE_SYSTEM, + DEG_OPCODE_PARTICLE_SYSTEM_DONE); + ComponentKey eval_key(&object->id, DEG_NODE_TYPE_PARTICLE_SYSTEM); + ComponentKey point_cache_key(&object->id, DEG_NODE_TYPE_POINT_CACHE); + add_relation(eval_key, point_cache_key, "Particle Point Cache"); /* Particle systems. */ LISTBASE_FOREACH (ParticleSystem *, psys, &object->particlesystem) { ParticleSettings *part = psys->part; @@ -1714,16 +1720,17 @@ void DepsgraphRelationBuilder::build_particles(Object *object) /* This particle system. */ OperationKey psys_key(&object->id, - DEG_NODE_TYPE_EVAL_PARTICLES, + DEG_NODE_TYPE_PARTICLE_SYSTEM, DEG_OPCODE_PARTICLE_SYSTEM_EVAL, psys->name); /* Update particle system when settings changes. */ OperationKey particle_settings_key(&part->id, - DEG_NODE_TYPE_PARAMETERS, + DEG_NODE_TYPE_PARTICLE_SETTINGS, DEG_OPCODE_PARTICLE_SETTINGS_EVAL); add_relation(particle_settings_key, eval_init_key, "Particle Settings Change"); add_relation(eval_init_key, psys_key, "Init -> PSys"); + add_relation(psys_key, eval_done_key, "PSys -> Done"); /* TODO(sergey): Currently particle update is just a placeholder, * hook it to the ubereval node so particle system is getting updated * on playback. @@ -1777,18 +1784,16 @@ void DepsgraphRelationBuilder::build_particles(Object *object) /* Make sure object's relations are all built. */ build_object(NULL, part->dup_ob); /* Build relation for the particle visualization. */ - build_particles_visualization_object(object, - psys, - part->dup_ob); + build_particle_system_visualization_object( + object, psys, part->dup_ob); } break; case PART_DRAW_GR: if (part->dup_group != NULL) { build_collection(NULL, NULL, part->dup_group); LISTBASE_FOREACH (CollectionObject *, go, &part->dup_group->gobject) { - build_particles_visualization_object(object, - psys, - go->ob); + build_particle_system_visualization_object( + object, psys, go->ob); } } break; @@ -1802,7 +1807,7 @@ void DepsgraphRelationBuilder::build_particles(Object *object) * is implemented. */ ComponentKey transform_key(&object->id, DEG_NODE_TYPE_TRANSFORM); - add_relation(transform_key, obdata_ubereval_key, "Partcile Eval"); + add_relation(transform_key, obdata_ubereval_key, "Particle Eval"); } void DepsgraphRelationBuilder::build_particle_settings(ParticleSettings *part) @@ -1812,15 +1817,45 @@ void DepsgraphRelationBuilder::build_particle_settings(ParticleSettings *part) } /* Animation data relations. */ build_animdata(&part->id); + OperationKey particle_settings_init_key(&part->id, + DEG_NODE_TYPE_PARTICLE_SETTINGS, + DEG_OPCODE_PARTICLE_SETTINGS_INIT); + OperationKey particle_settings_eval_key(&part->id, + DEG_NODE_TYPE_PARTICLE_SETTINGS, + DEG_OPCODE_PARTICLE_SETTINGS_EVAL); + OperationKey particle_settings_reset_key( + &part->id, + DEG_NODE_TYPE_PARTICLE_SETTINGS, + DEG_OPCODE_PARTICLE_SETTINGS_RESET); + add_relation(particle_settings_init_key, + particle_settings_eval_key, + "Particle Settings Init Order"); + add_relation(particle_settings_reset_key, + particle_settings_eval_key, + "Particle Settings Reset"); + /* Texture slots. */ + for (int mtex_index = 0; mtex_index < MAX_MTEX; ++mtex_index) { + MTex *mtex = part->mtex[mtex_index]; + if (mtex == NULL || mtex->tex == NULL) { + continue; + } + build_texture(mtex->tex); + ComponentKey texture_key(&mtex->tex->id, + DEG_NODE_TYPE_GENERIC_DATABLOCK); + add_relation(texture_key, + particle_settings_reset_key, + "Particle Texture", + DEPSREL_FLAG_FLUSH_USER_EDIT_ONLY); + } } -void DepsgraphRelationBuilder::build_particles_visualization_object( +void DepsgraphRelationBuilder::build_particle_system_visualization_object( Object *object, ParticleSystem *psys, Object *draw_object) { OperationKey psys_key(&object->id, - DEG_NODE_TYPE_EVAL_PARTICLES, + DEG_NODE_TYPE_PARTICLE_SYSTEM, DEG_OPCODE_PARTICLE_SYSTEM_EVAL, psys->name); OperationKey obdata_ubereval_key(&object->id, @@ -2285,6 +2320,12 @@ void DepsgraphRelationBuilder::build_texture(Tex *texture) /* texture's nodetree */ build_nodetree(texture->nodetree); build_nested_nodetree(&texture->id, texture->nodetree); + if (check_id_has_anim_component(&texture->id)) { + ComponentKey animation_key(&texture->id, DEG_NODE_TYPE_ANIMATION); + ComponentKey datablock_key(&texture->id, + DEG_NODE_TYPE_GENERIC_DATABLOCK); + add_relation(animation_key, datablock_key, "Datablock Animation"); + } } void DepsgraphRelationBuilder::build_compositor(Scene *scene) diff --git a/source/blender/depsgraph/intern/builder/deg_builder_relations.h b/source/blender/depsgraph/intern/builder/deg_builder_relations.h index face2a1d43f..928834cbef7 100644 --- a/source/blender/depsgraph/intern/builder/deg_builder_relations.h +++ b/source/blender/depsgraph/intern/builder/deg_builder_relations.h @@ -252,11 +252,11 @@ struct DepsgraphRelationBuilder void build_driver_variables(ID *id, FCurve *fcurve); void build_world(World *world); void build_rigidbody(Scene *scene); - void build_particles(Object *object); + void build_particle_systems(Object *object); void build_particle_settings(ParticleSettings *part); - void build_particles_visualization_object(Object *object, - ParticleSystem *psys, - Object *draw_object); + void build_particle_system_visualization_object(Object *object, + ParticleSystem *psys, + Object *draw_object); void build_ik_pose(Object *object, bPoseChannel *pchan, bConstraint *con, diff --git a/source/blender/depsgraph/intern/debug/deg_debug_relations_graphviz.cc b/source/blender/depsgraph/intern/debug/deg_debug_relations_graphviz.cc index 15744ff614f..d8a24292aa6 100644 --- a/source/blender/depsgraph/intern/debug/deg_debug_relations_graphviz.cc +++ b/source/blender/depsgraph/intern/debug/deg_debug_relations_graphviz.cc @@ -416,7 +416,8 @@ static void deg_debug_graphviz_node(const DebugContext &ctx, case DEG_NODE_TYPE_CACHE: case DEG_NODE_TYPE_POINT_CACHE: case DEG_NODE_TYPE_LAYER_COLLECTIONS: - case DEG_NODE_TYPE_EVAL_PARTICLES: + case DEG_NODE_TYPE_PARTICLE_SYSTEM: + case DEG_NODE_TYPE_PARTICLE_SETTINGS: case DEG_NODE_TYPE_COPY_ON_WRITE: case DEG_NODE_TYPE_OBJECT_FROM_LAYER: case DEG_NODE_TYPE_BATCH_CACHE: diff --git a/source/blender/depsgraph/intern/depsgraph_tag.cc b/source/blender/depsgraph/intern/depsgraph_tag.cc index 69c6d17cc7e..a1083cbfe0a 100644 --- a/source/blender/depsgraph/intern/depsgraph_tag.cc +++ b/source/blender/depsgraph/intern/depsgraph_tag.cc @@ -177,10 +177,10 @@ void depsgraph_tag_to_component_opcode(const ID *id, * but we can survive for now with single exception here. * Particles needs reconsideration anyway, */ - *component_type = DEG_NODE_TYPE_PARAMETERS; + *component_type = DEG_NODE_TYPE_PARTICLE_SYSTEM; } else { - *component_type = DEG_NODE_TYPE_EVAL_PARTICLES; + *component_type = DEG_NODE_TYPE_PARTICLE_SYSTEM; } break; case ID_RECALC_COPY_ON_WRITE: diff --git a/source/blender/depsgraph/intern/depsgraph_type_defines.cc b/source/blender/depsgraph/intern/depsgraph_type_defines.cc index 4edf616961c..a89446ea28f 100644 --- a/source/blender/depsgraph/intern/depsgraph_type_defines.cc +++ b/source/blender/depsgraph/intern/depsgraph_type_defines.cc @@ -96,7 +96,8 @@ const char *nodeTypeAsString(eDepsNode_Type type) /* **** Evaluation-Related Outer Types (with Subdata) **** */ STRINGIFY_TYPE(EVAL_POSE); STRINGIFY_TYPE(BONE); - STRINGIFY_TYPE(EVAL_PARTICLES); + STRINGIFY_TYPE(PARTICLE_SYSTEM); + STRINGIFY_TYPE(PARTICLE_SETTINGS); STRINGIFY_TYPE(SHADING); STRINGIFY_TYPE(SHADING_PARAMETERS); STRINGIFY_TYPE(CACHE); @@ -162,10 +163,14 @@ const char *operationCodeAsString(eDepsOperation_Code opcode) STRINGIFY_OPCODE(BONE_READY); STRINGIFY_OPCODE(BONE_DONE); STRINGIFY_OPCODE(BONE_SEGMENTS); - /* Particles. */ - STRINGIFY_OPCODE(PARTICLE_SYSTEM_EVAL_INIT); + /* Particle System. */ + STRINGIFY_OPCODE(PARTICLE_SYSTEM_INIT); STRINGIFY_OPCODE(PARTICLE_SYSTEM_EVAL); + STRINGIFY_OPCODE(PARTICLE_SYSTEM_DONE); + /* Particles Settings. */ + STRINGIFY_OPCODE(PARTICLE_SETTINGS_INIT); STRINGIFY_OPCODE(PARTICLE_SETTINGS_EVAL); + STRINGIFY_OPCODE(PARTICLE_SETTINGS_RESET); /* Point Cache. */ STRINGIFY_OPCODE(POINT_CACHE_RESET); /* Batch cache. */ diff --git a/source/blender/depsgraph/intern/depsgraph_types.h b/source/blender/depsgraph/intern/depsgraph_types.h index 2de614ff8ad..5d51e367394 100644 --- a/source/blender/depsgraph/intern/depsgraph_types.h +++ b/source/blender/depsgraph/intern/depsgraph_types.h @@ -149,7 +149,8 @@ typedef enum eDepsNode_Type { /* Bone Component - Child/Subcomponent of Pose */ DEG_NODE_TYPE_BONE, /* Particle Systems Component */ - DEG_NODE_TYPE_EVAL_PARTICLES, + DEG_NODE_TYPE_PARTICLE_SYSTEM, + DEG_NODE_TYPE_PARTICLE_SETTINGS, /* Material Shading Component */ DEG_NODE_TYPE_SHADING, DEG_NODE_TYPE_SHADING_PARAMETERS, @@ -261,11 +262,15 @@ typedef enum eDepsOperation_Code { /* B-Bone segment shape computation (after DONE) */ DEG_OPCODE_BONE_SEGMENTS, - /* Particles. ----------------------------------------------------------- */ - /* Particle System evaluation. */ - DEG_OPCODE_PARTICLE_SYSTEM_EVAL_INIT, + /* Particle System. ----------------------------------------------------- */ + DEG_OPCODE_PARTICLE_SYSTEM_INIT, DEG_OPCODE_PARTICLE_SYSTEM_EVAL, + DEG_OPCODE_PARTICLE_SYSTEM_DONE, + + /* Particle Settings. --------------------------------------------------- */ + DEG_OPCODE_PARTICLE_SETTINGS_INIT, DEG_OPCODE_PARTICLE_SETTINGS_EVAL, + DEG_OPCODE_PARTICLE_SETTINGS_RESET, /* Point Cache. --------------------------------------------------------- */ DEG_OPCODE_POINT_CACHE_RESET, diff --git a/source/blender/depsgraph/intern/nodes/deg_node_component.cc b/source/blender/depsgraph/intern/nodes/deg_node_component.cc index 6840aa0e7e5..5eb8dc9dd09 100644 --- a/source/blender/depsgraph/intern/nodes/deg_node_component.cc +++ b/source/blender/depsgraph/intern/nodes/deg_node_component.cc @@ -392,7 +392,8 @@ DEG_COMPONENT_NODE_DEFINE(CopyOnWrite, COPY_ON_WRITE, ID_RECALC_COPY_ DEG_COMPONENT_NODE_DEFINE(Geometry, GEOMETRY, ID_RECALC_GEOMETRY); DEG_COMPONENT_NODE_DEFINE(LayerCollections, LAYER_COLLECTIONS, 0); DEG_COMPONENT_NODE_DEFINE(Parameters, PARAMETERS, 0); -DEG_COMPONENT_NODE_DEFINE(Particles, EVAL_PARTICLES, ID_RECALC_GEOMETRY); +DEG_COMPONENT_NODE_DEFINE(Particles, PARTICLE_SYSTEM, ID_RECALC_GEOMETRY); +DEG_COMPONENT_NODE_DEFINE(ParticleSettings, PARTICLE_SETTINGS, 0); DEG_COMPONENT_NODE_DEFINE(PointCache, POINT_CACHE, 0); DEG_COMPONENT_NODE_DEFINE(Pose, EVAL_POSE, ID_RECALC_GEOMETRY); DEG_COMPONENT_NODE_DEFINE(Proxy, PROXY, ID_RECALC_GEOMETRY); @@ -417,7 +418,8 @@ void deg_register_component_depsnodes() deg_register_node_typeinfo(&DNTI_GEOMETRY); deg_register_node_typeinfo(&DNTI_LAYER_COLLECTIONS); deg_register_node_typeinfo(&DNTI_PARAMETERS); - deg_register_node_typeinfo(&DNTI_EVAL_PARTICLES); + deg_register_node_typeinfo(&DNTI_PARTICLE_SYSTEM); + deg_register_node_typeinfo(&DNTI_PARTICLE_SETTINGS); deg_register_node_typeinfo(&DNTI_POINT_CACHE); deg_register_node_typeinfo(&DNTI_PROXY); deg_register_node_typeinfo(&DNTI_EVAL_POSE); diff --git a/source/blender/depsgraph/intern/nodes/deg_node_component.h b/source/blender/depsgraph/intern/nodes/deg_node_component.h index 0852d886ae4..151e37f7772 100644 --- a/source/blender/depsgraph/intern/nodes/deg_node_component.h +++ b/source/blender/depsgraph/intern/nodes/deg_node_component.h @@ -191,6 +191,7 @@ DEG_COMPONENT_NODE_DECLARE_GENERIC(Geometry); DEG_COMPONENT_NODE_DECLARE_GENERIC(LayerCollections); DEG_COMPONENT_NODE_DECLARE_GENERIC(Parameters); DEG_COMPONENT_NODE_DECLARE_GENERIC(Particles); +DEG_COMPONENT_NODE_DECLARE_GENERIC(ParticleSettings); DEG_COMPONENT_NODE_DECLARE_GENERIC(Pose); DEG_COMPONENT_NODE_DECLARE_GENERIC(PointCache); DEG_COMPONENT_NODE_DECLARE_GENERIC(Proxy); -- cgit v1.2.3