Mesh: Replace auto smooth with node group #108014

Merged
Hans Goudey merged 149 commits from HooglyBoogly/blender:refactor-mesh-corner-normals-lazy into main 2023-10-20 16:54:20 +02:00
20 changed files with 267 additions and 128 deletions
Showing only changes of commit c0a2871f72 - Show all commits

View File

@ -517,11 +517,7 @@ if(PLATFORM_BUNDLED_LIBRARIES)
# Environment variables to run precompiled executables that needed libraries.
list(JOIN PLATFORM_BUNDLED_LIBRARY_DIRS ":" _library_paths)
if(DEFINED DYLD_LIBRARY_PATH)
set(PLATFORM_ENV_BUILD "DYLD_LIBRARY_PATH=\"${_library_paths};${DYLD_LIBRARY_PATH}\"")
else()
set(PLATFORM_ENV_BUILD "DYLD_LIBRARY_PATH=\"${_library_paths}\"")
endif()
set(PLATFORM_ENV_BUILD "DYLD_LIBRARY_PATH=\"${_library_paths};$DYLD_LIBRARY_PATH\"")
set(PLATFORM_ENV_INSTALL "DYLD_LIBRARY_PATH=${CMAKE_INSTALL_PREFIX_WITH_CONFIG}/Blender.app/Contents/Resources/lib/;$DYLD_LIBRARY_PATH")
unset(_library_paths)
endif()

View File

@ -1066,11 +1066,7 @@ if(PLATFORM_BUNDLED_LIBRARIES)
# Environment variables to run precompiled executables that needed libraries.
list(JOIN PLATFORM_BUNDLED_LIBRARY_DIRS ":" _library_paths)
if(DEFINED LD_LIBRARY_PATH)
set(PLATFORM_ENV_BUILD "LD_LIBRARY_PATH=\"${_library_paths}:${LD_LIBRARY_PATH}\"")
else()
set(PLATFORM_ENV_BUILD "LD_LIBRARY_PATH=\"${_library_paths}\"")
endif()
set(PLATFORM_ENV_BUILD "LD_LIBRARY_PATH=\"${_library_paths}:$LD_LIBRARY_PATH\"")
set(PLATFORM_ENV_INSTALL "LD_LIBRARY_PATH=${CMAKE_INSTALL_PREFIX_WITH_CONFIG}/lib/;$LD_LIBRARY_PATH")
unset(_library_paths)
endif()

View File

@ -906,6 +906,7 @@ class NODE_PT_node_tree_interface(Panel):
active_item = tree.interface.active
if active_item is not None:
layout.use_property_split = True
layout.use_property_decorate = False
if active_item.item_type == 'SOCKET':
layout.prop(active_item, "socket_type", text="Type")

View File

@ -3,7 +3,7 @@ import bpy
class MyAssetShelf(bpy.types.AssetShelf):
bl_space_type = 'VIEW_3D'
bl_idname = "my_template.my_material_asset_shelf"
bl_idname = "VIEW3D_AST_my_asset_shelf"
@classmethod
def poll(cls, context):

View File

