Files
test/source/blender/blenkernel/intern/node_enum_definition.cc
Brecht Van Lommel 7a395e2e7f Revert changes from main commits that were merged into blender-v4.1-release
The last good commit was f57e4c5b98.

After this one more fix was committed, this one is preserved as well:
67bd678887.
2024-03-18 15:04:12 +01:00

148 lines
4.1 KiB
C++

/* SPDX-FileCopyrightText: 2023 Blender Authors
*
* SPDX-License-Identifier: GPL-2.0-or-later */
#include "BLI_string.h"
#include "BLI_string_utils.hh"
#include "DNA_array_utils.hh"
#include "DNA_node_types.h"
#include "BKE_node_enum.hh"
using blender::bke::NodeSocketValueMenuRuntimeFlag;
bool bNodeSocketValueMenu::has_conflict() const
{
return this->runtime_flag & NodeSocketValueMenuRuntimeFlag::NODE_MENU_ITEMS_CONFLICT;
}
blender::Span<NodeEnumItem> NodeEnumDefinition::items() const
{
return {this->items_array, this->items_num};
}
blender::MutableSpan<NodeEnumItem> NodeEnumDefinition::items_for_write()
{
return {this->items_array, this->items_num};
}
NodeEnumItem *NodeEnumDefinition::add_item(const blender::StringRef name)
{
const int insert_index = this->items_num;
NodeEnumItem *old_items = this->items_array;
this->items_array = MEM_cnew_array<NodeEnumItem>(this->items_num + 1, __func__);
std::copy_n(old_items, insert_index, this->items_array);
NodeEnumItem &new_item = this->items_array[insert_index];
std::copy_n(old_items + insert_index + 1,
this->items_num - insert_index,
this->items_array + insert_index + 1);
new_item.identifier = this->next_identifier++;
this->set_item_name(new_item, name);
this->items_num++;
MEM_SAFE_FREE(old_items);
return &new_item;
}
static void free_enum_item(NodeEnumItem *item)
{
MEM_SAFE_FREE(item->name);
MEM_SAFE_FREE(item->description);
}
bool NodeEnumDefinition::remove_item(NodeEnumItem &item)
{
if (!this->items().contains_ptr(&item)) {
return false;
}
const int remove_index = &item - this->items().begin();
/* DNA fields are 16 bits, can't use directly. */
int items_num = this->items_num;
int active_index = this->active_index;
blender::dna::array::remove_index(
&this->items_array, &items_num, &active_index, remove_index, free_enum_item);
this->items_num = int16_t(items_num);
this->active_index = int16_t(active_index);
return true;
}
void NodeEnumDefinition::clear()
{
/* DNA fields are 16 bits, can't use directly. */
int items_num = this->items_num;
int active_index = this->active_index;
blender::dna::array::clear(&this->items_array, &items_num, &active_index, free_enum_item);
this->items_num = int16_t(items_num);
this->active_index = int16_t(active_index);
}
bool NodeEnumDefinition::move_item(const int from_index, const int to_index)
{
if (to_index < this->items_num) {
const int items_num = this->items_num;
const int active_index = this->active_index;
blender::dna::array::move_index(this->items_array, items_num, from_index, to_index);
this->items_num = int16_t(items_num);
this->active_index = int16_t(active_index);
}
return true;
}
const NodeEnumItem *NodeEnumDefinition::active_item() const
{
if (blender::IndexRange(this->items_num).contains(this->active_index)) {
return &this->items()[this->active_index];
}
return nullptr;
}
NodeEnumItem *NodeEnumDefinition::active_item()
{
if (blender::IndexRange(this->items_num).contains(this->active_index)) {
return &this->items_for_write()[this->active_index];
}
return nullptr;
}
void NodeEnumDefinition::active_item_set(NodeEnumItem *item)
{
this->active_index = this->items().contains_ptr(item) ? item - this->items_array : -1;
}
void NodeEnumDefinition::set_item_name(NodeEnumItem &item, const blender::StringRef name)
{
char unique_name[MAX_NAME + 4];
STRNCPY(unique_name, name.data());
struct Args {
NodeEnumDefinition *enum_def;
const NodeEnumItem *item;
} args = {this, &item};
const char *default_name = items().is_empty() ? "Name" : items().last().name;
BLI_uniquename_cb(
[](void *arg, const char *name) {
const Args &args = *static_cast<Args *>(arg);
for (const NodeEnumItem &item : args.enum_def->items()) {
if (&item != args.item) {
if (STREQ(item.name, name)) {
return true;
}
}
}
return false;
},
&args,
default_name,
'.',
unique_name,
ARRAY_SIZE(unique_name));
MEM_SAFE_FREE(item.name);
item.name = BLI_strdup(unique_name);
}