Asset System: Data-block asset metadata storage, reading and API
Asset metadata is what turns a regular data-block into an asset. It is a small data-structure, but a key part of the technical design of the asset system. The design foresees that asset data-blocks store an `ID.asset_data` pointer of type `AssetMetaData`. This data **must not** have dependencies on other data-blocks or data-block data, it must be an independent unit. That way we can read asset-metadata from .blends without reading anything else from the file. The Asset Browser will use this metadata (together with the data-block name, preview and file path) to represent assets in the file list. Includes: * New `ID.asset_data` for asset metadata. * Asset tags, description and custom properties. * BKE code to manage asset meta-data and asset tags. * Code to read asset data from files, without reading IDs. * RNA for asset metadata (including tags) Part of the first Asset Browser milestone. Check the #asset_browser_milestone_1 project milestone on developer.blender.org. Differential Revision: https://developer.blender.org/D9716 Reviewed by: Bastien Montagne, Brecht Van Lommel
This commit is contained in:
parent
82645ff739
commit
b71eb3a105
|
@ -23,6 +23,7 @@ set(SRC_DNA_INC
|
||||||
${CMAKE_CURRENT_SOURCE_DIR}/makesdna/DNA_action_types.h
|
${CMAKE_CURRENT_SOURCE_DIR}/makesdna/DNA_action_types.h
|
||||||
${CMAKE_CURRENT_SOURCE_DIR}/makesdna/DNA_anim_types.h
|
${CMAKE_CURRENT_SOURCE_DIR}/makesdna/DNA_anim_types.h
|
||||||
${CMAKE_CURRENT_SOURCE_DIR}/makesdna/DNA_armature_types.h
|
${CMAKE_CURRENT_SOURCE_DIR}/makesdna/DNA_armature_types.h
|
||||||
|
${CMAKE_CURRENT_SOURCE_DIR}/makesdna/DNA_asset_types.h
|
||||||
${CMAKE_CURRENT_SOURCE_DIR}/makesdna/DNA_boid_types.h
|
${CMAKE_CURRENT_SOURCE_DIR}/makesdna/DNA_boid_types.h
|
||||||
${CMAKE_CURRENT_SOURCE_DIR}/makesdna/DNA_brush_enums.h
|
${CMAKE_CURRENT_SOURCE_DIR}/makesdna/DNA_brush_enums.h
|
||||||
${CMAKE_CURRENT_SOURCE_DIR}/makesdna/DNA_brush_types.h
|
${CMAKE_CURRENT_SOURCE_DIR}/makesdna/DNA_brush_types.h
|
||||||
|
|
|
@ -0,0 +1,56 @@
|
||||||
|
/*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software Foundation,
|
||||||
|
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef __BKE_ASSET_H__
|
||||||
|
#define __BKE_ASSET_H__
|
||||||
|
|
||||||
|
/** \file
|
||||||
|
* \ingroup bke
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "BLI_utildefines.h"
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
extern "C" {
|
||||||
|
#endif
|
||||||
|
|
||||||
|
struct BlendWriter;
|
||||||
|
struct BlendDataReader;
|
||||||
|
struct ID;
|
||||||
|
struct PreviewImage;
|
||||||
|
|
||||||
|
struct AssetMetaData *BKE_asset_metadata_create(void);
|
||||||
|
void BKE_asset_metadata_free(struct AssetMetaData **asset_data);
|
||||||
|
|
||||||
|
struct AssetTagEnsureResult {
|
||||||
|
struct AssetTag *tag;
|
||||||
|
/* Set to false if a tag of this name was already present. */
|
||||||
|
bool is_new;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct AssetTag *BKE_asset_metadata_tag_add(struct AssetMetaData *asset_data, const char *name);
|
||||||
|
struct AssetTagEnsureResult BKE_asset_metadata_tag_ensure(struct AssetMetaData *asset_data,
|
||||||
|
const char *name);
|
||||||
|
void BKE_asset_metadata_tag_remove(struct AssetMetaData *asset_data, struct AssetTag *tag);
|
||||||
|
|
||||||
|
void BKE_asset_metadata_write(struct BlendWriter *writer, struct AssetMetaData *asset_data);
|
||||||
|
void BKE_asset_metadata_read(struct BlendDataReader *reader, struct AssetMetaData *asset_data);
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#endif /* __BKE_ASSET_H__ */
|
|
@ -77,6 +77,7 @@ set(SRC
|
||||||
intern/armature.c
|
intern/armature.c
|
||||||
intern/armature_deform.c
|
intern/armature_deform.c
|
||||||
intern/armature_update.c
|
intern/armature_update.c
|
||||||
|
intern/asset.c
|
||||||
intern/attribute.c
|
intern/attribute.c
|
||||||
intern/attribute_access.cc
|
intern/attribute_access.cc
|
||||||
intern/autoexec.c
|
intern/autoexec.c
|
||||||
|
@ -271,6 +272,7 @@ set(SRC
|
||||||
BKE_attribute.h
|
BKE_attribute.h
|
||||||
BKE_attribute_access.hh
|
BKE_attribute_access.hh
|
||||||
BKE_autoexec.h
|
BKE_autoexec.h
|
||||||
|
BKE_asset.h
|
||||||
BKE_blender.h
|
BKE_blender.h
|
||||||
BKE_blender_copybuffer.h
|
BKE_blender_copybuffer.h
|
||||||
BKE_blender_undo.h
|
BKE_blender_undo.h
|
||||||
|
|
|
@ -0,0 +1,143 @@
|
||||||
|
/*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software Foundation,
|
||||||
|
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** \file
|
||||||
|
* \ingroup bke
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#include "BLI_listbase.h"
|
||||||
|
#include "BLI_string.h"
|
||||||
|
#include "BLI_string_utils.h"
|
||||||
|
#include "BLI_utildefines.h"
|
||||||
|
|
||||||
|
#include "BKE_asset.h"
|
||||||
|
#include "BKE_icons.h"
|
||||||
|
#include "BKE_idprop.h"
|
||||||
|
|
||||||
|
#include "DNA_ID.h"
|
||||||
|
#include "DNA_asset_types.h"
|
||||||
|
#include "DNA_defaults.h"
|
||||||
|
|
||||||
|
#include "BLO_read_write.h"
|
||||||
|
|
||||||
|
#include "MEM_guardedalloc.h"
|
||||||
|
|
||||||
|
AssetMetaData *BKE_asset_metadata_create(void)
|
||||||
|
{
|
||||||
|
AssetMetaData *asset_data = MEM_callocN(sizeof(*asset_data), __func__);
|
||||||
|
memcpy(asset_data, DNA_struct_default_get(AssetMetaData), sizeof(*asset_data));
|
||||||
|
return asset_data;
|
||||||
|
}
|
||||||
|
|
||||||
|
void BKE_asset_metadata_free(AssetMetaData **asset_data)
|
||||||
|
{
|
||||||
|
if ((*asset_data)->properties) {
|
||||||
|
IDP_FreeProperty((*asset_data)->properties);
|
||||||
|
}
|
||||||
|
MEM_SAFE_FREE((*asset_data)->description);
|
||||||
|
BLI_freelistN(&(*asset_data)->tags);
|
||||||
|
|
||||||
|
MEM_SAFE_FREE(*asset_data);
|
||||||
|
}
|
||||||
|
|
||||||
|
static AssetTag *asset_metadata_tag_add(AssetMetaData *asset_data, const char *const name)
|
||||||
|
{
|
||||||
|
AssetTag *tag = MEM_callocN(sizeof(*tag), __func__);
|
||||||
|
BLI_strncpy(tag->name, name, sizeof(tag->name));
|
||||||
|
|
||||||
|
BLI_addtail(&asset_data->tags, tag);
|
||||||
|
asset_data->tot_tags++;
|
||||||
|
/* Invariant! */
|
||||||
|
BLI_assert(BLI_listbase_count(&asset_data->tags) == asset_data->tot_tags);
|
||||||
|
|
||||||
|
return tag;
|
||||||
|
}
|
||||||
|
|
||||||
|
AssetTag *BKE_asset_metadata_tag_add(AssetMetaData *asset_data, const char *name)
|
||||||
|
{
|
||||||
|
AssetTag *tag = asset_metadata_tag_add(asset_data, name);
|
||||||
|
BLI_uniquename(&asset_data->tags, tag, name, '.', offsetof(AssetTag, name), sizeof(tag->name));
|
||||||
|
return tag;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Make sure there is a tag with name \a name, create one if needed.
|
||||||
|
*/
|
||||||
|
struct AssetTagEnsureResult BKE_asset_metadata_tag_ensure(AssetMetaData *asset_data,
|
||||||
|
const char *name)
|
||||||
|
{
|
||||||
|
struct AssetTagEnsureResult result = {.tag = NULL};
|
||||||
|
if (!name[0]) {
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
AssetTag *tag = BLI_findstring(&asset_data->tags, name, offsetof(AssetTag, name));
|
||||||
|
|
||||||
|
if (tag) {
|
||||||
|
result.tag = tag;
|
||||||
|
result.is_new = false;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
tag = asset_metadata_tag_add(asset_data, name);
|
||||||
|
|
||||||
|
result.tag = tag;
|
||||||
|
result.is_new = true;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
void BKE_asset_metadata_tag_remove(AssetMetaData *asset_data, AssetTag *tag)
|
||||||
|
{
|
||||||
|
BLI_assert(BLI_findindex(&asset_data->tags, tag) >= 0);
|
||||||
|
BLI_freelinkN(&asset_data->tags, tag);
|
||||||
|
asset_data->tot_tags--;
|
||||||
|
/* Invariant! */
|
||||||
|
BLI_assert(BLI_listbase_count(&asset_data->tags) == asset_data->tot_tags);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* .blend file API -------------------------------------------- */
|
||||||
|
|
||||||
|
void BKE_asset_metadata_write(BlendWriter *writer, AssetMetaData *asset_data)
|
||||||
|
{
|
||||||
|
BLO_write_struct(writer, AssetMetaData, asset_data);
|
||||||
|
|
||||||
|
if (asset_data->properties) {
|
||||||
|
IDP_BlendWrite(writer, asset_data->properties);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (asset_data->description) {
|
||||||
|
BLO_write_string(writer, asset_data->description);
|
||||||
|
}
|
||||||
|
LISTBASE_FOREACH (AssetTag *, tag, &asset_data->tags) {
|
||||||
|
BLO_write_struct(writer, AssetTag, tag);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void BKE_asset_metadata_read(BlendDataReader *reader, AssetMetaData *asset_data)
|
||||||
|
{
|
||||||
|
/* asset_data itself has been read already. */
|
||||||
|
|
||||||
|
if (asset_data->properties) {
|
||||||
|
BLO_read_data_address(reader, &asset_data->properties);
|
||||||
|
IDP_BlendDataRead(reader, &asset_data->properties);
|
||||||
|
}
|
||||||
|
|
||||||
|
BLO_read_data_address(reader, &asset_data->description);
|
||||||
|
BLO_read_list(reader, &asset_data->tags);
|
||||||
|
BLI_assert(BLI_listbase_count(&asset_data->tags) == asset_data->tot_tags);
|
||||||
|
}
|
|
@ -56,6 +56,7 @@
|
||||||
|
|
||||||
#include "BKE_anim_data.h"
|
#include "BKE_anim_data.h"
|
||||||
#include "BKE_armature.h"
|
#include "BKE_armature.h"
|
||||||
|
#include "BKE_asset.h"
|
||||||
#include "BKE_bpath.h"
|
#include "BKE_bpath.h"
|
||||||
#include "BKE_context.h"
|
#include "BKE_context.h"
|
||||||
#include "BKE_global.h"
|
#include "BKE_global.h"
|
||||||
|
@ -2362,6 +2363,10 @@ void BKE_id_reorder(const ListBase *lb, ID *id, ID *relative, bool after)
|
||||||
|
|
||||||
void BKE_id_blend_write(BlendWriter *writer, ID *id)
|
void BKE_id_blend_write(BlendWriter *writer, ID *id)
|
||||||
{
|
{
|
||||||
|
if (id->asset_data) {
|
||||||
|
BKE_asset_metadata_write(writer, id->asset_data);
|
||||||
|
}
|
||||||
|
|
||||||
/* ID_WM's id->properties are considered runtime only, and never written in .blend file. */
|
/* ID_WM's id->properties are considered runtime only, and never written in .blend file. */
|
||||||
if (id->properties && !ELEM(GS(id->name), ID_WM)) {
|
if (id->properties && !ELEM(GS(id->name), ID_WM)) {
|
||||||
IDP_BlendWrite(writer, id->properties);
|
IDP_BlendWrite(writer, id->properties);
|
||||||
|
|
|
@ -31,6 +31,7 @@
|
||||||
#include "BLI_listbase.h"
|
#include "BLI_listbase.h"
|
||||||
|
|
||||||
#include "BKE_anim_data.h"
|
#include "BKE_anim_data.h"
|
||||||
|
#include "BKE_asset.h"
|
||||||
#include "BKE_idprop.h"
|
#include "BKE_idprop.h"
|
||||||
#include "BKE_idtype.h"
|
#include "BKE_idtype.h"
|
||||||
#include "BKE_key.h"
|
#include "BKE_key.h"
|
||||||
|
@ -64,6 +65,10 @@ void BKE_libblock_free_data(ID *id, const bool do_id_user)
|
||||||
id->override_library = NULL;
|
id->override_library = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (id->asset_data) {
|
||||||
|
BKE_asset_metadata_free(&id->asset_data);
|
||||||
|
}
|
||||||
|
|
||||||
BKE_animdata_free(id, do_id_user);
|
BKE_animdata_free(id, do_id_user);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -119,12 +119,20 @@ void BLO_blendfiledata_free(BlendFileData *bfd);
|
||||||
/** \name BLO Blend File Handle API
|
/** \name BLO Blend File Handle API
|
||||||
* \{ */
|
* \{ */
|
||||||
|
|
||||||
|
struct BLODataBlockInfo {
|
||||||
|
char name[64]; /* MAX_NAME */
|
||||||
|
struct AssetMetaData *asset_data;
|
||||||
|
};
|
||||||
|
|
||||||
BlendHandle *BLO_blendhandle_from_file(const char *filepath, struct ReportList *reports);
|
BlendHandle *BLO_blendhandle_from_file(const char *filepath, struct ReportList *reports);
|
||||||
BlendHandle *BLO_blendhandle_from_memory(const void *mem, int memsize);
|
BlendHandle *BLO_blendhandle_from_memory(const void *mem, int memsize);
|
||||||
|
|
||||||
struct LinkNode *BLO_blendhandle_get_datablock_names(BlendHandle *bh,
|
struct LinkNode *BLO_blendhandle_get_datablock_names(BlendHandle *bh,
|
||||||
int ofblocktype,
|
int ofblocktype,
|
||||||
int *tot_names);
|
int *tot_names);
|
||||||
|
struct LinkNode *BLO_blendhandle_get_datablock_info(BlendHandle *bh,
|
||||||
|
int ofblocktype,
|
||||||
|
int *tot_info_items);
|
||||||
struct LinkNode *BLO_blendhandle_get_previews(BlendHandle *bh, int ofblocktype, int *tot_prev);
|
struct LinkNode *BLO_blendhandle_get_previews(BlendHandle *bh, int ofblocktype, int *tot_prev);
|
||||||
struct LinkNode *BLO_blendhandle_get_linkable_groups(BlendHandle *bh);
|
struct LinkNode *BLO_blendhandle_get_linkable_groups(BlendHandle *bh);
|
||||||
|
|
||||||
|
|
|
@ -159,6 +159,51 @@ LinkNode *BLO_blendhandle_get_datablock_names(BlendHandle *bh, int ofblocktype,
|
||||||
return names;
|
return names;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the names and asset-data (if ID is an asset) of all the data-blocks in a file of a certain
|
||||||
|
* type (e.g. all the scene names in a file).
|
||||||
|
*
|
||||||
|
* \param bh: The blendhandle to access.
|
||||||
|
* \param ofblocktype: The type of names to get.
|
||||||
|
* \param tot_info_items: The length of the returned list.
|
||||||
|
* \return A BLI_linklist of BLODataBlockInfo *. The links and #BLODataBlockInfo.asset_data should
|
||||||
|
* be freed with MEM_freeN.
|
||||||
|
*/
|
||||||
|
LinkNode *BLO_blendhandle_get_datablock_info(BlendHandle *bh, int ofblocktype, int *tot_info_items)
|
||||||
|
{
|
||||||
|
FileData *fd = (FileData *)bh;
|
||||||
|
LinkNode *infos = NULL;
|
||||||
|
BHead *bhead;
|
||||||
|
int tot = 0;
|
||||||
|
|
||||||
|
for (bhead = blo_bhead_first(fd); bhead; bhead = blo_bhead_next(fd, bhead)) {
|
||||||
|
if (bhead->code == ofblocktype) {
|
||||||
|
struct BLODataBlockInfo *info = MEM_mallocN(sizeof(*info), __func__);
|
||||||
|
const char *name = blo_bhead_id_name(fd, bhead) + 2;
|
||||||
|
|
||||||
|
STRNCPY(info->name, name);
|
||||||
|
|
||||||
|
/* Lastly, read asset data from the following blocks. */
|
||||||
|
info->asset_data = blo_bhead_id_asset_data_address(fd, bhead);
|
||||||
|
if (info->asset_data) {
|
||||||
|
bhead = blo_read_asset_data_block(fd, bhead, &info->asset_data);
|
||||||
|
/* blo_read_asset_data_block() reads all DATA heads and already advances bhead to the next
|
||||||
|
* non-DATA one. Go back, so the loop doesn't skip the non-DATA head. */
|
||||||
|
bhead = blo_bhead_prev(fd, bhead);
|
||||||
|
}
|
||||||
|
|
||||||
|
BLI_linklist_prepend(&infos, info);
|
||||||
|
tot++;
|
||||||
|
}
|
||||||
|
else if (bhead->code == ENDB) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
*tot_info_items = tot;
|
||||||
|
return infos;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets the previews of all the data-blocks in a file of a certain type
|
* Gets the previews of all the data-blocks in a file of a certain type
|
||||||
* (e.g. all the scene previews in a file).
|
* (e.g. all the scene previews in a file).
|
||||||
|
|
|
@ -44,6 +44,7 @@
|
||||||
#define DNA_DEPRECATED_ALLOW
|
#define DNA_DEPRECATED_ALLOW
|
||||||
|
|
||||||
#include "DNA_anim_types.h"
|
#include "DNA_anim_types.h"
|
||||||
|
#include "DNA_asset_types.h"
|
||||||
#include "DNA_cachefile_types.h"
|
#include "DNA_cachefile_types.h"
|
||||||
#include "DNA_collection_types.h"
|
#include "DNA_collection_types.h"
|
||||||
#include "DNA_fileglobal_types.h"
|
#include "DNA_fileglobal_types.h"
|
||||||
|
@ -73,6 +74,7 @@
|
||||||
|
|
||||||
#include "BKE_anim_data.h"
|
#include "BKE_anim_data.h"
|
||||||
#include "BKE_animsys.h"
|
#include "BKE_animsys.h"
|
||||||
|
#include "BKE_asset.h"
|
||||||
#include "BKE_collection.h"
|
#include "BKE_collection.h"
|
||||||
#include "BKE_global.h" /* for G */
|
#include "BKE_global.h" /* for G */
|
||||||
#include "BKE_idprop.h"
|
#include "BKE_idprop.h"
|
||||||
|
@ -957,12 +959,21 @@ static BHead *blo_bhead_read_full(FileData *fd, BHead *thisblock)
|
||||||
}
|
}
|
||||||
#endif /* USE_BHEAD_READ_ON_DEMAND */
|
#endif /* USE_BHEAD_READ_ON_DEMAND */
|
||||||
|
|
||||||
/* Warning! Caller's responsibility to ensure given bhead **is** and ID one! */
|
/* Warning! Caller's responsibility to ensure given bhead **is** an ID one! */
|
||||||
const char *blo_bhead_id_name(const FileData *fd, const BHead *bhead)
|
const char *blo_bhead_id_name(const FileData *fd, const BHead *bhead)
|
||||||
{
|
{
|
||||||
return (const char *)POINTER_OFFSET(bhead, sizeof(*bhead) + fd->id_name_offs);
|
return (const char *)POINTER_OFFSET(bhead, sizeof(*bhead) + fd->id_name_offs);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Warning! Caller's responsibility to ensure given bhead **is** an ID one! */
|
||||||
|
AssetMetaData *blo_bhead_id_asset_data_address(const FileData *fd, const BHead *bhead)
|
||||||
|
{
|
||||||
|
BLI_assert(BKE_idtype_idcode_is_valid(bhead->code));
|
||||||
|
return (fd->id_asset_data_offs >= 0) ?
|
||||||
|
*(AssetMetaData **)POINTER_OFFSET(bhead, sizeof(*bhead) + fd->id_asset_data_offs) :
|
||||||
|
NULL;
|
||||||
|
}
|
||||||
|
|
||||||
static void decode_blender_header(FileData *fd)
|
static void decode_blender_header(FileData *fd)
|
||||||
{
|
{
|
||||||
char header[SIZEOFBLENDERHEADER], num[4];
|
char header[SIZEOFBLENDERHEADER], num[4];
|
||||||
|
@ -1040,6 +1051,8 @@ static bool read_file_dna(FileData *fd, const char **r_error_message)
|
||||||
/* used to retrieve ID names from (bhead+1) */
|
/* used to retrieve ID names from (bhead+1) */
|
||||||
fd->id_name_offs = DNA_elem_offset(fd->filesdna, "ID", "char", "name[]");
|
fd->id_name_offs = DNA_elem_offset(fd->filesdna, "ID", "char", "name[]");
|
||||||
BLI_assert(fd->id_name_offs != -1);
|
BLI_assert(fd->id_name_offs != -1);
|
||||||
|
fd->id_asset_data_offs = DNA_elem_offset(
|
||||||
|
fd->filesdna, "ID", "AssetMetaData", "*asset_data");
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -2360,6 +2373,11 @@ static void direct_link_id_common(
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (id->asset_data) {
|
||||||
|
BLO_read_data_address(reader, &id->asset_data);
|
||||||
|
BKE_asset_metadata_read(reader, id->asset_data);
|
||||||
|
}
|
||||||
|
|
||||||
/*link direct data of ID properties*/
|
/*link direct data of ID properties*/
|
||||||
if (id->properties) {
|
if (id->properties) {
|
||||||
BLO_read_data_address(reader, &id->properties);
|
BLO_read_data_address(reader, &id->properties);
|
||||||
|
@ -3607,6 +3625,27 @@ static BHead *read_libblock(FileData *fd,
|
||||||
|
|
||||||
/** \} */
|
/** \} */
|
||||||
|
|
||||||
|
/* -------------------------------------------------------------------- */
|
||||||
|
/** \name Read Asset Data
|
||||||
|
* \{ */
|
||||||
|
|
||||||
|
BHead *blo_read_asset_data_block(FileData *fd, BHead *bhead, AssetMetaData **r_asset_data)
|
||||||
|
{
|
||||||
|
BLI_assert(BKE_idtype_idcode_is_valid(bhead->code));
|
||||||
|
|
||||||
|
bhead = read_data_into_datamap(fd, bhead, "asset-data read");
|
||||||
|
|
||||||
|
BlendDataReader reader = {fd};
|
||||||
|
BLO_read_data_address(&reader, r_asset_data);
|
||||||
|
BKE_asset_metadata_read(&reader, *r_asset_data);
|
||||||
|
|
||||||
|
oldnewmap_clear(fd->datamap);
|
||||||
|
|
||||||
|
return bhead;
|
||||||
|
}
|
||||||
|
|
||||||
|
/** \} */
|
||||||
|
|
||||||
/* -------------------------------------------------------------------- */
|
/* -------------------------------------------------------------------- */
|
||||||
/** \name Read Global Data
|
/** \name Read Global Data
|
||||||
* \{ */
|
* \{ */
|
||||||
|
|
|
@ -112,6 +112,9 @@ typedef struct FileData {
|
||||||
int fileversion;
|
int fileversion;
|
||||||
/** Used to retrieve ID names from (bhead+1). */
|
/** Used to retrieve ID names from (bhead+1). */
|
||||||
int id_name_offs;
|
int id_name_offs;
|
||||||
|
/** Used to retrieve asset data from (bhead+1). NOTE: This may not be available in old files,
|
||||||
|
* will be -1 then! */
|
||||||
|
int id_asset_data_offs;
|
||||||
/** For do_versions patching. */
|
/** For do_versions patching. */
|
||||||
int globalf, fileflags;
|
int globalf, fileflags;
|
||||||
|
|
||||||
|
@ -159,6 +162,8 @@ void blo_end_packed_pointer_map(FileData *fd, struct Main *oldmain);
|
||||||
void blo_add_library_pointer_map(ListBase *old_mainlist, FileData *fd);
|
void blo_add_library_pointer_map(ListBase *old_mainlist, FileData *fd);
|
||||||
void blo_make_old_idmap_from_main(FileData *fd, struct Main *bmain);
|
void blo_make_old_idmap_from_main(FileData *fd, struct Main *bmain);
|
||||||
|
|
||||||
|
BHead *blo_read_asset_data_block(FileData *fd, BHead *bhead, struct AssetMetaData **r_asset_data);
|
||||||
|
|
||||||
void blo_cache_storage_init(FileData *fd, struct Main *bmain);
|
void blo_cache_storage_init(FileData *fd, struct Main *bmain);
|
||||||
void blo_cache_storage_old_bmain_clear(FileData *fd, struct Main *bmain_old);
|
void blo_cache_storage_old_bmain_clear(FileData *fd, struct Main *bmain_old);
|
||||||
void blo_cache_storage_end(FileData *fd);
|
void blo_cache_storage_end(FileData *fd);
|
||||||
|
@ -170,6 +175,7 @@ BHead *blo_bhead_next(FileData *fd, BHead *thisblock);
|
||||||
BHead *blo_bhead_prev(FileData *fd, BHead *thisblock);
|
BHead *blo_bhead_prev(FileData *fd, BHead *thisblock);
|
||||||
|
|
||||||
const char *blo_bhead_id_name(const FileData *fd, const BHead *bhead);
|
const char *blo_bhead_id_name(const FileData *fd, const BHead *bhead);
|
||||||
|
struct AssetMetaData *blo_bhead_id_asset_data_address(const FileData *fd, const BHead *bhead);
|
||||||
|
|
||||||
/* do versions stuff */
|
/* do versions stuff */
|
||||||
|
|
||||||
|
|
|
@ -264,7 +264,12 @@ typedef struct IDOverrideLibrary {
|
||||||
typedef struct ID {
|
typedef struct ID {
|
||||||
void *next, *prev;
|
void *next, *prev;
|
||||||
struct ID *newid;
|
struct ID *newid;
|
||||||
|
|
||||||
struct Library *lib;
|
struct Library *lib;
|
||||||
|
|
||||||
|
/** If the ID is an asset, this pointer is set. Owning pointer. */
|
||||||
|
struct AssetMetaData *asset_data;
|
||||||
|
|
||||||
/** MAX_ID_NAME. */
|
/** MAX_ID_NAME. */
|
||||||
char name[66];
|
char name[66];
|
||||||
/**
|
/**
|
||||||
|
@ -310,6 +315,7 @@ typedef struct ID {
|
||||||
struct ID *orig_id;
|
struct ID *orig_id;
|
||||||
|
|
||||||
void *py_instance;
|
void *py_instance;
|
||||||
|
void *_pad1;
|
||||||
} ID;
|
} ID;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -0,0 +1,37 @@
|
||||||
|
/*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software Foundation,
|
||||||
|
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** \file
|
||||||
|
* \ingroup DNA
|
||||||
|
*/
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
/* Struct members on own line. */
|
||||||
|
/* clang-format off */
|
||||||
|
|
||||||
|
/* -------------------------------------------------------------------- */
|
||||||
|
/** \name Asset Struct
|
||||||
|
* \{ */
|
||||||
|
|
||||||
|
#define _DNA_DEFAULT_AssetMetaData \
|
||||||
|
{ \
|
||||||
|
0 \
|
||||||
|
}
|
||||||
|
|
||||||
|
/** \} */
|
||||||
|
|
||||||
|
/* clang-format on */
|
|
@ -0,0 +1,62 @@
|
||||||
|
/*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software Foundation,
|
||||||
|
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** \file
|
||||||
|
* \ingroup DNA
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef __DNA_ASSET_TYPES_H__
|
||||||
|
#define __DNA_ASSET_TYPES_H__
|
||||||
|
|
||||||
|
#include "DNA_listBase.h"
|
||||||
|
|
||||||
|
/**
|
||||||
|
* \brief User defined tag.
|
||||||
|
* Currently only used by assets, could be used more often at some point.
|
||||||
|
* Maybe add a custom icon and color to these in future?
|
||||||
|
*/
|
||||||
|
typedef struct AssetTag {
|
||||||
|
struct AssetTag *next, *prev;
|
||||||
|
char name[64]; /* MAX_NAME */
|
||||||
|
} AssetTag;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* \brief The meta-data of an asset.
|
||||||
|
* By creating and giving this for a data-block (#ID.asset_data), the data-block becomes an asset.
|
||||||
|
*
|
||||||
|
* \note This struct must be readable without having to read anything but blocks from the ID it is
|
||||||
|
* attached to! That way, asset information of a file can be read, without reading anything
|
||||||
|
* more than that from the file. So pointers to other IDs or ID data are strictly forbidden.
|
||||||
|
*/
|
||||||
|
typedef struct AssetMetaData {
|
||||||
|
/** Custom asset meta-data. Cannot store pointers to IDs (#STRUCT_NO_DATABLOCK_IDPROPERTIES)! */
|
||||||
|
struct IDProperty *properties;
|
||||||
|
|
||||||
|
/** Optional description of this asset for display in the UI. Dynamic length. */
|
||||||
|
char *description;
|
||||||
|
/** User defined tags for this asset. The asset manager uses these for filtering, but how they
|
||||||
|
* function exactly (e.g. how they are registered to provide a list of searchable available tags)
|
||||||
|
* is up to the asset-engine. */
|
||||||
|
ListBase tags; /* AssetTag */
|
||||||
|
short active_tag;
|
||||||
|
/** Store the number of tags to avoid continuous counting. Could be turned into runtime data, we
|
||||||
|
* can always reliably reconstruct it from the list. */
|
||||||
|
short tot_tags;
|
||||||
|
|
||||||
|
char _pad[4];
|
||||||
|
} AssetMetaData;
|
||||||
|
|
||||||
|
#endif /* __DNA_ASSET_TYPES_H__ */
|
|
@ -138,6 +138,7 @@ set(SRC
|
||||||
../../blenlib/intern/hash_mm2a.c
|
../../blenlib/intern/hash_mm2a.c
|
||||||
../../blenlib/intern/listbase.c
|
../../blenlib/intern/listbase.c
|
||||||
|
|
||||||
|
../DNA_asset_defaults.h
|
||||||
../DNA_brush_defaults.h
|
../DNA_brush_defaults.h
|
||||||
../DNA_cachefile_defaults.h
|
../DNA_cachefile_defaults.h
|
||||||
../DNA_camera_defaults.h
|
../DNA_camera_defaults.h
|
||||||
|
|
|
@ -85,6 +85,7 @@
|
||||||
#include "DNA_defaults.h"
|
#include "DNA_defaults.h"
|
||||||
|
|
||||||
#include "DNA_armature_types.h"
|
#include "DNA_armature_types.h"
|
||||||
|
#include "DNA_asset_types.h"
|
||||||
#include "DNA_brush_types.h"
|
#include "DNA_brush_types.h"
|
||||||
#include "DNA_cachefile_types.h"
|
#include "DNA_cachefile_types.h"
|
||||||
#include "DNA_camera_types.h"
|
#include "DNA_camera_types.h"
|
||||||
|
@ -117,6 +118,7 @@
|
||||||
#include "DNA_world_types.h"
|
#include "DNA_world_types.h"
|
||||||
|
|
||||||
#include "DNA_armature_defaults.h"
|
#include "DNA_armature_defaults.h"
|
||||||
|
#include "DNA_asset_defaults.h"
|
||||||
#include "DNA_brush_defaults.h"
|
#include "DNA_brush_defaults.h"
|
||||||
#include "DNA_cachefile_defaults.h"
|
#include "DNA_cachefile_defaults.h"
|
||||||
#include "DNA_camera_defaults.h"
|
#include "DNA_camera_defaults.h"
|
||||||
|
@ -148,6 +150,9 @@
|
||||||
#define SDNA_DEFAULT_DECL_STRUCT(struct_name) \
|
#define SDNA_DEFAULT_DECL_STRUCT(struct_name) \
|
||||||
static const struct_name DNA_DEFAULT_##struct_name = _DNA_DEFAULT_##struct_name
|
static const struct_name DNA_DEFAULT_##struct_name = _DNA_DEFAULT_##struct_name
|
||||||
|
|
||||||
|
/* DNA_asset_defaults.h */
|
||||||
|
SDNA_DEFAULT_DECL_STRUCT(AssetMetaData);
|
||||||
|
|
||||||
/* DNA_armature_defaults.h */
|
/* DNA_armature_defaults.h */
|
||||||
SDNA_DEFAULT_DECL_STRUCT(bArmature);
|
SDNA_DEFAULT_DECL_STRUCT(bArmature);
|
||||||
|
|
||||||
|
@ -338,7 +343,10 @@ extern const bTheme U_theme_default;
|
||||||
/** Keep headers sorted. */
|
/** Keep headers sorted. */
|
||||||
const void *DNA_default_table[SDNA_TYPE_MAX] = {
|
const void *DNA_default_table[SDNA_TYPE_MAX] = {
|
||||||
|
|
||||||
/* DNA_arnature_defaults.h */
|
/* DNA_asset_defaults.h */
|
||||||
|
SDNA_DEFAULT_DECL(AssetMetaData),
|
||||||
|
|
||||||
|
/* DNA_armature_defaults.h */
|
||||||
SDNA_DEFAULT_DECL(bArmature),
|
SDNA_DEFAULT_DECL(bArmature),
|
||||||
|
|
||||||
/* DNA_brush_defaults.h */
|
/* DNA_brush_defaults.h */
|
||||||
|
|
|
@ -139,6 +139,7 @@ static const char *includefiles[] = {
|
||||||
"DNA_volume_types.h",
|
"DNA_volume_types.h",
|
||||||
"DNA_simulation_types.h",
|
"DNA_simulation_types.h",
|
||||||
"DNA_pointcache_types.h",
|
"DNA_pointcache_types.h",
|
||||||
|
"DNA_asset_types.h",
|
||||||
|
|
||||||
/* see comment above before editing! */
|
/* see comment above before editing! */
|
||||||
|
|
||||||
|
@ -1533,6 +1534,7 @@ int main(int argc, char **argv)
|
||||||
#include "DNA_action_types.h"
|
#include "DNA_action_types.h"
|
||||||
#include "DNA_anim_types.h"
|
#include "DNA_anim_types.h"
|
||||||
#include "DNA_armature_types.h"
|
#include "DNA_armature_types.h"
|
||||||
|
#include "DNA_asset_types.h"
|
||||||
#include "DNA_boid_types.h"
|
#include "DNA_boid_types.h"
|
||||||
#include "DNA_brush_types.h"
|
#include "DNA_brush_types.h"
|
||||||
#include "DNA_cachefile_types.h"
|
#include "DNA_cachefile_types.h"
|
||||||
|
|
|
@ -70,6 +70,8 @@ extern StructRNA RNA_ArrayGpencilModifier;
|
||||||
extern StructRNA RNA_ArrayModifier;
|
extern StructRNA RNA_ArrayModifier;
|
||||||
extern StructRNA RNA_Attribute;
|
extern StructRNA RNA_Attribute;
|
||||||
extern StructRNA RNA_AttributeGroup;
|
extern StructRNA RNA_AttributeGroup;
|
||||||
|
extern StructRNA RNA_AssetMetaData;
|
||||||
|
extern StructRNA RNA_AssetTag;
|
||||||
extern StructRNA RNA_BackgroundImage;
|
extern StructRNA RNA_BackgroundImage;
|
||||||
extern StructRNA RNA_BevelModifier;
|
extern StructRNA RNA_BevelModifier;
|
||||||
extern StructRNA RNA_BezierSplinePoint;
|
extern StructRNA RNA_BezierSplinePoint;
|
||||||
|
|
|
@ -31,6 +31,7 @@ set(DEFSRC
|
||||||
rna_animviz.c
|
rna_animviz.c
|
||||||
rna_armature.c
|
rna_armature.c
|
||||||
rna_attribute.c
|
rna_attribute.c
|
||||||
|
rna_asset.c
|
||||||
rna_boid.c
|
rna_boid.c
|
||||||
rna_brush.c
|
rna_brush.c
|
||||||
rna_cachefile.c
|
rna_cachefile.c
|
||||||
|
|
|
@ -4270,6 +4270,7 @@ static RNAProcessItem PROCESS_ITEMS[] = {
|
||||||
{"rna_animviz.c", NULL, RNA_def_animviz},
|
{"rna_animviz.c", NULL, RNA_def_animviz},
|
||||||
{"rna_armature.c", "rna_armature_api.c", RNA_def_armature},
|
{"rna_armature.c", "rna_armature_api.c", RNA_def_armature},
|
||||||
{"rna_attribute.c", NULL, RNA_def_attribute},
|
{"rna_attribute.c", NULL, RNA_def_attribute},
|
||||||
|
{"rna_asset.c", NULL, RNA_def_asset},
|
||||||
{"rna_boid.c", NULL, RNA_def_boid},
|
{"rna_boid.c", NULL, RNA_def_boid},
|
||||||
{"rna_brush.c", NULL, RNA_def_brush},
|
{"rna_brush.c", NULL, RNA_def_brush},
|
||||||
{"rna_cachefile.c", NULL, RNA_def_cachefile},
|
{"rna_cachefile.c", NULL, RNA_def_cachefile},
|
||||||
|
|
|
@ -1528,6 +1528,11 @@ static void rna_def_ID(BlenderRNA *brna)
|
||||||
RNA_def_property_override_flag(prop, PROPOVERRIDE_NO_COMPARISON);
|
RNA_def_property_override_flag(prop, PROPOVERRIDE_NO_COMPARISON);
|
||||||
RNA_def_property_ui_text(prop, "Library", "Library file the data-block is linked from");
|
RNA_def_property_ui_text(prop, "Library", "Library file the data-block is linked from");
|
||||||
|
|
||||||
|
prop = RNA_def_property(srna, "asset_data", PROP_POINTER, PROP_NONE);
|
||||||
|
RNA_def_property_clear_flag(prop, PROP_EDITABLE);
|
||||||
|
RNA_def_property_override_flag(prop, PROPOVERRIDE_NO_COMPARISON);
|
||||||
|
RNA_def_property_ui_text(prop, "Asset Data", "Additional data for an asset data-block");
|
||||||
|
|
||||||
prop = RNA_def_pointer(
|
prop = RNA_def_pointer(
|
||||||
srna, "override_library", "IDOverrideLibrary", "Library Override", "Library override data");
|
srna, "override_library", "IDOverrideLibrary", "Library Override", "Library override data");
|
||||||
RNA_def_property_clear_flag(prop, PROP_EDITABLE);
|
RNA_def_property_clear_flag(prop, PROP_EDITABLE);
|
||||||
|
|
|
@ -0,0 +1,228 @@
|
||||||
|
/*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software Foundation,
|
||||||
|
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** \file
|
||||||
|
* \ingroup RNA
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <stdlib.h>
|
||||||
|
|
||||||
|
#include "RNA_define.h"
|
||||||
|
#include "RNA_enum_types.h"
|
||||||
|
|
||||||
|
#include "DNA_asset_types.h"
|
||||||
|
#include "DNA_defs.h"
|
||||||
|
|
||||||
|
#include "rna_internal.h"
|
||||||
|
|
||||||
|
#ifdef RNA_RUNTIME
|
||||||
|
|
||||||
|
# include "BKE_asset.h"
|
||||||
|
# include "BKE_idprop.h"
|
||||||
|
|
||||||
|
# include "BLI_listbase.h"
|
||||||
|
|
||||||
|
# include "RNA_access.h"
|
||||||
|
|
||||||
|
static AssetTag *rna_AssetMetaData_tag_new(AssetMetaData *asset_data,
|
||||||
|
ReportList *reports,
|
||||||
|
const char *name,
|
||||||
|
bool skip_if_exists)
|
||||||
|
{
|
||||||
|
AssetTag *tag = NULL;
|
||||||
|
|
||||||
|
if (skip_if_exists) {
|
||||||
|
struct AssetTagEnsureResult result = BKE_asset_metadata_tag_ensure(asset_data, name);
|
||||||
|
|
||||||
|
if (!result.is_new) {
|
||||||
|
BKE_reportf(
|
||||||
|
reports, RPT_WARNING, "Tag '%s' already present for given asset", result.tag->name);
|
||||||
|
/* Report, but still return valid item. */
|
||||||
|
}
|
||||||
|
tag = result.tag;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
tag = BKE_asset_metadata_tag_add(asset_data, name);
|
||||||
|
}
|
||||||
|
|
||||||
|
return tag;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void rna_AssetMetaData_tag_remove(AssetMetaData *asset_data,
|
||||||
|
ReportList *reports,
|
||||||
|
PointerRNA *tag_ptr)
|
||||||
|
{
|
||||||
|
AssetTag *tag = tag_ptr->data;
|
||||||
|
if (BLI_findindex(&asset_data->tags, tag) == -1) {
|
||||||
|
BKE_reportf(reports, RPT_ERROR, "Tag '%s' not found in given asset", tag->name);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
BKE_asset_metadata_tag_remove(asset_data, tag);
|
||||||
|
RNA_POINTER_INVALIDATE(tag_ptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
static IDProperty *rna_AssetMetaData_idprops(PointerRNA *ptr, bool create)
|
||||||
|
{
|
||||||
|
AssetMetaData *asset_data = ptr->data;
|
||||||
|
|
||||||
|
if (create && !asset_data->properties) {
|
||||||
|
IDPropertyTemplate val = {0};
|
||||||
|
asset_data->properties = IDP_New(IDP_GROUP, &val, "RNA_AssetMetaData group");
|
||||||
|
}
|
||||||
|
|
||||||
|
return asset_data->properties;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void rna_AssetMetaData_description_get(PointerRNA *ptr, char *value)
|
||||||
|
{
|
||||||
|
AssetMetaData *asset_data = ptr->data;
|
||||||
|
|
||||||
|
if (asset_data->description) {
|
||||||
|
strcpy(value, asset_data->description);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
value[0] = '\0';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static int rna_AssetMetaData_description_length(PointerRNA *ptr)
|
||||||
|
{
|
||||||
|
AssetMetaData *asset_data = ptr->data;
|
||||||
|
return asset_data->description ? strlen(asset_data->description) : 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void rna_AssetMetaData_description_set(PointerRNA *ptr, const char *value)
|
||||||
|
{
|
||||||
|
AssetMetaData *asset_data = ptr->data;
|
||||||
|
|
||||||
|
if (asset_data->description) {
|
||||||
|
MEM_freeN(asset_data->description);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (value[0]) {
|
||||||
|
asset_data->description = BLI_strdup(value);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
asset_data->description = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void rna_AssetMetaData_active_tag_range(
|
||||||
|
PointerRNA *ptr, int *min, int *max, int *softmin, int *softmax)
|
||||||
|
{
|
||||||
|
const AssetMetaData *asset_data = ptr->data;
|
||||||
|
*min = *softmin = 0;
|
||||||
|
*max = *softmax = MAX2(asset_data->tot_tags - 1, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
#else
|
||||||
|
|
||||||
|
static void rna_def_asset_tag(BlenderRNA *brna)
|
||||||
|
{
|
||||||
|
StructRNA *srna;
|
||||||
|
PropertyRNA *prop;
|
||||||
|
|
||||||
|
srna = RNA_def_struct(brna, "AssetTag", NULL);
|
||||||
|
RNA_def_struct_ui_text(srna, "Asset Tag", "User defined tag (name token)");
|
||||||
|
|
||||||
|
prop = RNA_def_property(srna, "name", PROP_STRING, PROP_NONE);
|
||||||
|
RNA_def_property_string_maxlength(prop, MAX_NAME);
|
||||||
|
RNA_def_property_ui_text(prop, "Name", "The identifier that makes up this tag");
|
||||||
|
RNA_def_struct_name_property(srna, prop);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void rna_def_asset_tags_api(BlenderRNA *brna, PropertyRNA *cprop)
|
||||||
|
{
|
||||||
|
StructRNA *srna;
|
||||||
|
|
||||||
|
FunctionRNA *func;
|
||||||
|
PropertyRNA *parm;
|
||||||
|
|
||||||
|
RNA_def_property_srna(cprop, "AssetTags");
|
||||||
|
srna = RNA_def_struct(brna, "AssetTags", NULL);
|
||||||
|
RNA_def_struct_sdna(srna, "AssetMetaData");
|
||||||
|
RNA_def_struct_ui_text(srna, "Asset Tags", "Collection of custom asset tags");
|
||||||
|
|
||||||
|
/* Tag collection */
|
||||||
|
func = RNA_def_function(srna, "new", "rna_AssetMetaData_tag_new");
|
||||||
|
RNA_def_function_ui_description(func, "Add a new tag to this asset");
|
||||||
|
RNA_def_function_flag(func, FUNC_USE_REPORTS);
|
||||||
|
parm = RNA_def_string(func, "name", NULL, MAX_NAME, "Name", "");
|
||||||
|
RNA_def_parameter_flags(parm, 0, PARM_REQUIRED);
|
||||||
|
parm = RNA_def_boolean(func,
|
||||||
|
"skip_if_exists",
|
||||||
|
false,
|
||||||
|
"Skip if Exists",
|
||||||
|
"Do not add a new tag if one of the same type already exists");
|
||||||
|
/* return type */
|
||||||
|
parm = RNA_def_pointer(func, "tag", "AssetTag", "", "New tag");
|
||||||
|
RNA_def_function_return(func, parm);
|
||||||
|
|
||||||
|
func = RNA_def_function(srna, "remove", "rna_AssetMetaData_tag_remove");
|
||||||
|
RNA_def_function_ui_description(func, "Remove an existing tag from this asset");
|
||||||
|
RNA_def_function_flag(func, FUNC_USE_REPORTS);
|
||||||
|
/* tag to remove */
|
||||||
|
parm = RNA_def_pointer(func, "tag", "AssetTag", "", "Removed tag");
|
||||||
|
RNA_def_parameter_flags(parm, PROP_NEVER_NULL, PARM_REQUIRED | PARM_RNAPTR);
|
||||||
|
RNA_def_parameter_clear_flags(parm, PROP_THICK_WRAP, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void rna_def_asset_data(BlenderRNA *brna)
|
||||||
|
{
|
||||||
|
StructRNA *srna;
|
||||||
|
PropertyRNA *prop;
|
||||||
|
|
||||||
|
srna = RNA_def_struct(brna, "AssetMetaData", NULL);
|
||||||
|
RNA_def_struct_ui_text(srna, "Asset Data", "Additional data stored for an asset data-block");
|
||||||
|
// RNA_def_struct_ui_icon(srna, ICON_ASSET); /* TODO: Icon doesn't exist!. */
|
||||||
|
/* The struct has custom properties, but no pointer properties to other IDs! */
|
||||||
|
RNA_def_struct_idprops_func(srna, "rna_AssetMetaData_idprops");
|
||||||
|
RNA_def_struct_flag(srna, STRUCT_NO_DATABLOCK_IDPROPERTIES); /* Mandatory! */
|
||||||
|
|
||||||
|
prop = RNA_def_property(srna, "description", PROP_STRING, PROP_NONE);
|
||||||
|
RNA_def_property_string_funcs(prop,
|
||||||
|
"rna_AssetMetaData_description_get",
|
||||||
|
"rna_AssetMetaData_description_length",
|
||||||
|
"rna_AssetMetaData_description_set");
|
||||||
|
RNA_def_property_ui_text(
|
||||||
|
prop, "Description", "A description of the asset to be displayed for the user");
|
||||||
|
|
||||||
|
prop = RNA_def_property(srna, "tags", PROP_COLLECTION, PROP_NONE);
|
||||||
|
RNA_def_property_struct_type(prop, "AssetTag");
|
||||||
|
RNA_def_property_flag(prop, PROP_EDITABLE);
|
||||||
|
RNA_def_property_ui_text(prop,
|
||||||
|
"Tags",
|
||||||
|
"Custom tags (name tokens) for the asset, used for filtering and "
|
||||||
|
"general asset management");
|
||||||
|
rna_def_asset_tags_api(brna, prop);
|
||||||
|
|
||||||
|
prop = RNA_def_property(srna, "active_tag", PROP_INT, PROP_NONE);
|
||||||
|
RNA_def_property_int_funcs(prop, NULL, NULL, "rna_AssetMetaData_active_tag_range");
|
||||||
|
RNA_def_property_ui_text(prop, "Active Tag", "Index of the tag set for editing");
|
||||||
|
}
|
||||||
|
|
||||||
|
void RNA_def_asset(BlenderRNA *brna)
|
||||||
|
{
|
||||||
|
RNA_define_animate_sdna(false);
|
||||||
|
|
||||||
|
rna_def_asset_tag(brna);
|
||||||
|
rna_def_asset_data(brna);
|
||||||
|
|
||||||
|
RNA_define_animate_sdna(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
|
@ -152,6 +152,7 @@ void RNA_def_animation(struct BlenderRNA *brna);
|
||||||
void RNA_def_animviz(struct BlenderRNA *brna);
|
void RNA_def_animviz(struct BlenderRNA *brna);
|
||||||
void RNA_def_armature(struct BlenderRNA *brna);
|
void RNA_def_armature(struct BlenderRNA *brna);
|
||||||
void RNA_def_attribute(struct BlenderRNA *brna);
|
void RNA_def_attribute(struct BlenderRNA *brna);
|
||||||
|
void RNA_def_asset(struct BlenderRNA *brna);
|
||||||
void RNA_def_boid(struct BlenderRNA *brna);
|
void RNA_def_boid(struct BlenderRNA *brna);
|
||||||
void RNA_def_brush(struct BlenderRNA *brna);
|
void RNA_def_brush(struct BlenderRNA *brna);
|
||||||
void RNA_def_cachefile(struct BlenderRNA *brna);
|
void RNA_def_cachefile(struct BlenderRNA *brna);
|
||||||
|
|
Loading…
Reference in New Issue