@ -16,6 +16,9 @@
*/
#ifdef __cplusplus
# include <optional>
extern "C" {
#endif
@ -211,6 +214,11 @@ struct PreviewImage *BKE_previewimg_id_ensure(struct ID *id);
*/
void BKE_previewimg_ensure(struct PreviewImage *prv, int size);
const char *BKE_previewimg_deferred_filepath_get(const struct PreviewImage *prv);
#ifdef __cplusplus
std::optional<int> BKE_previewimg_deferred_thumb_source_get(const struct PreviewImage *prv);
#endif
/**
* Create an #ImBuf holding a copy of the preview image buffer in \a prv.
* \note The returned image buffer has to be free'd (#IMB_freeImBuf()).

View File

@ -11,6 +11,7 @@
struct Main;
struct ModifierData;
struct Object;
namespace blender {
class fstream;

View File

@ -8,6 +8,7 @@
#pragma once
#include "BLI_array.hh"
#include "BLI_bitmap.h"
#include "BLI_offset_indices.hh"
#include "BLI_sys_types.h"
@ -115,66 +116,66 @@ struct SubdivCCG {
*
* TODO(sergey): Make sure the whole descriptor is valid, including all the
* displacement attached to the surface. */
Subdiv *subdiv;
Subdiv *subdiv = nullptr;
/* A level at which geometry was subdivided. This is what defines grid
* resolution. It is NOT the topology refinement level. */
int level;
int level = -1;
/* Resolution of grid. All grids have matching resolution, and resolution
* is same as ptex created for non-quad faces. */
int grid_size;
int grid_size = -1;
/* Size of a single element of a grid (including coordinate and all the other layers).
* Measured in bytes. */
int grid_element_size;
int grid_element_size = -1;
/* Grids represent limit surface, with displacement applied. Grids are
* corresponding to face-corners of coarse mesh, each grid has
* grid_size^2 elements.
*/
/* Indexed by a grid index, points to a grid data which is stored in
* grids_storage. */
CCGElem **grids;
CCGElem **grids = nullptr;
/* Flat array of all grids' data. */
unsigned char *grids_storage;
int num_grids;
unsigned char *grids_storage = nullptr;
int num_grids = -1;
/* Loose edges, each array element contains grid_size elements
* corresponding to vertices created by subdividing coarse edges. */
CCGElem **edges;
int num_edges;
CCGElem **edges = nullptr;
int num_edges = -1;
/* Loose vertices. Every element corresponds to a loose vertex from a coarse
* mesh, every coarse loose vertex corresponds to a single subdivided
* element. */
CCGElem *vertices;
int num_vertices;
CCGElem *vertices = nullptr;
int num_vertices = -1;
/* Denotes which layers present in the elements.
*
* Grids always has coordinates, followed by extra layers which are set to
* truth here.
*/
bool has_normal;
bool has_mask;
bool has_normal = false;
bool has_mask = false;
/* Offsets of corresponding data layers in the elements. */
int normal_offset;
int mask_offset;
int normal_offset = -1;
int mask_offset = -1;
/* Faces from which grids are emitted. */
int num_faces;
SubdivCCGFace *faces;
int num_faces = -1;
SubdivCCGFace *faces = nullptr;
/* Indexed by grid index, points to corresponding face from `faces`. */
SubdivCCGFace **grid_faces;
SubdivCCGFace **grid_faces = nullptr;
/* Edges which are adjacent to faces.
* Used for faster grid stitching, in the cost of extra memory.
*/
int num_adjacent_edges;
SubdivCCGAdjacentEdge *adjacent_edges;
int num_adjacent_edges = -1;
SubdivCCGAdjacentEdge *adjacent_edges = nullptr;
/* Vertices which are adjacent to faces
* Used for faster grid stitching, in the cost of extra memory.
*/
int num_adjacent_vertices;
SubdivCCGAdjacentVertex *adjacent_vertices;
int num_adjacent_vertices = -1;
SubdivCCGAdjacentVertex *adjacent_vertices = nullptr;
DMFlagMat *grid_flag_mats;
BLI_bitmap **grid_hidden;
DMFlagMat *grid_flag_mats = nullptr;
BLI_bitmap **grid_hidden = nullptr;
/* TODO(sergey): Consider adding some accessors to a "decoded" geometry,
* to make integration with draw manager and such easy.
@ -189,15 +190,15 @@ struct SubdivCCG {
* such use-related flags in a more or less generic structure. */
struct {
/* Corresponds to MULTIRES_COORDS_MODIFIED. */
bool coords;
bool coords = false;
/* Corresponds to MULTIRES_HIDDEN_MODIFIED. */
bool hidden;
bool hidden = false;
} dirty;
/* Cached values, are not supposed to be accessed directly. */
struct {
/* Indexed by face, indicates index of the first grid which corresponds to the face. */
int *start_face_grid_index;
int *start_face_grid_index = nullptr;
} cache_;
};

View File

