Fix #129207: GPv3: Linked GPv2 objects disappear when reopening file.
This happens because blender 4.3 only knows about GPv3 IDs, and therefore stores a reference to a directly linked GPv2 obdata as a GPv3 one, which cannot be found again on next file load in the GPv2 library. The idea of this fix is, if the looup of a idcode+idname fails, to also search for the same name but with an older, deprecated ID code. Pull Request: https://projects.blender.org/blender/blender/pulls/129220
This commit is contained in:
committed by
Bastien Montagne
parent
acc2772c45
commit
7937a7eadf
@@ -108,6 +108,7 @@
|
||||
#include "SEQ_utils.hh"
|
||||
|
||||
#include "readfile.hh"
|
||||
#include "versioning_common.hh"
|
||||
|
||||
/* Make preferences read-only. */
|
||||
#define U (*((const UserDef *)&U))
|
||||
@@ -3932,9 +3933,27 @@ static BHead *find_bhead_from_code_name(FileData *fd, const short idcode, const
|
||||
static BHead *find_bhead_from_idname(FileData *fd, const char *idname)
|
||||
{
|
||||
#ifdef USE_GHASH_BHEAD
|
||||
return static_cast<BHead *>(BLI_ghash_lookup(fd->bhead_idname_hash, idname));
|
||||
BHead *bhead = static_cast<BHead *>(BLI_ghash_lookup(fd->bhead_idname_hash, idname));
|
||||
#else
|
||||
return find_bhead_from_code_name(fd, GS(idname), idname + 2);
|
||||
BHead *bhead = find_bhead_from_code_name(fd, GS(idname), idname + 2);
|
||||
#endif
|
||||
if (LIKELY(bhead)) {
|
||||
return bhead;
|
||||
}
|
||||
|
||||
/* Expected ID was not found, attempt to load the same name, but for an older, deprecated and
|
||||
* converted ID type. */
|
||||
const short id_code_old = do_versions_new_to_old_idcode_get(GS(idname));
|
||||
if (id_code_old == ID_LINK_PLACEHOLDER) {
|
||||
return bhead;
|
||||
}
|
||||
#ifdef USE_GHASH_BHEAD
|
||||
char id_name_old[MAX_ID_NAME];
|
||||
BLI_strncpy(id_name_old, idname, sizeof(id_name_old));
|
||||
*reinterpret_cast<short *>(id_name_old) = id_code_old;
|
||||
return static_cast<BHead *>(BLI_ghash_lookup(fd->bhead_idname_hash, id_name_old));
|
||||
#else
|
||||
return find_bhead_from_code_name(fd, id_code_old, idname + 2);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
@@ -47,6 +47,17 @@
|
||||
using blender::Map;
|
||||
using blender::StringRef;
|
||||
|
||||
short do_versions_new_to_old_idcode_get(const short id_code_new)
|
||||
{
|
||||
switch (id_code_new) {
|
||||
case ID_GP:
|
||||
/* ID_GD_LEGACY (Grease Pencil v2) is now converted to ID_GP (Grease Pencil v3). */
|
||||
return ID_GD_LEGACY;
|
||||
default:
|
||||
return ID_LINK_PLACEHOLDER;
|
||||
}
|
||||
}
|
||||
|
||||
ARegion *do_versions_add_region_if_not_found(ListBase *regionbase,
|
||||
int region_type,
|
||||
const char *allocname,
|
||||
|
||||
@@ -24,6 +24,22 @@ struct SceneRenderLayer;
|
||||
|
||||
using blender::FunctionRef;
|
||||
|
||||
/**
|
||||
* Mapping from new ID types to old converted ID types.
|
||||
*
|
||||
* This is used by linking code, when a directly linked data comes from a library where it exists
|
||||
* as an older, different type of ID.
|
||||
*
|
||||
* Since the current blendfile will convert that older ID type to the new one as part of its
|
||||
* versioning process, when saved, it will store a reference to that linked ID using the _new_ ID
|
||||
* type, which will not be found on next blendfile opening/reloading when searching for that ID in
|
||||
* the library blendfile.
|
||||
*
|
||||
* \returns The old, deprecated ID type code if any matches the given `id_code_new` one, otherwise
|
||||
* `ID_LINK_PLACEHOLDER`.
|
||||
*/
|
||||
short do_versions_new_to_old_idcode_get(short id_code_new);
|
||||
|
||||
/**
|
||||
* Check if a region of type \a region_type exists in \a regionbase. Otherwise add it after the
|
||||
* first region of type \a link_after_region_type.
|
||||
|
||||
Reference in New Issue
Block a user