From 1da08a55563da3614d3818b74379e82a8bf6022f Mon Sep 17 00:00:00 2001 From: Julian Eisel Date: Tue, 26 Sep 2023 18:41:46 +0200 Subject: [PATCH] Asset shelf: Add asset library selector Adds a menu to choose the asset library to use to the asset shelf catalogs selector popover. This is consistent with the asset browser. After talking to animators and some artists, this is likely something they would want to have, since they don't always want all their assets and catalogs to populate the asset shelf. It's also necessary for the pose library UI to provide the same features roughly than the old one (in the sidebar, before the asset shelf was introduced). --- .../blenloader/intern/versioning_400.cc | 26 +++++++ .../editors/asset/intern/asset_shelf.cc | 68 ++++++++++--------- .../intern/asset_shelf_catalog_selector.cc | 27 ++++++-- source/blender/makesdna/DNA_screen_types.h | 3 + source/blender/makesrna/intern/rna_ui.cc | 19 ++++++ 5 files changed, 106 insertions(+), 37 deletions(-) diff --git a/source/blender/blenloader/intern/versioning_400.cc b/source/blender/blenloader/intern/versioning_400.cc index 02c46f1d357..22ac8cb1ed4 100644 --- a/source/blender/blenloader/intern/versioning_400.cc +++ b/source/blender/blenloader/intern/versioning_400.cc @@ -1533,5 +1533,31 @@ void blo_do_versions_400(FileData *fd, Library * /*lib*/, Main *bmain) */ { /* Keep this block, even when empty. */ + if (!DNA_struct_member_exists(fd->filesdna, + "AssetShelfSettings", + "AssetLibraryReference", + "asset_library_reference")) + { + LISTBASE_FOREACH (bScreen *, screen, &bmain->screens) { + LISTBASE_FOREACH (ScrArea *, area, &screen->areabase) { + LISTBASE_FOREACH (SpaceLink *, sl, &area->spacedata) { + const ListBase *regionbase = (sl == area->spacedata.first) ? &area->regionbase : + &sl->regionbase; + LISTBASE_FOREACH (ARegion *, region, regionbase) { + if (region->regiontype != RGN_TYPE_ASSET_SHELF) { + continue; + } + + RegionAssetShelf *shelf_data = static_cast(region->regiondata); + if (shelf_data && shelf_data->active_shelf) { + AssetShelfSettings &settings = shelf_data->active_shelf->settings; + settings.asset_library_reference.custom_library_index = -1; + settings.asset_library_reference.type = ASSET_LIBRARY_ALL; + } + } + } + } + } + } } } diff --git a/source/blender/editors/asset/intern/asset_shelf.cc b/source/blender/editors/asset/intern/asset_shelf.cc index 8cb6e8aa67c..ab8012f333e 100644 --- a/source/blender/editors/asset/intern/asset_shelf.cc +++ b/source/blender/editors/asset/intern/asset_shelf.cc @@ -11,6 +11,7 @@ #include #include "AS_asset_catalog_path.hh" +#include "AS_asset_library.hh" #include "BLI_string.h" @@ -91,6 +92,7 @@ static AssetShelf *create_shelf_from_type(AssetShelfType &type) AssetShelf *shelf = MEM_new(__func__); *shelf = dna::shallow_zero_initialize(); shelf->settings.preview_size = shelf::DEFAULT_TILE_SIZE; + shelf->settings.asset_library_reference = asset_system::all_library_reference(); shelf->type = &type; shelf->preferred_row_count = 1; STRNCPY(shelf->idname, type.idname); @@ -407,17 +409,6 @@ int ED_asset_shelf_region_prefsizey() return asset_shelf_default_tile_height() + 2 * main_region_padding_y(); } -/** - * The asset shelf always uses the "All" library for now. - */ -static const AssetLibraryReference &asset_shelf_library_ref() -{ - static AssetLibraryReference all_library_ref = {}; - all_library_ref.type = ASSET_LIBRARY_ALL; - all_library_ref.custom_library_index = -1; - return all_library_ref; -} - void ED_asset_shelf_region_layout(const bContext *C, ARegion *region) { const SpaceLink *space = CTX_wm_space_data(C); @@ -435,8 +426,6 @@ void ED_asset_shelf_region_layout(const bContext *C, ARegion *region) return; } - const AssetLibraryReference &library_ref = asset_shelf_library_ref(); - uiBlock *block = UI_block_begin(C, region, __func__, UI_EMBOSS); const uiStyle *style = UI_style_get_dpi(); @@ -452,7 +441,8 @@ void ED_asset_shelf_region_layout(const bContext *C, ARegion *region) 0, style); - shelf::build_asset_view(*layout, library_ref, *active_shelf, *C, *region); + shelf::build_asset_view( + *layout, active_shelf->settings.asset_library_reference, *active_shelf, *C, *region); int layout_height; UI_block_layout_resolve(block, nullptr, &layout_height); @@ -544,6 +534,29 @@ void ED_asset_shelf_region_blend_write(BlendWriter *writer, ARegion *region) /** \name Asset Shelf Context * \{ */ +static AssetShelf *active_shelf_from_area(const ScrArea *area) +{ + const ARegion *shelf_region = BKE_area_find_region_type(area, RGN_TYPE_ASSET_SHELF); + if (!shelf_region) { + /* Called in wrong context, area doesn't have a shelf. */ + BLI_assert_unreachable(); + return nullptr; + } + + if (shelf_region->flag & RGN_FLAG_POLL_FAILED) { + /* Don't return data when the region "doesn't exist" (poll failed). */ + return nullptr; + } + + const RegionAssetShelf *shelf_regiondata = RegionAssetShelf::get_from_asset_shelf_region( + *shelf_region); + if (!shelf_regiondata) { + return nullptr; + } + + return shelf_regiondata->active_shelf; +} + int ED_asset_shelf_context(const bContext *C, const char *member, bContextDataResult *result) { static const char *context_dir[] = { @@ -561,34 +574,25 @@ int ED_asset_shelf_context(const bContext *C, const char *member, bContextDataRe bScreen *screen = CTX_wm_screen(C); if (CTX_data_equals(member, "asset_shelf")) { - const ARegion *shelf_region = BKE_area_find_region_type(CTX_wm_area(C), RGN_TYPE_ASSET_SHELF); - if (!shelf_region) { - /* Called in wrong context, area doesn't have a shelf. */ - BLI_assert_unreachable(); + AssetShelf *active_shelf = active_shelf_from_area(CTX_wm_area(C)); + if (!active_shelf) { return CTX_RESULT_NO_DATA; } - if (shelf_region->flag & RGN_FLAG_POLL_FAILED) { - /* Don't return data when the region "doesn't exist" (poll failed). */ - return CTX_RESULT_NO_DATA; - } - - const RegionAssetShelf *shelf_regiondata = RegionAssetShelf::get_from_asset_shelf_region( - *shelf_region); - if (!shelf_regiondata) { - return CTX_RESULT_NO_DATA; - } - - CTX_data_pointer_set(result, &screen->id, &RNA_AssetShelf, shelf_regiondata->active_shelf); - + CTX_data_pointer_set(result, &screen->id, &RNA_AssetShelf, active_shelf); return CTX_RESULT_OK; } if (CTX_data_equals(member, "asset_library_reference")) { + AssetShelf *active_shelf = active_shelf_from_area(CTX_wm_area(C)); + if (!active_shelf) { + return CTX_RESULT_NO_DATA; + } + CTX_data_pointer_set(result, &screen->id, &RNA_AssetLibraryReference, - const_cast(&asset_shelf_library_ref())); + &active_shelf->settings.asset_library_reference); return CTX_RESULT_OK; } diff --git a/source/blender/editors/asset/intern/asset_shelf_catalog_selector.cc b/source/blender/editors/asset/intern/asset_shelf_catalog_selector.cc index 0f5c60d1150..df1b72f8000 100644 --- a/source/blender/editors/asset/intern/asset_shelf_catalog_selector.cc +++ b/source/blender/editors/asset/intern/asset_shelf_catalog_selector.cc @@ -22,8 +22,12 @@ #include "BLT_translation.h" #include "ED_asset_filter.hh" +#include "ED_asset_list.h" #include "ED_asset_list.hh" +#include "RNA_access.hh" +#include "RNA_prototypes.h" + #include "UI_interface.hh" #include "UI_tree_view.hh" @@ -46,7 +50,7 @@ class AssetCatalogSelectorTree : public ui::AbstractTreeView { { catalog_tree_ = build_filtered_catalog_tree( library, - asset_system::all_library_reference(), + shelf_settings_.asset_library_reference, [this](const asset_system::AssetRepresentation &asset) { return (!shelf_.type->asset_poll || shelf_.type->asset_poll(shelf_.type, &asset)); }); @@ -180,15 +184,26 @@ void AssetCatalogSelectorTree::update_shelf_settings_from_enabled_catalogs() static void catalog_selector_panel_draw(const bContext *C, Panel *panel) { const AssetLibraryReference *library_ref = CTX_wm_asset_library_ref(C); - asset_system::AssetLibrary *library = ED_assetlist_library_get_once_available(*library_ref); AssetShelf *shelf = active_shelf_from_context(C); + if (!shelf) { + return; + } uiLayout *layout = panel->layout; uiBlock *block = uiLayoutGetBlock(layout); - uiItemL(layout, IFACE_("Catalogs"), ICON_NONE); + uiLayoutSetOperatorContext(layout, WM_OP_INVOKE_DEFAULT); - if (!library || !shelf) { + PointerRNA shelf_ptr = RNA_pointer_create(&CTX_wm_screen(C)->id, &RNA_AssetShelf, shelf); + + uiLayout *row = uiLayoutRow(layout, true); + uiItemR(row, &shelf_ptr, "asset_library_reference", UI_ITEM_NONE, "", ICON_NONE); + if (library_ref->type != ASSET_LIBRARY_LOCAL) { + uiItemO(row, "", ICON_FILE_REFRESH, "ASSET_OT_library_refresh"); + } + + asset_system::AssetLibrary *library = ED_assetlist_library_get_once_available(*library_ref); + if (!library) { return; } @@ -212,8 +227,10 @@ void catalog_selector_panel_register(ARegionType *region_type) STRNCPY(pt->idname, "ASSETSHELF_PT_catalog_selector"); STRNCPY(pt->label, N_("Catalog Selector")); STRNCPY(pt->translation_context, BLT_I18NCONTEXT_DEFAULT_BPYRNA); - pt->description = N_("Select catalogs to display in the asset shelf"); + pt->description = N_( + "Select the asset library and the contained catalogs to display in the asset shelf"); pt->draw = catalog_selector_panel_draw; + pt->listener = asset::asset_reading_region_listen_fn; BLI_addtail(®ion_type->paneltypes, pt); WM_paneltype_add(pt); } diff --git a/source/blender/makesdna/DNA_screen_types.h b/source/blender/makesdna/DNA_screen_types.h index 77f563ea37c..5ce238e4f70 100644 --- a/source/blender/makesdna/DNA_screen_types.h +++ b/source/blender/makesdna/DNA_screen_types.h @@ -10,6 +10,7 @@ #include "BLI_utildefines.h" +#include "DNA_asset_types.h" #include "DNA_defs.h" #include "DNA_listBase.h" #include "DNA_vec_types.h" @@ -771,6 +772,8 @@ enum { typedef struct AssetShelfSettings { struct AssetShelfSettings *next, *prev; + AssetLibraryReference asset_library_reference; + ListBase enabled_catalog_paths; /* #LinkData */ /** If not set (null or empty string), all assets will be displayed ("All" catalog behavior). */ const char *active_catalog_path; diff --git a/source/blender/makesrna/intern/rna_ui.cc b/source/blender/makesrna/intern/rna_ui.cc index 4446dc645d0..a53413e323b 100644 --- a/source/blender/makesrna/intern/rna_ui.cc +++ b/source/blender/makesrna/intern/rna_ui.cc @@ -65,6 +65,7 @@ const EnumPropertyItem rna_enum_uilist_layout_type_items[] = { # include "BKE_report.h" # include "BKE_screen.hh" +# include "ED_asset_library.h" # include "ED_asset_shelf.h" # include "WM_api.hh" @@ -1246,6 +1247,18 @@ static StructRNA *rna_AssetShelf_refine(PointerRNA *shelf_ptr) return (shelf->type && shelf->type->rna_ext.srna) ? shelf->type->rna_ext.srna : &RNA_AssetShelf; } +static int rna_AssetShelf_asset_library_get(PointerRNA *ptr) +{ + AssetShelf *shelf = static_cast(ptr->data); + return ED_asset_library_reference_to_enum_value(&shelf->settings.asset_library_reference); +} + +static void rna_AssetShelf_asset_library_set(PointerRNA *ptr, int value) +{ + AssetShelf *shelf = static_cast(ptr->data); + shelf->settings.asset_library_reference = ED_asset_library_reference_from_enum_value(value); +} + static void rna_Panel_bl_description_set(PointerRNA *ptr, const char *value) { Panel *data = (Panel *)(ptr->data); @@ -2158,6 +2171,12 @@ static void rna_def_asset_shelf(BlenderRNA *brna) parm = RNA_def_pointer(func, "layout", "UILayout", "", ""); RNA_def_parameter_flags(parm, PropertyFlag(0), PARM_REQUIRED); + prop = rna_def_asset_library_reference_common( + srna, "rna_AssetShelf_asset_library_get", "rna_AssetShelf_asset_library_set"); + RNA_def_property_ui_text( + prop, "Asset Library", "Choose the asset library to display assets from"); + RNA_def_property_update(prop, NC_SPACE | ND_REGIONS_ASSET_SHELF, nullptr); + prop = RNA_def_property(srna, "show_names", PROP_BOOLEAN, PROP_NONE); RNA_def_property_boolean_sdna(prop, nullptr, "settings.display_flag", ASSETSHELF_SHOW_NAMES); RNA_def_property_ui_text(