Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'source/blender/nodes/intern')
-rw-r--r--source/blender/nodes/intern/derived_node_tree.cc2
-rw-r--r--source/blender/nodes/intern/geometry_nodes_lazy_function.cc279
-rw-r--r--source/blender/nodes/intern/geometry_nodes_log.cc77
-rw-r--r--source/blender/nodes/intern/node_common.cc169
-rw-r--r--source/blender/nodes/intern/node_declaration.cc27
-rw-r--r--source/blender/nodes/intern/node_exec.cc2
-rw-r--r--source/blender/nodes/intern/node_exec.h4
-rw-r--r--source/blender/nodes/intern/node_geometry_exec.cc12
-rw-r--r--source/blender/nodes/intern/node_socket.cc26
-rw-r--r--source/blender/nodes/intern/node_socket_declarations.cc2
-rw-r--r--source/blender/nodes/intern/node_util.cc (renamed from source/blender/nodes/intern/node_util.c)16
-rw-r--r--source/blender/nodes/intern/socket_search_link.cc63
12 files changed, 363 insertions, 316 deletions
diff --git a/source/blender/nodes/intern/derived_node_tree.cc b/source/blender/nodes/intern/derived_node_tree.cc
index e8e0f0fa61c..2ea80008af8 100644
--- a/source/blender/nodes/intern/derived_node_tree.cc
+++ b/source/blender/nodes/intern/derived_node_tree.cc
@@ -58,7 +58,7 @@ void DerivedNodeTree::destruct_context_recursively(DTreeContext *context)
bool DerivedNodeTree::has_link_cycles() const
{
for (const bNodeTree *btree : used_btrees_) {
- if (btree->has_link_cycle()) {
+ if (btree->has_available_link_cycle()) {
return true;
}
}
diff --git a/source/blender/nodes/intern/geometry_nodes_lazy_function.cc b/source/blender/nodes/intern/geometry_nodes_lazy_function.cc
index e4d476e6374..197f0997160 100644
--- a/source/blender/nodes/intern/geometry_nodes_lazy_function.cc
+++ b/source/blender/nodes/intern/geometry_nodes_lazy_function.cc
@@ -16,6 +16,7 @@
#include "NOD_multi_function.hh"
#include "NOD_node_declaration.hh"
+#include "BLI_lazy_threading.hh"
#include "BLI_map.hh"
#include "DNA_ID.h"
@@ -27,6 +28,8 @@
#include "FN_field_cpp_type.hh"
#include "FN_lazy_function_graph_executor.hh"
+#include "DEG_depsgraph_query.h"
+
namespace blender::nodes {
using fn::ValueOrField;
@@ -134,13 +137,14 @@ class LazyFunctionForGeometryNode : public LazyFunction {
if (geo_eval_log::GeoModifierLog *modifier_log = user_data->modifier_data->eval_log) {
geo_eval_log::GeoTreeLogger &tree_logger = modifier_log->get_local_tree_logger(
*user_data->compute_context);
- tree_logger.node_execution_times.append({node_.name, start_time, end_time});
+ tree_logger.node_execution_times.append(
+ {tree_logger.allocator->copy_string(node_.name), start_time, end_time});
}
}
};
/**
- * Used to gather all inputs of a multi-input socket. A separate node is necessary, because
+ * Used to gather all inputs of a multi-input socket. A separate node is necessary because
* multi-inputs are not supported in lazy-function graphs.
*/
class LazyFunctionForMultiInput : public LazyFunction {
@@ -154,8 +158,9 @@ class LazyFunctionForMultiInput : public LazyFunction {
base_type_ = get_socket_cpp_type(socket);
BLI_assert(base_type_ != nullptr);
BLI_assert(socket.is_multi_input());
+ const bNodeTree &btree = socket.owner_tree();
for (const bNodeLink *link : socket.directly_linked_links()) {
- if (!link->is_muted()) {
+ if (!(link->is_muted() || nodeIsDanglingReroute(&btree, link->fromnode))) {
inputs_.append({"Input", *base_type_});
}
}
@@ -164,14 +169,14 @@ class LazyFunctionForMultiInput : public LazyFunction {
outputs_.append({"Output", *vector_type});
}
- void execute_impl(lf::Params &params, const lf::Context &UNUSED(context)) const override
+ void execute_impl(lf::Params &params, const lf::Context & /*context*/) const override
{
/* Currently we only have multi-inputs for geometry and string sockets. This could be
* generalized in the future. */
base_type_->to_static_type_tag<GeometrySet, ValueOrField<std::string>>([&](auto type_tag) {
using T = typename decltype(type_tag)::type;
if constexpr (std::is_void_v<T>) {
- /* This type is not support in this node for now. */
+ /* This type is not supported in this node for now. */
BLI_assert_unreachable();
}
else {
@@ -198,7 +203,7 @@ class LazyFunctionForRerouteNode : public LazyFunction {
outputs_.append({"Output", type});
}
- void execute_impl(lf::Params &params, const lf::Context &UNUSED(context)) const override
+ void execute_impl(lf::Params &params, const lf::Context & /*context*/) const override
{
void *input_value = params.try_get_input_data_ptr(0);
void *output_value = params.get_output_data_ptr(0);
@@ -211,6 +216,28 @@ class LazyFunctionForRerouteNode : public LazyFunction {
};
/**
+ * Lazy functions for nodes whose type cannot be found. An undefined function just outputs default
+ * values. It's useful to have so other parts of the conversion don't have to care about undefined
+ * nodes.
+ */
+class LazyFunctionForUndefinedNode : public LazyFunction {
+ public:
+ LazyFunctionForUndefinedNode(const bNode &node, Vector<const bNodeSocket *> &r_used_outputs)
+ {
+ debug_name_ = "Undefined";
+ Vector<const bNodeSocket *> dummy_used_inputs;
+ Vector<lf::Input> dummy_inputs;
+ lazy_function_interface_from_node(
+ node, dummy_used_inputs, r_used_outputs, dummy_inputs, outputs_);
+ }
+
+ void execute_impl(lf::Params &params, const lf::Context & /*context*/) const override
+ {
+ params.set_default_remaining_outputs();
+ }
+};
+
+/**
* Executes a multi-function. If all inputs are single values, the results will also be single
* values. If any input is a field, the outputs will also be fields.
*/
@@ -325,7 +352,7 @@ class LazyFunctionForMutedNode : public LazyFunction {
}
}
- void execute_impl(lf::Params &params, const lf::Context &UNUSED(context)) const override
+ void execute_impl(lf::Params &params, const lf::Context & /*context*/) const override
{
for (const int output_i : outputs_.index_range()) {
if (params.output_was_set(output_i)) {
@@ -397,7 +424,7 @@ class LazyFunctionForMultiFunctionConversion : public LazyFunction {
outputs_.append({"To", to});
}
- void execute_impl(lf::Params &params, const lf::Context &UNUSED(context)) const override
+ void execute_impl(lf::Params &params, const lf::Context & /*context*/) const override
{
const void *from_value = params.try_get_input_data_ptr(0);
void *to_value = params.get_output_data_ptr(0);
@@ -416,18 +443,16 @@ class LazyFunctionForMultiFunctionConversion : public LazyFunction {
*/
class LazyFunctionForMultiFunctionNode : public LazyFunction {
private:
- const bNode &node_;
const NodeMultiFunctions::Item fn_item_;
Vector<const ValueOrFieldCPPType *> input_types_;
Vector<const ValueOrFieldCPPType *> output_types_;
- Vector<const bNodeSocket *> output_sockets_;
public:
LazyFunctionForMultiFunctionNode(const bNode &node,
NodeMultiFunctions::Item fn_item,
Vector<const bNodeSocket *> &r_used_inputs,
Vector<const bNodeSocket *> &r_used_outputs)
- : node_(node), fn_item_(std::move(fn_item))
+ : fn_item_(std::move(fn_item))
{
BLI_assert(fn_item_.fn != nullptr);
debug_name_ = node.name;
@@ -438,10 +463,9 @@ class LazyFunctionForMultiFunctionNode : public LazyFunction {
for (const lf::Output &fn_output : outputs_) {
output_types_.append(dynamic_cast<const ValueOrFieldCPPType *>(fn_output.type));
}
- output_sockets_ = r_used_outputs;
}
- void execute_impl(lf::Params &params, const lf::Context &UNUSED(context)) const override
+ void execute_impl(lf::Params &params, const lf::Context & /*context*/) const override
{
Vector<const void *> input_values(inputs_.size());
Vector<void *> output_values(outputs_.size());
@@ -478,7 +502,7 @@ class LazyFunctionForImplicitInput : public LazyFunction {
outputs_.append({"Output", type});
}
- void execute_impl(lf::Params &params, const lf::Context &UNUSED(context)) const override
+ void execute_impl(lf::Params &params, const lf::Context & /*context*/) const override
{
void *value = params.get_output_data_ptr(0);
init_fn_(value);
@@ -514,21 +538,61 @@ class LazyFunctionForViewerNode : public LazyFunction {
{
GeoNodesLFUserData *user_data = dynamic_cast<GeoNodesLFUserData *>(context.user_data);
BLI_assert(user_data != nullptr);
+ if (user_data->modifier_data == nullptr) {
+ return;
+ }
+ if (user_data->modifier_data->eval_log == nullptr) {
+ return;
+ }
GeometrySet geometry = params.extract_input<GeometrySet>(0);
+ const NodeGeometryViewer *storage = static_cast<NodeGeometryViewer *>(bnode_.storage);
- GField field;
if (use_field_input_) {
const void *value_or_field = params.try_get_input_data_ptr(1);
BLI_assert(value_or_field != nullptr);
const ValueOrFieldCPPType &value_or_field_type = static_cast<const ValueOrFieldCPPType &>(
*inputs_[1].type);
- field = value_or_field_type.as_field(value_or_field);
+ GField field = value_or_field_type.as_field(value_or_field);
+ const eAttrDomain domain = eAttrDomain(storage->domain);
+ const StringRefNull viewer_attribute_name = ".viewer";
+ if (domain == ATTR_DOMAIN_INSTANCE) {
+ if (geometry.has_instances()) {
+ GeometryComponent &component = geometry.get_component_for_write(
+ GEO_COMPONENT_TYPE_INSTANCES);
+ bke::try_capture_field_on_geometry(
+ component, viewer_attribute_name, ATTR_DOMAIN_INSTANCE, field);
+ }
+ }
+ else {
+ geometry.modify_geometry_sets([&](GeometrySet &geometry) {
+ for (const GeometryComponentType type : {GEO_COMPONENT_TYPE_MESH,
+ GEO_COMPONENT_TYPE_POINT_CLOUD,
+ GEO_COMPONENT_TYPE_CURVE}) {
+ if (geometry.has(type)) {
+ GeometryComponent &component = geometry.get_component_for_write(type);
+ eAttrDomain used_domain = domain;
+ if (used_domain == ATTR_DOMAIN_AUTO) {
+ if (const std::optional<eAttrDomain> detected_domain =
+ bke::try_detect_field_domain(component, field)) {
+ used_domain = *detected_domain;
+ }
+ else {
+ used_domain = type == GEO_COMPONENT_TYPE_MESH ? ATTR_DOMAIN_CORNER :
+ ATTR_DOMAIN_POINT;
+ }
+ }
+ bke::try_capture_field_on_geometry(
+ component, viewer_attribute_name, used_domain, field);
+ }
+ }
+ });
+ }
}
geo_eval_log::GeoTreeLogger &tree_logger =
user_data->modifier_data->eval_log->get_local_tree_logger(*user_data->compute_context);
- tree_logger.log_viewer_node(bnode_, geometry, field);
+ tree_logger.log_viewer_node(bnode_, std::move(geometry));
}
};
@@ -539,6 +603,8 @@ class LazyFunctionForViewerNode : public LazyFunction {
class LazyFunctionForGroupNode : public LazyFunction {
private:
const bNode &group_node_;
+ bool has_many_nodes_ = false;
+ bool use_fallback_outputs_ = false;
std::optional<GeometryNodesLazyFunctionLogger> lf_logger_;
std::optional<GeometryNodesLazyFunctionSideEffectProvider> lf_side_effect_provider_;
std::optional<lf::GraphExecutor> graph_executor_;
@@ -557,6 +623,8 @@ class LazyFunctionForGroupNode : public LazyFunction {
bNodeTree *group_btree = reinterpret_cast<bNodeTree *>(group_node_.id);
BLI_assert(group_btree != nullptr);
+ has_many_nodes_ = lf_graph_info.num_inline_nodes_approximate > 1000;
+
Vector<const lf::OutputSocket *> graph_inputs;
for (const lf::OutputSocket *socket : lf_graph_info.mapping.group_input_sockets) {
if (socket != nullptr) {
@@ -573,9 +641,12 @@ class LazyFunctionForGroupNode : public LazyFunction {
}
}
}
+ else {
+ use_fallback_outputs_ = true;
+ }
lf_logger_.emplace(lf_graph_info);
- lf_side_effect_provider_.emplace(lf_graph_info);
+ lf_side_effect_provider_.emplace();
graph_executor_.emplace(lf_graph_info.graph,
std::move(graph_inputs),
std::move(graph_outputs),
@@ -588,6 +659,17 @@ class LazyFunctionForGroupNode : public LazyFunction {
GeoNodesLFUserData *user_data = dynamic_cast<GeoNodesLFUserData *>(context.user_data);
BLI_assert(user_data != nullptr);
+ if (has_many_nodes_) {
+ /* If the called node group has many nodes, it's likely that executing it takes a while even
+ * if every individual node is very small. */
+ lazy_threading::send_hint();
+ }
+ if (use_fallback_outputs_) {
+ /* The node group itself does not have an output node, so use default values as outputs.
+ * The group should still be executed in case it has side effects. */
+ params.set_default_remaining_outputs();
+ }
+
/* The compute context changes when entering a node group. */
bke::NodeGroupComputeContext compute_context{user_data->compute_context, group_node_.name};
GeoNodesLFUserData group_user_data = *user_data;
@@ -599,12 +681,12 @@ class LazyFunctionForGroupNode : public LazyFunction {
graph_executor_->execute(params, group_context);
}
- void *init_storage(LinearAllocator<> &allocator) const
+ void *init_storage(LinearAllocator<> &allocator) const override
{
return graph_executor_->init_storage(allocator);
}
- void destruct_storage(void *storage) const
+ void destruct_storage(void *storage) const override
{
graph_executor_->destruct_storage(storage);
}
@@ -679,6 +761,7 @@ struct GeometryNodesLazyFunctionGraphBuilder {
this->add_default_inputs();
lf_graph_->update_node_indices();
+ lf_graph_info_->num_inline_nodes_approximate += lf_graph_->nodes().size();
}
private:
@@ -776,6 +859,11 @@ struct GeometryNodesLazyFunctionGraphBuilder {
*bnode);
if (fn_item.fn != nullptr) {
this->handle_multi_function_node(*bnode, fn_item);
+ break;
+ }
+ if (node_type == &NodeTypeUndefined) {
+ this->handle_undefined_node(*bnode);
+ break;
}
/* Nodes that don't match any of the criteria above are just ignored. */
break;
@@ -890,6 +978,8 @@ struct GeometryNodesLazyFunctionGraphBuilder {
mapping_->bsockets_by_lf_socket_map.add(&lf_socket, &bsocket);
}
mapping_->group_node_map.add(&bnode, &lf_node);
+ lf_graph_info_->num_inline_nodes_approximate +=
+ group_lf_graph_info->num_inline_nodes_approximate;
}
void handle_geometry_node(const bNode &bnode)
@@ -969,6 +1059,21 @@ struct GeometryNodesLazyFunctionGraphBuilder {
mapping_->viewer_node_map.add(&bnode, &lf_node);
}
+ void handle_undefined_node(const bNode &bnode)
+ {
+ Vector<const bNodeSocket *> used_outputs;
+ auto lazy_function = std::make_unique<LazyFunctionForUndefinedNode>(bnode, used_outputs);
+ lf::FunctionNode &lf_node = lf_graph_->add_function(*lazy_function);
+ lf_graph_info_->functions.append(std::move(lazy_function));
+
+ for (const int i : used_outputs.index_range()) {
+ const bNodeSocket &bsocket = *used_outputs[i];
+ lf::OutputSocket &lf_socket = lf_node.output(i);
+ output_socket_map_.add(&bsocket, &lf_socket);
+ mapping_->bsockets_by_lf_socket_map.add(&lf_socket, &bsocket);
+ }
+ }
+
void handle_links()
{
for (const auto item : output_socket_map_.items()) {
@@ -978,6 +1083,10 @@ struct GeometryNodesLazyFunctionGraphBuilder {
void insert_links_from_socket(const bNodeSocket &from_bsocket, lf::OutputSocket &from_lf_socket)
{
+ if (nodeIsDanglingReroute(&btree_, &from_bsocket.owner_node())) {
+ return;
+ }
+
const Span<const bNodeLink *> links_from_bsocket = from_bsocket.directly_linked_links();
struct TypeWithLinks {
@@ -991,10 +1100,10 @@ struct GeometryNodesLazyFunctionGraphBuilder {
if (link->is_muted()) {
continue;
}
- const bNodeSocket &to_bsocket = *link->tosock;
- if (!to_bsocket.is_available()) {
+ if (!link->is_available()) {
continue;
}
+ const bNodeSocket &to_bsocket = *link->tosock;
const CPPType *to_type = get_socket_cpp_type(to_bsocket);
if (to_type == nullptr) {
continue;
@@ -1044,7 +1153,8 @@ struct GeometryNodesLazyFunctionGraphBuilder {
if (multi_input_link == link) {
break;
}
- if (!multi_input_link->is_muted()) {
+ if (!(multi_input_link->is_muted() ||
+ nodeIsDanglingReroute(&btree_, multi_input_link->fromnode))) {
link_index++;
}
}
@@ -1135,79 +1245,41 @@ struct GeometryNodesLazyFunctionGraphBuilder {
bool try_add_implicit_input(const bNodeSocket &input_bsocket, lf::InputSocket &input_lf_socket)
{
const bNode &bnode = input_bsocket.owner_node();
- const NodeDeclaration *node_declaration = bnode.declaration();
- if (node_declaration == nullptr) {
+ const SocketDeclaration *socket_decl = input_bsocket.runtime->declaration;
+ if (socket_decl == nullptr) {
return false;
}
- const SocketDeclaration &socket_declaration =
- *node_declaration->inputs()[input_bsocket.index()];
- if (socket_declaration.input_field_type() != InputSocketFieldType::Implicit) {
+ if (socket_decl->input_field_type() != InputSocketFieldType::Implicit) {
return false;
}
- const CPPType &type = input_lf_socket.type();
- std::function<void(void *)> init_fn = this->get_implicit_input_init_function(bnode,
- input_bsocket);
- if (!init_fn) {
+ const ImplicitInputValueFn *implicit_input_fn = socket_decl->implicit_input_fn();
+ if (implicit_input_fn == nullptr) {
return false;
}
-
+ std::function<void(void *)> init_fn = [&bnode, implicit_input_fn](void *r_value) {
+ (*implicit_input_fn)(bnode, r_value);
+ };
+ const CPPType &type = input_lf_socket.type();
auto lazy_function = std::make_unique<LazyFunctionForImplicitInput>(type, std::move(init_fn));
lf::Node &lf_node = lf_graph_->add_function(*lazy_function);
lf_graph_info_->functions.append(std::move(lazy_function));
lf_graph_->add_link(lf_node.output(0), input_lf_socket);
return true;
}
-
- std::function<void(void *)> get_implicit_input_init_function(const bNode &bnode,
- const bNodeSocket &bsocket)
- {
- const bNodeSocketType &socket_type = *bsocket.typeinfo;
- if (socket_type.type == SOCK_VECTOR) {
- if (bnode.type == GEO_NODE_SET_CURVE_HANDLES) {
- StringRef side = ((NodeGeometrySetCurveHandlePositions *)bnode.storage)->mode ==
- GEO_NODE_CURVE_HANDLE_LEFT ?
- "handle_left" :
- "handle_right";
- return [side](void *r_value) {
- new (r_value) ValueOrField<float3>(bke::AttributeFieldInput::Create<float3>(side));
- };
- }
- else if (bnode.type == GEO_NODE_EXTRUDE_MESH) {
- return [](void *r_value) {
- new (r_value)
- ValueOrField<float3>(Field<float3>(std::make_shared<bke::NormalFieldInput>()));
- };
- }
- else {
- return [](void *r_value) {
- new (r_value) ValueOrField<float3>(bke::AttributeFieldInput::Create<float3>("position"));
- };
- }
- }
- else if (socket_type.type == SOCK_INT) {
- if (ELEM(bnode.type, FN_NODE_RANDOM_VALUE, GEO_NODE_INSTANCE_ON_POINTS)) {
- return [](void *r_value) {
- new (r_value)
- ValueOrField<int>(Field<int>(std::make_shared<bke::IDAttributeFieldInput>()));
- };
- }
- else {
- return [](void *r_value) {
- new (r_value) ValueOrField<int>(Field<int>(std::make_shared<fn::IndexFieldInput>()));
- };
- }
- }
- return {};
- }
};
const GeometryNodesLazyFunctionGraphInfo *ensure_geometry_nodes_lazy_function_graph(
const bNodeTree &btree)
{
btree.ensure_topology_cache();
- if (btree.has_link_cycle()) {
+ if (btree.has_available_link_cycle()) {
return nullptr;
}
+ if (const ID *id_orig = DEG_get_original_id(const_cast<ID *>(&btree.id))) {
+ if (id_orig->tag & LIB_TAG_MISSING) {
+ return nullptr;
+ }
+ }
std::unique_ptr<GeometryNodesLazyFunctionGraphInfo> &lf_graph_info_ptr =
btree.runtime->geometry_nodes_lazy_function_graph_info;
@@ -1300,12 +1372,6 @@ void GeometryNodesLazyFunctionLogger::dump_when_input_is_set_twice(
user_data->compute_context->print_stack(std::cout, ss.str());
}
-GeometryNodesLazyFunctionSideEffectProvider::GeometryNodesLazyFunctionSideEffectProvider(
- const GeometryNodesLazyFunctionGraphInfo &lf_graph_info)
- : lf_graph_info_(lf_graph_info)
-{
-}
-
Vector<const lf::FunctionNode *> GeometryNodesLazyFunctionSideEffectProvider::
get_nodes_with_side_effects(const lf::Context &context) const
{
@@ -1324,4 +1390,53 @@ GeometryNodesLazyFunctionGraphInfo::~GeometryNodesLazyFunctionGraphInfo()
}
}
+[[maybe_unused]] static void add_thread_id_debug_message(
+ const GeometryNodesLazyFunctionGraphInfo &lf_graph_info,
+ const lf::FunctionNode &node,
+ const lf::Context &context)
+{
+ static std::atomic<int> thread_id_source = 0;
+ static thread_local const int thread_id = thread_id_source.fetch_add(1);
+ static thread_local const std::string thread_id_str = "Thread: " + std::to_string(thread_id);
+
+ GeoNodesLFUserData *user_data = dynamic_cast<GeoNodesLFUserData *>(context.user_data);
+ BLI_assert(user_data != nullptr);
+ if (user_data->modifier_data->eval_log == nullptr) {
+ return;
+ }
+ geo_eval_log::GeoTreeLogger &tree_logger =
+ user_data->modifier_data->eval_log->get_local_tree_logger(*user_data->compute_context);
+
+ /* Find corresponding node based on the socket mapping. */
+ auto check_sockets = [&](const Span<const lf::Socket *> lf_sockets) {
+ for (const lf::Socket *lf_socket : lf_sockets) {
+ const Span<const bNodeSocket *> bsockets =
+ lf_graph_info.mapping.bsockets_by_lf_socket_map.lookup(lf_socket);
+ if (!bsockets.is_empty()) {
+ const bNodeSocket &bsocket = *bsockets[0];
+ const bNode &bnode = bsocket.owner_node();
+ tree_logger.debug_messages.append(
+ {tree_logger.allocator->copy_string(bnode.name), thread_id_str});
+ return true;
+ }
+ }
+ return false;
+ };
+
+ if (check_sockets(node.inputs().cast<const lf::Socket *>())) {
+ return;
+ }
+ check_sockets(node.outputs().cast<const lf::Socket *>());
+}
+
+void GeometryNodesLazyFunctionLogger::log_before_node_execute(const lf::FunctionNode &node,
+ const lf::Params & /*params*/,
+ const lf::Context &context) const
+{
+ /* Enable this to see the threads that invoked a node. */
+ if constexpr (false) {
+ add_thread_id_debug_message(lf_graph_info_, node, context);
+ }
+}
+
} // namespace blender::nodes
diff --git a/source/blender/nodes/intern/geometry_nodes_log.cc b/source/blender/nodes/intern/geometry_nodes_log.cc
index 350b199cd60..0f122307328 100644
--- a/source/blender/nodes/intern/geometry_nodes_log.cc
+++ b/source/blender/nodes/intern/geometry_nodes_log.cc
@@ -6,12 +6,15 @@
#include "BKE_compute_contexts.hh"
#include "BKE_curves.hh"
#include "BKE_node_runtime.hh"
+#include "BKE_viewer_path.h"
#include "FN_field_cpp_type.hh"
#include "DNA_modifier_types.h"
#include "DNA_space_types.h"
+#include "ED_viewer_path.hh"
+
namespace blender::nodes::geo_eval_log {
using fn::FieldInput;
@@ -35,8 +38,8 @@ FieldInfoLog::FieldInfoLog(const GField &field) : type(field.cpp_type())
std::sort(
field_inputs.begin(), field_inputs.end(), [](const FieldInput &a, const FieldInput &b) {
- const int index_a = (int)a.category();
- const int index_b = (int)b.category();
+ const int index_a = int(a.category());
+ const int index_b = int(b.category());
if (index_a == index_b) {
return a.socket_inspection_name().size() < b.socket_inspection_name().size();
}
@@ -66,7 +69,7 @@ GeometryInfoLog::GeometryInfoLog(const GeometrySet &geometry_set)
true,
[&](const bke::AttributeIDRef &attribute_id,
const bke::AttributeMetaData &meta_data,
- const GeometryComponent &UNUSED(component)) {
+ const GeometryComponent & /*component*/) {
if (attribute_id.is_named() && names.add(attribute_id.name())) {
this->attributes.append({attribute_id.name(), meta_data.domain, meta_data.data_type});
}
@@ -98,7 +101,7 @@ GeometryInfoLog::GeometryInfoLog(const GeometrySet &geometry_set)
case GEO_COMPONENT_TYPE_INSTANCES: {
const InstancesComponent &instances_component = *(const InstancesComponent *)component;
InstancesInfo &info = this->instances_info.emplace();
- info.instances_num = instances_component.instances_num();
+ info.instances_num = instances_component.attribute_domain_size(ATTR_DOMAIN_INSTANCE);
break;
}
case GEO_COMPONENT_TYPE_EDIT: {
@@ -148,7 +151,9 @@ void GeoTreeLogger::log_value(const bNode &node, const bNodeSocket &socket, cons
auto store_logged_value = [&](destruct_ptr<ValueLog> value_log) {
auto &socket_values = socket.in_out == SOCK_IN ? this->input_socket_values :
this->output_socket_values;
- socket_values.append({node.name, socket.identifier, std::move(value_log)});
+ socket_values.append({this->allocator->copy_string(node.name),
+ this->allocator->copy_string(socket.identifier),
+ std::move(value_log)});
};
auto log_generic_value = [&](const CPPType &type, const void *value) {
@@ -186,15 +191,12 @@ void GeoTreeLogger::log_value(const bNode &node, const bNodeSocket &socket, cons
}
}
-void GeoTreeLogger::log_viewer_node(const bNode &viewer_node,
- const GeometrySet &geometry,
- const GField &field)
+void GeoTreeLogger::log_viewer_node(const bNode &viewer_node, GeometrySet geometry)
{
destruct_ptr<ViewerNodeLog> log = this->allocator->construct<ViewerNodeLog>();
- log->geometry = geometry;
- log->field = field;
+ log->geometry = std::move(geometry);
log->geometry.ensure_owns_direct_data();
- this->viewer_node_logs.append({viewer_node.name, std::move(log)});
+ this->viewer_node_logs.append({this->allocator->copy_string(viewer_node.name), std::move(log)});
}
void GeoTreeLog::ensure_node_warnings()
@@ -315,11 +317,11 @@ void GeoTreeLog::ensure_used_named_attributes()
return;
}
- auto add_attribute = [&](const StringRef node_name,
- const StringRef attribute_name,
+ auto add_attribute = [&](const StringRefNull node_name,
+ const StringRefNull attribute_name,
const NamedAttributeUsage &usage) {
- this->nodes.lookup_or_add_as(node_name).used_named_attributes.lookup_or_add_as(attribute_name,
- usage) |= usage;
+ this->nodes.lookup_or_add_default(node_name).used_named_attributes.lookup_or_add(
+ attribute_name, usage) |= usage;
this->used_named_attributes.lookup_or_add_as(attribute_name, usage) |= usage;
};
@@ -543,29 +545,17 @@ GeoTreeLog *GeoModifierLog::get_tree_log_for_node_editor(const SpaceNode &snode)
return &modifier_log->get_tree_log(compute_context_builder.hash());
}
-const ViewerNodeLog *GeoModifierLog::find_viewer_node_log_for_spreadsheet(
- const SpaceSpreadsheet &sspreadsheet)
+const ViewerNodeLog *GeoModifierLog::find_viewer_node_log_for_path(const ViewerPath &viewer_path)
{
- Vector<const SpreadsheetContext *> context_path = sspreadsheet.context_path;
- if (context_path.size() < 3) {
- return nullptr;
- }
- if (context_path[0]->type != SPREADSHEET_CONTEXT_OBJECT) {
- return nullptr;
- }
- if (context_path[1]->type != SPREADSHEET_CONTEXT_MODIFIER) {
- return nullptr;
- }
- const SpreadsheetContextObject *object_context =
- reinterpret_cast<const SpreadsheetContextObject *>(context_path[0]);
- const SpreadsheetContextModifier *modifier_context =
- reinterpret_cast<const SpreadsheetContextModifier *>(context_path[1]);
- if (object_context->object == nullptr) {
+ const std::optional<ed::viewer_path::ViewerPathForGeometryNodesViewer> parsed_path =
+ ed::viewer_path::parse_geometry_nodes_viewer(viewer_path);
+ if (!parsed_path.has_value()) {
return nullptr;
}
+ const Object *object = parsed_path->object;
NodesModifierData *nmd = nullptr;
- LISTBASE_FOREACH (ModifierData *, md, &object_context->object->modifiers) {
- if (STREQ(md->name, modifier_context->modifier_name)) {
+ LISTBASE_FOREACH (ModifierData *, md, &object->modifiers) {
+ if (md->name == parsed_path->modifier_name) {
if (md->type == eModifierType_Nodes) {
nmd = reinterpret_cast<NodesModifierData *>(md);
}
@@ -581,27 +571,16 @@ const ViewerNodeLog *GeoModifierLog::find_viewer_node_log_for_spreadsheet(
static_cast<nodes::geo_eval_log::GeoModifierLog *>(nmd->runtime_eval_log);
ComputeContextBuilder compute_context_builder;
- compute_context_builder.push<bke::ModifierComputeContext>(modifier_context->modifier_name);
- for (const SpreadsheetContext *context : context_path.as_span().drop_front(2).drop_back(1)) {
- if (context->type != SPREADSHEET_CONTEXT_NODE) {
- return nullptr;
- }
- const SpreadsheetContextNode &node_context = *reinterpret_cast<const SpreadsheetContextNode *>(
- context);
- compute_context_builder.push<bke::NodeGroupComputeContext>(node_context.node_name);
+ compute_context_builder.push<bke::ModifierComputeContext>(parsed_path->modifier_name);
+ for (const StringRef group_node_name : parsed_path->group_node_names) {
+ compute_context_builder.push<bke::NodeGroupComputeContext>(group_node_name);
}
const ComputeContextHash context_hash = compute_context_builder.hash();
nodes::geo_eval_log::GeoTreeLog &tree_log = modifier_log->get_tree_log(context_hash);
tree_log.ensure_viewer_node_logs();
- const SpreadsheetContext *last_context = context_path.last();
- if (last_context->type != SPREADSHEET_CONTEXT_NODE) {
- return nullptr;
- }
- const SpreadsheetContextNode &last_node_context =
- *reinterpret_cast<const SpreadsheetContextNode *>(last_context);
const ViewerNodeLog *viewer_log = tree_log.viewer_node_logs.lookup_default(
- last_node_context.node_name, nullptr);
+ parsed_path->viewer_node_name, nullptr);
return viewer_log;
}
diff --git a/source/blender/nodes/intern/node_common.cc b/source/blender/nodes/intern/node_common.cc
index 6402ec3f3d6..975bf0c01ca 100644
--- a/source/blender/nodes/intern/node_common.cc
+++ b/source/blender/nodes/intern/node_common.cc
@@ -22,6 +22,7 @@
#include "BLT_translation.h"
#include "BKE_node.h"
+#include "BKE_node_runtime.hh"
#include "BKE_node_tree_update.h"
#include "RNA_types.h"
@@ -63,7 +64,7 @@ bNodeSocket *node_group_find_output_socket(bNode *groupnode, const char *identif
return find_matching_socket(groupnode->outputs, identifier);
}
-void node_group_label(const bNodeTree *UNUSED(ntree), const bNode *node, char *label, int maxlen)
+void node_group_label(const bNodeTree * /*ntree*/, const bNode *node, char *label, int maxlen)
{
BLI_strncpy(label, (node->id) ? node->id->name + 2 : IFACE_("Missing Data-Block"), maxlen);
}
@@ -82,10 +83,10 @@ bool node_group_poll_instance(bNode *node, bNodeTree *nodetree, const char **dis
return false;
}
-bool nodeGroupPoll(bNodeTree *nodetree, bNodeTree *grouptree, const char **r_disabled_hint)
+bool nodeGroupPoll(const bNodeTree *nodetree,
+ const bNodeTree *grouptree,
+ const char **r_disabled_hint)
{
- bool valid = true;
-
/* unspecified node group, generally allowed
* (if anything, should be avoided on operator level)
*/
@@ -94,18 +95,20 @@ bool nodeGroupPoll(bNodeTree *nodetree, bNodeTree *grouptree, const char **r_dis
}
if (nodetree == grouptree) {
- *r_disabled_hint = TIP_("Nesting a node group inside of itself is not allowed");
+ if (r_disabled_hint) {
+ *r_disabled_hint = TIP_("Nesting a node group inside of itself is not allowed");
+ }
return false;
}
- LISTBASE_FOREACH (bNode *, node, &grouptree->nodes) {
+ LISTBASE_FOREACH (const bNode *, node, &grouptree->nodes) {
if (node->typeinfo->poll_instance &&
- !node->typeinfo->poll_instance(node, nodetree, r_disabled_hint)) {
- valid = false;
- break;
+ !node->typeinfo->poll_instance(
+ const_cast<bNode *>(node), const_cast<bNodeTree *>(nodetree), r_disabled_hint)) {
+ return false;
}
}
- return valid;
+ return true;
}
static void add_new_socket_from_interface(bNodeTree &node_tree,
@@ -216,7 +219,7 @@ void node_group_update(struct bNodeTree *ntree, struct bNode *node)
if (node->id == nullptr) {
nodeRemoveAllSockets(ntree, node);
}
- else if ((ID_IS_LINKED(node->id) && (node->id->tag & LIB_TAG_MISSING))) {
+ else if (ID_IS_LINKED(node->id) && (node->id->tag & LIB_TAG_MISSING)) {
/* Missing data-block, leave sockets unchanged so that when it comes back
* the links remain valid. */
}
@@ -233,7 +236,7 @@ void node_group_update(struct bNodeTree *ntree, struct bNode *node)
/** \name Node Frame
* \{ */
-static void node_frame_init(bNodeTree *UNUSED(ntree), bNode *node)
+static void node_frame_init(bNodeTree * /*ntree*/, bNode *node)
{
NodeFrame *data = MEM_cnew<NodeFrame>("frame node storage");
node->storage = data;
@@ -250,7 +253,7 @@ void register_node_type_frame()
ntype->free_self = (void (*)(bNodeType *))MEM_freeN;
node_type_base(ntype, NODE_FRAME, "Frame", NODE_CLASS_LAYOUT);
- node_type_init(ntype, node_frame_init);
+ ntype->initfunc = node_frame_init;
node_type_storage(ntype, "NodeFrame", node_free_standard_storage, node_copy_standard_storage);
node_type_size(ntype, 150, 100, 0);
ntype->flag |= NODE_BACKGROUND;
@@ -280,7 +283,7 @@ void register_node_type_reroute()
ntype->free_self = (void (*)(bNodeType *))MEM_freeN;
node_type_base(ntype, NODE_REROUTE, "Reroute", NODE_CLASS_LAYOUT);
- node_type_init(ntype, node_reroute_init);
+ ntype->initfunc = node_reroute_init;
nodeRegisterType(ntype);
}
@@ -376,53 +379,29 @@ void ntree_update_reroute_nodes(bNodeTree *ntree)
}
}
-static bool node_is_connected_to_output_recursive(bNodeTree *ntree, bNode *node)
+bool BKE_node_is_connected_to_output(const bNodeTree *ntree, const bNode *node)
{
- bNodeLink *link;
-
- /* avoid redundant checks, and infinite loops in case of cyclic node links */
- if (node->done) {
- return false;
- }
- node->done = 1;
-
- /* main test, done before child loop so it catches output nodes themselves as well */
- if (node->typeinfo->nclass == NODE_CLASS_OUTPUT && node->flag & NODE_DO_OUTPUT) {
- return true;
+ ntree->ensure_topology_cache();
+ Stack<const bNode *> nodes_to_check;
+ for (const bNodeSocket *socket : node->output_sockets()) {
+ for (const bNodeLink *link : socket->directly_linked_links()) {
+ nodes_to_check.push(link->tonode);
+ }
}
-
- /* test all connected nodes, first positive find is sufficient to return true */
- for (link = (bNodeLink *)ntree->links.first; link; link = link->next) {
- if (link->fromnode == node) {
- if (node_is_connected_to_output_recursive(ntree, link->tonode)) {
- return true;
+ while (!nodes_to_check.is_empty()) {
+ const bNode *next_node = nodes_to_check.pop();
+ for (const bNodeSocket *socket : next_node->output_sockets()) {
+ for (const bNodeLink *link : socket->directly_linked_links()) {
+ if (link->tonode->typeinfo->nclass == NODE_CLASS_OUTPUT &&
+ link->tonode->flag & NODE_DO_OUTPUT) {
+ return true;
+ }
+ nodes_to_check.push(link->tonode);
}
}
}
- return false;
-}
-
-bool BKE_node_is_connected_to_output(bNodeTree *ntree, bNode *node)
-{
- bNode *tnode;
-
- /* clear flags */
- for (tnode = (bNode *)ntree->nodes.first; tnode; tnode = tnode->next) {
- tnode->done = 0;
- }
-
- return node_is_connected_to_output_recursive(ntree, node);
-}
-
-void BKE_node_tree_unlink_id(ID *id, struct bNodeTree *ntree)
-{
- bNode *node;
- for (node = (bNode *)ntree->nodes.first; node; node = node->next) {
- if (node->id == id) {
- node->id = nullptr;
- }
- }
+ return false;
}
/** \} */
@@ -455,62 +434,53 @@ bNodeSocket *node_group_input_find_socket(bNode *node, const char *identifier)
void node_group_input_update(bNodeTree *ntree, bNode *node)
{
bNodeSocket *extsock = (bNodeSocket *)node->outputs.last;
- bNodeLink *link, *linknext, *exposelink;
/* Adding a tree socket and verifying will remove the extension socket!
* This list caches the existing links from the extension socket
- * so they can be recreated after verification.
- */
- ListBase tmplinks;
+ * so they can be recreated after verification. */
+ Vector<bNodeLink> temp_links;
/* find links from the extension socket and store them */
- BLI_listbase_clear(&tmplinks);
- for (link = (bNodeLink *)ntree->links.first; link; link = linknext) {
- linknext = link->next;
+ LISTBASE_FOREACH_MUTABLE (bNodeLink *, link, &ntree->links) {
if (nodeLinkIsHidden(link)) {
continue;
}
if (link->fromsock == extsock) {
- bNodeLink *tlink = MEM_cnew<bNodeLink>("temporary link");
- *tlink = *link;
- BLI_addtail(&tmplinks, tlink);
-
+ temp_links.append(*link);
nodeRemLink(ntree, link);
}
}
/* find valid link to expose */
- exposelink = nullptr;
- for (link = (bNodeLink *)tmplinks.first; link; link = link->next) {
+ bNodeLink *exposelink = nullptr;
+ for (bNodeLink &link : temp_links) {
/* XXX Multiple sockets can be connected to the extension socket at once,
* in that case the arbitrary first link determines name and type.
* This could be improved by choosing the "best" type among all links,
* whatever that means.
*/
- if (!is_group_extension_socket(link->tonode, link->tosock)) {
- exposelink = link;
+ if (!is_group_extension_socket(link.tonode, link.tosock)) {
+ exposelink = &link;
break;
}
}
if (exposelink) {
- bNodeSocket *gsock, *newsock;
-
- gsock = ntreeAddSocketInterfaceFromSocket(ntree, exposelink->tonode, exposelink->tosock);
+ bNodeSocket *gsock = ntreeAddSocketInterfaceFromSocket(
+ ntree, exposelink->tonode, exposelink->tosock);
node_group_input_update(ntree, node);
- newsock = node_group_input_find_socket(node, gsock->identifier);
+ bNodeSocket *newsock = node_group_input_find_socket(node, gsock->identifier);
/* redirect links from the extension socket */
- for (link = (bNodeLink *)tmplinks.first; link; link = link->next) {
- bNodeLink *newlink = nodeAddLink(ntree, node, newsock, link->tonode, link->tosock);
+ for (bNodeLink &link : temp_links) {
+ bNodeLink *newlink = nodeAddLink(ntree, node, newsock, link.tonode, link.tosock);
if (newlink->tosock->flag & SOCK_MULTI_INPUT) {
- newlink->multi_input_socket_index = link->multi_input_socket_index;
+ newlink->multi_input_socket_index = link.multi_input_socket_index;
}
}
}
- BLI_freelistN(&tmplinks);
group_verify_socket_list(*ntree, *node, ntree->inputs, node->outputs, SOCK_OUT, true);
}
@@ -522,8 +492,8 @@ void register_node_type_group_input()
node_type_base(ntype, NODE_GROUP_INPUT, "Group Input", NODE_CLASS_INTERFACE);
node_type_size(ntype, 140, 80, 400);
- node_type_init(ntype, node_group_input_init);
- node_type_update(ntype, node_group_input_update);
+ ntype->initfunc = node_group_input_init;
+ ntype->updatefunc = node_group_input_update;
nodeRegisterType(ntype);
}
@@ -547,60 +517,51 @@ bNodeSocket *node_group_output_find_socket(bNode *node, const char *identifier)
void node_group_output_update(bNodeTree *ntree, bNode *node)
{
bNodeSocket *extsock = (bNodeSocket *)node->inputs.last;
- bNodeLink *link, *linknext, *exposelink;
/* Adding a tree socket and verifying will remove the extension socket!
* This list caches the existing links to the extension socket
- * so they can be recreated after verification.
- */
- ListBase tmplinks;
+ * so they can be recreated after verification. */
+ Vector<bNodeLink> temp_links;
/* find links to the extension socket and store them */
- BLI_listbase_clear(&tmplinks);
- for (link = (bNodeLink *)ntree->links.first; link; link = linknext) {
- linknext = link->next;
+ LISTBASE_FOREACH_MUTABLE (bNodeLink *, link, &ntree->links) {
if (nodeLinkIsHidden(link)) {
continue;
}
if (link->tosock == extsock) {
- bNodeLink *tlink = MEM_cnew<bNodeLink>("temporary link");
- *tlink = *link;
- BLI_addtail(&tmplinks, tlink);
-
+ temp_links.append(*link);
nodeRemLink(ntree, link);
}
}
/* find valid link to expose */
- exposelink = nullptr;
- for (link = (bNodeLink *)tmplinks.first; link; link = link->next) {
+ bNodeLink *exposelink = nullptr;
+ for (bNodeLink &link : temp_links) {
/* XXX Multiple sockets can be connected to the extension socket at once,
* in that case the arbitrary first link determines name and type.
* This could be improved by choosing the "best" type among all links,
* whatever that means.
*/
- if (!is_group_extension_socket(link->fromnode, link->fromsock)) {
- exposelink = link;
+ if (!is_group_extension_socket(link.fromnode, link.fromsock)) {
+ exposelink = &link;
break;
}
}
if (exposelink) {
- bNodeSocket *gsock, *newsock;
-
/* XXX what if connecting virtual to virtual socket?? */
- gsock = ntreeAddSocketInterfaceFromSocket(ntree, exposelink->fromnode, exposelink->fromsock);
+ bNodeSocket *gsock = ntreeAddSocketInterfaceFromSocket(
+ ntree, exposelink->fromnode, exposelink->fromsock);
node_group_output_update(ntree, node);
- newsock = node_group_output_find_socket(node, gsock->identifier);
+ bNodeSocket *newsock = node_group_output_find_socket(node, gsock->identifier);
/* redirect links to the extension socket */
- for (link = (bNodeLink *)tmplinks.first; link; link = link->next) {
- nodeAddLink(ntree, link->fromnode, link->fromsock, node, newsock);
+ for (bNodeLink &link : temp_links) {
+ nodeAddLink(ntree, link.fromnode, link.fromsock, node, newsock);
}
}
- BLI_freelistN(&tmplinks);
group_verify_socket_list(*ntree, *node, ntree->outputs, node->inputs, SOCK_IN, true);
}
@@ -612,8 +573,8 @@ void register_node_type_group_output()
node_type_base(ntype, NODE_GROUP_OUTPUT, "Group Output", NODE_CLASS_INTERFACE);
node_type_size(ntype, 140, 80, 400);
- node_type_init(ntype, node_group_output_init);
- node_type_update(ntype, node_group_output_update);
+ ntype->initfunc = node_group_output_init;
+ ntype->updatefunc = node_group_output_update;
ntype->no_muting = true;
diff --git a/source/blender/nodes/intern/node_declaration.cc b/source/blender/nodes/intern/node_declaration.cc
index 2cd9c6000c0..f323d035668 100644
--- a/source/blender/nodes/intern/node_declaration.cc
+++ b/source/blender/nodes/intern/node_declaration.cc
@@ -2,6 +2,7 @@
#include "NOD_node_declaration.hh"
+#include "BKE_geometry_fields.hh"
#include "BKE_node.h"
namespace blender::nodes {
@@ -81,4 +82,30 @@ bool SocketDeclaration::matches_common_data(const bNodeSocket &socket) const
return true;
}
+namespace implicit_field_inputs {
+
+void position(const bNode & /*node*/, void *r_value)
+{
+ new (r_value) fn::ValueOrField<float3>(bke::AttributeFieldInput::Create<float3>("position"));
+}
+
+void normal(const bNode & /*node*/, void *r_value)
+{
+ new (r_value)
+ fn::ValueOrField<float3>(fn::Field<float3>(std::make_shared<bke::NormalFieldInput>()));
+}
+
+void index(const bNode & /*node*/, void *r_value)
+{
+ new (r_value) fn::ValueOrField<int>(fn::Field<int>(std::make_shared<fn::IndexFieldInput>()));
+}
+
+void id_or_index(const bNode & /*node*/, void *r_value)
+{
+ new (r_value)
+ fn::ValueOrField<int>(fn::Field<int>(std::make_shared<bke::IDAttributeFieldInput>()));
+}
+
+} // namespace implicit_field_inputs
+
} // namespace blender::nodes
diff --git a/source/blender/nodes/intern/node_exec.cc b/source/blender/nodes/intern/node_exec.cc
index 724d6f1a1e1..af783ca391f 100644
--- a/source/blender/nodes/intern/node_exec.cc
+++ b/source/blender/nodes/intern/node_exec.cc
@@ -162,7 +162,7 @@ bNodeTreeExec *ntree_exec_begin(bNodeExecContext *context,
/* XXX could let callbacks do this for specialized data */
exec = MEM_cnew<bNodeTreeExec>("node tree execution data");
- /* backpointer to node tree */
+ /* Back-pointer to node tree. */
exec->nodetree = ntree;
/* set stack indices */
diff --git a/source/blender/nodes/intern/node_exec.h b/source/blender/nodes/intern/node_exec.h
index dc07f52e23f..55bf409444e 100644
--- a/source/blender/nodes/intern/node_exec.h
+++ b/source/blender/nodes/intern/node_exec.h
@@ -27,7 +27,7 @@ struct bNodeTree;
/* Node execution data */
typedef struct bNodeExec {
- /** Backpointer to node. */
+ /** Back-pointer to node. */
struct bNode *node;
bNodeExecData data;
@@ -37,7 +37,7 @@ typedef struct bNodeExec {
/* Execution Data for each instance of node tree execution */
typedef struct bNodeTreeExec {
- struct bNodeTree *nodetree; /* backpointer to node tree */
+ struct bNodeTree *nodetree; /* Back-pointer to node tree. */
int totnodes; /* total node count */
struct bNodeExec *nodeexec; /* per-node execution data */
diff --git a/source/blender/nodes/intern/node_geometry_exec.cc b/source/blender/nodes/intern/node_geometry_exec.cc
index 1833774fe33..1de92fa8409 100644
--- a/source/blender/nodes/intern/node_geometry_exec.cc
+++ b/source/blender/nodes/intern/node_geometry_exec.cc
@@ -13,18 +13,22 @@
namespace blender::nodes {
-void GeoNodeExecParams::error_message_add(const NodeWarningType type, std::string message) const
+void GeoNodeExecParams::error_message_add(const NodeWarningType type,
+ const StringRef message) const
{
if (geo_eval_log::GeoTreeLogger *tree_logger = this->get_local_tree_logger()) {
- tree_logger->node_warnings.append({node_.name, {type, std::move(message)}});
+ tree_logger->node_warnings.append({tree_logger->allocator->copy_string(node_.name),
+ {type, tree_logger->allocator->copy_string(message)}});
}
}
-void GeoNodeExecParams::used_named_attribute(std::string attribute_name,
+void GeoNodeExecParams::used_named_attribute(const StringRef attribute_name,
const NamedAttributeUsage usage)
{
if (geo_eval_log::GeoTreeLogger *tree_logger = this->get_local_tree_logger()) {
- tree_logger->used_named_attributes.append({node_.name, std::move(attribute_name), usage});
+ tree_logger->used_named_attributes.append({tree_logger->allocator->copy_string(node_.name),
+ tree_logger->allocator->copy_string(attribute_name),
+ usage});
}
}
diff --git a/source/blender/nodes/intern/node_socket.cc b/source/blender/nodes/intern/node_socket.cc
index 098f766589d..f2f4519625a 100644
--- a/source/blender/nodes/intern/node_socket.cc
+++ b/source/blender/nodes/intern/node_socket.cc
@@ -59,14 +59,14 @@ struct bNodeSocket *node_add_socket_from_template(struct bNodeTree *ntree,
}
case SOCK_INT: {
bNodeSocketValueInt *dval = (bNodeSocketValueInt *)sock->default_value;
- dval->value = (int)stemp->val1;
- dval->min = (int)stemp->min;
- dval->max = (int)stemp->max;
+ dval->value = int(stemp->val1);
+ dval->min = int(stemp->min);
+ dval->max = int(stemp->max);
break;
}
case SOCK_BOOLEAN: {
bNodeSocketValueBoolean *dval = (bNodeSocketValueBoolean *)sock->default_value;
- dval->value = (int)stemp->val1;
+ dval->value = int(stemp->val1);
break;
}
case SOCK_VECTOR: {
@@ -531,11 +531,11 @@ void node_socket_skip_reroutes(
}
}
-static void standard_node_socket_interface_init_socket(bNodeTree *UNUSED(ntree),
+static void standard_node_socket_interface_init_socket(bNodeTree * /*ntree*/,
const bNodeSocket *interface_socket,
- bNode *UNUSED(node),
+ bNode * /*node*/,
bNodeSocket *sock,
- const char *UNUSED(data_path))
+ const char * /*data_path*/)
{
/* initialize the type value */
sock->type = sock->typeinfo->type;
@@ -549,11 +549,11 @@ static void standard_node_socket_interface_init_socket(bNodeTree *UNUSED(ntree),
}
/* copies settings that are not changed for each socket instance */
-static void standard_node_socket_interface_verify_socket(bNodeTree *UNUSED(ntree),
+static void standard_node_socket_interface_verify_socket(bNodeTree * /*ntree*/,
const bNodeSocket *interface_socket,
- bNode *UNUSED(node),
+ bNode * /*node*/,
bNodeSocket *sock,
- const char *UNUSED(data_path))
+ const char * /*data_path*/)
{
/* sanity check */
if (sock->type != interface_socket->typeinfo->type) {
@@ -594,9 +594,9 @@ static void standard_node_socket_interface_verify_socket(bNodeTree *UNUSED(ntree
}
}
-static void standard_node_socket_interface_from_socket(bNodeTree *UNUSED(ntree),
+static void standard_node_socket_interface_from_socket(bNodeTree * /*ntree*/,
bNodeSocket *stemp,
- bNode *UNUSED(node),
+ bNode * /*node*/,
bNodeSocket *sock)
{
/* initialize settings */
@@ -801,7 +801,7 @@ static bNodeSocketType *make_socket_type_geometry()
{
bNodeSocketType *socktype = make_standard_socket_type(SOCK_GEOMETRY, PROP_NONE);
socktype->base_cpp_type = &blender::CPPType::get<GeometrySet>();
- socktype->get_base_cpp_value = [](const bNodeSocket &UNUSED(socket), void *r_value) {
+ socktype->get_base_cpp_value = [](const bNodeSocket & /*socket*/, void *r_value) {
new (r_value) GeometrySet();
};
socktype->geometry_nodes_cpp_type = socktype->base_cpp_type;
diff --git a/source/blender/nodes/intern/node_socket_declarations.cc b/source/blender/nodes/intern/node_socket_declarations.cc
index b9fb75f30c7..a7d281bcf52 100644
--- a/source/blender/nodes/intern/node_socket_declarations.cc
+++ b/source/blender/nodes/intern/node_socket_declarations.cc
@@ -50,7 +50,7 @@ static bool sockets_can_connect(const SocketDeclaration &socket_decl,
return true;
}
-static bool basic_types_can_connect(const SocketDeclaration &UNUSED(socket_decl),
+static bool basic_types_can_connect(const SocketDeclaration & /*socket_decl*/,
const bNodeSocket &other_socket)
{
return ELEM(other_socket.type, SOCK_FLOAT, SOCK_INT, SOCK_BOOLEAN, SOCK_VECTOR, SOCK_RGBA);
diff --git a/source/blender/nodes/intern/node_util.c b/source/blender/nodes/intern/node_util.cc
index ddab455509d..17be20b4e4b 100644
--- a/source/blender/nodes/intern/node_util.c
+++ b/source/blender/nodes/intern/node_util.cc
@@ -37,7 +37,7 @@
void node_free_curves(bNode *node)
{
- BKE_curvemapping_free(node->storage);
+ BKE_curvemapping_free(static_cast<CurveMapping *>(node->storage));
}
void node_free_standard_storage(bNode *node)
@@ -49,7 +49,7 @@ void node_free_standard_storage(bNode *node)
void node_copy_curves(bNodeTree *UNUSED(dest_ntree), bNode *dest_node, const bNode *src_node)
{
- dest_node->storage = BKE_curvemapping_copy(src_node->storage);
+ dest_node->storage = BKE_curvemapping_copy(static_cast<CurveMapping *>(src_node->storage));
}
void node_copy_standard_storage(bNodeTree *UNUSED(dest_ntree),
@@ -63,7 +63,7 @@ void *node_initexec_curves(bNodeExecContext *UNUSED(context),
bNode *node,
bNodeInstanceKey UNUSED(key))
{
- BKE_curvemapping_init(node->storage);
+ BKE_curvemapping_init(static_cast<CurveMapping *>(node->storage));
return NULL; /* unused return */
}
@@ -87,9 +87,9 @@ void node_sock_label_clear(bNodeSocket *sock)
void node_math_update(bNodeTree *ntree, bNode *node)
{
- bNodeSocket *sock1 = BLI_findlink(&node->inputs, 0);
- bNodeSocket *sock2 = BLI_findlink(&node->inputs, 1);
- bNodeSocket *sock3 = BLI_findlink(&node->inputs, 2);
+ bNodeSocket *sock1 = static_cast<bNodeSocket *>(BLI_findlink(&node->inputs, 0));
+ bNodeSocket *sock2 = static_cast<bNodeSocket *>(BLI_findlink(&node->inputs, 1));
+ bNodeSocket *sock3 = static_cast<bNodeSocket *>(BLI_findlink(&node->inputs, 2));
nodeSetSocketAvailability(ntree,
sock2,
!ELEM(node->custom1,
@@ -305,7 +305,9 @@ static bNodeSocket *node_find_linkable_socket(bNodeTree *ntree,
bNode *node,
bNodeSocket *to_socket)
{
- bNodeSocket *first = to_socket->in_out == SOCK_IN ? node->inputs.first : node->outputs.first;
+ bNodeSocket *first = to_socket->in_out == SOCK_IN ?
+ static_cast<bNodeSocket *>(node->inputs.first) :
+ static_cast<bNodeSocket *>((node->outputs.first));
/* Wrap around the list end. */
bNodeSocket *socket_iter = to_socket->next ? to_socket->next : first;
diff --git a/source/blender/nodes/intern/socket_search_link.cc b/source/blender/nodes/intern/socket_search_link.cc
index 0bd838ff002..b440952b503 100644
--- a/source/blender/nodes/intern/socket_search_link.cc
+++ b/source/blender/nodes/intern/socket_search_link.cc
@@ -125,64 +125,23 @@ void search_link_ops_for_declarations(GatherLinkSearchOpParams &params,
}
}
-static void search_link_ops_for_socket_templates(GatherLinkSearchOpParams &params,
- const bNodeSocketTemplate *templates,
- const eNodeSocketInOut in_out)
-{
- const bNodeType &node_type = params.node_type();
- const bNodeTreeType &node_tree_type = *params.node_tree().typeinfo;
-
- Set<StringRef> socket_names;
- for (const bNodeSocketTemplate *socket_template = templates; socket_template->type != -1;
- socket_template++) {
- eNodeSocketDatatype from = (eNodeSocketDatatype)socket_template->type;
- eNodeSocketDatatype to = (eNodeSocketDatatype)params.other_socket().type;
- if (in_out == SOCK_IN) {
- std::swap(from, to);
- }
- if (node_tree_type.validate_link && !node_tree_type.validate_link(from, to)) {
- continue;
- }
- if (!socket_names.add(socket_template->name)) {
- /* See comment in #search_link_ops_for_declarations. */
- continue;
- }
-
- params.add_item(
- socket_template->name, [socket_template, node_type, in_out](LinkSearchOpParams &params) {
- bNode &node = params.add_node(node_type);
- bNodeSocket *new_node_socket = bke::node_find_enabled_socket(
- node, in_out, socket_template->name);
- if (new_node_socket != nullptr) {
- /* Rely on the way #nodeAddLink switches in/out if necessary. */
- nodeAddLink(&params.node_tree, &params.node, &params.socket, &node, new_node_socket);
- }
- });
- }
-}
-
void search_link_ops_for_basic_node(GatherLinkSearchOpParams &params)
{
const bNodeType &node_type = params.node_type();
+ if (!node_type.declare) {
+ return;
+ }
- if (node_type.declare) {
- if (node_type.declaration_is_dynamic) {
- /* Dynamic declarations (whatever they end up being) aren't supported
- * by this function, but still avoid a crash in release builds. */
- BLI_assert_unreachable();
- return;
- }
+ if (node_type.declaration_is_dynamic) {
+ /* Dynamic declarations (whatever they end up being) aren't supported
+ * by this function, but still avoid a crash in release builds. */
+ BLI_assert_unreachable();
+ return;
+ }
- const NodeDeclaration &declaration = *node_type.fixed_declaration;
+ const NodeDeclaration &declaration = *node_type.fixed_declaration;
- search_link_ops_for_declarations(params, declaration.sockets(params.in_out()));
- }
- else if (node_type.inputs && params.in_out() == SOCK_IN) {
- search_link_ops_for_socket_templates(params, node_type.inputs, SOCK_IN);
- }
- else if (node_type.outputs && params.in_out() == SOCK_OUT) {
- search_link_ops_for_socket_templates(params, node_type.outputs, SOCK_OUT);
- }
+ search_link_ops_for_declarations(params, declaration.sockets(params.in_out()));
}
} // namespace blender::nodes