Refactor: Nodes: return pointer instead of reference from in/output_by_identifier

This makes it possible to use these methods in cases where it's not guaranteed
that the identifier exists on a node.
This commit is contained in:
Jacques Lucke
2025-07-31 21:58:58 +02:00
parent 90b0e06fc7
commit 890ab23e0d
17 changed files with 51 additions and 53 deletions

View File

@@ -814,28 +814,28 @@ inline const bNodeSocket &bNode::output_socket(int index) const
return *this->runtime->outputs[index];
}
inline const bNodeSocket &bNode::input_by_identifier(blender::StringRef identifier) const
inline const bNodeSocket *bNode::input_by_identifier(blender::StringRef identifier) const
{
BLI_assert(blender::bke::node_tree_runtime::topology_cache_is_available(*this));
return *this->runtime->inputs_by_identifier.lookup_as(identifier);
return this->runtime->inputs_by_identifier.lookup_default_as(identifier, nullptr);
}
inline const bNodeSocket &bNode::output_by_identifier(blender::StringRef identifier) const
inline const bNodeSocket *bNode::output_by_identifier(blender::StringRef identifier) const
{
BLI_assert(blender::bke::node_tree_runtime::topology_cache_is_available(*this));
return *this->runtime->outputs_by_identifier.lookup_as(identifier);
return this->runtime->outputs_by_identifier.lookup_default_as(identifier, nullptr);
}
inline bNodeSocket &bNode::input_by_identifier(blender::StringRef identifier)
inline bNodeSocket *bNode::input_by_identifier(blender::StringRef identifier)
{
BLI_assert(blender::bke::node_tree_runtime::topology_cache_is_available(*this));
return *this->runtime->inputs_by_identifier.lookup_as(identifier);
return this->runtime->inputs_by_identifier.lookup_default_as(identifier, nullptr);
}
inline bNodeSocket &bNode::output_by_identifier(blender::StringRef identifier)
inline bNodeSocket *bNode::output_by_identifier(blender::StringRef identifier)
{
BLI_assert(blender::bke::node_tree_runtime::topology_cache_is_available(*this));
return *this->runtime->outputs_by_identifier.lookup_as(identifier);
return this->runtime->outputs_by_identifier.lookup_default_as(identifier, nullptr);
}
inline const bNodeTree &bNode::owner_tree() const

View File

