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:
authorDalai Felinto <dfelinto@gmail.com>2017-10-24 15:21:24 +0300
committerDalai Felinto <dfelinto@gmail.com>2017-10-24 15:28:01 +0300
commit7484c6c5ee68c313e72394f7538d1c7386c0ced7 (patch)
treebba6ceda59eb83244fb54a4925cb5f1a1bc9c3f7 /source/blender/blenloader
parentbac740085ccc65ad7852637e59a5ba5fdc65e338 (diff)
Fix non-instanced groups in no-collection file creating collections
This is a corner-case, but one that is too easy to reproduce: * Unlink all the collections of active view layer. * Link a group without "Instancing" it.
Diffstat (limited to 'source/blender/blenloader')
-rw-r--r--source/blender/blenloader/intern/readfile.c43
1 files changed, 25 insertions, 18 deletions
diff --git a/source/blender/blenloader/intern/readfile.c b/source/blender/blenloader/intern/readfile.c
index c0580660e2b..ce7914b0f37 100644
--- a/source/blender/blenloader/intern/readfile.c
+++ b/source/blender/blenloader/intern/readfile.c
@@ -252,6 +252,7 @@ static void *read_struct(FileData *fd, BHead *bh, const char *blockname);
static void direct_link_modifiers(FileData *fd, ListBase *lb);
static BHead *find_bhead_from_code_name(FileData *fd, const short idcode, const char *name);
static BHead *find_bhead_from_idname(FileData *fd, const char *idname);
+static SceneCollection *get_scene_collection_active_or_create(struct Scene *scene, struct SceneLayer *sl, const short flag);
/* this function ensures that reports are printed,
* in the case of libraray linking errors this is important!
@@ -10142,15 +10143,16 @@ static bool object_in_any_scene(Main *mainvar, Object *ob)
}
static void give_base_to_objects(
- Main *mainvar, Scene *scene, SceneLayer *sl, SceneCollection *sc, Library *lib, const short flag)
+ Main *mainvar, Scene *scene, SceneLayer *scene_layer, Library *lib, const short flag)
{
Object *ob;
Base *base;
+ SceneCollection *scene_collection = NULL;
const bool is_link = (flag & FILE_LINK) != 0;
BLI_assert(scene);
- /* give all objects which are LIB_TAG_INDIRECT a base, or for a group when *lib has been set */
+ /* Give all objects which are LIB_TAG_INDIRECT a base, or for a group when *lib has been set. */
for (ob = mainvar->object.first; ob; ob = ob->id.next) {
if ((ob->id.tag & LIB_TAG_INDIRECT) && (ob->id.tag & LIB_TAG_PRE_EXISTING) == 0) {
bool do_it = false;
@@ -10167,8 +10169,12 @@ static void give_base_to_objects(
if (do_it) {
CLAMP_MIN(ob->id.us, 0);
- BKE_collection_object_add(scene, sc, ob);
- base = BKE_scene_layer_base_find(sl, ob);
+ if (scene_collection == NULL) {
+ scene_collection = get_scene_collection_active_or_create(scene, scene_layer, FILE_ACTIVE_COLLECTION);
+ }
+
+ BKE_collection_object_add(scene, scene_collection, ob);
+ base = BKE_scene_layer_base_find(scene_layer, ob);
BKE_scene_object_base_flag_sync_from_base(base);
if (flag & FILE_AUTOSELECT) {
@@ -10178,10 +10184,9 @@ static void give_base_to_objects(
base->flag |= BASE_SELECTED;
BKE_scene_base_flag_sync_from_base(base);
}
- /* do NOT make base active here! screws up GUI stuff, if you want it do it on src/ level */
+ /* Do NOT make base active here! screws up GUI stuff, if you want it do it on src/ level. */
}
-
ob->id.tag &= ~LIB_TAG_INDIRECT;
ob->id.tag |= LIB_TAG_EXTERN;
}
@@ -10190,25 +10195,28 @@ static void give_base_to_objects(
}
static void give_base_to_groups(
- Main *mainvar, Scene *scene, SceneLayer *sl, SceneCollection *sc,
- Library *UNUSED(lib), const short UNUSED(flag))
+ Main *mainvar, Scene *scene, SceneLayer *scene_layer, Library *UNUSED(lib), const short UNUSED(flag))
{
Group *group;
Base *base;
Object *ob;
+ SceneCollection *scene_collection;
+
+ /* If the group is empty this function is not even called, so it's safe to ensure a collection at this point. */
+ scene_collection = get_scene_collection_active_or_create(scene, scene_layer, FILE_ACTIVE_COLLECTION);
- /* give all objects which are tagged a base */
+ /* Give all objects which are tagged a base. */
for (group = mainvar->group.first; group; group = group->id.next) {
if (group->id.tag & LIB_TAG_DOIT) {
- /* any indirect group should not have been tagged */
+ /* Any indirect group should not have been tagged. */
BLI_assert((group->id.tag & LIB_TAG_INDIRECT) == 0);
- /* BKE_object_add(...) messes with the selection */
+ /* BKE_object_add(...) messes with the selection. */
ob = BKE_object_add_only_object(mainvar, OB_EMPTY, group->id.name + 2);
ob->type = OB_EMPTY;
- BKE_collection_object_add(scene, sc, ob);
- base = BKE_scene_layer_base_find(sl, ob);
+ BKE_collection_object_add(scene, scene_collection, ob);
+ base = BKE_scene_layer_base_find(scene_layer, ob);
if (base->flag & BASE_SELECTABLED) {
base->flag |= BASE_SELECTED;
@@ -10216,9 +10224,9 @@ static void give_base_to_groups(
BKE_scene_object_base_flag_sync_from_base(base);
DEG_id_tag_update(&ob->id, OB_RECALC_OB | OB_RECALC_DATA | OB_RECALC_TIME);
- sl->basact = base;
+ scene_layer->basact = base;
- /* assign the group */
+ /* Assign the group. */
ob->dup_group = group;
ob->transflag |= OB_DUPLIGROUP;
copy_v3_v3(ob->loc, scene->cursor);
@@ -10593,11 +10601,10 @@ static void library_link_end(Main *mainl, FileData **fd, const short flag, Scene
* Only directly linked objects & groups are instantiated by `BLO_library_link_named_part_ex()` & co,
* here we handle indirect ones and other possible edge-cases. */
if (scene) {
- SceneCollection *sc = get_scene_collection_active_or_create(scene, sl, FILE_ACTIVE_COLLECTION);
- give_base_to_objects(mainvar, scene, sl, sc, curlib, flag);
+ give_base_to_objects(mainvar, scene, sl, curlib, flag);
if (flag & FILE_GROUP_INSTANCE) {
- give_base_to_groups(mainvar, scene, sl, sc, curlib, flag);
+ give_base_to_groups(mainvar, scene, sl, curlib, flag);
}
}
else {