Blender V4.5
brush_asset_ops.cc
Go to the documentation of this file.
1/* SPDX-FileCopyrightText: 2024 Blender Authors
2 *
3 * SPDX-License-Identifier: GPL-2.0-or-later */
4
5#include "BLI_fileops.h"
6#include "BLI_listbase.h"
7#include "BLI_path_utils.hh"
8#include "BLI_string.h"
9
10#include "DNA_brush_types.h"
11#include "DNA_scene_types.h"
12#include "DNA_space_types.h"
13#include "DNA_userdef_types.h"
14
15#include "BKE_asset.hh"
16#include "BKE_asset_edit.hh"
17#include "BKE_blendfile.hh"
18#include "BKE_brush.hh"
19#include "BKE_context.hh"
20#include "BKE_global.hh"
21#include "BKE_lib_id.hh"
22#include "BKE_paint.hh"
23#include "BKE_preferences.h"
24#include "BKE_preview_image.hh"
25#include "BKE_report.hh"
26
28#include "AS_asset_library.hh"
30
31#include "RNA_access.hh"
32#include "RNA_define.hh"
33
34#include "ED_asset.hh"
35#include "ED_asset_handle.hh"
36#include "ED_asset_library.hh"
37#include "ED_asset_list.hh"
40#include "ED_asset_shelf.hh"
41
42#include "UI_interface_icons.hh"
43
44#include "BLT_translation.hh"
45
46#include "WM_api.hh"
47#include "WM_toolsystem.hh"
48
49#include "paint_intern.hh"
50
52
54{
55 /* This operator currently covers both cases: the file/asset browser file list and the asset list
56 * used for the asset-view template. Once the asset list design is used by the Asset Browser,
57 * this can be simplified to just that case. */
58 Main *bmain = CTX_data_main(C);
59
60 if (G.background) {
61 /* As asset loading can take upwards of a few minutes on production libraries, we typically
62 * do not want this to execute in a blocking fashion. However, for testing / profiling
63 * purposes, this is an acceptable workaround for now until a proper python API is created
64 * for this use case. */
66 }
69 if (!asset) {
70 return OPERATOR_CANCELLED;
71 }
72
73 const bool use_toggle = RNA_boolean_get(op->ptr, "use_toggle");
74 AssetWeakReference brush_asset_reference = asset->make_weak_reference();
76 std::optional<AssetWeakReference> asset_to_save;
77 if (use_toggle) {
78 BLI_assert(paint->brush_asset_reference);
79 if (brush_asset_reference == *paint->brush_asset_reference) {
80 if (paint->runtime.previous_active_brush_reference != nullptr) {
81 brush_asset_reference = *paint->runtime.previous_active_brush_reference;
82 }
83 }
84 else {
85 asset_to_save = *paint->brush_asset_reference;
86 }
87 }
88 Brush *brush = reinterpret_cast<Brush *>(
89 bke::asset_edit_id_from_weak_reference(*bmain, ID_BR, brush_asset_reference));
90
91 /* Activate brush through tool system rather than calling #BKE_paint_brush_set() directly, to let
92 * the tool system switch tools if necessary, and update which brush was the last recently used
93 * one for the current tool. */
95 /* Note brush datablock was still added, so was not a no-op. */
96 BKE_report(op->reports, RPT_WARNING, "Unable to activate brush, wrong object mode");
97 return OPERATOR_FINISHED;
98 }
99
100 if (asset_to_save) {
101 BKE_paint_previous_asset_reference_set(paint, std::move(*asset_to_save));
102 }
103 else if (!use_toggle) {
104 /* If we aren't toggling, clear the previous reference so that we don't swap back to an
105 * incorrect "previous" asset */
107 }
108
111
112 return OPERATOR_FINISHED;
113}
114
116{
117 ot->name = "Activate Brush Asset";
118 ot->description = "Activate a brush asset as current sculpt and paint tool";
119 ot->idname = "BRUSH_OT_asset_activate";
120
122
124 PropertyRNA *prop;
125 prop = RNA_def_boolean(ot->srna,
126 "use_toggle",
127 false,
128 "Toggle",
129 "Switch between the current and assigned brushes on consecutive uses.");
131}
132
134{
136 Brush *brush = (paint) ? BKE_paint_brush(paint) : nullptr;
137 if (paint == nullptr || brush == nullptr) {
138 return false;
139 }
140 if (!paint->brush_asset_reference) {
141 /* The brush should always be an imported asset. We use this asset reference to find
142 * which library and catalog the brush came from, as defaults for the popup. */
143 return false;
144 }
145
146 return true;
147}
148
150{
151 Main *bmain = CTX_data_main(C);
153 Brush *brush = (paint) ? BKE_paint_brush(paint) : nullptr;
154
155 /* Determine file path to save to. */
156 PropertyRNA *name_prop = RNA_struct_find_property(op->ptr, "name");
157 char name[MAX_NAME] = "";
158 if (RNA_property_is_set(op->ptr, name_prop)) {
159 RNA_property_string_get(op->ptr, name_prop, name);
160 }
161 if (name[0] == '\0') {
162 STRNCPY(name, brush->id.name + 2);
163 }
164
165 const eAssetLibraryType enum_value = (eAssetLibraryType)RNA_enum_get(op->ptr,
166 "asset_library_reference");
167 const bool is_local_library = enum_value == ASSET_LIBRARY_LOCAL;
168
169 AssetLibraryReference library_reference;
170 const bUserAssetLibrary *user_library = nullptr;
171 if (is_local_library) {
173 }
174 else {
175 user_library = asset::get_asset_library_from_opptr(*op->ptr);
176 if (!user_library) {
177 return OPERATOR_CANCELLED;
178 }
179 library_reference = asset::user_library_to_library_ref(*user_library);
180 }
181 asset_system::AssetLibrary *library = AS_asset_library_load(bmain, library_reference);
182 if (!library) {
183 BKE_report(op->reports, RPT_ERROR, "Failed to load asset library");
184 return OPERATOR_CANCELLED;
185 }
186
187 BLI_assert(is_local_library || user_library);
188
189 /* Turn brush into asset if it isn't yet. */
190 if (!ID_IS_ASSET(&brush->id)) {
191 asset::mark_id(&brush->id);
192 asset::generate_preview(C, &brush->id);
193 }
194 BLI_assert(ID_IS_ASSET(&brush->id));
195
196 if (is_local_library) {
197 const Brush *original_brush = brush;
198 brush = BKE_brush_duplicate(
200
201 BKE_libblock_rename(*bmain, brush->id, name);
202 asset::mark_id(&brush->id);
203 BLI_assert(brush->id.us == 1);
204
206 brush->id.asset_data = BKE_asset_metadata_copy(original_brush->id.asset_data);
207 BLI_assert(brush->id.asset_data != nullptr);
208 }
209
210 /* Add asset to catalog. */
211 /* Note: This needs to happen after the local asset is created but BEFORE a non-local library
212 * is saved */
213 char catalog_path_c[MAX_NAME];
214 RNA_string_get(op->ptr, "catalog_path", catalog_path_c);
215
216 AssetMetaData &meta_data = *brush->id.asset_data;
217 if (catalog_path_c[0]) {
218 const asset_system::AssetCatalogPath catalog_path(catalog_path_c);
220 *library, catalog_path);
221 BKE_asset_metadata_catalog_id_set(&meta_data, catalog.catalog_id, catalog.simple_name.c_str());
222 }
223
224 if (!is_local_library) {
225 AssetWeakReference brush_asset_reference;
226 const std::optional<std::string> final_full_asset_filepath = bke::asset_edit_id_save_as(
227 *bmain, brush->id, name, *user_library, brush_asset_reference, *op->reports);
228 if (!final_full_asset_filepath) {
229 return OPERATOR_CANCELLED;
230 }
231 library->catalog_service().write_to_disk(*final_full_asset_filepath);
232
233 brush = reinterpret_cast<Brush *>(
234 bke::asset_edit_id_from_weak_reference(*bmain, ID_BR, brush_asset_reference));
235 brush->has_unsaved_changes = false;
236 }
237
239
241 /* Note brush asset was still saved in editable asset library, so was not a no-op. */
242 BKE_report(op->reports, RPT_WARNING, "Unable to activate just-saved brush asset");
243 }
244
245 asset::refresh_asset_library(C, library_reference);
247 if (is_local_library) {
250 }
251 else {
253 }
254
255 return OPERATOR_FINISHED;
256}
257
259{
260 if (library.type == ASSET_LIBRARY_ESSENTIALS) {
261 return false;
262 }
263 return true;
264}
265
267 wmOperator *op,
268 const wmEvent * /*event*/)
269{
271 const AssetWeakReference &brush_weak_ref = *paint->brush_asset_reference;
273 *C, brush_weak_ref, op->reports);
274 if (!asset) {
275 return OPERATOR_CANCELLED;
276 }
277 const asset_system::AssetLibrary &library = asset->owner_asset_library();
278 const std::optional<AssetLibraryReference> library_ref = library.library_reference();
279 if (!library_ref) {
281 return OPERATOR_CANCELLED;
282 }
283
284 RNA_string_set(op->ptr, "name", asset->get_name().c_str());
285
286 /* If the library isn't saved from the operator's last execution, find the current library or the
287 * first library if the current library isn't editable. */
288 if (!RNA_struct_property_is_set_ex(op->ptr, "asset_library_reference", false)) {
289 if (library_is_editable(*library_ref)) {
290 RNA_enum_set(op->ptr,
291 "asset_library_reference",
293 }
294 else {
296 *static_cast<const bUserAssetLibrary *>(U.asset_libraries.first));
297 RNA_enum_set(op->ptr,
298 "asset_library_reference",
300 }
301 }
302
303 /* By default, put the new asset in the same catalog as the existing asset. */
304 if (!RNA_struct_property_is_set(op->ptr, "catalog_path")) {
305 const asset_system::CatalogID &id = asset->get_metadata().catalog_id;
306 if (const asset_system::AssetCatalog *catalog = library.catalog_service().find_catalog(id)) {
307 RNA_string_set(op->ptr, "catalog_path", catalog->path.c_str());
308 }
309 }
310
311 return WM_operator_props_dialog_popup(C, op, 400, std::nullopt, IFACE_("Save"));
312}
313
315 PointerRNA * /*ptr*/,
316 PropertyRNA * /*prop*/,
317 bool *r_free)
318{
320 /* Only get writable libraries. */
321 /*include_readonly=*/false,
322 /*include_current_file=*/true);
323 if (!items) {
324 *r_free = false;
325 return nullptr;
326 }
327
328 *r_free = true;
329 return items;
330}
331
333 const bContext *C,
335 PropertyRNA * /*prop*/,
336 const char *edit_text,
338{
339 /* NOTE: Using the all library would also be a valid choice. */
342}
343
345{
346 ot->name = "Save as Brush Asset";
347 ot->description =
348 "Save a copy of the active brush asset into the default asset library, and make it the "
349 "active brush";
350 ot->idname = "BRUSH_OT_asset_save_as";
351
355
356 ot->prop = RNA_def_string(
357 ot->srna, "name", nullptr, MAX_NAME, "Name", "Name for the new brush asset");
358
359 PropertyRNA *prop = RNA_def_property(ot->srna, "asset_library_reference", PROP_ENUM, PROP_NONE);
361 RNA_def_property_ui_text(prop, "Library", "Asset library used to store the new brush");
362
363 prop = RNA_def_string(
364 ot->srna, "catalog_path", nullptr, MAX_NAME, "Catalog", "Catalog to use for the new asset");
367}
368
370{
371 Main *bmain = CTX_data_main(C);
373 Brush *brush = BKE_paint_brush(paint);
374 BLI_assert(ID_IS_ASSET(&brush->id));
375 const AssetWeakReference &brush_weak_ref = *paint->brush_asset_reference;
377 *C, brush_weak_ref, op->reports);
378 if (!asset) {
379 return OPERATOR_CANCELLED;
380 }
381 asset_system::AssetLibrary &library = asset->owner_asset_library();
382
383 char catalog_path_c[MAX_NAME];
384 RNA_string_get(op->ptr, "catalog_path", catalog_path_c);
385
386 AssetMetaData &meta_data = *brush->id.asset_data;
387 MEM_SAFE_FREE(meta_data.author);
388 meta_data.author = RNA_string_get_alloc(op->ptr, "author", nullptr, 0, nullptr);
389 MEM_SAFE_FREE(meta_data.description);
390 meta_data.description = RNA_string_get_alloc(op->ptr, "description", nullptr, 0, nullptr);
391
392 if (catalog_path_c[0]) {
393 const asset_system::AssetCatalogPath catalog_path(catalog_path_c);
395 library, catalog_path);
396 BKE_asset_metadata_catalog_id_set(&meta_data, catalog.catalog_id, catalog.simple_name.c_str());
397 }
398
399 if (!bke::asset_edit_id_save(*bmain, brush->id, *op->reports)) {
400 return OPERATOR_CANCELLED;
401 }
402
403 asset::catalogs_save_from_asset_reference(library, brush_weak_ref);
404
407
408 return OPERATOR_FINISHED;
409}
410
412 wmOperator *op,
413 const wmEvent * /*event*/)
414{
416 const AssetWeakReference &brush_weak_ref = *paint->brush_asset_reference;
418 *C, brush_weak_ref, op->reports);
419 if (!asset) {
420 return OPERATOR_CANCELLED;
421 }
422 const asset_system::AssetLibrary &library = asset->owner_asset_library();
423 const AssetMetaData &meta_data = asset->get_metadata();
424
425 if (!RNA_struct_property_is_set(op->ptr, "catalog_path")) {
426 const asset_system::CatalogID &id = meta_data.catalog_id;
427 if (const asset_system::AssetCatalog *catalog = library.catalog_service().find_catalog(id)) {
428 RNA_string_set(op->ptr, "catalog_path", catalog->path.c_str());
429 }
430 }
431 if (!RNA_struct_property_is_set(op->ptr, "author")) {
432 RNA_string_set(op->ptr, "author", meta_data.author ? meta_data.author : "");
433 }
434 if (!RNA_struct_property_is_set(op->ptr, "description")) {
435 RNA_string_set(op->ptr, "description", meta_data.description ? meta_data.description : "");
436 }
437
438 return WM_operator_props_dialog_popup(C, op, 400, std::nullopt, IFACE_("Edit Metadata"));
439}
440
442 const bContext *C,
443 PointerRNA * /*ptr*/,
444 PropertyRNA * /*prop*/,
445 const char *edit_text,
447{
449 const AssetWeakReference &brush_weak_ref = *paint->brush_asset_reference;
451 *C, brush_weak_ref, nullptr);
452 if (!asset) {
453 return;
454 }
455
456 const asset_system::AssetLibrary &library = asset->owner_asset_library();
457
458 /* NOTE: Using the all library would also be a valid choice. */
460 *CTX_data_main(C), *library.library_reference(), edit_text, visit_fn);
461}
462
464{
466 Brush *brush = (paint) ? BKE_paint_brush(paint) : nullptr;
467 if (paint == nullptr || brush == nullptr) {
468 return false;
469 }
470 if (!ID_IS_ASSET(&brush->id)) {
472 return false;
473 }
474 const AssetWeakReference *brush_weak_ref = paint->brush_asset_reference;
475 if (!brush_weak_ref) {
477 return false;
478 }
480 *C, *brush_weak_ref, CTX_wm_reports(C));
481 if (!asset) {
482 /* May happen if library loading hasn't finished. */
483 return false;
484 }
485 const std::optional<AssetLibraryReference> library_ref =
486 asset->owner_asset_library().library_reference();
487 if (!library_ref) {
489 return false;
490 }
491 if (!library_is_editable(*library_ref)) {
492 CTX_wm_operator_poll_msg_set(C, "Asset library is not editable");
493 return false;
494 }
495 if (!(library_ref->type & ASSET_LIBRARY_LOCAL) && !bke::asset_edit_id_is_writable(brush->id)) {
496 CTX_wm_operator_poll_msg_set(C, "Asset file is not editable");
497 return false;
498 }
499 return true;
500}
501
503{
504 ot->name = "Edit Metadata";
505 ot->description = "Edit asset information like the catalog, preview image, tags, or author";
506 ot->idname = "BRUSH_OT_asset_edit_metadata";
507
511
513 ot->srna, "catalog_path", nullptr, MAX_NAME, "Catalog", "The asset's catalog path");
516 RNA_def_string(ot->srna, "author", nullptr, 0, "Author", "");
517 RNA_def_string(ot->srna, "description", nullptr, 0, "Description", "");
518}
519
521{
522 Main *bmain = CTX_data_main(C);
524 Brush *brush = BKE_paint_brush(paint);
525 BLI_assert(ID_IS_ASSET(&brush->id));
526 const AssetWeakReference &brush_weak_ref = *paint->brush_asset_reference;
528 *C, brush_weak_ref, op->reports);
529 if (!asset) {
530 return OPERATOR_CANCELLED;
531 }
532
533 char filepath[FILE_MAX];
534 RNA_string_get(op->ptr, "filepath", filepath);
535 if (!BLI_is_file(filepath)) {
536 BKE_reportf(op->reports, RPT_ERROR, "File not found '%s'", filepath);
537 return OPERATOR_CANCELLED;
538 }
539
540 BKE_previewimg_id_custom_set(&brush->id, filepath);
541
542 if (!bke::asset_edit_id_save(*bmain, brush->id, *op->reports)) {
543 return OPERATOR_CANCELLED;
544 }
545
548
549 return OPERATOR_FINISHED;
550}
551
553 wmOperator *op,
554 const wmEvent *event)
555{
556 if (RNA_struct_property_is_set(op->ptr, "filepath")) {
558 }
559 return WM_operator_filesel(C, op, event);
560}
561
563{
564 ot->name = "Load Preview Image";
565 ot->description = "Choose a preview image for the brush";
566 ot->idname = "BRUSH_OT_asset_load_preview";
567
571
579}
580
582{
584 Brush *brush = (paint) ? BKE_paint_brush(paint) : nullptr;
585 if (paint == nullptr || brush == nullptr) {
586 return false;
587 }
588
589 /* Linked brush, check if belongs to an editable blend file. */
590 if (ID_IS_LINKED(brush)) {
591 if (!bke::asset_edit_id_is_writable(brush->id)) {
592 CTX_wm_operator_poll_msg_set(C, "Asset blend file is not editable");
593 return false;
594 }
595 }
596
597 return true;
598}
599
601{
603 Brush *brush = BKE_paint_brush(paint);
604 Main *bmain = CTX_data_main(C);
605 bUserAssetLibrary *library = (paint->brush_asset_reference) ?
607 &U,
608 paint->brush_asset_reference->asset_library_identifier) :
609 nullptr;
610
611 bke::asset_edit_id_delete(*bmain, brush->id, *op->reports);
612
614
615 if (library) {
617 }
618
621
622 return OPERATOR_FINISHED;
623}
624
626 wmOperator *op,
627 const wmEvent * /*event*/)
628{
630 Brush *brush = BKE_paint_brush(paint);
631
633 C,
634 op,
635 IFACE_("Delete Brush Asset"),
636 ID_IS_LINKED(brush) ?
637 IFACE_("Permanently delete brush asset blend file. This cannot be undone.") :
638 IFACE_("Permanently delete brush. This cannot be undone."),
639 IFACE_("Delete"),
641 false);
642}
643
645{
646 ot->name = "Delete Brush Asset";
647 ot->description = "Delete the active brush asset";
648 ot->idname = "BRUSH_OT_asset_delete";
649
653}
654
655static std::optional<AssetLibraryReference> get_asset_library_reference(const bContext &C,
656 const Paint &paint,
657 const Brush &brush)
658{
659 if (!ID_IS_ASSET(&brush.id)) {
661 return std::nullopt;
662 }
663 const AssetWeakReference *brush_weak_ref = paint.brush_asset_reference;
664 if (!brush_weak_ref) {
666 return std::nullopt;
667 }
669 C, *brush_weak_ref, CTX_wm_reports(&C));
670 if (!asset) {
671 /* May happen if library loading hasn't finished. */
672 return std::nullopt;
673 }
674 return asset->owner_asset_library().library_reference();
675}
676
678{
680 Brush *brush = (paint) ? BKE_paint_brush(paint) : nullptr;
681 if (paint == nullptr || brush == nullptr) {
682 return false;
683 }
684
685 const std::optional<AssetLibraryReference> library_ref = get_asset_library_reference(
686 *C, *paint, *brush);
687 if (!library_ref) {
689 return false;
690 }
691
692 if ((library_ref->type == ASSET_LIBRARY_LOCAL)) {
693 CTX_wm_operator_poll_msg_set(C, "Assets in the current file cannot be individually saved");
694 return false;
695 }
696
697 if (!bke::asset_edit_id_is_writable(brush->id)) {
698 CTX_wm_operator_poll_msg_set(C, "Asset blend file is not editable");
699 return false;
700 }
701
702 return true;
703}
704
706{
707 Main *bmain = CTX_data_main(C);
709 Brush *brush = BKE_paint_brush(paint);
710 const AssetWeakReference *asset_weak_ref = paint->brush_asset_reference;
711
713 &U, asset_weak_ref->asset_library_identifier);
714 if (!user_library) {
715 return OPERATOR_CANCELLED;
716 }
717
718 BLI_assert(ID_IS_ASSET(brush));
719
720 bke::asset_edit_id_save(*bmain, brush->id, *op->reports);
721 brush->has_unsaved_changes = false;
722
723 asset::refresh_asset_library(C, *user_library);
726
727 return OPERATOR_FINISHED;
728}
729
731{
732 ot->name = "Save Brush Asset";
733 ot->description = "Update the active brush asset in the asset library with current settings";
734 ot->idname = "BRUSH_OT_asset_save";
735
738}
739
741{
743 Brush *brush = (paint) ? BKE_paint_brush(paint) : nullptr;
744 if (paint == nullptr || brush == nullptr) {
745 return false;
746 }
747
748 const std::optional<AssetLibraryReference> library_ref = get_asset_library_reference(
749 *C, *paint, *brush);
750 if (!library_ref) {
752 return false;
753 }
754 if ((library_ref->type == ASSET_LIBRARY_LOCAL)) {
755 CTX_wm_operator_poll_msg_set(C, "Assets in the current file cannot be reverted");
756 return false;
757 }
758
759 return bke::asset_edit_id_is_editable(brush->id);
760}
761
763{
764 Main *bmain = CTX_data_main(C);
766 Brush *brush = BKE_paint_brush(paint);
767
768 if (ID *reverted_id = bke::asset_edit_id_revert(*bmain, brush->id, *op->reports)) {
769 BLI_assert(GS(reverted_id->name) == ID_BR);
770 BKE_paint_brush_set(paint, reinterpret_cast<Brush *>(reverted_id));
771 }
772 else {
773 /* bke::asset_edit_id_revert() deleted the brush for sure, even on failure. Fall back to the
774 * default. */
776 }
777
780
781 return OPERATOR_FINISHED;
782}
783
785{
786 ot->name = "Revert Brush Asset";
787 ot->description =
788 "Revert the active brush settings to the default values from the asset library";
789 ot->idname = "BRUSH_OT_asset_revert";
790
793}
794
795} // namespace blender::ed::sculpt_paint
blender::asset_system::AssetLibrary * AS_asset_library_load(const Main *bmain, const AssetLibraryReference &library_reference)
Main runtime representation of an asset.
AssetMetaData * BKE_asset_metadata_copy(const AssetMetaData *source)
Definition asset.cc:44
void BKE_asset_metadata_free(AssetMetaData **asset_data)
Definition asset.cc:38
void BKE_asset_metadata_catalog_id_set(AssetMetaData *asset_data, bUUID catalog_id, const char *catalog_simple_name)
Brush * BKE_brush_duplicate(Main *bmain, Brush *brush, eDupli_ID_Flags dupflag, uint duplicate_options)
Definition brush.cc:646
ReportList * CTX_wm_reports(const bContext *C)
void CTX_wm_operator_poll_msg_set(bContext *C, const char *msg)
Main * CTX_data_main(const bContext *C)
IDNewNameResult BKE_libblock_rename(Main &bmain, ID &id, blender::StringRefNull name, const IDNewNameMode mode=IDNewNameMode::RenameExistingNever)
Definition lib_id.cc:2350
@ LIB_ID_DUPLICATE_IS_ROOT_ID
bool BKE_paint_brush_set(Paint *paint, Brush *brush)
Definition paint.cc:701
void BKE_paint_previous_asset_reference_set(Paint *paint, AssetWeakReference &&asset_weak_reference)
Definition paint.cc:1095
void BKE_paint_previous_asset_reference_clear(Paint *paint)
Definition paint.cc:1104
Paint * BKE_paint_get_active_from_context(const bContext *C)
Definition paint.cc:467
bool BKE_paint_brush_set_default(Main *bmain, Paint *paint)
Definition paint.cc:1083
Brush * BKE_paint_brush(Paint *paint)
Definition paint.cc:636
struct bUserAssetLibrary * BKE_preferences_asset_library_find_by_name(const struct UserDef *userdef, const char *name) ATTR_NONNULL() ATTR_WARN_UNUSED_RESULT
void BKE_previewimg_id_custom_set(ID *id, const char *filepath)
void BKE_reportf(ReportList *reports, eReportType type, const char *format,...) ATTR_PRINTF_FORMAT(3
void BKE_report(ReportList *reports, eReportType type, const char *message)
Definition report.cc:126
#define BLI_assert_unreachable()
Definition BLI_assert.h:93
#define BLI_assert(a)
Definition BLI_assert.h:46
File and directory operations.
bool BLI_is_file(const char *path) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL()
Definition storage.cc:461
#define FILE_MAX
char * STRNCPY(char(&dst)[N], const char *src)
Definition BLI_string.h:688
#define IFACE_(msgid)
@ ID_BR
eAssetLibraryType
@ ASSET_LIBRARY_ESSENTIALS
@ ASSET_LIBRARY_LOCAL
@ FILE_SORT_DEFAULT
@ FILE_SPECIAL
@ FILE_TYPE_FOLDER
@ FILE_TYPE_IMAGE
@ FILE_DEFAULTDISPLAY
@ USER_DUP_LINKED_ID
@ USER_DUP_OBDATA
@ OPERATOR_CANCELLED
@ OPERATOR_FINISHED
@ PROP_STRING_SEARCH_SUGGESTION
Definition RNA_types.hh:701
@ PROP_ENUM
Definition RNA_types.hh:154
PropertyFlag
Definition RNA_types.hh:286
@ PROP_SKIP_SAVE
Definition RNA_types.hh:330
@ PROP_HIDDEN
Definition RNA_types.hh:324
@ PROP_NONE
Definition RNA_types.hh:221
#define C
Definition RandGen.cpp:29
@ ALERT_ICON_WARNING
@ WM_FILESEL_FILEPATH
Definition WM_api.hh:1075
@ FILE_OPENFILE
Definition WM_api.hh:1084
#define NA_ACTIVATED
Definition WM_types.hh:587
#define NC_BRUSH
Definition WM_types.hh:382
#define NC_SCENE
Definition WM_types.hh:375
#define NA_ADDED
Definition WM_types.hh:583
#define ND_NODES
Definition WM_types.hh:433
#define ND_TOOLSETTINGS
Definition WM_types.hh:446
#define NA_EDITED
Definition WM_types.hh:581
#define NC_ASSET
Definition WM_types.hh:401
#define NA_REMOVED
Definition WM_types.hh:584
#define NC_TEXTURE
Definition WM_types.hh:378
#define ND_ASSET_LIST
Definition WM_types.hh:545
#define U
AssetCatalog * find_catalog(CatalogID catalog_id) const
bool write_to_disk(const CatalogFilePath &blend_file_path)
AssetCatalogService & catalog_service() const
virtual std::optional< AssetLibraryReference > library_reference() const =0
#define MEM_SAFE_FREE(v)
#define ID_IS_LINKED(_id)
#define ID_IS_ASSET(_id)
#define MAX_NAME
#define GS(a)
#define G(x, y, z)
AssetLibraryReference all_library_reference()
AssetLibraryReference current_file_library_reference()
ID * asset_edit_id_from_weak_reference(Main &global_main, ID_Type id_type, const AssetWeakReference &weak_ref)
std::optional< std::string > asset_edit_id_save_as(Main &global_main, const ID &id, StringRefNull name, const bUserAssetLibrary &user_library, AssetWeakReference &r_weak_ref, ReportList &reports)
ID * asset_edit_id_revert(Main &global_main, ID &id, ReportList &reports)
bool asset_edit_id_delete(Main &global_main, ID &id, ReportList &reports)
bool asset_edit_id_is_writable(const ID &id)
bool asset_edit_id_is_editable(const ID &id)
bool asset_edit_id_save(Main &global_main, const ID &id, ReportList &reports)
void storage_fetch_blocking(const AssetLibraryReference &library_reference, const bContext &C)
void show_catalog_in_visible_shelves(const bContext &C, const StringRefNull catalog_path)
const asset_system::AssetRepresentation * find_asset_from_weak_ref(const bContext &C, const AssetWeakReference &weak_ref, ReportList *reports)
AssetLibraryReference get_asset_library_ref_from_opptr(PointerRNA &ptr)
int library_reference_to_enum_value(const AssetLibraryReference *library)
const EnumPropertyItem * library_reference_to_rna_enum_itemf(bool include_readonly, bool include_current_file)
void refresh_asset_library(const bContext *C, const AssetLibraryReference &library_ref)
void operator_asset_reference_props_register(StructRNA &srna)
void catalogs_save_from_asset_reference(asset_system::AssetLibrary &library, const AssetWeakReference &reference)
void generate_preview(const bContext *C, ID *id)
const asset_system::AssetRepresentation * operator_asset_reference_props_get_asset_from_all_library(const bContext &C, PointerRNA &ptr, ReportList *reports)
void visit_library_catalogs_catalog_for_search(const Main &bmain, const AssetLibraryReference lib, const StringRef edit_text, const FunctionRef< void(StringPropertySearchVisitParams)> visit_fn)
const bUserAssetLibrary * get_asset_library_from_opptr(PointerRNA &ptr)
void refresh_asset_library_from_asset(const bContext *C, const blender::asset_system::AssetRepresentation &asset)
AssetLibraryReference user_library_to_library_ref(const bUserAssetLibrary &user_library)
blender::asset_system::AssetCatalog & library_ensure_catalogs_in_path(blender::asset_system::AssetLibrary &library, const blender::asset_system::AssetCatalogPath &path)
void BRUSH_OT_asset_save(wmOperatorType *ot)
static bool brush_asset_edit_metadata_poll(bContext *C)
static std::optional< AssetLibraryReference > get_asset_library_reference(const bContext &C, const Paint &paint, const Brush &brush)
void BRUSH_OT_asset_delete(wmOperatorType *ot)
static wmOperatorStatus brush_asset_save_as_exec(bContext *C, wmOperator *op)
void BRUSH_OT_asset_edit_metadata(wmOperatorType *ot)
static bool brush_asset_delete_poll(bContext *C)
static void visit_library_prop_catalogs_catalog_for_search_fn(const bContext *C, PointerRNA *ptr, PropertyRNA *, const char *edit_text, FunctionRef< void(StringPropertySearchVisitParams)> visit_fn)
static wmOperatorStatus brush_asset_revert_exec(bContext *C, wmOperator *op)
static bool library_is_editable(const AssetLibraryReference &library)
static void visit_active_library_catalogs_catalog_for_search_fn(const bContext *C, PointerRNA *, PropertyRNA *, const char *edit_text, FunctionRef< void(StringPropertySearchVisitParams)> visit_fn)
static wmOperatorStatus brush_asset_load_preview_invoke(bContext *C, wmOperator *op, const wmEvent *event)
void BRUSH_OT_asset_load_preview(wmOperatorType *ot)
static wmOperatorStatus brush_asset_delete_invoke(bContext *C, wmOperator *op, const wmEvent *)
static bool brush_asset_save_as_poll(bContext *C)
static wmOperatorStatus brush_asset_delete_exec(bContext *C, wmOperator *op)
static bool brush_asset_revert_poll(bContext *C)
static wmOperatorStatus brush_asset_load_preview_exec(bContext *C, wmOperator *op)
static wmOperatorStatus brush_asset_activate_exec(bContext *C, wmOperator *op)
static wmOperatorStatus brush_asset_edit_metadata_exec(bContext *C, wmOperator *op)
static wmOperatorStatus brush_asset_edit_metadata_invoke(bContext *C, wmOperator *op, const wmEvent *)
void BRUSH_OT_asset_revert(wmOperatorType *ot)
static bool brush_asset_save_poll(bContext *C)
void BRUSH_OT_asset_save_as(wmOperatorType *ot)
static wmOperatorStatus brush_asset_save_as_invoke(bContext *C, wmOperator *op, const wmEvent *)
static const EnumPropertyItem * rna_asset_library_reference_itemf(bContext *, PointerRNA *, PropertyRNA *, bool *r_free)
void BRUSH_OT_asset_activate(wmOperatorType *ot)
static wmOperatorStatus brush_asset_save_exec(bContext *C, wmOperator *op)
void RNA_string_set(PointerRNA *ptr, const char *name, const char *value)
PropertyRNA * RNA_struct_find_property(PointerRNA *ptr, const char *identifier)
bool RNA_struct_property_is_set_ex(PointerRNA *ptr, const char *identifier, bool use_ghost)
bool RNA_property_is_set(PointerRNA *ptr, PropertyRNA *prop)
void RNA_string_get(PointerRNA *ptr, const char *name, char *value)
char * RNA_string_get_alloc(PointerRNA *ptr, const char *name, char *fixedbuf, int fixedlen, int *r_len)
std::string RNA_property_string_get(PointerRNA *ptr, PropertyRNA *prop)
bool RNA_struct_property_is_set(PointerRNA *ptr, const char *identifier)
bool RNA_boolean_get(PointerRNA *ptr, const char *name)
void RNA_enum_set(PointerRNA *ptr, const char *name, int value)
int RNA_enum_get(PointerRNA *ptr, const char *name)
PropertyRNA * RNA_def_string(StructOrFunctionRNA *cont_, const char *identifier, const char *default_value, const int maxlen, const char *ui_name, const char *ui_description)
void RNA_def_property_string_search_func_runtime(PropertyRNA *prop, StringPropertySearchFunc search_fn, const eStringPropertySearchFlag search_flag)
void RNA_def_property_ui_text(PropertyRNA *prop, const char *name, const char *description)
PropertyRNA * RNA_def_property(StructOrFunctionRNA *cont_, const char *identifier, int type, int subtype)
PropertyRNA * RNA_def_boolean(StructOrFunctionRNA *cont_, const char *identifier, const bool default_value, const char *ui_name, const char *ui_description)
void RNA_def_property_flag(PropertyRNA *prop, PropertyFlag flag)
void RNA_def_enum_funcs(PropertyRNA *prop, EnumPropertyItemFunc itemfunc)
The meta-data of an asset. By creating and giving this for a data-block (ID.asset_data),...
struct bUUID catalog_id
const char * asset_library_identifier
char has_unsaved_changes
Definition DNA_ID.h:404
struct AssetMetaData * asset_data
Definition DNA_ID.h:413
int us
Definition DNA_ID.h:425
char name[66]
Definition DNA_ID.h:415
struct ReportList * reports
struct PointerRNA * ptr
void WM_main_add_notifier(uint type, void *reference)
void WM_file_tag_modified()
Definition wm_files.cc:174
PointerRNA * ptr
Definition wm_files.cc:4227
wmOperatorType * ot
Definition wm_files.cc:4226
void WM_operator_properties_filesel(wmOperatorType *ot, const int filter, const short type, const eFileSel_Action action, const eFileSel_Flag flag, const short display, const short sort)
wmOperatorStatus WM_operator_props_dialog_popup(bContext *C, wmOperator *op, int width, std::optional< std::string > title, std::optional< std::string > confirm_text, const bool cancel_default)
wmOperatorStatus WM_operator_confirm_ex(bContext *C, wmOperator *op, const char *title, const char *message, const char *confirm_text, int icon, bool cancel_default)
wmOperatorStatus WM_operator_filesel(bContext *C, wmOperator *op, const wmEvent *)
bool WM_toolsystem_activate_brush_and_tool(bContext *C, Paint *paint, Brush *brush)