@@ -18,14 +18,14 @@ GPUNodeStack &get_shader_node_input(const bNode &node,
GPUNodeStack inputs[],
const StringRef identifier)
{
return inputs[node.input_by_identifier(identifier).index()];
return inputs[node.input_by_identifier(identifier)->index()];
}
GPUNodeStack &get_shader_node_output(const bNode &node,
GPUNodeStack outputs[],
const StringRef identifier)
{
return outputs[node.output_by_identifier(identifier).index()];
return outputs[node.output_by_identifier(identifier)->index()];
}
GPUNodeLink *get_shader_node_input_link(const bNode &node,

View File

@@ -1092,7 +1092,7 @@ static wmOperatorStatus node_add_import_node_exec(bContext *C, wmOperator *op)
}
if (node) {
bNodeSocket &path_socket = node->input_by_identifier("Path");
bNodeSocket &path_socket = *node->input_by_identifier("Path");
BLI_assert(path_socket.type == SOCK_STRING);
auto *socket_data = static_cast<bNodeSocketValueString *>(path_socket.default_value);
STRNCPY(socket_data->value, path.c_str());

View File

@@ -128,7 +128,7 @@ struct GizmosUpdateParams {
template<typename T> [[nodiscard]] bool get_input_value(const StringRef identifier, T &r_value)
{
const bNodeSocket &socket = this->gizmo_node.input_by_identifier(identifier);
const bNodeSocket &socket = *this->gizmo_node.input_by_identifier(identifier);
const std::optional<T> value_opt = this->tree_log.find_primitive_socket_value<T>(socket);
if (!value_opt) {
return false;
@@ -1056,7 +1056,7 @@ static void WIDGETGROUP_geometry_nodes_refresh(const bContext *C, wmGizmoGroup *
const StringRef socket_identifier,
const FunctionRef<void(bke::SocketValueVariant &)> modify_value) {
gizmo_node_tree->ensure_topology_cache();
const bNodeSocket &socket = gizmo_node->input_by_identifier(socket_identifier);
const bNodeSocket &socket = *gizmo_node->input_by_identifier(socket_identifier);
nodes::gizmos::apply_gizmo_change(*const_cast<bContext *>(C),
const_cast<Object &>(*object_orig),

View File

@@ -82,8 +82,8 @@ void WorldData::init()
return;
}
const bNodeSocket &color_input = input_node->input_by_identifier("Color");
const bNodeSocket &strength_input = input_node->input_by_identifier("Strength");
const bNodeSocket &color_input = *input_node->input_by_identifier("Color");
const bNodeSocket &strength_input = *input_node->input_by_identifier("Strength");
float const *strength = strength_input.default_value_typed<float>();
float const *input_color = color_input.default_value_typed<float>();

View File

@@ -575,10 +575,10 @@ typedef struct bNode {
bNodeSocket &output_socket(int index);
const bNodeSocket &output_socket(int index) const;
/** Lookup socket of this node by its identifier. */
const bNodeSocket &input_by_identifier(blender::StringRef identifier) const;
const bNodeSocket &output_by_identifier(blender::StringRef identifier) const;
bNodeSocket &input_by_identifier(blender::StringRef identifier);
bNodeSocket &output_by_identifier(blender::StringRef identifier);
const bNodeSocket *input_by_identifier(blender::StringRef identifier) const;
const bNodeSocket *output_by_identifier(blender::StringRef identifier) const;
bNodeSocket *input_by_identifier(blender::StringRef identifier);
bNodeSocket *output_by_identifier(blender::StringRef identifier);
/** Lookup socket by its declaration. */
const bNodeSocket &socket_by_decl(const blender::nodes::SocketDeclaration &decl) const;
bNodeSocket &socket_by_decl(const blender::nodes::SocketDeclaration &decl);

View File

@@ -328,12 +328,12 @@ inline DOutputSocket DNode::output(int index) const
inline DInputSocket DNode::input_by_identifier(StringRef identifier) const
{
return {context_, &bnode_->input_by_identifier(identifier)};
return {context_, bnode_->input_by_identifier(identifier)};
}
inline DOutputSocket DNode::output_by_identifier(StringRef identifier) const
{
return {context_, &bnode_->output_by_identifier(identifier)};
return {context_, bnode_->output_by_identifier(identifier)};
}
/** \} */

View File

@@ -123,7 +123,7 @@ class GeoNodeExecParams {
}
if constexpr (std::is_same_v<T, SocketValueVariant>) {
BLI_assert(value.valid_for_socket(
eNodeSocketDatatype(node_.input_by_identifier(identifier).type)));
eNodeSocketDatatype(node_.input_by_identifier(identifier)->type)));
}
return value;
}
@@ -155,7 +155,7 @@ class GeoNodeExecParams {
}
if constexpr (std::is_same_v<T, SocketValueVariant>) {
BLI_assert(value.valid_for_socket(
eNodeSocketDatatype(node_.input_by_identifier(identifier).type)));
eNodeSocketDatatype(node_.input_by_identifier(identifier)->type)));
}
return value;
}
@@ -186,7 +186,7 @@ class GeoNodeExecParams {
this->check_output_access(identifier, type);
if constexpr (std::is_same_v<StoredT, SocketValueVariant>) {
BLI_assert(value.valid_for_socket(
eNodeSocketDatatype(node_.output_by_identifier(identifier).type)));
eNodeSocketDatatype(node_.output_by_identifier(identifier)->type)));
}
#endif
if constexpr (std::is_same_v<StoredT, GeometrySet>) {
@@ -278,7 +278,7 @@ class GeoNodeExecParams {
{
const int lf_index =
lf_input_for_output_bsocket_usage_[node_.output_by_identifier(output_identifier)
.index_in_all_outputs()];
->index_in_all_outputs()];
return params_.get_input<bool>(lf_index);
}
@@ -292,7 +292,7 @@ class GeoNodeExecParams {
if (!this->anonymous_attribute_output_is_required(output_identifier) && !force_create) {
return std::nullopt;
}
const bNodeSocket &output_socket = node_.output_by_identifier(output_identifier);
const bNodeSocket &output_socket = *node_.output_by_identifier(output_identifier);
return get_output_attribute_id_(output_socket.index());
}
@@ -301,9 +301,8 @@ class GeoNodeExecParams {
*/
NodeAttributeFilter get_attribute_filter(const StringRef output_identifier) const
{
const int lf_index =
lf_input_for_attribute_propagation_to_output_[node_.output_by_identifier(output_identifier)
.index_in_all_outputs()];
const int lf_index = lf_input_for_attribute_propagation_to_output_
[node_.output_by_identifier(output_identifier)->index_in_all_outputs()];
const GeometryNodesReferenceSet &set = params_.get_input<GeometryNodesReferenceSet>(lf_index);
return NodeAttributeFilter(set);
}

View File

@@ -34,7 +34,7 @@ class InverseEvalParams {
template<typename T> T get_output(const StringRef identifier) const
{
const bNodeSocket &socket = node.output_by_identifier(identifier);
const bNodeSocket &socket = *node.output_by_identifier(identifier);
if (const bke::SocketValueVariant *value = socket_values_.lookup_ptr(&socket)) {
return value->get<T>();
}
@@ -43,7 +43,7 @@ class InverseEvalParams {
template<typename T> T get_input(const StringRef identifier) const
{
const bNodeSocket &socket = node.input_by_identifier(identifier);
const bNodeSocket &socket = *node.input_by_identifier(identifier);
if (const bke::SocketValueVariant *value = socket_values_.lookup_ptr(&socket)) {
return value->get<T>();
}
@@ -52,7 +52,7 @@ class InverseEvalParams {
template<typename T> void set_input(const StringRef identifier, T value)
{
const bNodeSocket &socket = node.input_by_identifier(identifier);
const bNodeSocket &socket = *node.input_by_identifier(identifier);
updated_socket_values_.add(&socket, bke::SocketValueVariant(value));
}
};

View File

@@ -28,7 +28,7 @@ class ElemEvalParams {
template<typename T> T get_input_elem(const StringRef identifier) const
{
const bNodeSocket &socket = node.input_by_identifier(identifier);
const bNodeSocket &socket = *node.input_by_identifier(identifier);
if (const ElemVariant *elem = this->elem_by_socket_.lookup_ptr(&socket)) {
return std::get<T>(elem->elem);
}
@@ -37,7 +37,7 @@ class ElemEvalParams {
template<typename T> void set_output_elem(const StringRef identifier, T elem)
{
const bNodeSocket &socket = node.output_by_identifier(identifier);
const bNodeSocket &socket = *node.output_by_identifier(identifier);
output_elems_.append({&socket, ElemVariant{elem}});
}
};
@@ -60,7 +60,7 @@ class InverseElemEvalParams {
template<typename T> T get_output_elem(const StringRef identifier) const
{
const bNodeSocket &socket = node.output_by_identifier(identifier);
const bNodeSocket &socket = *node.output_by_identifier(identifier);
if (const ElemVariant *elem = this->elem_by_socket_.lookup_ptr(&socket)) {
return std::get<T>(elem->elem);
}
@@ -69,7 +69,7 @@ class InverseElemEvalParams {
template<typename T> void set_input_elem(const StringRef identifier, T elem)
{
const bNodeSocket &socket = node.input_by_identifier(identifier);
const bNodeSocket &socket = *node.input_by_identifier(identifier);
input_elems_.append({&socket, ElemVariant{elem}});
}
};

View File

@@ -227,10 +227,10 @@ static int node_gpu_material(GPUMaterial *material,
material, node, "node_composite_color_balance_asc_cdl", inputs, outputs);
}
case CMP_NODE_COLOR_BALANCE_WHITEPOINT: {
const bNodeSocket &input_temperature = node->input_by_identifier("Input Temperature");
const bNodeSocket &input_tint = node->input_by_identifier("Input Tint");
const bNodeSocket &output_temperature = node->input_by_identifier("Output Temperature");
const bNodeSocket &output_tint = node->input_by_identifier("Output Tint");
const bNodeSocket &input_temperature = *node->input_by_identifier("Input Temperature");
const bNodeSocket &input_tint = *node->input_by_identifier("Input Tint");
const bNodeSocket &output_temperature = *node->input_by_identifier("Output Temperature");
const bNodeSocket &output_tint = *node->input_by_identifier("Output Tint");
/* If all inputs are not linked, compute the white point matrix on the host and pass it to
* the shader. */

View File

@@ -38,7 +38,7 @@ using namespace blender::compositor;
/* The vector value is stored in the default value of the output socket. */
static float3 get_normal(const bNode &node)
{
const bNodeSocket &normal_output = node.output_by_identifier("Normal");
const bNodeSocket &normal_output = *node.output_by_identifier("Normal");
const float3 node_normal = normal_output.default_value_typed<bNodeSocketValueVector>()->value;
return math::normalize(node_normal);
}

View File

@@ -582,7 +582,7 @@ static const bNodeSocket *node_internally_linked_input(const bNodeTree & /*tree*
const bNodeSocket &output_socket)
{
/* Internal links should always map corresponding input and output sockets. */
return &node.input_by_identifier(output_socket.identifier);
return node.input_by_identifier(output_socket.identifier);
}
static void node_blend_write(const bNodeTree & /*tree*/, const bNode &node, BlendWriter &writer)

View File

@@ -173,7 +173,7 @@ static bool needs_scene_render_params(const bNodeTree &ntree)
if (node->is_muted()) {
continue;
}
const bNodeSocket &projection_matrix_socket = node->output_by_identifier("Projection Matrix");
const bNodeSocket &projection_matrix_socket = *node->output_by_identifier("Projection Matrix");
if (projection_matrix_socket.is_logically_linked()) {
return true;
}

View File

@@ -55,7 +55,7 @@ void GeoNodeExecParams::used_named_attribute(const StringRef attribute_name,
void GeoNodeExecParams::check_input_geometry_set(StringRef identifier,
const GeometrySet &geometry_set) const
{
const SocketDeclaration &decl = *node_.input_by_identifier(identifier).runtime->declaration;
const SocketDeclaration &decl = *node_.input_by_identifier(identifier)->runtime->declaration;
const decl::Geometry *geo_decl = dynamic_cast<const decl::Geometry *>(&decl);
if (geo_decl == nullptr) {
return;

View File

@@ -419,7 +419,7 @@ struct SocketUsageInferencer {
{
const NodeInContext node = socket.owner_node();
this->usage_task__with_dependent_sockets(
socket, {&node->output_by_identifier(socket->identifier)}, {}, socket.context);
socket, {node->output_by_identifier(socket->identifier)}, {}, socket.context);
}
void usage_task__input__capture_attribute_node(const SocketInContext &socket)
@@ -465,7 +465,7 @@ struct SocketUsageInferencer {
}
Vector<const bNodeSocket *, 16> dependent_sockets;
if (StringRef(socket->identifier).startswith("Input_")) {
dependent_sockets.append(&node->output_by_identifier(socket->identifier));
dependent_sockets.append(node->output_by_identifier(socket->identifier));
}
else {
/* The geometry and selection inputs are used whenever any of the zone outputs is used. */
@@ -1527,15 +1527,14 @@ InputSocketUsageParams::InputSocketUsageParams(SocketUsageInferencer &inferencer
InferenceValue InputSocketUsageParams::get_input(const StringRef identifier) const
{
const SocketInContext input_socket{compute_context_,
&this->node.input_by_identifier(identifier)};
const SocketInContext input_socket{compute_context_, this->node.input_by_identifier(identifier)};
return inferencer_.get_socket_value(input_socket);
}
bool InputSocketUsageParams::menu_input_may_be(const StringRef identifier,
const int enum_value) const
{
BLI_assert(this->node.input_by_identifier(identifier).type == SOCK_MENU);
BLI_assert(this->node.input_by_identifier(identifier)->type == SOCK_MENU);
const InferenceValue value = this->get_input(identifier);
if (value.is_unknown()) {
/* The value is unknown, so it may be the requested enum value. */

View File

@@ -89,7 +89,7 @@ NodeItem NodeParser::create_output(const std::string &name, const NodeItem &item
NodeItem NodeParser::get_input_default(const std::string &name, NodeItem::Type to_type)
{
return get_default(node_->input_by_identifier(name), to_type);
return get_default(*node_->input_by_identifier(name), to_type);
}
NodeItem NodeParser::get_input_default(int index, NodeItem::Type to_type)
@@ -99,7 +99,7 @@ NodeItem NodeParser::get_input_default(int index, NodeItem::Type to_type)
NodeItem NodeParser::get_input_link(const std::string &name, NodeItem::Type to_type)
{
return get_input_link(node_->input_by_identifier(name), to_type, false);
return get_input_link(*node_->input_by_identifier(name), to_type, false);
}
NodeItem NodeParser::get_input_link(int index, NodeItem::Type to_type)
@@ -109,7 +109,7 @@ NodeItem NodeParser::get_input_link(int index, NodeItem::Type to_type)
NodeItem NodeParser::get_input_value(const std::string &name, NodeItem::Type to_type)
{
return get_input_value(node_->input_by_identifier(name), to_type);
return get_input_value(*node_->input_by_identifier(name), to_type);
}
NodeItem NodeParser::get_input_value(int index, NodeItem::Type to_type)
@@ -119,7 +119,7 @@ NodeItem NodeParser::get_input_value(int index, NodeItem::Type to_type)
NodeItem NodeParser::get_output_default(const std::string &name, NodeItem::Type to_type)
{
return get_default(node_->output_by_identifier(name), to_type);
return get_default(*node_->output_by_identifier(name), to_type);
}
NodeItem NodeParser::get_output_default(int index, NodeItem::Type to_type)