@ -15,6 +15,7 @@
#include "MEM_guardedalloc.h"
#include "DNA_ID.h"
#include "DNA_brush_types.h"
#include "DNA_collection_types.h"
#include "DNA_gpencil_legacy_types.h"
@ -85,6 +86,24 @@ struct DeferredIconDeleteNode {
/* Protected by gIconMutex. */
static LockfreeLinkList g_icon_delete_queue;
class PreviewImageDeferred : public PreviewImage {
public:
const std::string filepath;
const ThumbSource source;
/* Behavior is undefined if \a prv is not a deferred preview (#PRV_TAG_DEFFERED not set). */
static PreviewImageDeferred &from_base(PreviewImage &prv);
static const PreviewImageDeferred &from_base(const PreviewImage &prv);
PreviewImageDeferred(blender::StringRef filepath, ThumbSource source);
PreviewImageDeferred(const PreviewImageDeferred &) = delete;
/* Delete through #BKE_previewimg_free()! */
~PreviewImageDeferred() = delete;
/* Keep this type non-copyable since ownership of #PreviewImage can be ambiguous (#PreviewImage
* allows shallow copies). */
PreviewImageDeferred &operator=(const PreviewImageDeferred &) = delete;
};
static void icon_free(void *val)
{
Icon *icon = (Icon *)val;
@ -230,40 +249,40 @@ void BKE_icons_deferred_free()
BLI_linklist_lockfree_clear(&g_icon_delete_queue, MEM_freeN);
}
static PreviewImage *previewimg_create_ex(size_t deferred_data_size)
PreviewImage::PreviewImage()
{
PreviewImage *prv_img = (PreviewImage *)MEM_mallocN(sizeof(PreviewImage) + deferred_data_size,
"img_prv");
memset(prv_img, 0, sizeof(*prv_img)); /* leave deferred data dirty */
if (deferred_data_size) {
prv_img->tag |= PRV_TAG_DEFFERED;
}
/* Zero initialize */
memset(this, 0, sizeof(*this));
for (int i = 0; i < NUM_ICON_SIZES; i++) {
prv_img->flag[i] |= PRV_CHANGED;
prv_img->changed_timestamp[i] = 0;
flag[i] |= PRV_CHANGED;
changed_timestamp[i] = 0;
}
return prv_img;
}
static PreviewImage *previewimg_deferred_create(const char *filepath, int source)
PreviewImageDeferred &PreviewImageDeferred::from_base(PreviewImage &prv)
{
/* We pack needed data for lazy loading (source type, in a single char, and filepath). */
const size_t deferred_data_size = strlen(filepath) + 2;
char *deferred_data;
return static_cast<PreviewImageDeferred &>(prv);
}
const PreviewImageDeferred &PreviewImageDeferred::from_base(const PreviewImage &prv)
{
return static_cast<const PreviewImageDeferred &>(prv);
}
PreviewImage *prv = previewimg_create_ex(deferred_data_size);
deferred_data = (char *)PRV_DEFERRED_DATA(prv);
deferred_data[0] = source;
memcpy(&deferred_data[1], filepath, deferred_data_size - 1);
PreviewImageDeferred::PreviewImageDeferred(blender::StringRef filepath, ThumbSource source)
: PreviewImage(), filepath(filepath), source(source)
{
tag |= PRV_TAG_DEFFERED;
}
return prv;
static PreviewImageDeferred *previewimg_deferred_create(const char *filepath, ThumbSource source)
{
return MEM_new<PreviewImageDeferred>(__func__, filepath, source);
}
PreviewImage *BKE_previewimg_create()
{
return previewimg_create_ex(0);
return MEM_new<PreviewImage>(__func__);
}
void BKE_previewimg_freefunc(void *link)
@ -272,27 +291,40 @@ void BKE_previewimg_freefunc(void *link)
if (!prv) {
return;
}
for (int i = 0; i < NUM_ICON_SIZES; i++) {
if (prv->rect[i]) {
MEM_freeN(prv->rect[i]);
}
if (prv->gputexture[i]) {
GPU_texture_free(prv->gputexture[i]);
}
}
MEM_freeN(prv);
BKE_previewimg_freefunc(&prv);
}
void BKE_previewimg_free(PreviewImage **prv)
{
if (prv && (*prv)) {
BKE_previewimg_freefunc(*prv);
for (int i = 0; i < NUM_ICON_SIZES; i++) {
if ((*prv)->rect[i]) {
MEM_freeN((*prv)->rect[i]);
}
if ((*prv)->gputexture[i]) {
GPU_texture_free((*prv)->gputexture[i]);
}
}
if ((*prv)->tag & PRV_TAG_DEFFERED) {
PreviewImageDeferred &this_deferred = PreviewImageDeferred::from_base(**prv);
std::destroy_at(&this_deferred.filepath);
}
else {
MEM_delete(*prv);
}
*prv = nullptr;
}
}
/** Handy override for the deferred type (derives from #PreviewImage). */
static void BKE_previewimg_free(PreviewImageDeferred **prv)
{
PreviewImage *prv_base = *prv;
BKE_previewimg_free(&prv_base);
*prv = nullptr;
}
void BKE_previewimg_clear_single(PreviewImage *prv, enum eIconSizes size)
{
MEM_SAFE_FREE(prv->rect[size]);
@ -442,7 +474,7 @@ void BKE_previewimg_deferred_release(PreviewImage *prv)
if (prv->icon_id) {
BKE_icon_delete(prv->icon_id);
}
BKE_previewimg_freefunc(prv);
BKE_previewimg_free(&prv);
}
PreviewImage *BKE_previewimg_cached_get(const char *name)
@ -475,19 +507,19 @@ PreviewImage *BKE_previewimg_cached_thumbnail_read(const char *name,
{
BLI_assert(BLI_thread_is_main());
PreviewImage *prv = nullptr;
PreviewImageDeferred *prv = nullptr;
void **prv_p;
prv_p = BLI_ghash_lookup_p(gCachedPreviews, name);
if (prv_p) {
prv = *(PreviewImage **)prv_p;
prv = static_cast<PreviewImageDeferred *>(*prv_p);
BLI_assert(prv);
BLI_assert(prv->tag & PRV_TAG_DEFFERED);
}
if (prv && force_update) {
const char *prv_deferred_data = (char *)PRV_DEFERRED_DATA(prv);
if ((int(prv_deferred_data[0]) == source) && STREQ(&prv_deferred_data[1], filepath)) {
if ((prv->source == source) && (prv->filepath == filepath)) {
/* If same filepath, no need to re-allocate preview, just clear it up. */
BKE_previewimg_clear(prv);
}
@ -497,7 +529,7 @@ PreviewImage *BKE_previewimg_cached_thumbnail_read(const char *name,
}
if (!prv) {
prv = previewimg_deferred_create(filepath, source);
prv = previewimg_deferred_create(filepath, ThumbSource(source));
force_update = true;
}
@ -536,13 +568,10 @@ void BKE_previewimg_ensure(PreviewImage *prv, const int size)
return;
}
ImBuf *thumb;
char *prv_deferred_data = (char *)PRV_DEFERRED_DATA(prv);
int source = prv_deferred_data[0];
char *filepath = &prv_deferred_data[1];
PreviewImageDeferred &prv_deferred = PreviewImageDeferred::from_base(*prv);
int icon_w, icon_h;
thumb = IMB_thumb_manage(filepath, THB_LARGE, (ThumbSource)source);
ImBuf *thumb = IMB_thumb_manage(prv_deferred.filepath.c_str(), THB_LARGE, prv_deferred.source);
if (!thumb) {
return;
}
@ -578,6 +607,26 @@ void BKE_previewimg_ensure(PreviewImage *prv, const int size)
IMB_freeImBuf(thumb);
}
const char *BKE_previewimg_deferred_filepath_get(const PreviewImage *prv)
{
if ((prv->tag & PRV_TAG_DEFFERED) == 0) {
return nullptr;
}
const PreviewImageDeferred &prv_deferred = PreviewImageDeferred::from_base(*prv);
return prv_deferred.filepath.c_str();
}
std::optional<int> BKE_previewimg_deferred_thumb_source_get(const PreviewImage *prv)
{
if ((prv->tag & PRV_TAG_DEFFERED) == 0) {
return std::nullopt;
}
const PreviewImageDeferred &prv_deferred = PreviewImageDeferred::from_base(*prv);
return prv_deferred.source;
}
ImBuf *BKE_previewimg_to_imbuf(PreviewImage *prv, const int size)
{
const uint w = prv->w[size];

View File

@ -68,13 +68,23 @@ static Vector<std::unique_ptr<bNodeTreeZone>> find_zone_nodes(
struct ZoneRelation {
bNodeTreeZone *parent;
bNodeTreeZone *child;
uint64_t hash() const
{
return get_default_hash_2(this->parent, this->child);
}
friend bool operator==(const ZoneRelation &a, const ZoneRelation &b)
{
return a.parent == b.parent && a.child == b.child;
}
};
static Vector<ZoneRelation> get_direct_zone_relations(
static std::optional<Vector<ZoneRelation>> get_direct_zone_relations(
const Span<std::unique_ptr<bNodeTreeZone>> all_zones,
const BitGroupVector<> &depend_on_input_flag_array)
{
Vector<ZoneRelation> zone_relations;
VectorSet<ZoneRelation> all_zone_relations;
/* Gather all relations, even the transitive once. */
for (const std::unique_ptr<bNodeTreeZone> &zone : all_zones) {
@ -86,35 +96,42 @@ static Vector<ZoneRelation> get_direct_zone_relations(
const BoundedBitSpan depend_on_input_flags = depend_on_input_flag_array[node->index()];
bits::foreach_1_index(depend_on_input_flags, [&](const int parent_zone_i) {
if (parent_zone_i != zone_i) {
zone_relations.append({all_zones[parent_zone_i].get(), zone.get()});
all_zone_relations.add_new({all_zones[parent_zone_i].get(), zone.get()});
}
});
}
}
for (const ZoneRelation &relation : all_zone_relations) {
const ZoneRelation reverse_relation{relation.child, relation.parent};
if (all_zone_relations.contains(reverse_relation)) {
/* There is a cyclic zone dependency. */
return std::nullopt;
}
}
/* Remove transitive relations. This is a brute force algorithm currently. */
Vector<int> transitive_relations;
for (const int a : zone_relations.index_range()) {
const ZoneRelation &relation_a = zone_relations[a];
for (const int b : zone_relations.index_range()) {
for (const int a : all_zone_relations.index_range()) {
const ZoneRelation &relation_a = all_zone_relations[a];
for (const int b : all_zone_relations.index_range()) {
if (a == b) {
continue;
}
const ZoneRelation &relation_b = zone_relations[b];
for (const int c : zone_relations.index_range()) {
if (a == c || b == c) {
continue;
}
const ZoneRelation &relation_c = zone_relations[c];
if (relation_a.child == relation_b.parent && relation_a.parent == relation_c.parent &&
relation_b.child == relation_c.child)
{
transitive_relations.append_non_duplicates(c);
}
const ZoneRelation &relation_b = all_zone_relations[b];
if (relation_a.child != relation_b.parent) {
continue;
}
const ZoneRelation transitive_relation{relation_a.parent, relation_b.child};
const int transitive_relation_i = all_zone_relations.index_of_try(transitive_relation);
if (transitive_relation_i != -1) {
transitive_relations.append_non_duplicates(transitive_relation_i);
}
}
}
std::sort(transitive_relations.begin(), transitive_relations.end(), std::greater<>());
Vector<ZoneRelation> zone_relations = all_zone_relations.as_span();
for (const int i : transitive_relations) {
zone_relations.remove_and_reorder(i);
}
@ -266,11 +283,15 @@ static std::unique_ptr<bNodeTreeZones> discover_tree_zones(const bNodeTree &tree
}
}
const Vector<ZoneRelation> zone_relations = get_direct_zone_relations(
const std::optional<Vector<ZoneRelation>> zone_relations = get_direct_zone_relations(
tree_zones->zones, depend_on_input_flag_array);
if (!zone_relations) {
/* Found cyclic relations. */
return {};
}
/* Set parent and child pointers in zones. */
for (const ZoneRelation &relation : zone_relations) {
for (const ZoneRelation &relation : *zone_relations) {
relation.parent->child_zones.append(relation.child);
BLI_assert(relation.child->parent_zone == nullptr);
relation.child->parent_zone = relation.parent;

View File

@ -529,7 +529,7 @@ SubdivCCG *BKE_subdiv_to_ccg(Subdiv *subdiv,
SubdivCCGMaterialFlagsEvaluator *material_flags_evaluator)
{
BKE_subdiv_stats_begin(&subdiv->stats, SUBDIV_STATS_SUBDIV_TO_CCG);
SubdivCCG *subdiv_ccg = MEM_cnew<SubdivCCG>(__func__);
SubdivCCG *subdiv_ccg = MEM_new<SubdivCCG>(__func__);
subdiv_ccg->subdiv = subdiv;
subdiv_ccg->level = bitscan_forward_i(settings->resolution - 1);
subdiv_ccg->grid_size = BKE_subdiv_grid_size_from_level(subdiv_ccg->level);
@ -613,7 +613,7 @@ void BKE_subdiv_ccg_destroy(SubdivCCG *subdiv_ccg)
}
MEM_SAFE_FREE(subdiv_ccg->adjacent_vertices);
MEM_SAFE_FREE(subdiv_ccg->cache_.start_face_grid_index);
MEM_freeN(subdiv_ccg);
MEM_delete(subdiv_ccg);
}
void BKE_subdiv_ccg_key(CCGKey *key, const SubdivCCG *subdiv_ccg, int level)

View File

@ -1412,7 +1412,7 @@ static void write_file_main_validate_pre(Main *bmain, ReportList *reports)
return;
}
BKE_report(reports, RPT_INFO, "Checking sanity of current .blend file *BEFORE* save to disk");
BKE_report(reports, RPT_DEBUG, "Checking validity of current .blend file *BEFORE* save to disk");
BLO_main_validate_shapekeys(bmain, reports);
if (!BKE_main_namemap_validate_and_fix(bmain)) {
@ -1434,7 +1434,8 @@ static void write_file_main_validate_post(Main *bmain, ReportList *reports)
}
if (G.debug & G_DEBUG_IO) {
BKE_report(reports, RPT_INFO, "Checking sanity of current .blend file *AFTER* save to disk");
BKE_report(
reports, RPT_DEBUG, "Checking validity of current .blend file *BEFORE* save to disk");
BLO_main_validate_libraries(bmain, reports);
}
}

View File

@ -15,10 +15,12 @@ extern "C" {
struct ARegion;
struct ARegionType;
struct AssetShelfSettings;
struct AssetShelfType;
struct bContext;
struct bContextDataResult;
struct BlendDataReader;
struct BlendWriter;
struct Main;
struct wmWindowManager;
struct RegionPollParams;
@ -59,6 +61,8 @@ void ED_asset_shelf_header_regiontype_register(struct ARegionType *region_type,
/* -------------------------------------------------------------------- */
void ED_asset_shelf_type_unlink(const struct Main &bmain, const struct AssetShelfType &shelf_type);
int ED_asset_shelf_tile_width(const struct AssetShelfSettings &settings);
int ED_asset_shelf_tile_height(const struct AssetShelfSettings &settings);

View File

@ -15,6 +15,7 @@
#include "BLI_string.h"
#include "BKE_context.h"
#include "BKE_main.h"
#include "BKE_screen.h"
#include "BLT_translation.h"
@ -54,11 +55,18 @@ void send_redraw_notifier(const bContext &C)
/** \name Shelf Type
* \{ */
static bool asset_shelf_type_poll(const bContext &C, AssetShelfType *shelf_type)
static bool asset_shelf_type_poll(const bContext &C,
const SpaceType &space_type,
AssetShelfType *shelf_type)
{
if (!shelf_type) {
return false;
}
BLI_assert_msg(BLI_findindex(&space_type.asset_shelf_types, shelf_type) != -1,
"Asset shelf type is not registered");
UNUSED_VARS_NDEBUG(space_type);
return !shelf_type->poll || shelf_type->poll(&C, shelf_type);
}
@ -134,8 +142,8 @@ static AssetShelf *update_active_shelf(const bContext &C,
/* Case 1: */
if (shelf_regiondata.active_shelf &&
asset_shelf_type_poll(C,
asset_shelf_type_ensure(space_type, *shelf_regiondata.active_shelf)))
asset_shelf_type_poll(
C, space_type, asset_shelf_type_ensure(space_type, *shelf_regiondata.active_shelf)))
{
/* Not a strong precondition, but if this is wrong something weird might be going on. */
BLI_assert(shelf_regiondata.active_shelf == shelf_regiondata.shelves.first);
@ -149,7 +157,7 @@ static AssetShelf *update_active_shelf(const bContext &C,
continue;
}
if (asset_shelf_type_poll(C, asset_shelf_type_ensure(space_type, *shelf))) {
if (asset_shelf_type_poll(C, space_type, asset_shelf_type_ensure(space_type, *shelf))) {
/* Found a valid previously activated shelf, reactivate it. */
activate_shelf(shelf_regiondata, *shelf);
return shelf;
@ -158,7 +166,7 @@ static AssetShelf *update_active_shelf(const bContext &C,
/* Case 3: */
LISTBASE_FOREACH (AssetShelfType *, shelf_type, &space_type.asset_shelf_types) {
if (asset_shelf_type_poll(C, shelf_type)) {
if (asset_shelf_type_poll(C, space_type, shelf_type)) {
AssetShelf *new_shelf = create_shelf_from_type(*shelf_type);
BLI_addhead(&shelf_regiondata.shelves, new_shelf);
/* Moves ownership to the regiondata. */
@ -206,7 +214,7 @@ static bool asset_shelf_space_poll(const bContext *C, const SpaceLink *space_lin
/* Is there any asset shelf type registered that returns true for it's poll? */
LISTBASE_FOREACH (AssetShelfType *, shelf_type, &space_type->asset_shelf_types) {
if (asset_shelf_type_poll(*C, shelf_type)) {
if (asset_shelf_type_poll(*C, *space_type, shelf_type)) {
return true;
}
}
@ -701,3 +709,39 @@ void ED_asset_shelf_header_regiontype_register(ARegionType *region_type, const i
}
/** \} */
/* -------------------------------------------------------------------- */
/** \name Asset Shelf Type (un)registration
* \{ */
void ED_asset_shelf_type_unlink(const Main &bmain, const AssetShelfType &shelf_type)
{
LISTBASE_FOREACH (bScreen *, screen, &bmain.screens) {
LISTBASE_FOREACH (ScrArea *, area, &screen->areabase) {
LISTBASE_FOREACH (SpaceLink *, sl, &area->spacedata) {
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_regiondata = RegionAssetShelf::get_from_asset_shelf_region(
*region);
if (!shelf_regiondata) {
continue;
}
LISTBASE_FOREACH (AssetShelf *, shelf, &shelf_regiondata->shelves) {
if (shelf->type == &shelf_type) {
shelf->type = nullptr;
}
}
BLI_assert((shelf_regiondata->active_shelf == nullptr) ||
(shelf_regiondata->active_shelf->type != &shelf_type));
}
}
}
}
}
/** \} */

View File

@ -4900,9 +4900,9 @@ static int ui_do_but_EXIT(bContext *C, uiBut *but, uiHandleButtonData *data, con
if (ELEM(event->type, LEFTMOUSE, EVT_PADENTER, EVT_RETKEY) && event->val == KM_PRESS) {
int ret = WM_UI_HANDLER_BREAK;
/* XXX: (a bit ugly) Special case handling for file-browser drag button. */
if (ui_but_drag_is_draggable(but) && but->imb &&
ui_but_contains_point_px_icon(but, data->region, event))
/* XXX: (a bit ugly) Special case handling for file-browser drag buttons (icon and filename
* label). */
if (ui_but_drag_is_draggable(but) && ui_but_contains_point_px_icon(but, data->region, event))
{
ret = WM_UI_HANDLER_CONTINUE;
}

View File

@ -1809,14 +1809,17 @@ void PreviewLoadJob::run_fn(void *customdata, bool *stop, bool *do_update, float
PreviewImage *preview = request->preview;
const char *deferred_data = static_cast<char *>(PRV_DEFERRED_DATA(preview));
const ThumbSource source = static_cast<ThumbSource>(deferred_data[0]);
const char *filepath = &deferred_data[1];
const std::optional<int> source = BKE_previewimg_deferred_thumb_source_get(preview);
const char *filepath = BKE_previewimg_deferred_filepath_get(preview);
if (!source || !filepath) {
continue;
}
// printf("loading deferred %d×%d preview for %s\n", request->sizex, request->sizey, filepath);
IMB_thumb_path_lock(filepath);
ImBuf *thumb = IMB_thumb_manage(filepath, THB_LARGE, source);
ImBuf *thumb = IMB_thumb_manage(filepath, THB_LARGE, ThumbSource(*source));
IMB_thumb_path_unlock(filepath);
if (thumb) {

View File

@ -172,7 +172,8 @@ static void ed_undo_step_pre(bContext *C,
if (G.debug & G_DEBUG_IO) {
if (bmain->lock != nullptr) {
BKE_report(reports, RPT_INFO, "Checking sanity of current .blend file *BEFORE* undo step");
BKE_report(
reports, RPT_DEBUG, "Checking validity of current .blend file *BEFORE* undo step");
BLO_main_validate_libraries(bmain, reports);
}
}
@ -237,7 +238,7 @@ static void ed_undo_step_post(bContext *C,
if (G.debug & G_DEBUG_IO) {
if (bmain->lock != nullptr) {
BKE_report(reports, RPT_INFO, "Checking sanity of current .blend file *AFTER* undo step");
BKE_report(reports, RPT_INFO, "Checking validity of current .blend file *AFTER* undo step");
BLO_main_validate_libraries(bmain, reports);
}
}

View File

@ -604,6 +604,10 @@ enum {
PRV_TAG_DEFFERED_DELETE = (1 << 2),
};
/**
* This type allows shallow copies. Use #BKE_previewimg_free() to release contained resources.
* Don't call this for shallow copies (or the original instance will have dangling pointers).
*/
typedef struct PreviewImage {
/* All values of 2 are really NUM_ICON_SIZES */
unsigned int w[2];
@ -620,12 +624,17 @@ typedef struct PreviewImage {
/** Runtime data. */
short tag;
char _pad[2];
} PreviewImage;
#define PRV_DEFERRED_DATA(prv) \
(CHECK_TYPE_INLINE(prv, PreviewImage *), \
BLI_assert((prv)->tag & PRV_TAG_DEFFERED), \
(void *)((prv) + 1))
#ifdef __cplusplus
PreviewImage();
/* Shallow copy! Contained data is not copied. */
PreviewImage(const PreviewImage &) = default;
/* Don't free contained data to allow shallow copies. */
~PreviewImage() = default;
/* Shallow copy! Contained data is not copied. */
PreviewImage &operator=(const PreviewImage &) = default;
#endif
} PreviewImage;
#define ID_FAKE_USERS(id) ((((const ID *)id)->flag & LIB_FAKEUSER) ? 1 : 0)
#define ID_REAL_USERS(id) (((const ID *)id)->us - ID_FAKE_USERS(id))

View File

@ -252,6 +252,7 @@ set(INC
../../sequencer
../../simulation
../../windowmanager
../../editors/asset
../../editors/include
../../render
../../../../intern/clog

View File

@ -65,6 +65,8 @@ const EnumPropertyItem rna_enum_uilist_layout_type_items[] = {
# include "BKE_report.h"
# include "BKE_screen.h"
# include "ED_asset_shelf.h"
# include "WM_api.hh"
static ARegionType *region_type_find(ReportList *reports, int space_type, int region_type)
@ -1149,7 +1151,7 @@ static void asset_shelf_draw_context_menu(const bContext *C,
RNA_parameter_list_free(&list);
}
static bool rna_AssetShelf_unregister(Main * /*bmain*/, StructRNA *type)
static bool rna_AssetShelf_unregister(Main *bmain, StructRNA *type)
{
AssetShelfType *shelf_type = static_cast<AssetShelfType *>(RNA_struct_blender_type_get(type));
@ -1162,6 +1164,8 @@ static bool rna_AssetShelf_unregister(Main * /*bmain*/, StructRNA *type)
return false;
}
ED_asset_shelf_type_unlink(*bmain, *shelf_type);
RNA_struct_free_extension(type, &shelf_type->rna_ext);
RNA_struct_free(&BLENDER_RNA, type);

View File

@ -160,7 +160,6 @@ struct Render : public BaseRender {
bool prepare_viewlayer(struct ViewLayer *view_layer, struct Depsgraph *depsgraph) override;
char name[RE_MAXNAME] = "";
int slot = 0;
/* state settings */
short flag = 0;
@ -183,7 +182,7 @@ struct Render : public BaseRender {
/* final picture width and height (within disprect) */
int rectx = 0, recty = 0;
/* Camera transform, only used by Freestyle. */
/* Camera transform. Used by Freestyle, Eevee, and other draw manager engines.. */
float winmat[4][4] = {{0}};
/* Clipping. */