[Bf-blender-cvs] [17c15798c35] master: Fix T63101: Blender crashes on adding any object to collection duplicated with added scene.

Bastien Montagne noreply at git.blender.org
Mon Apr 1 21:16:55 CEST 2019


Commit: 17c15798c35f33e4150beacb0f7b612bcef90c3e
Author: Bastien Montagne
Date:   Mon Apr 1 21:10:25 2019 +0200
Branches: master
https://developer.blender.org/rB17c15798c35f33e4150beacb0f7b612bcef90c3e

Fix T63101: Blender crashes on adding any object to collection duplicated with added scene.

Issue was that (deep) duplication code of scene ended up leaving
children collections of new master one without any parent.

Note that even though I think that fix is OK for now, we should really
make 'deep' duplication of IDs part of the generic ID management code.
Am less and less happy with current handling of this, done half from
/editors code, half from some semi-specialized helpers from /blenkernel,
with sometimes nearly the same logic replicated several times for
slightly different needs, etc. Unfortunately this would not be a small
refactor, so it will have to wait...

===================================================================

M	source/blender/editors/object/object_relations.c

===================================================================

diff --git a/source/blender/editors/object/object_relations.c b/source/blender/editors/object/object_relations.c
index dbee2e77cf5..ec6c1059ed3 100644
--- a/source/blender/editors/object/object_relations.c
+++ b/source/blender/editors/object/object_relations.c
@@ -1602,7 +1602,7 @@ static void libblock_relink_collection(Collection *collection)
 	}
 }
 
-static void single_object_users_collection(
+static Collection *single_object_users_collection(
         Main *bmain, Scene *scene, Collection *collection,
         const int flag, const bool copy_collections, const bool is_master_collection)
 {
@@ -1623,9 +1623,24 @@ static void single_object_users_collection(
 		}
 	}
 
-	for (CollectionChild *child = collection->children.first; child; child = child->next) {
-		single_object_users_collection(bmain, scene, child->collection, flag, copy_collections, false);
+	/* Since master collection has already be duplicated as part of scene copy, we do not duplictae it here.
+	 * However, this means its children need to be re-added manually here, otherwise their parent lists are empty
+	 * (which will lead to crashes, see T63101). */
+	CollectionChild *child_next, *child = collection->children.first;
+	if (is_master_collection) {
+		BLI_listbase_clear(&collection->children);
+	}
+	for (; child; child = child_next) {
+		child_next = child->next;
+		Collection *collection_child_new = single_object_users_collection(
+		                                       bmain, scene, child->collection, flag, copy_collections, false);
+		if (is_master_collection) {
+			BKE_collection_child_add(bmain, collection, collection_child_new);
+			MEM_freeN(child);
+		}
 	}
+
+	return collection;
 }
 
 /* Warning, sets ID->newid pointers of objects and collections, but does not clear them. */
@@ -1679,9 +1694,7 @@ static void single_object_users(Main *bmain, Scene *scene, View3D *v3d, const in
 	}
 
 	/* Making single user may affect other scenes if they share with current one some collections in their ViewLayer. */
-	for (Scene *sce = bmain->scenes.first; sce != NULL; sce = sce->id.next) {
-		BKE_scene_collection_sync(sce);
-	}
+	BKE_main_collection_sync(bmain);
 }
 
 /* not an especially efficient function, only added so the single user



More information about the Bf-blender-cvs mailing list