Files
test/source/blender/nodes/NOD_geometry_nodes_execute.hh
Jacques Lucke 80441190c6 Nodes: automatically gray out input values that don't affect the output
This patch automatically grays out input values which can't affect the output
currently. It works with inputs of group nodes, geometry nodes modifiers and
node tools.

To achieve this, it analyses the node tree and partially evaluates it to figure
out which group inputs are currently not linked to an output or are disabled by e.g.
some switch node.

Original proposal: https://devtalk.blender.org/t/dynamic-socket-visibility/31874
Related info in blog post:
https://code.blender.org/2023/11/geometry-nodes-workshop-november-2023/#dynamic-socket-visibility

Follow up task for designing a UI that allows hiding sockets: #132706

Limitations:
* The inferencing does not update correctly when a socket starts being
  animated/driven. I haven't found a good way to invalidate the cache in a good
  way reliably yet. It's only a very short term problem though. It fixes itself
  after the next modification of the node tree and is only noticeable when
  animating some specific sockets such as the switch node condition.
* Whether a socket is grayed out is not exposed in the Python API yet. That will
  be done separately.
* Only a partial evaluation is done to determine if an input affects an output.
  There should be no cases where a socket is found to be unused when it can actually
  affect the output. However, there can be cases where a socket is inferenced to be used
  even if it is not due to some complex condition. Depending on the exact circumstances,
  this can either be improved or the condition in the node tree should be simplified.

Pull Request: https://projects.blender.org/blender/blender/pulls/132219
2025-01-21 12:53:24 +01:00

83 lines
3.2 KiB
C++

/* SPDX-FileCopyrightText: 2023 Blender Authors
*
* SPDX-License-Identifier: GPL-2.0-or-later */
#pragma once
#include "BLI_compute_context.hh"
#include "BLI_function_ref.hh"
#include "BLI_generic_pointer.hh"
#include "BLI_multi_value_map.hh"
#include "BLI_resource_scope.hh"
#include "BLI_set.hh"
#include "BKE_idprop.hh"
#include "BKE_node.hh"
struct bNodeTree;
struct bNodeTreeInterfaceSocket;
namespace blender::bke {
struct GeometrySet;
}
struct IDProperty;
namespace blender::nodes {
struct GeoNodesCallData;
namespace geo_eval_log {
class GeoModifierLog;
} // namespace geo_eval_log
} // namespace blender::nodes
namespace blender::nodes {
constexpr StringRef input_use_attribute_suffix = "_use_attribute";
constexpr StringRef input_attribute_name_suffix = "_attribute_name";
std::optional<StringRef> input_attribute_name_get(const IDProperty &props,
const bNodeTreeInterfaceSocket &io_input);
/**
* \return Whether using an attribute to input values of this type is supported.
*/
bool socket_type_has_attribute_toggle(eNodeSocketDatatype type);
/**
* \return Whether using an attribute to input values of this type is supported, and the node
* group's input for this socket accepts a field rather than just single values.
*/
bool input_has_attribute_toggle(const bNodeTree &node_tree, const int socket_index);
bool id_property_type_matches_socket(const bNodeTreeInterfaceSocket &socket,
const IDProperty &property,
bool use_name_for_ids = false);
std::unique_ptr<IDProperty, bke::idprop::IDPropertyDeleter> id_property_create_from_socket(
const bNodeTreeInterfaceSocket &socket, bool use_name_for_ids);
bke::GeometrySet execute_geometry_nodes_on_geometry(const bNodeTree &btree,
const IDProperty *properties,
const ComputeContext &base_compute_context,
GeoNodesCallData &call_data,
bke::GeometrySet input_geometry);
void update_input_properties_from_node_tree(const bNodeTree &tree,
const IDProperty *old_properties,
IDProperty &properties,
bool use_name_for_ids = false);
void update_output_properties_from_node_tree(const bNodeTree &tree,
const IDProperty *old_properties,
IDProperty &properties);
/**
* Get the "base" input values that are passed into geometry nodes. In this context, "base" means
* that the retrieved input types are #bNodeSocketType::base_cpp_type (e.g. `float` for float
* sockets). If the input value can't be represented as base value, null is returned instead (e.g.
* for attribute inputs).
*/
void get_geometry_nodes_input_base_values(const bNodeTree &btree,
const IDProperty *properties,
ResourceScope &scope,
MutableSpan<GPointer> r_values);
} // namespace blender::nodes