Blender V5.0
BKE_node_tree_interface.hh
Go to the documentation of this file.
1/* SPDX-FileCopyrightText: 2023 Blender Authors
2 *
3 * SPDX-License-Identifier: GPL-2.0-or-later */
4
8
9#pragma once
10
12#include "DNA_node_types.h"
13
14#include "BKE_node.hh"
15
16#include <type_traits>
17
18#include "BLI_cache_mutex.hh"
20#include "BLI_vector_set.hh"
21
22namespace blender::bke {
23
25
27 friend bNodeTreeInterface;
28 friend bNodeTree;
29
30 private:
34 std::atomic<bool> interface_changed_ = true;
35
40 CacheMutex items_cache_mutex_;
41
42 /* Runtime topology cache for linear access to items. */
44 /* Socket-only lists for input/output access by index. */
47};
48
49namespace node_interface {
50
51namespace detail {
52
53template<typename T> static bool item_is_type(const bNodeTreeInterfaceItem &item)
54{
55 bool match = false;
58 match |= std::is_same_v<T, bNodeTreeInterfaceSocket>;
59 break;
60 }
62 match |= std::is_same_v<T, bNodeTreeInterfacePanel>;
63 break;
64 }
65 }
66 return match;
67}
68
69} // namespace detail
70
71template<typename T> T &get_item_as(bNodeTreeInterfaceItem &item)
72{
74 return reinterpret_cast<T &>(item);
75}
76
77template<typename T> const T &get_item_as(const bNodeTreeInterfaceItem &item)
78{
80 return reinterpret_cast<const T &>(item);
81}
82
83template<typename T> T *get_item_as(bNodeTreeInterfaceItem *item)
84{
85 if (item && detail::item_is_type<T>(*item)) {
86 return reinterpret_cast<T *>(item);
87 }
88 return nullptr;
89}
90
91template<typename T> const T *get_item_as(const bNodeTreeInterfaceItem *item)
92{
93 if (item && detail::item_is_type<T>(*item)) {
94 return reinterpret_cast<const T *>(item);
95 }
96 return nullptr;
97}
98
99namespace socket_types {
100
101/* Info for generating static subtypes. */
109
110/* NOTE: Socket and interface subtypes could be defined from a single central list,
111 * but makesrna cannot have a dependency on BKE, so this list would have to live in RNA itself,
112 * with BKE etc. accessing the RNA API to get the subtypes info. */
114 {"NodeSocketFloat", "NodeTreeInterfaceSocketFloat", SOCK_FLOAT, PROP_NONE},
115 {"NodeSocketFloatUnsigned", "NodeTreeInterfaceSocketFloatUnsigned", SOCK_FLOAT, PROP_UNSIGNED},
116 {"NodeSocketFloatPercentage",
117 "NodeTreeInterfaceSocketFloatPercentage",
120 {"NodeSocketFloatFactor", "NodeTreeInterfaceSocketFloatFactor", SOCK_FLOAT, PROP_FACTOR},
121 {"NodeSocketFloatAngle", "NodeTreeInterfaceSocketFloatAngle", SOCK_FLOAT, PROP_ANGLE},
122 {"NodeSocketFloatTime", "NodeTreeInterfaceSocketFloatTime", SOCK_FLOAT, PROP_TIME},
123 {"NodeSocketFloatTimeAbsolute",
124 "NodeTreeInterfaceSocketFloatTimeAbsolute",
127 {"NodeSocketFloatDistance", "NodeTreeInterfaceSocketFloatDistance", SOCK_FLOAT, PROP_DISTANCE},
128 {"NodeSocketFloatWavelength",
129 "NodeTreeInterfaceSocketFloatWavelength",
132 {"NodeSocketFloatColorTemperature",
133 "NodeTreeInterfaceSocketFloatColorTemperature",
136 {"NodeSocketFloatFrequency",
137 "NodeTreeInterfaceSocketFloatFrequency",
140 {"NodeSocketInt", "NodeTreeInterfaceSocketInt", SOCK_INT, PROP_NONE},
141 {"NodeSocketIntUnsigned", "NodeTreeInterfaceSocketIntUnsigned", SOCK_INT, PROP_UNSIGNED},
142 {"NodeSocketIntPercentage", "NodeTreeInterfaceSocketIntPercentage", SOCK_INT, PROP_PERCENTAGE},
143 {"NodeSocketIntFactor", "NodeTreeInterfaceSocketIntFactor", SOCK_INT, PROP_FACTOR},
144 {"NodeSocketBool", "NodeTreeInterfaceSocketBool", SOCK_BOOLEAN, PROP_NONE},
145
146 {"NodeSocketVector", "NodeTreeInterfaceSocketVector", SOCK_VECTOR, PROP_NONE},
147 {"NodeSocketVectorFactor", "NodeTreeInterfaceSocketVectorFactor", SOCK_VECTOR, PROP_FACTOR},
148 {"NodeSocketVectorPercentage",
149 "NodeTreeInterfaceSocketVectorPercentage",
152 {"NodeSocketVectorTranslation",
153 "NodeTreeInterfaceSocketVectorTranslation",
156 {"NodeSocketVectorDirection",
157 "NodeTreeInterfaceSocketVectorDirection",
160 {"NodeSocketVectorVelocity",
161 "NodeTreeInterfaceSocketVectorVelocity",
164 {"NodeSocketVectorAcceleration",
165 "NodeTreeInterfaceSocketVectorAcceleration",
168 {"NodeSocketVectorEuler", "NodeTreeInterfaceSocketVectorEuler", SOCK_VECTOR, PROP_EULER},
169 {"NodeSocketVectorXYZ", "NodeTreeInterfaceSocketVectorXYZ", SOCK_VECTOR, PROP_XYZ},
170
171 {"NodeSocketVector2D", "NodeTreeInterfaceSocketVector2D", SOCK_VECTOR, PROP_NONE},
172 {"NodeSocketVectorFactor2D",
173 "NodeTreeInterfaceSocketVectorFactor2D",
176 {"NodeSocketVectorPercentage2D",
177 "NodeTreeInterfaceSocketVectorPercentage2D",
180 {"NodeSocketVectorTranslation2D",
181 "NodeTreeInterfaceSocketVectorTranslation2D",
184 {"NodeSocketVectorDirection2D",
185 "NodeTreeInterfaceSocketVectorDirection2D",
188 {"NodeSocketVectorVelocity2D",
189 "NodeTreeInterfaceSocketVectorVelocity2D",
192 {"NodeSocketVectorAcceleration2D",
193 "NodeTreeInterfaceSocketVectorAcceleration2D",
196 {"NodeSocketVectorEuler2D", "NodeTreeInterfaceSocketVectorEuler2D", SOCK_VECTOR, PROP_EULER},
197 {"NodeSocketVectorXYZ2D", "NodeTreeInterfaceSocketVectorXYZ2D", SOCK_VECTOR, PROP_XYZ},
198
199 {"NodeSocketVector4D", "NodeTreeInterfaceSocketVector4D", SOCK_VECTOR, PROP_NONE},
200 {"NodeSocketVectorFactor4D",
201 "NodeTreeInterfaceSocketVectorFactor4D",
204 {"NodeSocketVectorPercentage4D",
205 "NodeTreeInterfaceSocketVectorPercentage4D",
208 {"NodeSocketVectorTranslation4D",
209 "NodeTreeInterfaceSocketVectorTranslation4D",
212 {"NodeSocketVectorDirection4D",
213 "NodeTreeInterfaceSocketVectorDirection4D",
216 {"NodeSocketVectorVelocity4D",
217 "NodeTreeInterfaceSocketVectorVelocity4D",
220 {"NodeSocketVectorAcceleration4D",
221 "NodeTreeInterfaceSocketVectorAcceleration4D",
224 {"NodeSocketVectorEuler4D", "NodeTreeInterfaceSocketVectorEuler4D", SOCK_VECTOR, PROP_EULER},
225 {"NodeSocketVectorXYZ4D", "NodeTreeInterfaceSocketVectorXYZ4D", SOCK_VECTOR, PROP_XYZ},
226
227 {"NodeSocketRotation", "NodeTreeInterfaceSocketRotation", SOCK_ROTATION, PROP_NONE},
228 {"NodeSocketMatrix", "NodeTreeInterfaceSocketMatrix", SOCK_MATRIX, PROP_NONE},
229
230 {"NodeSocketColor", "NodeTreeInterfaceSocketColor", SOCK_RGBA, PROP_NONE},
231 {"NodeSocketString", "NodeTreeInterfaceSocketString", SOCK_STRING, PROP_NONE},
232 {"NodeSocketStringFilePath",
233 "NodeTreeInterfaceSocketStringFilePath",
236 {"NodeSocketShader", "NodeTreeInterfaceSocketShader", SOCK_SHADER, PROP_NONE},
237 {"NodeSocketObject", "NodeTreeInterfaceSocketObject", SOCK_OBJECT, PROP_NONE},
238 {"NodeSocketImage", "NodeTreeInterfaceSocketImage", SOCK_IMAGE, PROP_NONE},
239 {"NodeSocketGeometry", "NodeTreeInterfaceSocketGeometry", SOCK_GEOMETRY, PROP_NONE},
240 {"NodeSocketCollection", "NodeTreeInterfaceSocketCollection", SOCK_COLLECTION, PROP_NONE},
241 {"NodeSocketTexture", "NodeTreeInterfaceSocketTexture", SOCK_TEXTURE, PROP_NONE},
242 {"NodeSocketMaterial", "NodeTreeInterfaceSocketMaterial", SOCK_MATERIAL, PROP_NONE},
243 {"NodeSocketMenu", "NodeTreeInterfaceSocketMenu", SOCK_MENU, PROP_NONE},
244 {"NodeSocketBundle", "NodeTreeInterfaceSocketBundle", SOCK_BUNDLE, PROP_NONE},
245 {"NodeSocketClosure", "NodeTreeInterfaceSocketClosure", SOCK_CLOSURE, PROP_NONE},
246};
247
248template<typename Fn> bool socket_data_to_static_type(const eNodeSocketDatatype type, const Fn &fn)
249{
250 switch (type) {
251 case SOCK_FLOAT:
252 fn.template operator()<bNodeSocketValueFloat>();
253 return true;
254 case SOCK_INT:
255 fn.template operator()<bNodeSocketValueInt>();
256 return true;
257 case SOCK_BOOLEAN:
258 fn.template operator()<bNodeSocketValueBoolean>();
259 return true;
260 case SOCK_ROTATION:
261 fn.template operator()<bNodeSocketValueRotation>();
262 return true;
263 case SOCK_VECTOR:
264 fn.template operator()<bNodeSocketValueVector>();
265 return true;
266 case SOCK_RGBA:
267 fn.template operator()<bNodeSocketValueRGBA>();
268 return true;
269 case SOCK_STRING:
270 fn.template operator()<bNodeSocketValueString>();
271 return true;
272 case SOCK_OBJECT:
273 fn.template operator()<bNodeSocketValueObject>();
274 return true;
275 case SOCK_IMAGE:
276 fn.template operator()<bNodeSocketValueImage>();
277 return true;
278 case SOCK_COLLECTION:
279 fn.template operator()<bNodeSocketValueCollection>();
280 return true;
281 case SOCK_TEXTURE:
282 fn.template operator()<bNodeSocketValueTexture>();
283 return true;
284 case SOCK_MATERIAL:
285 fn.template operator()<bNodeSocketValueMaterial>();
286 return true;
287 case SOCK_MENU:
288 fn.template operator()<bNodeSocketValueMenu>();
289 return true;
290
291 case SOCK_CUSTOM:
292 case SOCK_SHADER:
293 case SOCK_MATRIX:
294 case SOCK_GEOMETRY:
295 case SOCK_BUNDLE:
296 case SOCK_CLOSURE:
297 return true;
298 }
299 return false;
300}
301
302template<typename Fn> bool socket_data_to_static_type(const StringRef socket_type, const Fn &fn)
303{
305 if (socket_type == info.socket_identifier) {
306 return socket_data_to_static_type(info.type, fn);
307 }
308 }
309 return false;
310}
311
312namespace detail {
313
314template<typename Fn> struct TypeTagExecutor {
315 const Fn &fn;
316
317 TypeTagExecutor(const Fn &fn_) : fn(fn_) {}
318
319 template<typename T> void operator()() const
320 {
321 fn(TypeTag<T>{});
322 }
323};
324
325} // namespace detail
326
327template<typename Fn>
328void socket_data_to_static_type_tag(const StringRef socket_type, const Fn &fn)
329{
330 detail::TypeTagExecutor executor{fn};
331 socket_data_to_static_type(socket_type, executor);
332}
333
334} // namespace socket_types
335
336template<typename T> bool socket_data_is_type(const char *socket_type)
337{
338 bool match = false;
339 socket_types::socket_data_to_static_type_tag(socket_type, [&match](auto type_tag) {
340 using SocketDataType = typename decltype(type_tag)::type;
341 match |= std::is_same_v<T, SocketDataType>;
342 });
343 return match;
344}
345
347{
349 return *static_cast<T *>(item.socket_data);
350}
351
352template<typename T> const T &get_socket_data_as(const bNodeTreeInterfaceSocket &item)
353{
355 return *static_cast<const T *>(item.socket_data);
356}
357
359 const bNode &from_node,
360 const bNodeSocket &from_sock,
361 StringRef socket_type,
363
365 const bNode &from_node,
366 const bNodeSocket &from_sock,
367 const StringRef socket_type)
368{
370 ntree, from_node, from_sock, socket_type, node_socket_label(from_sock));
371}
372
374 const bNode &from_node,
375 const bNodeSocket &from_sock)
376{
378 ntree, from_node, from_sock, from_sock.typeinfo->idname, node_socket_label(from_sock));
379}
380
392
393} // namespace node_interface
394
395} // namespace blender::bke
#define BLI_assert(a)
Definition BLI_assert.h:46
eNodeSocketDatatype
@ SOCK_INT
@ SOCK_TEXTURE
@ SOCK_VECTOR
@ SOCK_CLOSURE
@ SOCK_BOOLEAN
@ SOCK_MATERIAL
@ SOCK_SHADER
@ SOCK_MATRIX
@ SOCK_FLOAT
@ SOCK_IMAGE
@ SOCK_COLLECTION
@ SOCK_CUSTOM
@ SOCK_BUNDLE
@ SOCK_GEOMETRY
@ SOCK_ROTATION
@ SOCK_OBJECT
@ SOCK_STRING
@ SOCK_RGBA
@ SOCK_MENU
PropertySubType
Definition RNA_types.hh:232
@ PROP_TIME
Definition RNA_types.hh:253
@ PROP_DIRECTION
Definition RNA_types.hh:262
@ PROP_XYZ
Definition RNA_types.hh:269
@ PROP_DISTANCE
Definition RNA_types.hh:256
@ PROP_ACCELERATION
Definition RNA_types.hh:264
@ PROP_ANGLE
Definition RNA_types.hh:252
@ PROP_TIME_ABSOLUTE
Definition RNA_types.hh:254
@ PROP_EULER
Definition RNA_types.hh:266
@ PROP_COLOR_TEMPERATURE
Definition RNA_types.hh:290
@ PROP_NONE
Definition RNA_types.hh:233
@ PROP_PERCENTAGE
Definition RNA_types.hh:250
@ PROP_FREQUENCY
Definition RNA_types.hh:292
@ PROP_FACTOR
Definition RNA_types.hh:251
@ PROP_TRANSLATION
Definition RNA_types.hh:261
@ PROP_UNSIGNED
Definition RNA_types.hh:249
@ PROP_FILEPATH
Definition RNA_types.hh:236
@ PROP_VELOCITY
Definition RNA_types.hh:263
@ PROP_WAVELENGTH
Definition RNA_types.hh:287
#define T
static bool item_is_type(const bNodeTreeInterfaceItem &item)
void socket_data_to_static_type_tag(const StringRef socket_type, const Fn &fn)
bool socket_data_to_static_type(const eNodeSocketDatatype type, const Fn &fn)
static const bNodeSocketStaticTypeInfo node_socket_subtypes[]
T & get_item_as(bNodeTreeInterfaceItem &item)
bNodeTreeInterfaceSocket * add_interface_socket_from_node(bNodeTree &ntree, const bNode &from_node, const bNodeSocket &from_sock, StringRef socket_type, StringRef name)
bool socket_data_is_type(const char *socket_type)
T & get_socket_data_as(bNodeTreeInterfaceSocket &item)
StringRefNull node_socket_label(const bNodeSocket &sock)
Definition node.cc:4996
const char * name
bNodeSocketTypeHandle * typeinfo