[Bf-blender-cvs] [5d2b23766bd] master: Link/Append: Instantiate collection rather than objects.

Bastien Montagne noreply at git.blender.org
Sun Feb 10 17:15:31 CET 2019


Commit: 5d2b23766bd1147801815e1c177b66b6fe6ec95c
Author: Bastien Montagne
Date:   Sun Feb 10 17:13:37 2019 +0100
Branches: master
https://developer.blender.org/rB5d2b23766bd1147801815e1c177b66b6fe6ec95c

Link/Append: Instantiate collection rather than objects.

When one is indirectly linking collections, better add collection to the
scene, than instantiating its objects into master collection of the
scene. That is much cleaner.

Noted/related to T61141.

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

M	source/blender/blenloader/intern/readfile.c

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

diff --git a/source/blender/blenloader/intern/readfile.c b/source/blender/blenloader/intern/readfile.c
index 1f112f41526..3afa5f4a406 100644
--- a/source/blender/blenloader/intern/readfile.c
+++ b/source/blender/blenloader/intern/readfile.c
@@ -10355,43 +10355,62 @@ static void add_loose_objects_to_scene(
 
 static void add_collections_to_scene(
         Main *mainvar, Main *bmain,
-        Scene *scene, ViewLayer *view_layer, const View3D *v3d, Library *UNUSED(lib), const short flag)
+        Scene *scene, ViewLayer *view_layer, const View3D *v3d, Library *lib, const short flag)
 {
 	Collection *active_collection = get_collection_active(bmain, scene, view_layer, FILE_ACTIVE_COLLECTION);
 
 	/* Give all objects which are tagged a base. */
 	for (Collection *collection = mainvar->collection.first; collection; collection = collection->id.next) {
-		if (collection->id.tag & LIB_TAG_DOIT) {
-			if (flag & FILE_GROUP_INSTANCE) {
-				/* Any indirect collection should not have been tagged. */
-				BLI_assert((collection->id.tag & LIB_TAG_INDIRECT) == 0);
+		if ((flag & FILE_GROUP_INSTANCE) && (collection->id.tag & LIB_TAG_DOIT)) {
+			/* Any indirect collection should not have been tagged. */
+			BLI_assert((collection->id.tag & LIB_TAG_INDIRECT) == 0);
 
-				/* BKE_object_add(...) messes with the selection. */
-				Object *ob = BKE_object_add_only_object(bmain, OB_EMPTY, collection->id.name + 2);
-				ob->type = OB_EMPTY;
+			/* BKE_object_add(...) messes with the selection. */
+			Object *ob = BKE_object_add_only_object(bmain, OB_EMPTY, collection->id.name + 2);
+			ob->type = OB_EMPTY;
 
-				BKE_collection_object_add(bmain, active_collection, ob);
-				Base *base = BKE_view_layer_base_find(view_layer, ob);
+			BKE_collection_object_add(bmain, active_collection, ob);
+			Base *base = BKE_view_layer_base_find(view_layer, ob);
 
-				if (v3d != NULL) {
-					base->local_view_bits |= v3d->local_view_uuid;
-				}
+			if (v3d != NULL) {
+				base->local_view_bits |= v3d->local_view_uuid;
+			}
 
-				if (base->flag & BASE_SELECTABLE) {
-					base->flag |= BASE_SELECTED;
-				}
+			if (base->flag & BASE_SELECTABLE) {
+				base->flag |= BASE_SELECTED;
+			}
 
-				BKE_scene_object_base_flag_sync_from_base(base);
-				DEG_id_tag_update(&ob->id, ID_RECALC_TRANSFORM | ID_RECALC_GEOMETRY | ID_RECALC_ANIMATION);
-				view_layer->basact = base;
+			BKE_scene_object_base_flag_sync_from_base(base);
+			DEG_id_tag_update(&ob->id, ID_RECALC_TRANSFORM | ID_RECALC_GEOMETRY | ID_RECALC_ANIMATION);
+			view_layer->basact = base;
 
-				/* Assign the collection. */
-				ob->dup_group = collection;
-				id_us_plus(&collection->id);
-				ob->transflag |= OB_DUPLICOLLECTION;
-				copy_v3_v3(ob->loc, scene->cursor.location);
+			/* Assign the collection. */
+			ob->dup_group = collection;
+			id_us_plus(&collection->id);
+			ob->transflag |= OB_DUPLICOLLECTION;
+			copy_v3_v3(ob->loc, scene->cursor.location);
+		}
+		else {
+			bool do_add_collection = (collection->id.tag & LIB_TAG_DOIT) != 0;
+			if (!do_add_collection) {
+				/* We need to check that objects in that collections are already instantiated in a scene.
+				 * Otherwise, it's better to add the collection to the scene's active collection, than to
+				 * instantiate its objects in active scene's collection directly. See T61141.
+				 * Note that we only check object directly into that collection, not recursively into its children.
+				 */
+				for (CollectionObject *coll_ob = collection->gobject.first; coll_ob != NULL; coll_ob = coll_ob->next)
+				{
+					Object *ob = coll_ob->ob;
+					if ((ob->id.tag & LIB_TAG_PRE_EXISTING) == 0 &&
+					    (ob->id.lib == lib) &&
+					    (object_in_any_scene(bmain, ob) == 0))
+					{
+						do_add_collection = true;
+						break;
+					}
+				}
 			}
-			else {
+			if (do_add_collection) {
 				/* Add collection as child of active collection. */
 				BKE_collection_child_add(bmain, active_collection, collection);



More information about the Bf-blender-cvs mailing list