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:
Diffstat (limited to 'source/blender')
-rw-r--r--source/blender/blenkernel/intern/library_override.c62
-rw-r--r--source/blender/editors/object/object_relations.c6
2 files changed, 54 insertions, 14 deletions
diff --git a/source/blender/blenkernel/intern/library_override.c b/source/blender/blenkernel/intern/library_override.c
index ba482359607..6532fce5778 100644
--- a/source/blender/blenkernel/intern/library_override.c
+++ b/source/blender/blenkernel/intern/library_override.c
@@ -207,6 +207,11 @@ ID *BKE_override_library_create_from_id(Main *bmain, ID *reference_id)
* \note Set id->newid of overridden libs with newly created overrides,
* caller is responsible to clean those pointers before/after usage as needed.
*
+ * \note By default, it will only remap newly created local overriding data-blocks between
+ * themselves, to avoid 'enforcing' those overrides into all other usages of the linked data in
+ * main. You can add more local IDs to be remapped to use new overriding ones by setting their
+ * LIB_TAG_DOIT tag.
+ *
* \return \a true on success, \a false otherwise.
*/
bool BKE_override_library_create_from_tag(Main *bmain)
@@ -214,26 +219,59 @@ bool BKE_override_library_create_from_tag(Main *bmain)
ID *reference_id;
bool ret = true;
+ ListBase todo_ids = {NULL};
+ LinkData *todo_id_iter;
+
+ /* Get all IDs we want to override. */
FOREACH_MAIN_ID_BEGIN (bmain, reference_id) {
if ((reference_id->tag & LIB_TAG_DOIT) != 0 && reference_id->lib != NULL) {
- if ((reference_id->newid = override_library_create_from(bmain, reference_id)) == NULL) {
- ret = false;
- }
+ todo_id_iter = MEM_callocN(sizeof(*todo_id_iter), __func__);
+ todo_id_iter->data = reference_id;
+ BLI_addtail(&todo_ids, todo_id_iter);
}
}
FOREACH_MAIN_ID_END;
- FOREACH_MAIN_ID_BEGIN (bmain, reference_id) {
- if ((reference_id->tag & LIB_TAG_DOIT) != 0 && reference_id->lib != NULL &&
- reference_id->newid != NULL) {
- ID *local_id = reference_id->newid;
- BKE_libblock_remap(bmain,
- reference_id,
- local_id,
- ID_REMAP_SKIP_INDIRECT_USAGE | ID_REMAP_SKIP_OVERRIDE_LIBRARY);
+ /* Override the IDs. */
+ for (todo_id_iter = todo_ids.first; todo_id_iter != NULL; todo_id_iter = todo_id_iter->next) {
+ reference_id = todo_id_iter->data;
+ if ((reference_id->newid = override_library_create_from(bmain, reference_id)) == NULL) {
+ ret = false;
+ }
+ else {
+ /* We also tag the new IDs so that in next step we can remap their pointers too. */
+ reference_id->newid->tag |= LIB_TAG_DOIT;
}
}
- FOREACH_MAIN_ID_END;
+
+ /* Only remap new local ID's pointers, we don't want to force our new overrides onto our whole
+ * existing linked IDs usages. */
+ for (todo_id_iter = todo_ids.first; todo_id_iter != NULL; todo_id_iter = todo_id_iter->next) {
+ ID *other_id;
+ reference_id = todo_id_iter->data;
+
+ if (reference_id->newid == NULL) {
+ continue;
+ }
+
+ /* Still checking the whole Main, that way we can tag other local IDs as needing to be remapped
+ * to use newly created overriding IDs, if needed. */
+ FOREACH_MAIN_ID_BEGIN (bmain, other_id) {
+ if ((other_id->tag & LIB_TAG_DOIT) != 0 && other_id->lib == NULL) {
+ ID *local_id = reference_id->newid;
+ /* Note that using ID_REMAP_SKIP_INDIRECT_USAGE below is superfluous, as we only remap
+ * local IDs usages anyway... */
+ BKE_libblock_relink_ex(bmain,
+ other_id,
+ reference_id,
+ local_id,
+ ID_REMAP_SKIP_INDIRECT_USAGE | ID_REMAP_SKIP_OVERRIDE_LIBRARY);
+ }
+ }
+ FOREACH_MAIN_ID_END;
+ }
+
+ BLI_freelistN(&todo_ids);
return ret;
}
diff --git a/source/blender/editors/object/object_relations.c b/source/blender/editors/object/object_relations.c
index 67364f275dd..df684bfc210 100644
--- a/source/blender/editors/object/object_relations.c
+++ b/source/blender/editors/object/object_relations.c
@@ -2426,6 +2426,8 @@ static int make_override_library_exec(bContext *C, wmOperator *op)
if (!ID_IS_LINKED(obact) && obact->instance_collection != NULL &&
ID_IS_LINKED(obact->instance_collection)) {
+ BKE_main_id_tag_all(bmain, LIB_TAG_DOIT, false);
+
Object *obcollection = obact;
Collection *collection = obcollection->instance_collection;
@@ -2503,7 +2505,7 @@ static int make_override_library_exec(bContext *C, wmOperator *op)
/* Cleanup. */
BKE_main_id_clear_newpoins(bmain);
- BKE_main_id_tag_listbase(&bmain->objects, LIB_TAG_DOIT, false);
+ BKE_main_id_tag_all(bmain, LIB_TAG_DOIT, false);
}
/* Else, poll func ensures us that ID_IS_LINKED(obact) is true. */
else if (obact->type == OB_ARMATURE) {
@@ -2522,7 +2524,7 @@ static int make_override_library_exec(bContext *C, wmOperator *op)
/* Cleanup. */
BKE_main_id_clear_newpoins(bmain);
- BKE_main_id_tag_listbase(&bmain->objects, LIB_TAG_DOIT, false);
+ BKE_main_id_tag_all(bmain, LIB_TAG_DOIT, false);
}
/* TODO: probably more cases where we want to do automated smart things in the future! */
else {