diff options
author | Antonis Ryakiotakis <kalast@gmail.com> | 2022-02-07 21:37:15 +0300 |
---|---|---|
committer | Antonis Ryakiotakis <kalast@gmail.com> | 2022-02-07 21:37:15 +0300 |
commit | d8c05502272990173381bfd2590884bbc95aa5f5 (patch) | |
tree | 8bd65efacbe6484b838d4550597d0f4a54ddddd9 /source/blender/blenkernel/intern/lib_id_delete.c | |
parent | b64d551f3b2fa409b4eeefb641fc581eb6cd0bd6 (diff) | |
parent | fe1816f67fbc6aaf383ec77847d668367335d093 (diff) |
Merge branch 'master' into KTX_supportKTX_support
Diffstat (limited to 'source/blender/blenkernel/intern/lib_id_delete.c')
-rw-r--r-- | source/blender/blenkernel/intern/lib_id_delete.c | 43 |
1 files changed, 27 insertions, 16 deletions
diff --git a/source/blender/blenkernel/intern/lib_id_delete.c b/source/blender/blenkernel/intern/lib_id_delete.c index 6d2e89187f7..5db70d85e71 100644 --- a/source/blender/blenkernel/intern/lib_id_delete.c +++ b/source/blender/blenkernel/intern/lib_id_delete.c @@ -154,7 +154,10 @@ void BKE_id_free_ex(Main *bmain, void *idv, int flag, const bool use_flag_from_i } if (remap_editor_id_reference_cb) { - remap_editor_id_reference_cb(id, NULL); + struct IDRemapper *remapper = BKE_id_remapper_create(); + BKE_id_remapper_add(remapper, id, NULL); + remap_editor_id_reference_cb(remapper); + BKE_id_remapper_free(remapper); } } @@ -262,8 +265,8 @@ static size_t id_delete(Main *bmain, const bool do_tagged_deletion) } for (id = last_remapped_id->next; id; id = id->next) { /* Will tag 'never NULL' users of this ID too. - * Note that we cannot use BKE_libblock_unlink() here, - * since it would ignore indirect (and proxy!) + * + * NOTE: #BKE_libblock_unlink() cannot be used here, since it would ignore indirect * links, this can lead to nasty crashing here in second, actual deleting loop. * Also, this will also flag users of deleted data that cannot be unlinked * (object using deleted obdata, etc.), so that they also get deleted. */ @@ -292,32 +295,40 @@ static size_t id_delete(Main *bmain, const bool do_tagged_deletion) * Note that we go forward here, since we want to check dependencies before users * (e.g. meshes before objects). * Avoids to have to loop twice. */ + struct IDRemapper *remapper = BKE_id_remapper_create(); for (i = 0; i < base_count; i++) { ListBase *lb = lbarray[i]; ID *id, *id_next; + BKE_id_remapper_clear(remapper); for (id = lb->first; id; id = id_next) { id_next = id->next; /* NOTE: in case we delete a library, we also delete all its datablocks! */ if ((id->tag & tag) || (id->lib != NULL && (id->lib->id.tag & tag))) { id->tag |= tag; - - /* Will tag 'never NULL' users of this ID too. - * Note that we cannot use BKE_libblock_unlink() here, since it would ignore indirect - * (and proxy!) links, this can lead to nasty crashing here in second, - * actual deleting loop. - * Also, this will also flag users of deleted data that cannot be unlinked - * (object using deleted obdata, etc.), so that they also get deleted. */ - BKE_libblock_remap_locked(bmain, - id, - NULL, - (ID_REMAP_FLAG_NEVER_NULL_USAGE | - ID_REMAP_FORCE_NEVER_NULL_USAGE | - ID_REMAP_FORCE_INTERNAL_RUNTIME_POINTERS)); + BKE_id_remapper_add(remapper, id, NULL); } } + + if (BKE_id_remapper_is_empty(remapper)) { + continue; + } + + /* Will tag 'never NULL' users of this ID too. + * + * NOTE: #BKE_libblock_unlink() cannot be used here, since it would ignore indirect + * links, this can lead to nasty crashing here in second, actual deleting loop. + * Also, this will also flag users of deleted data that cannot be unlinked + * (object using deleted obdata, etc.), so that they also get deleted. */ + BKE_libblock_remap_multiple_locked(bmain, + remapper, + (ID_REMAP_FLAG_NEVER_NULL_USAGE | + ID_REMAP_FORCE_NEVER_NULL_USAGE | + ID_REMAP_FORCE_INTERNAL_RUNTIME_POINTERS)); } + BKE_id_remapper_free(remapper); } + BKE_main_unlock(bmain); /* In usual reversed order, such that all usage of a given ID, even 'never NULL' ones, |