Blender V4.5
versioning_450.cc
Go to the documentation of this file.
1/* SPDX-FileCopyrightText: 2025 Blender Authors
2 *
3 * SPDX-License-Identifier: GPL-2.0-or-later */
4
8
9#define DNA_DEPRECATED_ALLOW
10
11#include <fmt/format.h>
12
13#include "DNA_anim_types.h"
14#include "DNA_brush_types.h"
15#include "DNA_defaults.h"
16#include "DNA_light_types.h"
17#include "DNA_mesh_types.h"
18#include "DNA_modifier_types.h"
20#include "DNA_sequence_types.h"
21
22#include "BLI_listbase.h"
23#include "BLI_math_vector.h"
24#include "BLI_set.hh"
25#include "BLI_string.h"
26#include "BLI_string_utf8.h"
27#include "BLI_string_utils.hh"
28#include "BLI_sys_types.h"
29
30#include "BKE_anim_data.hh"
31#include "BKE_animsys.h"
32#include "BKE_armature.hh"
33#include "BKE_curves.hh"
34#include "BKE_customdata.hh"
35#include "BKE_fcurve.hh"
36#include "BKE_grease_pencil.hh"
37#include "BKE_idprop.hh"
38#include "BKE_lib_id.hh"
39#include "BKE_lib_query.hh"
40#include "BKE_main.hh"
42#include "BKE_node.hh"
44#include "BKE_node_runtime.hh"
45#include "BKE_paint.hh"
46
47#include "SEQ_iterator.hh"
48#include "SEQ_sequencer.hh"
49
50#include "ANIM_action.hh"
52#include "ANIM_armature_iter.hh"
53#include "BKE_colortools.hh"
54
55#include "RNA_access.hh"
56
57#include "readfile.hh"
58
59#include "versioning_common.hh"
60
61// static CLG_LogRef LOG = {"blo.readfile.doversion"};
62
64{
65 auto idprops_process = [](IDProperty **idprops, IDProperty *system_idprops) -> void {
66 if (system_idprops) {
67 /* Other ID pointers have not yet been relinked,
68 * do not try to access them for reference-counting. */
69 if (*idprops) {
70 IDP_MergeGroup_ex(*idprops, system_idprops, true, LIB_ID_CREATE_NO_USER_REFCOUNT);
71 }
72 else {
73 *idprops = IDP_CopyProperty_ex(system_idprops, LIB_ID_CREATE_NO_USER_REFCOUNT);
74 }
75 }
76 };
77
78 ID *id_iter;
79 FOREACH_MAIN_ID_BEGIN (bmain, id_iter) {
80 idprops_process(&id_iter->properties, id_iter->system_properties);
81 }
83
84 LISTBASE_FOREACH (Scene *, scene, &bmain->scenes) {
85 LISTBASE_FOREACH (ViewLayer *, view_layer, &scene->view_layers) {
86 idprops_process(&view_layer->id_properties, view_layer->system_properties);
87 }
88
89 if (scene->ed != nullptr) {
90 blender::seq::for_each_callback(&scene->ed->seqbase,
91 [&idprops_process](Strip *strip) -> bool {
92 idprops_process(&strip->prop, strip->system_properties);
93 return true;
94 });
95 }
96 }
97
98 LISTBASE_FOREACH (Object *, object, &bmain->objects) {
99 if (!object->pose) {
100 continue;
101 }
102 LISTBASE_FOREACH (bPoseChannel *, pchan, &object->pose->chanbase) {
103 idprops_process(&pchan->prop, pchan->system_properties);
104 }
105 }
106
107 LISTBASE_FOREACH (bArmature *, armature, &bmain->armatures) {
108 for (BoneCollection *bcoll : armature->collections_span()) {
109 idprops_process(&bcoll->prop, bcoll->system_properties);
110 }
111 LISTBASE_FOREACH (Bone *, bone, &armature->bonebase) {
112 idprops_process(&bone->prop, bone->system_properties);
113 }
114 }
115}
116
118{
119 LISTBASE_FOREACH (FModifier *, fcurve_modifier, &fcurve.modifiers) {
120 if (fcurve_modifier->type != FMODIFIER_TYPE_NOISE) {
121 continue;
122 }
123 FMod_Noise *data = static_cast<FMod_Noise *>(fcurve_modifier->data);
124 if (data->legacy_noise) {
125 /* We don't want to modify anything if the noise is set to legacy, because the issue only
126 * occurred on the new style noise. */
127 continue;
128 }
129 data->offset *= data->size;
130 }
131}
132
138{
139 auto fix_curves = [](blender::bke::CurvesGeometry &curves) {
140 if (curves.custom_knots != nullptr) {
141 return;
142 }
143
144 int8_t *knot_modes = static_cast<int8_t *>(CustomData_get_layer_named_for_write(
145 &curves.curve_data, CD_PROP_INT8, "knots_mode", curves.curve_num));
146 if (knot_modes == nullptr) {
147 return;
148 }
149
150 for (const int curve : curves.curves_range()) {
151 int8_t &knot_mode = knot_modes[curve];
152 if (knot_mode == NURBS_KNOT_MODE_CUSTOM) {
153 knot_mode = NURBS_KNOT_MODE_NORMAL;
154 }
155 }
156 curves.nurbs_custom_knots_update_size();
157 };
158
159 LISTBASE_FOREACH (Curves *, curves_id, &bmain->hair_curves) {
160 blender::bke::CurvesGeometry &curves = curves_id->geometry.wrap();
161 fix_curves(curves);
162 }
163
164 LISTBASE_FOREACH (GreasePencil *, grease_pencil, &bmain->grease_pencils) {
165 for (GreasePencilDrawingBase *base : grease_pencil->drawings()) {
166 if (base->type != GP_DRAWING) {
167 continue;
168 }
170 reinterpret_cast<GreasePencilDrawing *>(base)->wrap();
171 fix_curves(drawing.strokes_for_write());
172 }
173 }
174}
175
177{
178 LISTBASE_FOREACH (NlaStrip *, strip, &strips) {
179 LISTBASE_FOREACH (FCurve *, fcurve, &strip->fcurves) {
181 }
182
183 /* Check sub-strips (if meta-strips). */
185 }
186}
187
188/* The compositor Value, Color Ramp, Mix Color, Map Range, Map Value, Math, Combine XYZ, Separate
189 * XYZ, and Vector Curves nodes are now deprecated and should be replaced by their generic Shader
190 * node counterpart. */
192{
193 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
194 switch (node->type_legacy) {
195 case CMP_NODE_VALUE:
196 node->type_legacy = SH_NODE_VALUE;
197 STRNCPY(node->idname, "ShaderNodeValue");
198 break;
199 case CMP_NODE_MATH:
200 node->type_legacy = SH_NODE_MATH;
201 STRNCPY(node->idname, "ShaderNodeMath");
202 break;
204 node->type_legacy = SH_NODE_COMBXYZ;
205 STRNCPY(node->idname, "ShaderNodeCombineXYZ");
206 break;
208 node->type_legacy = SH_NODE_SEPXYZ;
209 STRNCPY(node->idname, "ShaderNodeSeparateXYZ");
210 break;
212 node->type_legacy = SH_NODE_CURVE_VEC;
213 STRNCPY(node->idname, "ShaderNodeVectorCurve");
214 break;
215 case CMP_NODE_VALTORGB: {
216 node->type_legacy = SH_NODE_VALTORGB;
217 STRNCPY(node->idname, "ShaderNodeValToRGB");
218
219 /* Compositor node uses "Image" as the output name while the shader node uses "Color" as
220 * the output name. */
221 bNodeSocket *image_output = blender::bke::node_find_socket(*node, SOCK_OUT, "Image");
222 STRNCPY(image_output->identifier, "Color");
223 STRNCPY(image_output->name, "Color");
224
225 break;
226 }
227 case CMP_NODE_MAP_RANGE: {
228 node->type_legacy = SH_NODE_MAP_RANGE;
229 STRNCPY(node->idname, "ShaderNodeMapRange");
230
231 /* Transfer options from node to NodeMapRange storage. */
233 data->clamp = node->custom1;
234 data->data_type = CD_PROP_FLOAT;
235 data->interpolation_type = NODE_MAP_RANGE_LINEAR;
236 node->storage = data;
237
238 /* Compositor node uses "Value" as the output name while the shader node uses "Result" as
239 * the output name. */
240 bNodeSocket *value_output = blender::bke::node_find_socket(*node, SOCK_OUT, "Value");
241 STRNCPY(value_output->identifier, "Result");
242 STRNCPY(value_output->name, "Result");
243
244 break;
245 }
246 case CMP_NODE_MIX_RGB: {
247 node->type_legacy = SH_NODE_MIX;
248 STRNCPY(node->idname, "ShaderNodeMix");
249
250 /* Transfer options from node to NodeShaderMix storage. */
252 data->data_type = SOCK_RGBA;
253 data->factor_mode = NODE_MIX_MODE_UNIFORM;
254 data->clamp_factor = 0;
255 data->clamp_result = node->custom2 & SHD_MIXRGB_CLAMP ? 1 : 0;
256 data->blend_type = node->custom1;
257 node->storage = data;
258
259 /* Compositor node uses "Fac", "Image", and ("Image" "Image_001") as socket names and
260 * identifiers while the shader node uses ("Factor", "Factor_Float"), ("A", "A_Color"),
261 * ("B", "B_Color"), and ("Result", "Result_Color") as socket names and identifiers. */
262 bNodeSocket *factor_input = blender::bke::node_find_socket(*node, SOCK_IN, "Fac");
263 STRNCPY(factor_input->identifier, "Factor_Float");
264 STRNCPY(factor_input->name, "Factor");
265 bNodeSocket *first_input = blender::bke::node_find_socket(*node, SOCK_IN, "Image");
266 STRNCPY(first_input->identifier, "A_Color");
267 STRNCPY(first_input->name, "A");
268 bNodeSocket *second_input = blender::bke::node_find_socket(*node, SOCK_IN, "Image_001");
269 STRNCPY(second_input->identifier, "B_Color");
270 STRNCPY(second_input->name, "B");
271 bNodeSocket *image_output = blender::bke::node_find_socket(*node, SOCK_OUT, "Image");
272 STRNCPY(image_output->identifier, "Result_Color");
273 STRNCPY(image_output->name, "Result");
274
275 break;
276 }
277 default:
278 break;
279 }
280 }
281}
282
283/* The Use Alpha option is does not exist in the new generic Mix node, it essentially just
284 * multiplied the factor by the alpha of the second input. */
285static void do_version_mix_color_use_alpha(bNodeTree *node_tree, bNode *node)
286{
287 if (!(node->custom2 & SHD_MIXRGB_USE_ALPHA)) {
288 return;
289 }
290
291 bNodeSocket *factor_input = blender::bke::node_find_socket(*node, SOCK_IN, "Factor_Float");
292 bNodeSocket *b_input = blender::bke::node_find_socket(*node, SOCK_IN, "B_Color");
293
294 /* Find the links going into the factor and B input of the Mix node. */
295 bNodeLink *factor_link = nullptr;
296 bNodeLink *b_link = nullptr;
297 LISTBASE_FOREACH (bNodeLink *, link, &node_tree->links) {
298 if (link->tosock == factor_input) {
299 factor_link = link;
300 }
301 else if (link->tosock == b_input) {
302 b_link = link;
303 }
304 }
305
306 /* If neither sockets are connected, just multiply the factor by the alpha of the B input. */
307 if (!factor_link && !b_link) {
308 static_cast<bNodeSocketValueFloat *>(factor_input->default_value)->value *=
309 static_cast<bNodeSocketValueRGBA *>(b_input->default_value)->value[3];
310 return;
311 }
312
313 /* Otherwise, add a multiply node to do the multiplication. */
314 bNode *multiply_node = blender::bke::node_add_static_node(nullptr, *node_tree, SH_NODE_MATH);
315 multiply_node->parent = node->parent;
316 multiply_node->custom1 = NODE_MATH_MULTIPLY;
317 multiply_node->location[0] = node->location[0] - node->width - 20.0f;
318 multiply_node->location[1] = node->location[1];
319 multiply_node->flag |= NODE_HIDDEN;
320
321 bNodeSocket *multiply_input_a = static_cast<bNodeSocket *>(
322 BLI_findlink(&multiply_node->inputs, 0));
323 bNodeSocket *multiply_input_b = static_cast<bNodeSocket *>(
324 BLI_findlink(&multiply_node->inputs, 1));
325 bNodeSocket *multiply_output = blender::bke::node_find_socket(*multiply_node, SOCK_OUT, "Value");
326
327 /* Connect the output of the multiply node to the math node. */
328 version_node_add_link(*node_tree, *multiply_node, *multiply_output, *node, *factor_input);
329
330 if (factor_link) {
331 /* The factor input is linked, so connect its origin to the first input of the multiply and
332 * remove the original link. */
333 version_node_add_link(*node_tree,
334 *factor_link->fromnode,
335 *factor_link->fromsock,
336 *multiply_node,
337 *multiply_input_a);
338 blender::bke::node_remove_link(node_tree, *factor_link);
339 }
340 else {
341 /* Otherwise, the factor is unlinked and we just copy the factor value to the first input in
342 * the multiply.*/
343 static_cast<bNodeSocketValueFloat *>(multiply_input_a->default_value)->value =
344 static_cast<bNodeSocketValueFloat *>(factor_input->default_value)->value;
345 }
346
347 if (b_link) {
348 /* The B input is linked, so extract the alpha of its origin and connect it to the second input
349 * of the multiply and remove the original link. */
350 bNode *separate_color_node = blender::bke::node_add_static_node(
351 nullptr, *node_tree, CMP_NODE_SEPARATE_COLOR);
352 separate_color_node->parent = node->parent;
353 separate_color_node->location[0] = multiply_node->location[0] - multiply_node->width - 20.0f;
354 separate_color_node->location[1] = multiply_node->location[1];
355 separate_color_node->flag |= NODE_HIDDEN;
356
358 *separate_color_node, SOCK_IN, "Image");
360 *separate_color_node, SOCK_OUT, "Alpha");
361
363 *node_tree, *b_link->fromnode, *b_link->fromsock, *separate_color_node, *image_input);
365 *node_tree, *separate_color_node, *alpha_output, *multiply_node, *multiply_input_b);
366 }
367 else {
368 /* Otherwise, the B input is unlinked and we just copy the alpha value to the second input in
369 * the multiply.*/
370 static_cast<bNodeSocketValueFloat *>(multiply_input_b->default_value)->value =
371 static_cast<bNodeSocketValueRGBA *>(b_input->default_value)->value[3];
372 }
373
375}
376
377/* The Map Value node is now deprecated and should be replaced by other nodes. The node essentially
378 * just computes (value + offset) * size and clamps based on min and max. */
379static void do_version_map_value_node(bNodeTree *node_tree, bNode *node)
380{
381 const TexMapping &texture_mapping = *static_cast<TexMapping *>(node->storage);
382 const bool use_min = texture_mapping.flag & TEXMAP_CLIP_MIN;
383 const bool use_max = texture_mapping.flag & TEXMAP_CLIP_MAX;
384 const float offset = texture_mapping.loc[0];
385 const float size = texture_mapping.size[0];
386 const float min = texture_mapping.min[0];
387 const float max = texture_mapping.max[0];
388
389 bNodeSocket *value_input = blender::bke::node_find_socket(*node, SOCK_IN, "Value");
390
391 /* Find the link going into the value input Map Value node. */
392 bNodeLink *value_link = nullptr;
393 LISTBASE_FOREACH (bNodeLink *, link, &node_tree->links) {
394 if (link->tosock == value_input) {
395 value_link = link;
396 }
397 }
398
399 /* If the value input is not connected, add a value node with the computed value. */
400 if (!value_link) {
401 const float value = static_cast<bNodeSocketValueFloat *>(value_input->default_value)->value;
402 const float mapped_value = (value + offset) * size;
403 const float min_clamped_value = use_min ? blender::math::max(mapped_value, min) : mapped_value;
404 const float clamped_value = use_max ? blender::math::min(min_clamped_value, max) :
405 min_clamped_value;
406
407 bNode *value_node = blender::bke::node_add_static_node(nullptr, *node_tree, SH_NODE_VALUE);
408 value_node->parent = node->parent;
409 value_node->location[0] = node->location[0];
410 value_node->location[1] = node->location[1];
411
412 bNodeSocket *value_output = blender::bke::node_find_socket(*value_node, SOCK_OUT, "Value");
413 static_cast<bNodeSocketValueFloat *>(value_output->default_value)->value = clamped_value;
414
415 /* Relink from the Map Value node to the value node. */
416 LISTBASE_FOREACH_BACKWARD_MUTABLE (bNodeLink *, link, &node_tree->links) {
417 if (link->fromnode != node) {
418 continue;
419 }
420
421 version_node_add_link(*node_tree, *value_node, *value_output, *link->tonode, *link->tosock);
422 blender::bke::node_remove_link(node_tree, *link);
423 }
424
425 blender::bke::node_remove_node(nullptr, *node_tree, *node, false);
426
428 return;
429 }
430
431 /* Otherwise, add math nodes to do the computation, starting with an add node to add the offset
432 * of the range. */
434 add_node->parent = node->parent;
435 add_node->custom1 = NODE_MATH_ADD;
436 add_node->location[0] = node->location[0];
437 add_node->location[1] = node->location[1];
438 add_node->flag |= NODE_HIDDEN;
439
440 bNodeSocket *add_input_a = static_cast<bNodeSocket *>(BLI_findlink(&add_node->inputs, 0));
441 bNodeSocket *add_input_b = static_cast<bNodeSocket *>(BLI_findlink(&add_node->inputs, 1));
443
444 /* Connect the origin of the node to the first input of the add node and remove the original
445 * link. */
447 *node_tree, *value_link->fromnode, *value_link->fromsock, *add_node, *add_input_a);
448 blender::bke::node_remove_link(node_tree, *value_link);
449
450 /* Set the offset to the second input of the add node. */
451 static_cast<bNodeSocketValueFloat *>(add_input_b->default_value)->value = offset;
452
453 /* Add a multiply node to multiply by the size. */
454 bNode *multiply_node = blender::bke::node_add_static_node(nullptr, *node_tree, SH_NODE_MATH);
455 multiply_node->parent = node->parent;
456 multiply_node->custom1 = NODE_MATH_MULTIPLY;
457 multiply_node->location[0] = add_node->location[0];
458 multiply_node->location[1] = add_node->location[1] - 40.0f;
459 multiply_node->flag |= NODE_HIDDEN;
460
461 bNodeSocket *multiply_input_a = static_cast<bNodeSocket *>(
462 BLI_findlink(&multiply_node->inputs, 0));
463 bNodeSocket *multiply_input_b = static_cast<bNodeSocket *>(
464 BLI_findlink(&multiply_node->inputs, 1));
465 bNodeSocket *multiply_output = blender::bke::node_find_socket(*multiply_node, SOCK_OUT, "Value");
466
467 /* Connect the output of the add node to the first input of the multiply node. */
468 version_node_add_link(*node_tree, *add_node, *add_output, *multiply_node, *multiply_input_a);
469
470 /* Set the size to the second input of the multiply node. */
471 static_cast<bNodeSocketValueFloat *>(multiply_input_b->default_value)->value = size;
472
473 bNode *final_node = multiply_node;
474 bNodeSocket *final_output = multiply_output;
475
476 if (use_min) {
477 /* Add a maximum node to clamp by the minimum. */
478 bNode *max_node = blender::bke::node_add_static_node(nullptr, *node_tree, SH_NODE_MATH);
479 max_node->parent = node->parent;
480 max_node->custom1 = NODE_MATH_MAXIMUM;
481 max_node->location[0] = final_node->location[0];
482 max_node->location[1] = final_node->location[1] - 40.0f;
483 max_node->flag |= NODE_HIDDEN;
484
485 bNodeSocket *max_input_a = static_cast<bNodeSocket *>(BLI_findlink(&max_node->inputs, 0));
486 bNodeSocket *max_input_b = static_cast<bNodeSocket *>(BLI_findlink(&max_node->inputs, 1));
487 bNodeSocket *max_output = blender::bke::node_find_socket(*max_node, SOCK_OUT, "Value");
488
489 /* Connect the output of the final node to the first input of the maximum node. */
490 version_node_add_link(*node_tree, *final_node, *final_output, *max_node, *max_input_a);
491
492 /* Set the minimum to the second input of the maximum node. */
493 static_cast<bNodeSocketValueFloat *>(max_input_b->default_value)->value = min;
494
495 final_node = max_node;
496 final_output = max_output;
497 }
498
499 if (use_max) {
500 /* Add a minimum node to clamp by the maximum. */
501 bNode *min_node = blender::bke::node_add_static_node(nullptr, *node_tree, SH_NODE_MATH);
502 min_node->parent = node->parent;
503 min_node->custom1 = NODE_MATH_MINIMUM;
504 min_node->location[0] = final_node->location[0];
505 min_node->location[1] = final_node->location[1] - 40.0f;
506 min_node->flag |= NODE_HIDDEN;
507
508 bNodeSocket *min_input_a = static_cast<bNodeSocket *>(BLI_findlink(&min_node->inputs, 0));
509 bNodeSocket *min_input_b = static_cast<bNodeSocket *>(BLI_findlink(&min_node->inputs, 1));
510 bNodeSocket *min_output = blender::bke::node_find_socket(*min_node, SOCK_OUT, "Value");
511
512 /* Connect the output of the final node to the first input of the minimum node. */
513 version_node_add_link(*node_tree, *final_node, *final_output, *min_node, *min_input_a);
514
515 /* Set the maximum to the second input of the minimum node. */
516 static_cast<bNodeSocketValueFloat *>(min_input_b->default_value)->value = max;
517
518 final_node = min_node;
519 final_output = min_output;
520 }
521
522 /* Relink from the Map Value node to the final node. */
523 LISTBASE_FOREACH_BACKWARD_MUTABLE (bNodeLink *, link, &node_tree->links) {
524 if (link->fromnode != node) {
525 continue;
526 }
527
528 version_node_add_link(*node_tree, *final_node, *final_output, *link->tonode, *link->tosock);
529 blender::bke::node_remove_link(node_tree, *link);
530 }
531
532 blender::bke::node_remove_node(nullptr, *node_tree, *node, false);
533
535}
536
537/* Equivalent to do_version_convert_to_generic_nodes but performed after linking for handing things
538 * like animation or node construction. */
540 bNodeTree *node_tree,
541 ID *id)
542{
543 LISTBASE_FOREACH_MUTABLE (bNode *, node, &node_tree->nodes) {
544 char escaped_node_name[sizeof(node->name) * 2 + 1];
545 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
546 const std::string rna_path_prefix = fmt::format("nodes[\"{}\"].inputs", escaped_node_name);
547
548 switch (node->type_legacy) {
549 /* Notice that we use the shader type because the node is already converted in versioning
550 * before linking. */
551 case SH_NODE_CURVE_VEC: {
552 /* The node gained a new Factor input as a first socket, so the vector socket moved to be
553 * the second socket and we need to transfer its animation as well. */
555 bmain, id, rna_path_prefix.c_str(), nullptr, nullptr, 0, 1, false);
556 break;
557 }
558 /* Notice that we use the shader type because the node is already converted in versioning
559 * before linking. */
560 case SH_NODE_MIX: {
561 /* The node gained multiple new sockets after the factor socket, so the second and third
562 * sockets moved to be the 7th and 8th sockets. */
564 bmain, id, rna_path_prefix.c_str(), nullptr, nullptr, 1, 6, false);
566 bmain, id, rna_path_prefix.c_str(), nullptr, nullptr, 2, 7, false);
567
568 do_version_mix_color_use_alpha(node_tree, node);
569
570 break;
571 }
572 case CMP_NODE_MAP_VALUE: {
573 do_version_map_value_node(node_tree, node);
574 break;
575 }
576 default:
577 break;
578 }
579 }
580}
581
582/* A new Clamp boolean input was added that either enables clamping or disables it. Previously,
583 * Clamp was disabled when the maximum was zero. So we enable Clamp for non zero or linked maximum
584 * input. */
586{
587 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
588 if (node->type_legacy != CMP_NODE_GLARE) {
589 continue;
590 }
591
592 bNodeSocket *clamp_input = blender::bke::node_find_socket(*node, SOCK_IN, "Clamp Highlights");
594 *node, SOCK_IN, "Maximum Highlights");
595
596 const float maximum = maximum_input->default_value_typed<bNodeSocketValueFloat>()->value;
597 if (version_node_socket_is_used(maximum_input) || maximum != 0.0) {
598 clamp_input->default_value_typed<bNodeSocketValueBoolean>()->value = true;
599 }
600 }
601}
602
603/* The Rotate Star 45 option was converted into a Diagonal Star input. */
605{
606 NodeGlare *storage = static_cast<NodeGlare *>(node->storage);
607 if (!storage) {
608 return;
609 }
610
611 /* Input already exists, was already versioned. */
612 if (blender::bke::node_find_socket(*node, SOCK_IN, "Diagonal Star")) {
613 return;
614 }
615
617 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Diagonal Star", "Diagonal");
618 diagonal_star_input->default_value_typed<bNodeSocketValueBoolean>()->value = storage->star_45;
619}
620
621/* The Rotate Star 45 option was converted into a Diagonal Star input. */
623 bNode *node)
624{
625 /* Compute the RNA path of the node. */
626 char escaped_node_name[sizeof(node->name) * 2 + 1];
627 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
628 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
629
630 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
631 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
632 * path. */
633 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
634 return;
635 }
636
637 /* Change the RNA path of the FCurve from the old property to the new input. */
638 if (BLI_str_endswith(fcurve->rna_path, "use_rotate_45")) {
639 MEM_freeN(fcurve->rna_path);
640 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[14].default_value");
641 }
642 });
643}
644
645/* The options were converted into inputs. */
647{
648 NodeBokehImage *storage = static_cast<NodeBokehImage *>(node->storage);
649 if (!storage) {
650 return;
651 }
652
653 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Flaps")) {
655 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Flaps", "Flaps");
656 input->default_value_typed<bNodeSocketValueInt>()->value = storage->flaps;
657 }
658
659 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Angle")) {
661 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_ANGLE, "Angle", "Angle");
662 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->angle;
663 }
664
665 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Roundness")) {
667 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Roundness", "Roundness");
668 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->rounding;
669 }
670
671 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Catadioptric Size")) {
673 *node,
674 SOCK_IN,
677 "Catadioptric Size",
678 "Catadioptric Size");
679 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->catadioptric;
680 }
681
682 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Color Shift")) {
684 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Color Shift", "Color Shift");
685 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->lensshift;
686 }
687
688 MEM_freeN(storage);
689 node->storage = nullptr;
690}
691
692/* The options were converted into inputs. */
694 bNode *node)
695{
696 /* Compute the RNA path of the node. */
697 char escaped_node_name[sizeof(node->name) * 2 + 1];
698 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
699 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
700
701 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
702 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
703 * path. */
704 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
705 return;
706 }
707
708 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
709 * values of the FCurves frames when needed. */
710 char *old_rna_path = fcurve->rna_path;
711 if (BLI_str_endswith(fcurve->rna_path, "flaps")) {
712 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[0].default_value");
713 }
714 else if (BLI_str_endswith(fcurve->rna_path, "angle")) {
715 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
716 }
717 else if (BLI_str_endswith(fcurve->rna_path, "rounding")) {
718 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
719 }
720 else if (BLI_str_endswith(fcurve->rna_path, "catadioptric")) {
721 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
722 }
723 else if (BLI_str_endswith(fcurve->rna_path, "shift")) {
724 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
725 }
726
727 /* The RNA path was changed, free the old path. */
728 if (fcurve->rna_path != old_rna_path) {
729 MEM_freeN(old_rna_path);
730 }
731 });
732}
733
734/* The options were converted into inputs. */
736{
737 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Start Frame")) {
739 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Start Frame", "Start Frame");
740 input->default_value_typed<bNodeSocketValueInt>()->value = node->custom1;
741 }
742
743 if (!blender::bke::node_find_socket(*node, SOCK_IN, "End Frame")) {
745 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "End Frame", "End Frame");
746 input->default_value_typed<bNodeSocketValueInt>()->value = node->custom2;
747 }
748}
749
750/* The options were converted into inputs. */
752 bNode *node)
753{
754 /* Compute the RNA path of the node. */
755 char escaped_node_name[sizeof(node->name) * 2 + 1];
756 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
757 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
758
759 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
760 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
761 * path. */
762 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
763 return;
764 }
765
766 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
767 * values of the FCurves frames when needed. */
768 char *old_rna_path = fcurve->rna_path;
769 if (BLI_str_endswith(fcurve->rna_path, "frame_start")) {
770 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[0].default_value");
771 }
772 else if (BLI_str_endswith(fcurve->rna_path, "frame_end")) {
773 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
774 }
775
776 /* The RNA path was changed, free the old path. */
777 if (fcurve->rna_path != old_rna_path) {
778 MEM_freeN(old_rna_path);
779 }
780 });
781}
782
783/* The options were converted into inputs. */
785{
786 NodeMask *storage = static_cast<NodeMask *>(node->storage);
787 if (!storage) {
788 return;
789 }
790
791 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Size X")) {
793 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Size X", "Size X");
794 input->default_value_typed<bNodeSocketValueInt>()->value = storage->size_x;
795 }
796
797 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Size Y")) {
799 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Size Y", "Size Y");
800 input->default_value_typed<bNodeSocketValueInt>()->value = storage->size_y;
801 }
802
803 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Feather")) {
805 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Feather", "Feather");
806 input->default_value_typed<bNodeSocketValueBoolean>()->value = !(
808 }
809
810 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Motion Blur")) {
812 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Motion Blur", "Motion Blur");
813 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(
815 }
816
817 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Motion Blur Samples")) {
819 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Motion Blur Samples", "Samples");
820 input->default_value_typed<bNodeSocketValueInt>()->value = node->custom2;
821 }
822
823 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Motion Blur Shutter")) {
825 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Motion Blur Shutter", "Shutter");
826 input->default_value_typed<bNodeSocketValueFloat>()->value = node->custom3;
827 }
828
829 MEM_freeN(storage);
830 node->storage = nullptr;
831}
832
833/* The options were converted into inputs. */
835{
836 /* Compute the RNA path of the node. */
837 char escaped_node_name[sizeof(node->name) * 2 + 1];
838 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
839 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
840
841 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
842 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
843 * path. */
844 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
845 return;
846 }
847
848 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
849 * values of the FCurves frames when needed. */
850 char *old_rna_path = fcurve->rna_path;
851 if (BLI_str_endswith(fcurve->rna_path, "size_x")) {
852 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[0].default_value");
853 }
854 else if (BLI_str_endswith(fcurve->rna_path, "size_y")) {
855 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
856 }
857 else if (BLI_str_endswith(fcurve->rna_path, "use_feather")) {
858 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
859 }
860 else if (BLI_str_endswith(fcurve->rna_path, "use_motion_blur")) {
861 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
862 }
863 else if (BLI_str_endswith(fcurve->rna_path, "motion_blur_samples")) {
864 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
865 }
866 else if (BLI_str_endswith(fcurve->rna_path, "motion_blur_shutter")) {
867 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[5].default_value");
868 }
869
870 /* The RNA path was changed, free the old path. */
871 if (fcurve->rna_path != old_rna_path) {
872 MEM_freeN(old_rna_path);
873 }
874 });
875}
876
877/* The options were converted into inputs. */
879{
880 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Switch")) {
882 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Switch", "Switch");
883 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(node->custom1);
884 }
885}
886
887/* The options were converted into inputs. */
889{
890 /* Compute the RNA path of the node. */
891 char escaped_node_name[sizeof(node->name) * 2 + 1];
892 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
893 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
894
895 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
896 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
897 * path. */
898 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
899 return;
900 }
901
902 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
903 * values of the FCurves frames when needed. */
904 char *old_rna_path = fcurve->rna_path;
905 if (BLI_str_endswith(fcurve->rna_path, "check")) {
906 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[0].default_value");
907 }
908 else if (BLI_str_endswith(fcurve->rna_path, "inputs[0].default_value")) {
909 /* The new input was added at the start, so offset the animation indices by 1. */
910 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
911 }
912 else if (BLI_str_endswith(fcurve->rna_path, "inputs[1].default_value")) {
913 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
914 }
915
916 /* The RNA path was changed, free the old path. */
917 if (fcurve->rna_path != old_rna_path) {
918 MEM_freeN(old_rna_path);
919 }
920 });
921}
922
923/* The options were converted into inputs. */
925{
926 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Factor")) {
928 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Factor", "Factor");
929 input->default_value_typed<bNodeSocketValueFloat>()->value = node->custom1 / 100.0f;
930 }
931}
932
933/* The options were converted into inputs. */
935{
936 /* Compute the RNA path of the node. */
937 char escaped_node_name[sizeof(node->name) * 2 + 1];
938 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
939 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
940
941 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
942 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
943 * path. */
944 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
945 return;
946 }
947
948 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
949 * values of the FCurves frames when needed. */
950 char *old_rna_path = fcurve->rna_path;
951 if (BLI_str_endswith(fcurve->rna_path, "factor")) {
952 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[0].default_value");
953 adjust_fcurve_key_frame_values(
954 fcurve, PROP_FLOAT, [&](const float value) { return value / 100.0f; });
955 }
956 else if (BLI_str_endswith(fcurve->rna_path, "inputs[0].default_value")) {
957 /* The new input was added at the start, so offset the animation indices by 1. */
958 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
959 }
960 else if (BLI_str_endswith(fcurve->rna_path, "inputs[1].default_value")) {
961 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
962 }
963
964 /* The RNA path was changed, free the old path. */
965 if (fcurve->rna_path != old_rna_path) {
966 MEM_freeN(old_rna_path);
967 }
968 });
969}
970
971/* The options were converted into inputs. */
973{
974 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Invert Color")) {
976 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Invert Color", "Invert Color");
977 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(node->custom1 &
979 }
980
981 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Invert Alpha")) {
983 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Invert Alpha", "Invert Alpha");
984 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(node->custom1 &
985 CMP_CHAN_A);
986 }
987}
988
989/* The options were converted into inputs. */
991{
992 /* Compute the RNA path of the node. */
993 char escaped_node_name[sizeof(node->name) * 2 + 1];
994 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
995 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
996
997 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
998 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
999 * path. */
1000 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1001 return;
1002 }
1003
1004 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1005 * values of the FCurves frames when needed. */
1006 char *old_rna_path = fcurve->rna_path;
1007 if (BLI_str_endswith(fcurve->rna_path, "invert_rgb")) {
1008 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
1009 }
1010 else if (BLI_str_endswith(fcurve->rna_path, "invert_alpha")) {
1011 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
1012 }
1013
1014 /* The RNA path was changed, free the old path. */
1015 if (fcurve->rna_path != old_rna_path) {
1016 MEM_freeN(old_rna_path);
1017 }
1018 });
1019}
1020
1021/* The options were converted into inputs. */
1023{
1024 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Use Alpha")) {
1026 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Use Alpha", "Use Alpha");
1027 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(node->custom1);
1028 }
1029
1030 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Anti-Alias")) {
1032 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Anti-Alias", "Anti-Alias");
1033 input->default_value_typed<bNodeSocketValueBoolean>()->value = !bool(node->custom2);
1034 }
1035}
1036
1037/* The options were converted into inputs. */
1039 bNode *node)
1040{
1041 /* Compute the RNA path of the node. */
1042 char escaped_node_name[sizeof(node->name) * 2 + 1];
1043 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1044 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1045
1046 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1047 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1048 * path. */
1049 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1050 return;
1051 }
1052
1053 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1054 * values of the FCurves frames when needed. */
1055 char *old_rna_path = fcurve->rna_path;
1056 if (BLI_str_endswith(fcurve->rna_path, "use_alpha")) {
1057 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
1058 }
1059 else if (BLI_str_endswith(fcurve->rna_path, "use_antialias_z")) {
1060 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[5].default_value");
1061 }
1062
1063 /* The RNA path was changed, free the old path. */
1064 if (fcurve->rna_path != old_rna_path) {
1065 MEM_freeN(old_rna_path);
1066 }
1067 });
1068}
1069
1070/* The options were converted into inputs. */
1072{
1073 NodeTonemap *storage = static_cast<NodeTonemap *>(node->storage);
1074 if (!storage) {
1075 return;
1076 }
1077
1078 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Key")) {
1080 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "Key", "Key");
1081 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->key;
1082 }
1083
1084 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Balance")) {
1086 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "Balance", "Balance");
1087 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->offset;
1088 }
1089
1090 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Gamma")) {
1092 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "Gamma", "Gamma");
1093 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->gamma;
1094 }
1095
1096 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Intensity")) {
1098 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "Intensity", "Intensity");
1099 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->f;
1100 }
1101
1102 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Contrast")) {
1104 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "Contrast", "Contrast");
1105 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->m;
1106 }
1107
1108 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Light Adaptation")) {
1110 *node,
1111 SOCK_IN,
1112 SOCK_FLOAT,
1114 "Light Adaptation",
1115 "Light Adaptation");
1116 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->a;
1117 }
1118
1119 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Chromatic Adaptation")) {
1121 *node,
1122 SOCK_IN,
1123 SOCK_FLOAT,
1125 "Chromatic Adaptation",
1126 "Chromatic Adaptation");
1127 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->c;
1128 }
1129}
1130
1131/* The options were converted into inputs. */
1133{
1134 /* Compute the RNA path of the node. */
1135 char escaped_node_name[sizeof(node->name) * 2 + 1];
1136 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1137 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1138
1139 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1140 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1141 * path. */
1142 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1143 return;
1144 }
1145
1146 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1147 * values of the FCurves frames when needed. */
1148 char *old_rna_path = fcurve->rna_path;
1149 if (BLI_str_endswith(fcurve->rna_path, "key")) {
1150 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
1151 }
1152 else if (BLI_str_endswith(fcurve->rna_path, "offset")) {
1153 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
1154 }
1155 else if (BLI_str_endswith(fcurve->rna_path, "gamma")) {
1156 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
1157 }
1158 else if (BLI_str_endswith(fcurve->rna_path, "intensity")) {
1159 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
1160 }
1161 else if (BLI_str_endswith(fcurve->rna_path, "contrast")) {
1162 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[5].default_value");
1163 }
1164 else if (BLI_str_endswith(fcurve->rna_path, "adaptation")) {
1165 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[6].default_value");
1166 }
1167 else if (BLI_str_endswith(fcurve->rna_path, "correction")) {
1168 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[7].default_value");
1169 }
1170
1171 /* The RNA path was changed, free the old path. */
1172 if (fcurve->rna_path != old_rna_path) {
1173 MEM_freeN(old_rna_path);
1174 }
1175 });
1176}
1177
1178/* The options were converted into inputs. */
1180{
1181 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Size")) {
1183 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Size", "Size");
1184 input->default_value_typed<bNodeSocketValueInt>()->value = node->custom2;
1185 }
1186
1187 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Falloff Size")) {
1189 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "Falloff Size", "Falloff Size");
1190 input->default_value_typed<bNodeSocketValueFloat>()->value = node->custom3;
1191 }
1192}
1193
1194/* The options were converted into inputs. */
1196{
1197 /* Compute the RNA path of the node. */
1198 char escaped_node_name[sizeof(node->name) * 2 + 1];
1199 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1200 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1201
1202 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1203 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1204 * path. */
1205 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1206 return;
1207 }
1208
1209 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1210 * values of the FCurves frames when needed. */
1211 char *old_rna_path = fcurve->rna_path;
1212 if (BLI_str_endswith(fcurve->rna_path, "distance")) {
1213 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
1214 }
1215 else if (BLI_str_endswith(fcurve->rna_path, "edge")) {
1216 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
1217 }
1218
1219 /* The RNA path was changed, free the old path. */
1220 if (fcurve->rna_path != old_rna_path) {
1221 MEM_freeN(old_rna_path);
1222 }
1223 });
1224}
1225
1226/* The options were converted into inputs. */
1228{
1229 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Size")) {
1231 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Size", "Size");
1232 input->default_value_typed<bNodeSocketValueInt>()->value = node->custom2;
1233 }
1234}
1235
1236/* The options were converted into inputs. */
1238{
1239 /* Compute the RNA path of the node. */
1240 char escaped_node_name[sizeof(node->name) * 2 + 1];
1241 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1242 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1243
1244 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1245 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1246 * path. */
1247 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1248 return;
1249 }
1250
1251 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1252 * values of the FCurves frames when needed. */
1253 char *old_rna_path = fcurve->rna_path;
1254 if (BLI_str_endswith(fcurve->rna_path, "distance")) {
1255 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
1256 }
1257
1258 /* The RNA path was changed, free the old path. */
1259 if (fcurve->rna_path != old_rna_path) {
1260 MEM_freeN(old_rna_path);
1261 }
1262 });
1263}
1264
1265/* The options were converted into inputs. */
1267{
1268 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Size")) {
1270 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Size", "Size");
1271 input->default_value_typed<bNodeSocketValueInt>()->value = node->custom1;
1272 }
1273}
1274
1275/* The options were converted into inputs. */
1277{
1278 /* Compute the RNA path of the node. */
1279 char escaped_node_name[sizeof(node->name) * 2 + 1];
1280 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1281 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1282
1283 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1284 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1285 * path. */
1286 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1287 return;
1288 }
1289
1290 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1291 * values of the FCurves frames when needed. */
1292 char *old_rna_path = fcurve->rna_path;
1293 if (BLI_str_endswith(fcurve->rna_path, "pixel_size")) {
1294 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
1295 }
1296
1297 /* The RNA path was changed, free the old path. */
1298 if (fcurve->rna_path != old_rna_path) {
1299 MEM_freeN(old_rna_path);
1300 }
1301 });
1302}
1303
1304/* The options were converted into inputs. */
1306{
1307 NodeKuwaharaData *storage = static_cast<NodeKuwaharaData *>(node->storage);
1308 if (!storage) {
1309 return;
1310 }
1311
1312 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Uniformity")) {
1314 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Uniformity", "Uniformity");
1315 input->default_value_typed<bNodeSocketValueInt>()->value = storage->uniformity;
1316 }
1317
1318 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Sharpness")) {
1320 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Sharpness", "Sharpness");
1321 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->sharpness;
1322 }
1323
1324 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Eccentricity")) {
1326 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Eccentricity", "Eccentricity");
1327 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->eccentricity;
1328 }
1329
1330 if (!blender::bke::node_find_socket(*node, SOCK_IN, "High Precision")) {
1332 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "High Precision", "High Precision");
1333 input->default_value_typed<bNodeSocketValueBoolean>()->value = storage->high_precision;
1334 }
1335}
1336
1337/* The options were converted into inputs. */
1339{
1340 /* Compute the RNA path of the node. */
1341 char escaped_node_name[sizeof(node->name) * 2 + 1];
1342 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1343 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1344
1345 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1346 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1347 * path. */
1348 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1349 return;
1350 }
1351
1352 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1353 * values of the FCurves frames when needed. */
1354 char *old_rna_path = fcurve->rna_path;
1355 if (BLI_str_endswith(fcurve->rna_path, "uniformity")) {
1356 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
1357 }
1358 else if (BLI_str_endswith(fcurve->rna_path, "sharpness")) {
1359 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
1360 }
1361 else if (BLI_str_endswith(fcurve->rna_path, "eccentricity")) {
1362 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
1363 }
1364 else if (BLI_str_endswith(fcurve->rna_path, "high_precision")) {
1365 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[5].default_value");
1366 }
1367
1368 /* The RNA path was changed, free the old path. */
1369 if (fcurve->rna_path != old_rna_path) {
1370 MEM_freeN(old_rna_path);
1371 }
1372 });
1373}
1374
1375/* The options were converted into inputs. */
1377{
1378 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Color Threshold")) {
1380 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "Color Threshold", "Color Threshold");
1381 input->default_value_typed<bNodeSocketValueFloat>()->value = node->custom3;
1382 }
1383
1384 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Neighbor Threshold")) {
1386 *node,
1387 SOCK_IN,
1388 SOCK_FLOAT,
1390 "Neighbor Threshold",
1391 "Neighbor Threshold");
1392 input->default_value_typed<bNodeSocketValueFloat>()->value = node->custom4;
1393 }
1394}
1395
1396/* The options were converted into inputs. */
1398 bNode *node)
1399{
1400 /* Compute the RNA path of the node. */
1401 char escaped_node_name[sizeof(node->name) * 2 + 1];
1402 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1403 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1404
1405 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1406 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1407 * path. */
1408 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1409 return;
1410 }
1411
1412 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1413 * values of the FCurves frames when needed. */
1414 char *old_rna_path = fcurve->rna_path;
1415 if (BLI_str_endswith(fcurve->rna_path, "threshold")) {
1416 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
1417 }
1418 else if (BLI_str_endswith(fcurve->rna_path, "threshold_neighbor")) {
1419 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
1420 }
1421
1422 /* The RNA path was changed, free the old path. */
1423 if (fcurve->rna_path != old_rna_path) {
1424 MEM_freeN(old_rna_path);
1425 }
1426 });
1427}
1428
1429/* The options were converted into inputs. */
1431{
1432 NodeDenoise *storage = static_cast<NodeDenoise *>(node->storage);
1433 if (!storage) {
1434 return;
1435 }
1436
1437 if (!blender::bke::node_find_socket(*node, SOCK_IN, "HDR")) {
1439 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "HDR", "HDR");
1440 input->default_value_typed<bNodeSocketValueBoolean>()->value = storage->hdr;
1441 }
1442}
1443
1444/* The options were converted into inputs. */
1446{
1447 /* Compute the RNA path of the node. */
1448 char escaped_node_name[sizeof(node->name) * 2 + 1];
1449 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1450 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1451
1452 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1453 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1454 * path. */
1455 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1456 return;
1457 }
1458
1459 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1460 * values of the FCurves frames when needed. */
1461 char *old_rna_path = fcurve->rna_path;
1462 if (BLI_str_endswith(fcurve->rna_path, "use_hdr")) {
1463 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
1464 }
1465
1466 /* The RNA path was changed, free the old path. */
1467 if (fcurve->rna_path != old_rna_path) {
1468 MEM_freeN(old_rna_path);
1469 }
1470 });
1471}
1472
1473/* The options were converted into inputs. */
1475{
1476 NodeAntiAliasingData *storage = static_cast<NodeAntiAliasingData *>(node->storage);
1477 if (!storage) {
1478 return;
1479 }
1480
1481 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Threshold")) {
1483 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Threshold", "Threshold");
1484 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->threshold;
1485 }
1486
1487 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Contrast Limit")) {
1489 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "Contrast Limit", "Contrast Limit");
1490 /* Contrast limit was previously divided by 10. */
1491 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->contrast_limit * 10.0f;
1492 }
1493
1494 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Corner Rounding")) {
1496 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Corner Rounding", "Corner Rounding");
1497 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->corner_rounding;
1498 }
1499
1500 MEM_freeN(storage);
1501 node->storage = nullptr;
1502}
1503
1504/* The options were converted into inputs. */
1506 bNode *node)
1507{
1508 /* Compute the RNA path of the node. */
1509 char escaped_node_name[sizeof(node->name) * 2 + 1];
1510 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1511 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1512
1513 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1514 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1515 * path. */
1516 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1517 return;
1518 }
1519
1520 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1521 * values of the FCurves frames when needed. */
1522 char *old_rna_path = fcurve->rna_path;
1523 if (BLI_str_endswith(fcurve->rna_path, "threshold")) {
1524 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
1525 }
1526 else if (BLI_str_endswith(fcurve->rna_path, "contrast_limit")) {
1527 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
1528 /* Contrast limit was previously divided by 10. */
1529 adjust_fcurve_key_frame_values(
1530 fcurve, PROP_FLOAT, [&](const float value) { return value * 10.0f; });
1531 }
1532 else if (BLI_str_endswith(fcurve->rna_path, "corner_rounding")) {
1533 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
1534 }
1535
1536 /* The RNA path was changed, free the old path. */
1537 if (fcurve->rna_path != old_rna_path) {
1538 MEM_freeN(old_rna_path);
1539 }
1540 });
1541}
1542
1543/* The options were converted into inputs. */
1545{
1546 NodeBlurData *storage = static_cast<NodeBlurData *>(node->storage);
1547 if (!storage) {
1548 return;
1549 }
1550
1551 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Samples")) {
1553 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Samples", "Samples");
1554 input->default_value_typed<bNodeSocketValueInt>()->value = storage->samples;
1555 }
1556
1557 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Shutter")) {
1559 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "Shutter", "Shutter");
1560 /* Shutter was previously divided by 2. */
1561 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->fac * 2.0f;
1562 }
1563
1564 MEM_freeN(storage);
1565 node->storage = nullptr;
1566}
1567
1568/* The options were converted into inputs. */
1570 bNode *node)
1571{
1572 /* Compute the RNA path of the node. */
1573 char escaped_node_name[sizeof(node->name) * 2 + 1];
1574 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1575 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1576
1577 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1578 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1579 * path. */
1580 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1581 return;
1582 }
1583
1584 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1585 * values of the FCurves frames when needed. */
1586 char *old_rna_path = fcurve->rna_path;
1587 if (BLI_str_endswith(fcurve->rna_path, "samples")) {
1588 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
1589 }
1590 else if (BLI_str_endswith(fcurve->rna_path, "factor")) {
1591 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
1592 /* Shutter was previously divided by 2. */
1593 adjust_fcurve_key_frame_values(
1594 fcurve, PROP_FLOAT, [&](const float value) { return value * 2.0f; });
1595 }
1596
1597 /* The RNA path was changed, free the old path. */
1598 if (fcurve->rna_path != old_rna_path) {
1599 MEM_freeN(old_rna_path);
1600 }
1601 });
1602}
1603
1604/* The options were converted into inputs. */
1606{
1607 NodeChroma *storage = static_cast<NodeChroma *>(node->storage);
1608 if (!storage) {
1609 return;
1610 }
1611
1612 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Minimum")) {
1614 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Minimum", "Minimum");
1615 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->t2;
1616 }
1617
1618 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Maximum")) {
1620 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Maximum", "Maximum");
1621 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->t1;
1622 }
1623}
1624
1625/* The options were converted into inputs. */
1627 bNode *node)
1628{
1629 /* Compute the RNA path of the node. */
1630 char escaped_node_name[sizeof(node->name) * 2 + 1];
1631 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1632 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1633
1634 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1635 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1636 * path. */
1637 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1638 return;
1639 }
1640
1641 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1642 * values of the FCurves frames when needed. */
1643 char *old_rna_path = fcurve->rna_path;
1644 if (BLI_str_endswith(fcurve->rna_path, "limit_min")) {
1645 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
1646 }
1647 else if (BLI_str_endswith(fcurve->rna_path, "limit_max")) {
1648 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
1649 }
1650
1651 /* The RNA path was changed, free the old path. */
1652 if (fcurve->rna_path != old_rna_path) {
1653 MEM_freeN(old_rna_path);
1654 }
1655 });
1656}
1657
1658/* The options were converted into inputs. */
1660{
1661 NodeChroma *storage = static_cast<NodeChroma *>(node->storage);
1662 if (!storage) {
1663 return;
1664 }
1665
1666 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Minimum")) {
1668 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_ANGLE, "Minimum", "Minimum");
1669 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->t2;
1670 }
1671
1672 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Maximum")) {
1674 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_ANGLE, "Maximum", "Maximum");
1675 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->t1;
1676 }
1677
1678 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Falloff")) {
1680 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Falloff", "Falloff");
1681 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->fstrength;
1682 }
1683
1684 MEM_freeN(storage);
1685 node->storage = nullptr;
1686}
1687
1688/* The options were converted into inputs. */
1690 bNode *node)
1691{
1692 /* Compute the RNA path of the node. */
1693 char escaped_node_name[sizeof(node->name) * 2 + 1];
1694 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1695 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1696
1697 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1698 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1699 * path. */
1700 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1701 return;
1702 }
1703
1704 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1705 * values of the FCurves frames when needed. */
1706 char *old_rna_path = fcurve->rna_path;
1707 if (BLI_str_endswith(fcurve->rna_path, "threshold")) {
1708 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
1709 }
1710 else if (BLI_str_endswith(fcurve->rna_path, "tolerance")) {
1711 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
1712 }
1713 else if (BLI_str_endswith(fcurve->rna_path, "gain")) {
1714 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
1715 }
1716
1717 /* The RNA path was changed, free the old path. */
1718 if (fcurve->rna_path != old_rna_path) {
1719 MEM_freeN(old_rna_path);
1720 }
1721 });
1722}
1723
1724/* The options were converted into inputs. */
1726{
1727 NodeChroma *storage = static_cast<NodeChroma *>(node->storage);
1728 if (!storage) {
1729 return;
1730 }
1731
1732 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Hue")) {
1734 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Hue", "Hue");
1735 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->t1;
1736 }
1737
1738 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Saturation")) {
1740 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Saturation", "Saturation");
1741 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->t2;
1742 }
1743
1744 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Value")) {
1746 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Value", "Value");
1747 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->t3;
1748 }
1749
1750 MEM_freeN(storage);
1751 node->storage = nullptr;
1752}
1753
1754/* The options were converted into inputs. */
1756 bNode *node)
1757{
1758 /* Compute the RNA path of the node. */
1759 char escaped_node_name[sizeof(node->name) * 2 + 1];
1760 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1761 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1762
1763 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1764 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1765 * path. */
1766 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1767 return;
1768 }
1769
1770 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1771 * values of the FCurves frames when needed. */
1772 char *old_rna_path = fcurve->rna_path;
1773 if (BLI_str_endswith(fcurve->rna_path, "color_hue")) {
1774 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
1775 }
1776 else if (BLI_str_endswith(fcurve->rna_path, "color_saturation")) {
1777 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
1778 }
1779 else if (BLI_str_endswith(fcurve->rna_path, "color_value")) {
1780 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
1781 }
1782
1783 /* The RNA path was changed, free the old path. */
1784 if (fcurve->rna_path != old_rna_path) {
1785 MEM_freeN(old_rna_path);
1786 }
1787 });
1788}
1789
1790/* The options were converted into inputs. */
1792{
1793 NodeChroma *storage = static_cast<NodeChroma *>(node->storage);
1794 if (!storage) {
1795 return;
1796 }
1797
1798 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Tolerance")) {
1800 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Tolerance", "Tolerance");
1801 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->t1;
1802 }
1803
1804 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Falloff")) {
1806 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Falloff", "Falloff");
1807 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->t2;
1808 }
1809
1810 MEM_freeN(storage);
1811 node->storage = nullptr;
1812}
1813
1814/* The options were converted into inputs. */
1816 bNode *node)
1817{
1818 /* Compute the RNA path of the node. */
1819 char escaped_node_name[sizeof(node->name) * 2 + 1];
1820 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1821 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1822
1823 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1824 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1825 * path. */
1826 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1827 return;
1828 }
1829
1830 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1831 * values of the FCurves frames when needed. */
1832 char *old_rna_path = fcurve->rna_path;
1833 if (BLI_str_endswith(fcurve->rna_path, "tolerance")) {
1834 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
1835 }
1836 else if (BLI_str_endswith(fcurve->rna_path, "falloff")) {
1837 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
1838 }
1839
1840 /* The RNA path was changed, free the old path. */
1841 if (fcurve->rna_path != old_rna_path) {
1842 MEM_freeN(old_rna_path);
1843 }
1844 });
1845}
1846
1847/* The options were converted into inputs. */
1849{
1850 NodeChroma *storage = static_cast<NodeChroma *>(node->storage);
1851 if (!storage) {
1852 return;
1853 }
1854
1855 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Tolerance")) {
1857 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Tolerance", "Tolerance");
1858 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->t1;
1859 }
1860
1861 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Falloff")) {
1863 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Falloff", "Falloff");
1864 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->t2;
1865 }
1866}
1867
1868/* The options were converted into inputs. */
1870 bNode *node)
1871{
1872 /* Compute the RNA path of the node. */
1873 char escaped_node_name[sizeof(node->name) * 2 + 1];
1874 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1875 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1876
1877 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1878 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1879 * path. */
1880 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1881 return;
1882 }
1883
1884 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1885 * values of the FCurves frames when needed. */
1886 char *old_rna_path = fcurve->rna_path;
1887 if (BLI_str_endswith(fcurve->rna_path, "tolerance")) {
1888 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
1889 }
1890 else if (BLI_str_endswith(fcurve->rna_path, "falloff")) {
1891 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
1892 }
1893
1894 /* The RNA path was changed, free the old path. */
1895 if (fcurve->rna_path != old_rna_path) {
1896 MEM_freeN(old_rna_path);
1897 }
1898 });
1899}
1900
1901/* The options were converted into inputs. */
1903{
1904 NodeChroma *storage = static_cast<NodeChroma *>(node->storage);
1905 if (!storage) {
1906 return;
1907 }
1908
1909 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Minimum")) {
1911 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Minimum", "Minimum");
1912 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->t2;
1913 }
1914
1915 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Maximum")) {
1917 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Maximum", "Maximum");
1918 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->t1;
1919 }
1920
1921 MEM_freeN(storage);
1922 node->storage = nullptr;
1923}
1924
1925/* The options were converted into inputs. */
1927 bNode *node)
1928{
1929 /* Compute the RNA path of the node. */
1930 char escaped_node_name[sizeof(node->name) * 2 + 1];
1931 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1932 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
1933
1934 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
1935 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
1936 * path. */
1937 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
1938 return;
1939 }
1940
1941 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
1942 * values of the FCurves frames when needed. */
1943 char *old_rna_path = fcurve->rna_path;
1944 if (BLI_str_endswith(fcurve->rna_path, "limit_min")) {
1945 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
1946 }
1947 else if (BLI_str_endswith(fcurve->rna_path, "limit_max")) {
1948 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
1949 }
1950
1951 /* The RNA path was changed, free the old path. */
1952 if (fcurve->rna_path != old_rna_path) {
1953 MEM_freeN(old_rna_path);
1954 }
1955 });
1956}
1957
1958/* The options were converted into inputs. */
1960{
1961 NodeColorspill *storage = static_cast<NodeColorspill *>(node->storage);
1962 if (!storage) {
1963 return;
1964 }
1965
1966 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Limit Strength")) {
1968 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Limit Strength", "Limit Strength");
1969 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->limscale;
1970 }
1971
1972 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Use Spill Strength")) {
1974 *node,
1975 SOCK_IN,
1977 PROP_NONE,
1978 "Use Spill Strength",
1979 "Use Spill Strength");
1980 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(storage->unspill);
1981 }
1982
1983 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Spill Strength")) {
1985 *node_tree, *node, SOCK_IN, SOCK_RGBA, PROP_NONE, "Spill Strength", "Spill Strength");
1986 input->default_value_typed<bNodeSocketValueRGBA>()->value[0] = storage->uspillr;
1987 input->default_value_typed<bNodeSocketValueRGBA>()->value[1] = storage->uspillg;
1988 input->default_value_typed<bNodeSocketValueRGBA>()->value[2] = storage->uspillb;
1989 }
1990}
1991
1992/* The options were converted into inputs. */
1994 bNode *node)
1995{
1996 /* Compute the RNA path of the node. */
1997 char escaped_node_name[sizeof(node->name) * 2 + 1];
1998 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
1999 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
2000
2001 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
2002 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
2003 * path. */
2004 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
2005 return;
2006 }
2007
2008 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
2009 * values of the FCurves frames when needed. */
2010 char *old_rna_path = fcurve->rna_path;
2011 if (BLI_str_endswith(fcurve->rna_path, "ratio")) {
2012 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
2013 }
2014 else if (BLI_str_endswith(fcurve->rna_path, "use_unspill")) {
2015 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
2016 }
2017 else if (BLI_str_endswith(fcurve->rna_path, "unspill_red")) {
2018 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
2019 fcurve->array_index = 0;
2020 }
2021 else if (BLI_str_endswith(fcurve->rna_path, "unspill_green")) {
2022 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
2023 fcurve->array_index = 1;
2024 }
2025 else if (BLI_str_endswith(fcurve->rna_path, "unspill_blue")) {
2026 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
2027 fcurve->array_index = 2;
2028 }
2029
2030 /* The RNA path was changed, free the old path. */
2031 if (fcurve->rna_path != old_rna_path) {
2032 MEM_freeN(old_rna_path);
2033 }
2034 });
2035}
2036
2037/* The options were converted into inputs. */
2039{
2040 NodeKeyingScreenData *storage = static_cast<NodeKeyingScreenData *>(node->storage);
2041 if (!storage) {
2042 return;
2043 }
2044
2045 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Smoothness")) {
2047 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Smoothness", "Smoothness");
2048 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->smoothness;
2049 }
2050}
2051
2052/* The options were converted into inputs. */
2054 bNode *node)
2055{
2056 /* Compute the RNA path of the node. */
2057 char escaped_node_name[sizeof(node->name) * 2 + 1];
2058 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
2059 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
2060
2061 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
2062 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
2063 * path. */
2064 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
2065 return;
2066 }
2067
2068 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
2069 * values of the FCurves frames when needed. */
2070 char *old_rna_path = fcurve->rna_path;
2071 if (BLI_str_endswith(fcurve->rna_path, "smoothness")) {
2072 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[0].default_value");
2073 }
2074
2075 /* The RNA path was changed, free the old path. */
2076 if (fcurve->rna_path != old_rna_path) {
2077 MEM_freeN(old_rna_path);
2078 }
2079 });
2080}
2081
2082/* The options were converted into inputs. */
2084{
2085 NodeKeyingData *storage = static_cast<NodeKeyingData *>(node->storage);
2086 if (!storage) {
2087 return;
2088 }
2089
2090 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Preprocess Blur Size")) {
2092 *node,
2093 SOCK_IN,
2094 SOCK_INT,
2095 PROP_NONE,
2096 "Preprocess Blur Size",
2097 "Preprocess Blur Size");
2098 input->default_value_typed<bNodeSocketValueInt>()->value = storage->blur_pre;
2099 }
2100
2101 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Key Balance")) {
2103 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Key Balance", "Key Balance");
2104 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->screen_balance;
2105 }
2106
2107 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Edge Search Size")) {
2109 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Edge Search Size", "Edge Search Size");
2110 input->default_value_typed<bNodeSocketValueInt>()->value = storage->edge_kernel_radius;
2111 }
2112
2113 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Edge Tolerance")) {
2115 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Edge Tolerance", "Edge Tolerance");
2116 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->edge_kernel_tolerance;
2117 }
2118
2119 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Black Level")) {
2121 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Black Level", "Black Level");
2122 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->clip_black;
2123 }
2124
2125 if (!blender::bke::node_find_socket(*node, SOCK_IN, "White Level")) {
2127 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "White Level", "White Level");
2128 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->clip_white;
2129 }
2130
2131 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Postprocess Blur Size")) {
2133 *node,
2134 SOCK_IN,
2135 SOCK_INT,
2136 PROP_NONE,
2137 "Postprocess Blur Size",
2138 "Postprocess Blur Size");
2139 input->default_value_typed<bNodeSocketValueInt>()->value = storage->blur_post;
2140 }
2141
2142 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Postprocess Dilate Size")) {
2144 *node,
2145 SOCK_IN,
2146 SOCK_INT,
2147 PROP_NONE,
2148 "Postprocess Dilate Size",
2149 "Postprocess Dilate Size");
2150 input->default_value_typed<bNodeSocketValueInt>()->value = storage->dilate_distance;
2151 }
2152
2153 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Postprocess Feather Size")) {
2155 *node,
2156 SOCK_IN,
2157 SOCK_INT,
2158 PROP_NONE,
2159 "Postprocess Feather Size",
2160 "Postprocess Feather Size");
2161 input->default_value_typed<bNodeSocketValueInt>()->value = storage->feather_distance;
2162 }
2163
2164 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Despill Strength")) {
2166 *node,
2167 SOCK_IN,
2168 SOCK_FLOAT,
2170 "Despill Strength",
2171 "Despill Strength");
2172 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->despill_factor;
2173 }
2174
2175 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Despill Balance")) {
2177 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Despill Balance", "Despill Balance");
2178 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->despill_balance;
2179 }
2180}
2181
2182/* The options were converted into inputs. */
2184{
2185 /* Compute the RNA path of the node. */
2186 char escaped_node_name[sizeof(node->name) * 2 + 1];
2187 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
2188 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
2189
2190 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
2191 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
2192 * path. */
2193 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
2194 return;
2195 }
2196
2197 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
2198 * values of the FCurves frames when needed. */
2199 char *old_rna_path = fcurve->rna_path;
2200 if (BLI_str_endswith(fcurve->rna_path, "blur_pre")) {
2201 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
2202 }
2203 else if (BLI_str_endswith(fcurve->rna_path, "screen_balance")) {
2204 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
2205 }
2206 else if (BLI_str_endswith(fcurve->rna_path, "clip_black")) {
2207 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
2208 }
2209 else if (BLI_str_endswith(fcurve->rna_path, "clip_white")) {
2210 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[5].default_value");
2211 }
2212 else if (BLI_str_endswith(fcurve->rna_path, "edge_kernel_radius")) {
2213 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[6].default_value");
2214 }
2215 else if (BLI_str_endswith(fcurve->rna_path, "edge_kernel_tolerance")) {
2216 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[7].default_value");
2217 }
2218 else if (BLI_str_endswith(fcurve->rna_path, "blur_post")) {
2219 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[10].default_value");
2220 }
2221 else if (BLI_str_endswith(fcurve->rna_path, "dilate_distance")) {
2222 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[11].default_value");
2223 }
2224 else if (BLI_str_endswith(fcurve->rna_path, "feather_distance")) {
2225 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[12].default_value");
2226 }
2227 else if (BLI_str_endswith(fcurve->rna_path, "despill_factor")) {
2228 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[13].default_value");
2229 }
2230 else if (BLI_str_endswith(fcurve->rna_path, "despill_balance")) {
2231 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[14].default_value");
2232 }
2233
2234 /* The RNA path was changed, free the old path. */
2235 if (fcurve->rna_path != old_rna_path) {
2236 MEM_freeN(old_rna_path);
2237 }
2238 });
2239}
2240
2241/* The options were converted into inputs. */
2243{
2244 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Index")) {
2246 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Index", "Index");
2247 input->default_value_typed<bNodeSocketValueInt>()->value = node->custom1;
2248 }
2249
2250 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Anti-Alias")) {
2252 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Anti-Alias", "Anti-Alias");
2253 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(node->custom2);
2254 }
2255}
2256
2257/* The options were converted into inputs. */
2259{
2260 /* Compute the RNA path of the node. */
2261 char escaped_node_name[sizeof(node->name) * 2 + 1];
2262 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
2263 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
2264
2265 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
2266 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
2267 * path. */
2268 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
2269 return;
2270 }
2271
2272 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
2273 * values of the FCurves frames when needed. */
2274 char *old_rna_path = fcurve->rna_path;
2275 if (BLI_str_endswith(fcurve->rna_path, "index")) {
2276 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
2277 }
2278 else if (BLI_str_endswith(fcurve->rna_path, "use_antialiasing")) {
2279 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
2280 }
2281
2282 /* The RNA path was changed, free the old path. */
2283 if (fcurve->rna_path != old_rna_path) {
2284 MEM_freeN(old_rna_path);
2285 }
2286 });
2287}
2288
2289/* The options were converted into inputs. */
2291{
2292 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Invert")) {
2294 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Invert", "Invert");
2295 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(node->custom2);
2296 }
2297}
2298
2299/* The options were converted into inputs. */
2301 bNode *node)
2302{
2303 /* Compute the RNA path of the node. */
2304 char escaped_node_name[sizeof(node->name) * 2 + 1];
2305 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
2306 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
2307
2308 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
2309 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
2310 * path. */
2311 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
2312 return;
2313 }
2314
2315 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
2316 * values of the FCurves frames when needed. */
2317 char *old_rna_path = fcurve->rna_path;
2318 if (BLI_str_endswith(fcurve->rna_path, "invert")) {
2319 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
2320 }
2321
2322 /* The RNA path was changed, free the old path. */
2323 if (fcurve->rna_path != old_rna_path) {
2324 MEM_freeN(old_rna_path);
2325 }
2326 });
2327}
2328
2329/* The options were converted into inputs. */
2331{
2332 NodePlaneTrackDeformData *storage = static_cast<NodePlaneTrackDeformData *>(node->storage);
2333 if (!storage) {
2334 return;
2335 }
2336
2337 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Motion Blur")) {
2339 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Motion Blur", "Motion Blur");
2340 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(storage->flag);
2341 }
2342
2343 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Motion Blur Samples")) {
2345 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Motion Blur Samples", "Samples");
2346 input->default_value_typed<bNodeSocketValueInt>()->value = storage->motion_blur_samples;
2347 }
2348
2349 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Motion Blur Shutter")) {
2351 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Motion Blur Shutter", "Shutter");
2352 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->motion_blur_shutter;
2353 }
2354}
2355
2356/* The options were converted into inputs. */
2358 bNode *node)
2359{
2360 /* Compute the RNA path of the node. */
2361 char escaped_node_name[sizeof(node->name) * 2 + 1];
2362 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
2363 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
2364
2365 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
2366 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
2367 * path. */
2368 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
2369 return;
2370 }
2371
2372 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
2373 * values of the FCurves frames when needed. */
2374 char *old_rna_path = fcurve->rna_path;
2375 if (BLI_str_endswith(fcurve->rna_path, "use_motion_blur")) {
2376 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
2377 }
2378 else if (BLI_str_endswith(fcurve->rna_path, "motion_blur_samples")) {
2379 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
2380 }
2381 else if (BLI_str_endswith(fcurve->rna_path, "motion_blur_shutter")) {
2382 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
2383 }
2384
2385 /* The RNA path was changed, free the old path. */
2386 if (fcurve->rna_path != old_rna_path) {
2387 MEM_freeN(old_rna_path);
2388 }
2389 });
2390}
2391
2392/* The options were converted into inputs. */
2394{
2395 NodeColorCorrection *storage = static_cast<NodeColorCorrection *>(node->storage);
2396 if (!storage) {
2397 return;
2398 }
2399
2400 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Master Saturation")) {
2402 *node,
2403 SOCK_IN,
2404 SOCK_FLOAT,
2406 "Master Saturation",
2407 "Master Saturation");
2408 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->master.saturation;
2409 }
2410
2411 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Master Contrast")) {
2413 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Master Contrast", "Master Contrast");
2414 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->master.contrast;
2415 }
2416
2417 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Master Gamma")) {
2419 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Master Gamma", "Master Gamma");
2420 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->master.gamma;
2421 }
2422
2423 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Master Gain")) {
2425 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Master Gain", "Master Gain");
2426 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->master.gain;
2427 }
2428
2429 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Master Lift")) {
2431 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Master Lift", "Master Lift");
2432 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->master.lift;
2433 }
2434
2435 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Shadows Saturation")) {
2437 *node,
2438 SOCK_IN,
2439 SOCK_FLOAT,
2441 "Shadows Saturation",
2442 "Shadows Saturation");
2443 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->shadows.saturation;
2444 }
2445
2446 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Shadows Contrast")) {
2448 *node,
2449 SOCK_IN,
2450 SOCK_FLOAT,
2452 "Shadows Contrast",
2453 "Shadows Contrast");
2454 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->shadows.contrast;
2455 }
2456
2457 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Shadows Gamma")) {
2459 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Shadows Gamma", "Shadows Gamma");
2460 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->shadows.gamma;
2461 }
2462
2463 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Shadows Gain")) {
2465 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Shadows Gain", "Shadows Gain");
2466 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->shadows.gain;
2467 }
2468
2469 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Shadows Lift")) {
2471 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Shadows Lift", "Shadows Lift");
2472 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->shadows.lift;
2473 }
2474
2475 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Midtones Saturation")) {
2477 *node,
2478 SOCK_IN,
2479 SOCK_FLOAT,
2481 "Midtones Saturation",
2482 "Midtones Saturation");
2483 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->midtones.saturation;
2484 }
2485
2486 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Midtones Contrast")) {
2488 *node,
2489 SOCK_IN,
2490 SOCK_FLOAT,
2492 "Midtones Contrast",
2493 "Midtones Contrast");
2494 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->midtones.contrast;
2495 }
2496
2497 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Midtones Gamma")) {
2499 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Midtones Gamma", "Midtones Gamma");
2500 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->midtones.gamma;
2501 }
2502
2503 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Midtones Gain")) {
2505 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Midtones Gain", "Midtones Gain");
2506 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->midtones.gain;
2507 }
2508
2509 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Midtones Lift")) {
2511 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Midtones Lift", "Midtones Lift");
2512 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->midtones.lift;
2513 }
2514
2515 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Highlights Saturation")) {
2517 *node,
2518 SOCK_IN,
2519 SOCK_FLOAT,
2521 "Highlights Saturation",
2522 "Highlights Saturation");
2523 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->highlights.saturation;
2524 }
2525
2526 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Highlights Contrast")) {
2528 *node,
2529 SOCK_IN,
2530 SOCK_FLOAT,
2532 "Highlights Contrast",
2533 "Highlights Contrast");
2534 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->highlights.contrast;
2535 }
2536
2537 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Highlights Gamma")) {
2539 *node,
2540 SOCK_IN,
2541 SOCK_FLOAT,
2543 "Highlights Gamma",
2544 "Highlights Gamma");
2545 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->highlights.gamma;
2546 }
2547
2548 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Highlights Gain")) {
2550 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Highlights Gain", "Highlights Gain");
2551 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->highlights.gain;
2552 }
2553
2554 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Highlights Lift")) {
2556 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Highlights Lift", "Highlights Lift");
2557 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->highlights.lift;
2558 }
2559
2560 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Midtones Start")) {
2562 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Midtones Start", "Midtones Start");
2563 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->startmidtones;
2564 }
2565
2566 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Midtones End")) {
2568 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Midtones End", "Midtones End");
2569 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->endmidtones;
2570 }
2571
2572 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Apply On Red")) {
2574 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Apply On Red", "Apply On Red");
2575 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(node->custom1 & (1 << 0));
2576 }
2577
2578 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Apply On Green")) {
2580 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Apply On Green", "Apply On Green");
2581 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(node->custom1 & (1 << 1));
2582 }
2583
2584 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Apply On Blue")) {
2586 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Apply On Blue", "Apply On Blue");
2587 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(node->custom1 & (1 << 2));
2588 }
2589
2590 MEM_freeN(storage);
2591 node->storage = nullptr;
2592}
2593
2594/* The options were converted into inputs. */
2596 bNode *node)
2597{
2598 /* Compute the RNA path of the node. */
2599 char escaped_node_name[sizeof(node->name) * 2 + 1];
2600 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
2601 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
2602
2603 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
2604 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
2605 * path. */
2606 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
2607 return;
2608 }
2609
2610 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
2611 * values of the FCurves frames when needed. */
2612 char *old_rna_path = fcurve->rna_path;
2613 if (BLI_str_endswith(fcurve->rna_path, "use_motion_blur")) {
2614 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
2615 }
2616 else if (BLI_str_endswith(fcurve->rna_path, "master_saturation")) {
2617 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
2618 }
2619 else if (BLI_str_endswith(fcurve->rna_path, "master_contrast")) {
2620 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
2621 }
2622 else if (BLI_str_endswith(fcurve->rna_path, "master_gamma")) {
2623 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
2624 }
2625 else if (BLI_str_endswith(fcurve->rna_path, "master_gain")) {
2626 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[5].default_value");
2627 }
2628 else if (BLI_str_endswith(fcurve->rna_path, "master_lift")) {
2629 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[6].default_value");
2630 }
2631 else if (BLI_str_endswith(fcurve->rna_path, "highlights_saturation")) {
2632 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[7].default_value");
2633 }
2634 else if (BLI_str_endswith(fcurve->rna_path, "highlights_contrast")) {
2635 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[8].default_value");
2636 }
2637 else if (BLI_str_endswith(fcurve->rna_path, "highlights_gamma")) {
2638 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[9].default_value");
2639 }
2640 else if (BLI_str_endswith(fcurve->rna_path, "highlights_gain")) {
2641 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[10].default_value");
2642 }
2643 else if (BLI_str_endswith(fcurve->rna_path, "highlights_lift")) {
2644 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[11].default_value");
2645 }
2646 else if (BLI_str_endswith(fcurve->rna_path, "midtones_saturation")) {
2647 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[12].default_value");
2648 }
2649 else if (BLI_str_endswith(fcurve->rna_path, "midtones_contrast")) {
2650 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[13].default_value");
2651 }
2652 else if (BLI_str_endswith(fcurve->rna_path, "midtones_gamma")) {
2653 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[14].default_value");
2654 }
2655 else if (BLI_str_endswith(fcurve->rna_path, "midtones_gain")) {
2656 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[15].default_value");
2657 }
2658 else if (BLI_str_endswith(fcurve->rna_path, "midtones_lift")) {
2659 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[16].default_value");
2660 }
2661 else if (BLI_str_endswith(fcurve->rna_path, "shadows_saturation")) {
2662 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[17].default_value");
2663 }
2664 else if (BLI_str_endswith(fcurve->rna_path, "shadows_contrast")) {
2665 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[18].default_value");
2666 }
2667 else if (BLI_str_endswith(fcurve->rna_path, "shadows_gamma")) {
2668 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[19].default_value");
2669 }
2670 else if (BLI_str_endswith(fcurve->rna_path, "shadows_gain")) {
2671 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[20].default_value");
2672 }
2673 else if (BLI_str_endswith(fcurve->rna_path, "shadows_lift")) {
2674 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[21].default_value");
2675 }
2676 else if (BLI_str_endswith(fcurve->rna_path, "midtones_start")) {
2677 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[22].default_value");
2678 }
2679 else if (BLI_str_endswith(fcurve->rna_path, "midtones_end")) {
2680 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[23].default_value");
2681 }
2682 else if (BLI_str_endswith(fcurve->rna_path, "red")) {
2683 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[24].default_value");
2684 }
2685 else if (BLI_str_endswith(fcurve->rna_path, "green")) {
2686 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[25].default_value");
2687 }
2688 else if (BLI_str_endswith(fcurve->rna_path, "blue")) {
2689 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[26].default_value");
2690 }
2691
2692 /* The RNA path was changed, free the old path. */
2693 if (fcurve->rna_path != old_rna_path) {
2694 MEM_freeN(old_rna_path);
2695 }
2696 });
2697}
2698
2699/* The options were converted into inputs. */
2701{
2702 NodeLensDist *storage = static_cast<NodeLensDist *>(node->storage);
2703 if (!storage) {
2704 return;
2705 }
2706
2707 /* Use Projector boolean option is now an enum between two types. */
2708 storage->distortion_type = storage->proj ? CMP_NODE_LENS_DISTORTION_HORIZONTAL :
2710
2711 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Jitter")) {
2713 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Jitter", "Jitter");
2714 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(storage->jit);
2715 }
2716
2717 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Fit")) {
2719 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Fit", "Fit");
2720 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(storage->fit);
2721 }
2722}
2723
2724/* The options were converted into inputs. */
2726 bNode *node)
2727{
2728 /* Compute the RNA path of the node. */
2729 char escaped_node_name[sizeof(node->name) * 2 + 1];
2730 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
2731 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
2732
2733 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
2734 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
2735 * path. */
2736 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
2737 return;
2738 }
2739
2740 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
2741 * values of the FCurves frames when needed. */
2742 char *old_rna_path = fcurve->rna_path;
2743 if (BLI_str_endswith(fcurve->rna_path, "use_jitter")) {
2744 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
2745 }
2746 else if (BLI_str_endswith(fcurve->rna_path, "use_fit")) {
2747 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
2748 }
2749 else if (BLI_str_endswith(fcurve->rna_path, "use_projector")) {
2750 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "distortion_type");
2751 }
2752
2753 /* The RNA path was changed, free the old path. */
2754 if (fcurve->rna_path != old_rna_path) {
2755 MEM_freeN(old_rna_path);
2756 }
2757 });
2758}
2759
2760/* The options were converted into inputs. */
2762{
2763 NodeBoxMask *storage = static_cast<NodeBoxMask *>(node->storage);
2764 if (!storage) {
2765 return;
2766 }
2767
2768 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Position")) {
2770 *node_tree, *node, SOCK_IN, SOCK_VECTOR, PROP_FACTOR, "Position", "Position");
2771 input->default_value_typed<bNodeSocketValueVector>()->value[0] = storage->x;
2772 input->default_value_typed<bNodeSocketValueVector>()->value[1] = storage->y;
2773 }
2774
2775 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Size")) {
2777 *node_tree, *node, SOCK_IN, SOCK_VECTOR, PROP_FACTOR, "Size", "Size");
2778 input->default_value_typed<bNodeSocketValueVector>()->value[0] = storage->width;
2779 input->default_value_typed<bNodeSocketValueVector>()->value[1] = storage->height;
2780 }
2781
2782 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Rotation")) {
2784 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_ANGLE, "Rotation", "Rotation");
2785 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->rotation;
2786 }
2787
2788 MEM_freeN(storage);
2789 node->storage = nullptr;
2790}
2791
2792/* The options were converted into inputs. */
2794{
2795 /* Compute the RNA path of the node. */
2796 char escaped_node_name[sizeof(node->name) * 2 + 1];
2797 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
2798 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
2799
2800 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
2801 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
2802 * path. */
2803 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
2804 return;
2805 }
2806
2807 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
2808 * values of the FCurves frames when needed. */
2809 char *old_rna_path = fcurve->rna_path;
2810 if (BLI_str_endswith(fcurve->rna_path, "x")) {
2811 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
2812 fcurve->array_index = 0;
2813 }
2814 else if (BLI_str_endswith(fcurve->rna_path, "y")) {
2815 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
2816 fcurve->array_index = 1;
2817 }
2818 else if (BLI_str_endswith(fcurve->rna_path, "mask_width")) {
2819 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
2820 fcurve->array_index = 0;
2821 }
2822 else if (BLI_str_endswith(fcurve->rna_path, "mask_height")) {
2823 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
2824 fcurve->array_index = 1;
2825 }
2826 else if (BLI_str_endswith(fcurve->rna_path, "rotation")) {
2827 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
2828 }
2829
2830 /* The RNA path was changed, free the old path. */
2831 if (fcurve->rna_path != old_rna_path) {
2832 MEM_freeN(old_rna_path);
2833 }
2834 });
2835}
2836
2837/* The options were converted into inputs. */
2839{
2840 NodeEllipseMask *storage = static_cast<NodeEllipseMask *>(node->storage);
2841 if (!storage) {
2842 return;
2843 }
2844
2845 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Position")) {
2847 *node_tree, *node, SOCK_IN, SOCK_VECTOR, PROP_FACTOR, "Position", "Position");
2848 input->default_value_typed<bNodeSocketValueVector>()->value[0] = storage->x;
2849 input->default_value_typed<bNodeSocketValueVector>()->value[1] = storage->y;
2850 }
2851
2852 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Size")) {
2854 *node_tree, *node, SOCK_IN, SOCK_VECTOR, PROP_FACTOR, "Size", "Size");
2855 input->default_value_typed<bNodeSocketValueVector>()->value[0] = storage->width;
2856 input->default_value_typed<bNodeSocketValueVector>()->value[1] = storage->height;
2857 }
2858
2859 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Rotation")) {
2861 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_ANGLE, "Rotation", "Rotation");
2862 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->rotation;
2863 }
2864
2865 MEM_freeN(storage);
2866 node->storage = nullptr;
2867}
2868
2869/* The options were converted into inputs. */
2871 bNode *node)
2872{
2873 /* Compute the RNA path of the node. */
2874 char escaped_node_name[sizeof(node->name) * 2 + 1];
2875 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
2876 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
2877
2878 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
2879 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
2880 * path. */
2881 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
2882 return;
2883 }
2884
2885 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
2886 * values of the FCurves frames when needed. */
2887 char *old_rna_path = fcurve->rna_path;
2888 if (BLI_str_endswith(fcurve->rna_path, "x")) {
2889 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
2890 fcurve->array_index = 0;
2891 }
2892 else if (BLI_str_endswith(fcurve->rna_path, "y")) {
2893 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
2894 fcurve->array_index = 1;
2895 }
2896 else if (BLI_str_endswith(fcurve->rna_path, "mask_width")) {
2897 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
2898 fcurve->array_index = 0;
2899 }
2900 else if (BLI_str_endswith(fcurve->rna_path, "mask_height")) {
2901 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
2902 fcurve->array_index = 1;
2903 }
2904 else if (BLI_str_endswith(fcurve->rna_path, "rotation")) {
2905 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
2906 }
2907
2908 /* The RNA path was changed, free the old path. */
2909 if (fcurve->rna_path != old_rna_path) {
2910 MEM_freeN(old_rna_path);
2911 }
2912 });
2913}
2914
2915/* The options were converted into inputs. */
2917{
2918 NodeSunBeams *storage = static_cast<NodeSunBeams *>(node->storage);
2919 if (!storage) {
2920 return;
2921 }
2922
2923 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Source")) {
2925 *node_tree, *node, SOCK_IN, SOCK_VECTOR, PROP_FACTOR, "Source", "Source");
2926 input->default_value_typed<bNodeSocketValueVector>()->value[0] = storage->source[0];
2927 input->default_value_typed<bNodeSocketValueVector>()->value[1] = storage->source[1];
2928 }
2929
2930 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Length")) {
2932 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Length", "Length");
2933 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->ray_length;
2934 }
2935
2936 MEM_freeN(storage);
2937 node->storage = nullptr;
2938}
2939
2940/* The options were converted into inputs. */
2942 bNode *node)
2943{
2944 /* Compute the RNA path of the node. */
2945 char escaped_node_name[sizeof(node->name) * 2 + 1];
2946 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
2947 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
2948
2949 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
2950 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
2951 * path. */
2952 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
2953 return;
2954 }
2955
2956 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
2957 * values of the FCurves frames when needed. */
2958 char *old_rna_path = fcurve->rna_path;
2959 if (BLI_str_endswith(fcurve->rna_path, "source")) {
2960 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
2961 }
2962 else if (BLI_str_endswith(fcurve->rna_path, "ray_length")) {
2963 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
2964 }
2965
2966 /* The RNA path was changed, free the old path. */
2967 if (fcurve->rna_path != old_rna_path) {
2968 MEM_freeN(old_rna_path);
2969 }
2970 });
2971}
2972
2973/* The options were converted into inputs. */
2975{
2976 NodeDBlurData *storage = static_cast<NodeDBlurData *>(node->storage);
2977 if (!storage) {
2978 return;
2979 }
2980
2981 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Samples")) {
2983 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Samples", "Samples");
2984 input->default_value_typed<bNodeSocketValueInt>()->value = storage->iter;
2985 }
2986
2987 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Center")) {
2989 *node_tree, *node, SOCK_IN, SOCK_VECTOR, PROP_FACTOR, "Center", "Center");
2990 input->default_value_typed<bNodeSocketValueVector>()->value[0] = storage->center_x;
2991 input->default_value_typed<bNodeSocketValueVector>()->value[1] = storage->center_y;
2992 }
2993
2994 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Translation Amount")) {
2996 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_FACTOR, "Translation Amount", "Amount");
2997 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->distance;
2998 }
2999
3000 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Translation Direction")) {
3002 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_ANGLE, "Translation Direction", "Direction");
3003 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->angle;
3004 }
3005
3006 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Rotation")) {
3008 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_ANGLE, "Rotation", "Rotation");
3009 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->spin;
3010 }
3011
3012 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Scale")) {
3014 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "Scale", "Scale");
3015 /* Scale was previously minus 1. */
3016 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->zoom + 1.0f;
3017 }
3018
3019 MEM_freeN(storage);
3020 node->storage = nullptr;
3021}
3022
3023/* The options were converted into inputs. */
3025 bNode *node)
3026{
3027 /* Compute the RNA path of the node. */
3028 char escaped_node_name[sizeof(node->name) * 2 + 1];
3029 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
3030 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
3031
3032 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
3033 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
3034 * path. */
3035 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
3036 return;
3037 }
3038
3039 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
3040 * values of the FCurves frames when needed. */
3041 char *old_rna_path = fcurve->rna_path;
3042 if (BLI_str_endswith(fcurve->rna_path, "iterations")) {
3043 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
3044 }
3045 else if (BLI_str_endswith(fcurve->rna_path, "center_x")) {
3046 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
3047 fcurve->array_index = 0;
3048 }
3049 else if (BLI_str_endswith(fcurve->rna_path, "center_y")) {
3050 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
3051 fcurve->array_index = 1;
3052 }
3053 else if (BLI_str_endswith(fcurve->rna_path, "spin")) {
3054 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
3055 }
3056 else if (BLI_str_endswith(fcurve->rna_path, "zoom")) {
3057 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
3058 /* Scale was previously minus 1. */
3059 adjust_fcurve_key_frame_values(
3060 fcurve, PROP_FLOAT, [&](const float value) { return value + 1.0f; });
3061 }
3062 else if (BLI_str_endswith(fcurve->rna_path, "distance")) {
3063 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[5].default_value");
3064 }
3065 else if (BLI_str_endswith(fcurve->rna_path, "angle")) {
3066 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[6].default_value");
3067 }
3068
3069 /* The RNA path was changed, free the old path. */
3070 if (fcurve->rna_path != old_rna_path) {
3071 MEM_freeN(old_rna_path);
3072 }
3073 });
3074}
3075
3076/* The options were converted into inputs. */
3078{
3079 NodeBilateralBlurData *storage = static_cast<NodeBilateralBlurData *>(node->storage);
3080 if (!storage) {
3081 return;
3082 }
3083
3084 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Size")) {
3086 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Size", "Size");
3087 input->default_value_typed<bNodeSocketValueInt>()->value = std::ceil(storage->iter +
3088 storage->sigma_space);
3089 }
3090
3091 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Threshold")) {
3093 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "Threshold", "Threshold");
3094 /* Threshold was previously multiplied by 3. */
3095 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->sigma_color / 3.0f;
3096 }
3097
3098 MEM_freeN(storage);
3099 node->storage = nullptr;
3100}
3101
3102/* The options were converted into inputs. */
3104 bNode *node)
3105{
3106 /* Compute the RNA path of the node. */
3107 char escaped_node_name[sizeof(node->name) * 2 + 1];
3108 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
3109 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
3110
3111 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
3112 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
3113 * path. */
3114 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
3115 return;
3116 }
3117
3118 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
3119 * values of the FCurves frames when needed. */
3120 char *old_rna_path = fcurve->rna_path;
3121 if (BLI_str_endswith(fcurve->rna_path, "iterations")) {
3122 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
3123 }
3124 else if (BLI_str_endswith(fcurve->rna_path, "sigma_color")) {
3125 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
3126 }
3127
3128 /* The RNA path was changed, free the old path. */
3129 if (fcurve->rna_path != old_rna_path) {
3130 MEM_freeN(old_rna_path);
3131 }
3132 });
3133}
3134
3135/* The Use Alpha option and Alpha input were removed. If Use Alpha was disabled, set the input
3136 * alpha to 1 using a Set Alpha node, otherwise, if the Alpha input is linked, set it to the image
3137 * using a Set Alpha node. */
3139{
3140 /* Maps the names of the viewer and composite nodes to the links going into their image and alpha
3141 * inputs. */
3142 blender::Map<std::string, bNodeLink *> node_to_image_link_map;
3143 blender::Map<std::string, bNodeLink *> node_to_alpha_link_map;
3144
3145 /* Find links going into the composite and viewer nodes. */
3146 LISTBASE_FOREACH (bNodeLink *, link, &node_tree->links) {
3147 if (!ELEM(link->tonode->type_legacy, CMP_NODE_COMPOSITE, CMP_NODE_VIEWER)) {
3148 continue;
3149 }
3150
3151 if (blender::StringRef(link->tosock->identifier) == "Image") {
3152 node_to_image_link_map.add_new(link->tonode->name, link);
3153 }
3154 else if (blender::StringRef(link->tosock->identifier) == "Alpha") {
3155 node_to_alpha_link_map.add_new(link->tonode->name, link);
3156 }
3157 }
3158
3159 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
3160 if (!ELEM(node->type_legacy, CMP_NODE_COMPOSITE, CMP_NODE_VIEWER)) {
3161 continue;
3162 }
3163
3164 bNodeSocket *image_input = blender::bke::node_find_socket(*node, SOCK_IN, "Image");
3165
3166 /* Use Alpha is disabled, so we need to set the alpha to 1. */
3167 if (node->custom2 & CMP_NODE_OUTPUT_IGNORE_ALPHA) {
3168 /* Nothing is connected to the image, just set the default value alpha to 1. */
3169 if (!node_to_image_link_map.contains(node->name)) {
3170 image_input->default_value_typed<bNodeSocketValueRGBA>()->value[3] = 1.0f;
3171 continue;
3172 }
3173
3174 bNodeLink *image_link = node_to_image_link_map.lookup(node->name);
3175
3176 /* Add a set alpha node and make the necessary connections. */
3177 bNode *set_alpha_node = blender::bke::node_add_static_node(
3178 nullptr, *node_tree, CMP_NODE_SETALPHA);
3179 set_alpha_node->parent = node->parent;
3180 set_alpha_node->location[0] = node->location[0] - node->width - 20.0f;
3181 set_alpha_node->location[1] = node->location[1];
3182
3183 NodeSetAlpha *data = static_cast<NodeSetAlpha *>(set_alpha_node->storage);
3185
3187 *set_alpha_node, SOCK_IN, "Image");
3188 bNodeSocket *set_alpha_output = blender::bke::node_find_socket(
3189 *set_alpha_node, SOCK_OUT, "Image");
3190
3191 version_node_add_link(*node_tree,
3192 *image_link->fromnode,
3193 *image_link->fromsock,
3194 *set_alpha_node,
3195 *set_alpha_input);
3196 version_node_add_link(*node_tree, *set_alpha_node, *set_alpha_output, *node, *image_input);
3197
3198 blender::bke::node_remove_link(node_tree, *image_link);
3199 continue;
3200 }
3201
3202 /* If we don't continue, the alpha input is connected and Use Alpha is enabled, so we need to
3203 * set the alpha using a Set Alpha node. */
3204 if (!node_to_alpha_link_map.contains(node->name)) {
3205 continue;
3206 }
3207
3208 bNodeLink *alpha_link = node_to_alpha_link_map.lookup(node->name);
3209
3210 /* Add a set alpha node and make the necessary connections. */
3211 bNode *set_alpha_node = blender::bke::node_add_static_node(
3212 nullptr, *node_tree, CMP_NODE_SETALPHA);
3213 set_alpha_node->parent = node->parent;
3214 set_alpha_node->location[0] = node->location[0] - node->width - 20.0f;
3215 set_alpha_node->location[1] = node->location[1];
3216
3217 NodeSetAlpha *data = static_cast<NodeSetAlpha *>(set_alpha_node->storage);
3219
3221 *set_alpha_node, SOCK_IN, "Image");
3223 *set_alpha_node, SOCK_IN, "Alpha");
3224 bNodeSocket *set_alpha_output = blender::bke::node_find_socket(
3225 *set_alpha_node, SOCK_OUT, "Image");
3226
3227 version_node_add_link(*node_tree,
3228 *alpha_link->fromnode,
3229 *alpha_link->fromsock,
3230 *set_alpha_node,
3231 *set_alpha_alpha);
3232 version_node_add_link(*node_tree, *set_alpha_node, *set_alpha_output, *node, *image_input);
3233 blender::bke::node_remove_link(node_tree, *alpha_link);
3234
3235 if (!node_to_image_link_map.contains(node->name)) {
3236 copy_v4_v4(set_alpha_input->default_value_typed<bNodeSocketValueRGBA>()->value,
3237 image_input->default_value_typed<bNodeSocketValueRGBA>()->value);
3238 }
3239 else {
3240 bNodeLink *image_link = node_to_image_link_map.lookup(node->name);
3241 version_node_add_link(*node_tree,
3242 *image_link->fromnode,
3243 *image_link->fromsock,
3244 *set_alpha_node,
3245 *set_alpha_input);
3246 blender::bke::node_remove_link(node_tree, *image_link);
3247 }
3248 }
3249}
3250
3251/* The Convert Premultiplied option was removed. If enabled, a convert alpha node will be added
3252 * before and after the node to perform the adjustment in straight alpha. */
3254{
3255 LISTBASE_FOREACH_BACKWARD_MUTABLE (bNodeLink *, link, &node_tree->links) {
3256 if (link->tonode->type_legacy != CMP_NODE_BRIGHTCONTRAST) {
3257 continue;
3258 }
3259
3260 if (!bool(link->tonode->custom1)) {
3261 continue;
3262 }
3263
3264 if (blender::StringRef(link->tosock->identifier) != "Image") {
3265 continue;
3266 }
3267
3268 bNode *convert_alpha_node = blender::bke::node_add_static_node(
3269 nullptr, *node_tree, CMP_NODE_PREMULKEY);
3270 convert_alpha_node->parent = link->tonode->parent;
3271 convert_alpha_node->location[0] = link->tonode->location[0] - link->tonode->width - 20.0f;
3272 convert_alpha_node->location[1] = link->tonode->location[1];
3273 convert_alpha_node->custom1 = CMP_NODE_ALPHA_CONVERT_UNPREMULTIPLY;
3274
3275 bNodeSocket *convert_alpha_input = blender::bke::node_find_socket(
3276 *convert_alpha_node, SOCK_IN, "Image");
3277 bNodeSocket *convert_alpha_output = blender::bke::node_find_socket(
3278 *convert_alpha_node, SOCK_OUT, "Image");
3279
3281 *node_tree, *link->fromnode, *link->fromsock, *convert_alpha_node, *convert_alpha_input);
3283 *node_tree, *convert_alpha_node, *convert_alpha_output, *link->tonode, *link->tosock);
3284
3285 blender::bke::node_remove_link(node_tree, *link);
3286 }
3287
3288 LISTBASE_FOREACH_BACKWARD_MUTABLE (bNodeLink *, link, &node_tree->links) {
3289 if (link->fromnode->type_legacy != CMP_NODE_BRIGHTCONTRAST) {
3290 continue;
3291 }
3292
3293 if (!bool(link->fromnode->custom1)) {
3294 continue;
3295 }
3296
3297 bNode *convert_alpha_node = blender::bke::node_add_static_node(
3298 nullptr, *node_tree, CMP_NODE_PREMULKEY);
3299 convert_alpha_node->parent = link->fromnode->parent;
3300 convert_alpha_node->location[0] = link->fromnode->location[0] + link->fromnode->width + 20.0f;
3301 convert_alpha_node->location[1] = link->fromnode->location[1];
3302 convert_alpha_node->custom1 = CMP_NODE_ALPHA_CONVERT_PREMULTIPLY;
3303
3304 bNodeSocket *convert_alpha_input = blender::bke::node_find_socket(
3305 *convert_alpha_node, SOCK_IN, "Image");
3306 bNodeSocket *convert_alpha_output = blender::bke::node_find_socket(
3307 *convert_alpha_node, SOCK_OUT, "Image");
3308
3310 *node_tree, *link->fromnode, *link->fromsock, *convert_alpha_node, *convert_alpha_input);
3312 *node_tree, *convert_alpha_node, *convert_alpha_output, *link->tonode, *link->tosock);
3313
3314 blender::bke::node_remove_link(node_tree, *link);
3315 }
3316}
3317
3318/* The Premultiply Mix option was removed. If enabled, the image is converted to premultiplied then
3319 * to straight, and both are mixed using a mix node. */
3321{
3322 LISTBASE_FOREACH_BACKWARD_MUTABLE (bNodeLink *, link, &node_tree->links) {
3323 if (link->tonode->type_legacy != CMP_NODE_ALPHAOVER) {
3324 continue;
3325 }
3326
3327 const float mix_factor = static_cast<NodeTwoFloats *>(link->tonode->storage)->x;
3328 if (mix_factor == 0.0f) {
3329 continue;
3330 }
3331
3332 if (blender::StringRef(link->tosock->identifier) != "Image_001") {
3333 continue;
3334 }
3335
3336 /* Disable Convert Premultiplied option, since this will be done manually. */
3337 link->tonode->custom1 = false;
3338
3339 bNode *mix_node = blender::bke::node_add_static_node(nullptr, *node_tree, SH_NODE_MIX);
3340 mix_node->parent = link->tonode->parent;
3341 mix_node->location[0] = link->tonode->location[0] - link->tonode->width - 20.0f;
3342 mix_node->location[1] = link->tonode->location[1];
3343 static_cast<NodeShaderMix *>(mix_node->storage)->data_type = SOCK_RGBA;
3344
3345 bNodeSocket *mix_a_input = blender::bke::node_find_socket(*mix_node, SOCK_IN, "A_Color");
3346 bNodeSocket *mix_b_input = blender::bke::node_find_socket(*mix_node, SOCK_IN, "B_Color");
3347 bNodeSocket *mix_factor_input = blender::bke::node_find_socket(
3348 *mix_node, SOCK_IN, "Factor_Float");
3349 bNodeSocket *mix_output = blender::bke::node_find_socket(*mix_node, SOCK_OUT, "Result_Color");
3350
3351 mix_factor_input->default_value_typed<bNodeSocketValueFloat>()->value = mix_factor;
3352
3353 bNode *to_straight_node = blender::bke::node_add_static_node(
3354 nullptr, *node_tree, CMP_NODE_PREMULKEY);
3355 to_straight_node->parent = link->tonode->parent;
3356 to_straight_node->location[0] = mix_node->location[0] - mix_node->width - 20.0f;
3357 to_straight_node->location[1] = mix_node->location[1];
3358 to_straight_node->custom1 = CMP_NODE_ALPHA_CONVERT_UNPREMULTIPLY;
3359
3360 bNodeSocket *to_straight_input = blender::bke::node_find_socket(
3361 *to_straight_node, SOCK_IN, "Image");
3362 bNodeSocket *to_straight_output = blender::bke::node_find_socket(
3363 *to_straight_node, SOCK_OUT, "Image");
3364
3365 bNode *to_premultiplied_node = blender::bke::node_add_static_node(
3366 nullptr, *node_tree, CMP_NODE_PREMULKEY);
3367 to_premultiplied_node->parent = link->tonode->parent;
3368 to_premultiplied_node->location[0] = to_straight_node->location[0] - to_straight_node->width -
3369 20.0f;
3370 to_premultiplied_node->location[1] = to_straight_node->location[1];
3371 to_premultiplied_node->custom1 = CMP_NODE_ALPHA_CONVERT_PREMULTIPLY;
3372
3373 bNodeSocket *to_premultiplied_input = blender::bke::node_find_socket(
3374 *to_premultiplied_node, SOCK_IN, "Image");
3375 bNodeSocket *to_premultiplied_output = blender::bke::node_find_socket(
3376 *to_premultiplied_node, SOCK_OUT, "Image");
3377
3378 version_node_add_link(*node_tree,
3379 *link->fromnode,
3380 *link->fromsock,
3381 *to_premultiplied_node,
3382 *to_premultiplied_input);
3383 version_node_add_link(*node_tree,
3384 *to_premultiplied_node,
3385 *to_premultiplied_output,
3386 *to_straight_node,
3387 *to_straight_input);
3389 *node_tree, *to_premultiplied_node, *to_premultiplied_output, *mix_node, *mix_b_input);
3391 *node_tree, *to_straight_node, *to_straight_output, *mix_node, *mix_a_input);
3392 version_node_add_link(*node_tree, *mix_node, *mix_output, *link->tonode, *link->tosock);
3393
3394 blender::bke::node_remove_link(node_tree, *link);
3395 }
3396
3397 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
3398 if (node->type_legacy == CMP_NODE_ALPHAOVER) {
3399 NodeTwoFloats *storage = static_cast<NodeTwoFloats *>(node->storage);
3400 MEM_freeN(storage);
3401 node->storage = nullptr;
3402 }
3403 }
3404}
3405
3406/* The options were converted into inputs. */
3408{
3409 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Straight Alpha")) {
3411 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Straight Alpha", "Straight Alpha");
3412 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(node->custom1);
3413 }
3414}
3415
3416/* The options were converted into inputs. */
3418 bNode *node)
3419{
3420 /* Compute the RNA path of the node. */
3421 char escaped_node_name[sizeof(node->name) * 2 + 1];
3422 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
3423 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
3424
3425 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
3426 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
3427 * path. */
3428 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
3429 return;
3430 }
3431
3432 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
3433 * values of the FCurves frames when needed. */
3434 char *old_rna_path = fcurve->rna_path;
3435 if (BLI_str_endswith(fcurve->rna_path, "use_premultiply")) {
3436 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
3437 }
3438
3439 /* The RNA path was changed, free the old path. */
3440 if (fcurve->rna_path != old_rna_path) {
3441 MEM_freeN(old_rna_path);
3442 }
3443 });
3444}
3445
3446/* The options were converted into inputs. */
3448{
3449 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Extend Bounds")) {
3451 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Extend Bounds", "Extend Bounds");
3452 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(node->custom1);
3453 }
3454}
3455
3456/* The options were converted into inputs. */
3458 bNode *node)
3459{
3460 /* Compute the RNA path of the node. */
3461 char escaped_node_name[sizeof(node->name) * 2 + 1];
3462 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
3463 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
3464
3465 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
3466 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
3467 * path. */
3468 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
3469 return;
3470 }
3471
3472 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
3473 * values of the FCurves frames when needed. */
3474 char *old_rna_path = fcurve->rna_path;
3475 if (BLI_str_endswith(fcurve->rna_path, "use_extended_bounds")) {
3476 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
3477 }
3478
3479 /* The RNA path was changed, free the old path. */
3480 if (fcurve->rna_path != old_rna_path) {
3481 MEM_freeN(old_rna_path);
3482 }
3483 });
3484}
3485
3486/* The XY Offset option was removed. If enabled, the image is translated in relative space using X
3487 * and Y, so add a Translate node to achieve the same function. */
3489{
3490 LISTBASE_FOREACH_BACKWARD_MUTABLE (bNodeLink *, link, &node_tree->links) {
3491 if (link->fromnode->type_legacy != CMP_NODE_SCALE) {
3492 continue;
3493 }
3494
3495 if (link->fromnode->custom1 != CMP_NODE_SCALE_RENDER_SIZE) {
3496 continue;
3497 }
3498
3499 const float x = link->fromnode->custom3;
3500 const float y = link->fromnode->custom4;
3501 if (x == 0.0f && y == 0.0f) {
3502 continue;
3503 }
3504
3505 bNode *translate_node = blender::bke::node_add_static_node(
3506 nullptr, *node_tree, CMP_NODE_TRANSLATE);
3507 translate_node->parent = link->fromnode->parent;
3508 translate_node->location[0] = link->fromnode->location[0] + link->fromnode->width + 20.0f;
3509 translate_node->location[1] = link->fromnode->location[1];
3510 static_cast<NodeTranslateData *>(translate_node->storage)->interpolation =
3511 static_cast<NodeScaleData *>(link->fromnode->storage)->interpolation;
3512 static_cast<NodeTranslateData *>(translate_node->storage)->relative = true;
3513
3514 bNodeSocket *translate_image_input = blender::bke::node_find_socket(
3515 *translate_node, SOCK_IN, "Image");
3516 bNodeSocket *translate_x_input = blender::bke::node_find_socket(*translate_node, SOCK_IN, "X");
3517 bNodeSocket *translate_y_input = blender::bke::node_find_socket(*translate_node, SOCK_IN, "Y");
3518 bNodeSocket *translate_image_output = blender::bke::node_find_socket(
3519 *translate_node, SOCK_OUT, "Image");
3520
3521 translate_x_input->default_value_typed<bNodeSocketValueFloat>()->value = x;
3522 translate_y_input->default_value_typed<bNodeSocketValueFloat>()->value = y;
3523
3525 *node_tree, *link->fromnode, *link->fromsock, *translate_node, *translate_image_input);
3527 *node_tree, *translate_node, *translate_image_output, *link->tonode, *link->tosock);
3528
3529 blender::bke::node_remove_link(node_tree, *link);
3530 }
3531}
3532
3538static void version_escape_curly_braces(char string[], const int string_array_length)
3539{
3540 int bytes_processed = 0;
3541 while (bytes_processed < string_array_length && string[bytes_processed] != '\0') {
3542 if (string[bytes_processed] == '{') {
3544 string, string_array_length, bytes_processed, bytes_processed + 1, "{{");
3545 bytes_processed += 2;
3546 continue;
3547 }
3548 if (string[bytes_processed] == '}') {
3550 string, string_array_length, bytes_processed, bytes_processed + 1, "}}");
3551 bytes_processed += 2;
3552 continue;
3553 }
3554 bytes_processed++;
3555 }
3556}
3557
3558/* The Gamma option was removed. If enabled, a Gamma node will be added before and after
3559 * the node to perform the adjustment in sRGB space. */
3561{
3562 LISTBASE_FOREACH_BACKWARD_MUTABLE (bNodeLink *, link, &node_tree->links) {
3563 if (!ELEM(link->tonode->type_legacy, CMP_NODE_BLUR, CMP_NODE_DEFOCUS)) {
3564 continue;
3565 }
3566
3567 if (link->tonode->type_legacy == CMP_NODE_BLUR &&
3568 !bool(static_cast<NodeBlurData *>(link->tonode->storage)->gamma))
3569 {
3570 continue;
3571 }
3572
3573 if (link->tonode->type_legacy == CMP_NODE_DEFOCUS &&
3574 !bool(static_cast<NodeDefocus *>(link->tonode->storage)->gamco))
3575 {
3576 continue;
3577 }
3578
3579 if (blender::StringRef(link->tosock->identifier) != "Image") {
3580 continue;
3581 }
3582
3583 bNode *gamma_node = blender::bke::node_add_static_node(nullptr, *node_tree, CMP_NODE_GAMMA);
3584 gamma_node->parent = link->tonode->parent;
3585 gamma_node->location[0] = link->tonode->location[0] - link->tonode->width - 20.0f;
3586 gamma_node->location[1] = link->tonode->location[1];
3587
3588 bNodeSocket *image_input = blender::bke::node_find_socket(*gamma_node, SOCK_IN, "Image");
3589 bNodeSocket *image_output = blender::bke::node_find_socket(*gamma_node, SOCK_OUT, "Image");
3590
3591 bNodeSocket *gamma_input = blender::bke::node_find_socket(*gamma_node, SOCK_IN, "Gamma");
3592 gamma_input->default_value_typed<bNodeSocketValueFloat>()->value = 2.0f;
3593
3594 version_node_add_link(*node_tree, *link->fromnode, *link->fromsock, *gamma_node, *image_input);
3595 version_node_add_link(*node_tree, *gamma_node, *image_output, *link->tonode, *link->tosock);
3596
3597 blender::bke::node_remove_link(node_tree, *link);
3598 }
3599
3600 LISTBASE_FOREACH_BACKWARD_MUTABLE (bNodeLink *, link, &node_tree->links) {
3601 if (!ELEM(link->fromnode->type_legacy, CMP_NODE_BLUR, CMP_NODE_DEFOCUS)) {
3602 continue;
3603 }
3604
3605 if (link->fromnode->type_legacy == CMP_NODE_BLUR &&
3606 !bool(static_cast<NodeBlurData *>(link->fromnode->storage)->gamma))
3607 {
3608 continue;
3609 }
3610
3611 if (link->fromnode->type_legacy == CMP_NODE_DEFOCUS &&
3612 !bool(static_cast<NodeDefocus *>(link->fromnode->storage)->gamco))
3613 {
3614 continue;
3615 }
3616
3617 bNode *gamma_node = blender::bke::node_add_static_node(nullptr, *node_tree, CMP_NODE_GAMMA);
3618 gamma_node->parent = link->fromnode->parent;
3619 gamma_node->location[0] = link->fromnode->location[0] + link->fromnode->width + 20.0f;
3620 gamma_node->location[1] = link->fromnode->location[1];
3621
3622 bNodeSocket *image_input = blender::bke::node_find_socket(*gamma_node, SOCK_IN, "Image");
3623 bNodeSocket *image_output = blender::bke::node_find_socket(*gamma_node, SOCK_OUT, "Image");
3624
3625 bNodeSocket *gamma_input = blender::bke::node_find_socket(*gamma_node, SOCK_IN, "Gamma");
3626 gamma_input->default_value_typed<bNodeSocketValueFloat>()->value = 0.5f;
3627
3628 version_node_add_link(*node_tree, *link->fromnode, *link->fromsock, *gamma_node, *image_input);
3629 version_node_add_link(*node_tree, *gamma_node, *image_output, *link->tonode, *link->tosock);
3630
3631 blender::bke::node_remove_link(node_tree, *link);
3632 }
3633}
3634
3642{
3643 if (nodetree.type != NTREE_COMPOSIT) {
3644 return;
3645 }
3646
3647 LISTBASE_FOREACH (bNode *, node, &nodetree.nodes) {
3648 if (!STREQ(node->idname, "CompositorNodeOutputFile")) {
3649 continue;
3650 }
3651
3652 NodeImageMultiFile *node_data = static_cast<NodeImageMultiFile *>(node->storage);
3654
3655 LISTBASE_FOREACH (bNodeSocket *, sock, &node->inputs) {
3656 NodeImageMultiFileSocket *socket_data = static_cast<NodeImageMultiFileSocket *>(
3657 sock->storage);
3659 }
3660 }
3661}
3662
3663/* The Relative option was removed. Insert Relative To Pixel nodes for the X and Y inputs to
3664 * convert relative values to pixel values. */
3666{
3667 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
3668 if (!STREQ(node->idname, "CompositorNodeTranslate")) {
3669 continue;
3670 }
3671
3672 const NodeTranslateData *data = static_cast<NodeTranslateData *>(node->storage);
3673 if (!data) {
3674 continue;
3675 }
3676
3677 if (!bool(data->relative)) {
3678 continue;
3679 }
3680
3681 /* Find links going into the node. */
3682 bNodeLink *image_link = nullptr;
3683 bNodeLink *x_link = nullptr;
3684 bNodeLink *y_link = nullptr;
3685 LISTBASE_FOREACH (bNodeLink *, link, &node_tree->links) {
3686 if (link->tonode != node) {
3687 continue;
3688 }
3689
3690 if (blender::StringRef(link->tosock->identifier) == "Image") {
3691 image_link = link;
3692 }
3693
3694 if (blender::StringRef(link->tosock->identifier) == "X") {
3695 x_link = link;
3696 }
3697
3698 if (blender::StringRef(link->tosock->identifier) == "Y") {
3699 y_link = link;
3700 }
3701 }
3702
3703 /* Image input is unlinked, so the node does nothing. */
3704 if (!image_link) {
3705 continue;
3706 }
3707
3708 /* Add a Relative To Pixel node, assign it the input of the X translation and connect it to the
3709 * X translation input. */
3710 bNode *x_relative_to_pixel_node = blender::bke::node_add_node(
3711 nullptr, *node_tree, "CompositorNodeRelativeToPixel");
3712 x_relative_to_pixel_node->parent = node->parent;
3713 x_relative_to_pixel_node->location[0] = node->location[0] - node->width - 20.0f;
3714 x_relative_to_pixel_node->location[1] = node->location[1];
3715
3716 x_relative_to_pixel_node->custom1 = CMP_NODE_RELATIVE_TO_PIXEL_DATA_TYPE_FLOAT;
3718
3720 *x_relative_to_pixel_node, SOCK_IN, "Image");
3722 *x_relative_to_pixel_node, SOCK_IN, "Float Value");
3724 *x_relative_to_pixel_node, SOCK_OUT, "Float Value");
3725
3726 bNodeSocket *x_input = blender::bke::node_find_socket(*node, SOCK_IN, "X");
3727 x_value_input->default_value_typed<bNodeSocketValueFloat>()->value =
3728 x_input->default_value_typed<bNodeSocketValueFloat>()->value;
3729
3730 version_node_add_link(*node_tree, *x_relative_to_pixel_node, *x_value_output, *node, *x_input);
3731 version_node_add_link(*node_tree,
3732 *image_link->fromnode,
3733 *image_link->fromsock,
3734 *x_relative_to_pixel_node,
3735 *x_image_input);
3736
3737 if (x_link) {
3738 version_node_add_link(*node_tree,
3739 *x_link->fromnode,
3740 *x_link->fromsock,
3741 *x_relative_to_pixel_node,
3742 *x_value_input);
3743 blender::bke::node_remove_link(node_tree, *x_link);
3744 }
3745
3746 /* Add a Relative To Pixel node, assign it the input of the Y translation and connect it to the
3747 * Y translation input. */
3748 bNode *y_relative_to_pixel_node = blender::bke::node_add_node(
3749 nullptr, *node_tree, "CompositorNodeRelativeToPixel");
3750 y_relative_to_pixel_node->parent = node->parent;
3751 y_relative_to_pixel_node->location[0] = node->location[0] - node->width - 20.0f;
3752 y_relative_to_pixel_node->location[1] = node->location[1] - 20.0f;
3753
3754 y_relative_to_pixel_node->custom1 = CMP_NODE_RELATIVE_TO_PIXEL_DATA_TYPE_FLOAT;
3756
3758 *y_relative_to_pixel_node, SOCK_IN, "Image");
3760 *y_relative_to_pixel_node, SOCK_IN, "Float Value");
3762 *y_relative_to_pixel_node, SOCK_OUT, "Float Value");
3763
3764 bNodeSocket *y_input = blender::bke::node_find_socket(*node, SOCK_IN, "Y");
3765 y_value_input->default_value_typed<bNodeSocketValueFloat>()->value =
3766 y_input->default_value_typed<bNodeSocketValueFloat>()->value;
3767
3768 version_node_add_link(*node_tree, *y_relative_to_pixel_node, *y_value_output, *node, *y_input);
3769 version_node_add_link(*node_tree,
3770 *image_link->fromnode,
3771 *image_link->fromsock,
3772 *y_relative_to_pixel_node,
3773 *y_image_input);
3774
3775 if (y_link) {
3776 version_node_add_link(*node_tree,
3777 *y_link->fromnode,
3778 *y_link->fromsock,
3779 *y_relative_to_pixel_node,
3780 *y_value_input);
3781 blender::bke::node_remove_link(node_tree, *y_link);
3782 }
3783 }
3784}
3785
3786/* The options were converted into inputs, but the Relative option was removed. If relative is
3787 * enabled, we add Relative To Pixel nodes to convert the relative values to pixels. */
3789{
3790 NodeTwoXYs *storage = static_cast<NodeTwoXYs *>(node->storage);
3791 if (!storage) {
3792 return;
3793 }
3794
3795 if (!blender::bke::node_find_socket(*node, SOCK_IN, "X")) {
3797 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "X", "X");
3798 input->default_value_typed<bNodeSocketValueInt>()->value = storage->x1;
3799 }
3800
3801 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Y")) {
3803 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Y", "Y");
3804 input->default_value_typed<bNodeSocketValueInt>()->value = storage->y2;
3805 }
3806
3807 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Width")) {
3809 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Width", "Width");
3810 input->default_value_typed<bNodeSocketValueInt>()->value = storage->x2 - storage->x1;
3811 }
3812
3813 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Height")) {
3815 *node_tree, *node, SOCK_IN, SOCK_INT, PROP_NONE, "Height", "Height");
3816 input->default_value_typed<bNodeSocketValueInt>()->value = storage->y1 - storage->y2;
3817 }
3818
3819 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Alpha Crop")) {
3821 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Alpha Crop", "Alpha Crop");
3822 input->default_value_typed<bNodeSocketValueBoolean>()->value = !bool(node->custom1);
3823 }
3824
3825 /* Find links going into the node. */
3826 bNodeLink *image_link = nullptr;
3827 LISTBASE_FOREACH (bNodeLink *, link, &node_tree->links) {
3828 if (link->tonode != node) {
3829 continue;
3830 }
3831
3832 if (blender::StringRef(link->tosock->identifier) == "Image") {
3833 image_link = link;
3834 }
3835 }
3836
3837 /* If Relative is not enabled or no image is connected, nothing else to do. */
3838 if (!bool(node->custom2) || !image_link) {
3839 MEM_freeN(storage);
3840 node->storage = nullptr;
3841 return;
3842 }
3843
3844 bNode *x_relative_to_pixel_node = blender::bke::node_add_node(
3845 nullptr, *node_tree, "CompositorNodeRelativeToPixel");
3846 x_relative_to_pixel_node->parent = node->parent;
3847 x_relative_to_pixel_node->location[0] = node->location[0] - node->width - 20.0f;
3848 x_relative_to_pixel_node->location[1] = node->location[1];
3849
3850 x_relative_to_pixel_node->custom1 = CMP_NODE_RELATIVE_TO_PIXEL_DATA_TYPE_FLOAT;
3852
3854 *x_relative_to_pixel_node, SOCK_IN, "Image");
3856 *x_relative_to_pixel_node, SOCK_IN, "Float Value");
3858 *x_relative_to_pixel_node, SOCK_OUT, "Float Value");
3859
3860 x_value_input->default_value_typed<bNodeSocketValueFloat>()->value = storage->fac_x1;
3861
3862 bNodeSocket *x_input = blender::bke::node_find_socket(*node, SOCK_IN, "X");
3863 version_node_add_link(*node_tree, *x_relative_to_pixel_node, *x_value_output, *node, *x_input);
3864 version_node_add_link(*node_tree,
3865 *image_link->fromnode,
3866 *image_link->fromsock,
3867 *x_relative_to_pixel_node,
3868 *x_image_input);
3869
3870 bNode *y_relative_to_pixel_node = blender::bke::node_add_node(
3871 nullptr, *node_tree, "CompositorNodeRelativeToPixel");
3872 y_relative_to_pixel_node->parent = node->parent;
3873 y_relative_to_pixel_node->location[0] = node->location[0] - node->width - 20.0f;
3874 y_relative_to_pixel_node->location[1] = node->location[1] - 10;
3875
3876 y_relative_to_pixel_node->custom1 = CMP_NODE_RELATIVE_TO_PIXEL_DATA_TYPE_FLOAT;
3878
3880 *y_relative_to_pixel_node, SOCK_IN, "Image");
3882 *y_relative_to_pixel_node, SOCK_IN, "Float Value");
3884 *y_relative_to_pixel_node, SOCK_OUT, "Float Value");
3885
3886 bNodeSocket *y_input = blender::bke::node_find_socket(*node, SOCK_IN, "Y");
3887 y_value_input->default_value_typed<bNodeSocketValueFloat>()->value = storage->fac_y2;
3888
3889 version_node_add_link(*node_tree, *y_relative_to_pixel_node, *y_value_output, *node, *y_input);
3890 version_node_add_link(*node_tree,
3891 *image_link->fromnode,
3892 *image_link->fromsock,
3893 *y_relative_to_pixel_node,
3894 *y_image_input);
3895
3896 bNode *width_relative_to_pixel_node = blender::bke::node_add_node(
3897 nullptr, *node_tree, "CompositorNodeRelativeToPixel");
3898 width_relative_to_pixel_node->parent = node->parent;
3899 width_relative_to_pixel_node->location[0] = node->location[0] - node->width - 20.0f;
3900 width_relative_to_pixel_node->location[1] = node->location[1] - 20;
3901
3902 width_relative_to_pixel_node->custom1 = CMP_NODE_RELATIVE_TO_PIXEL_DATA_TYPE_FLOAT;
3903 width_relative_to_pixel_node->custom2 = CMP_NODE_RELATIVE_TO_PIXEL_REFERENCE_DIMENSION_X;
3904
3905 bNodeSocket *width_image_input = blender::bke::node_find_socket(
3906 *width_relative_to_pixel_node, SOCK_IN, "Image");
3907 bNodeSocket *width_value_input = blender::bke::node_find_socket(
3908 *width_relative_to_pixel_node, SOCK_IN, "Float Value");
3909 bNodeSocket *width_value_output = blender::bke::node_find_socket(
3910 *width_relative_to_pixel_node, SOCK_OUT, "Float Value");
3911
3912 bNodeSocket *width_input = blender::bke::node_find_socket(*node, SOCK_IN, "Width");
3913 width_value_input->default_value_typed<bNodeSocketValueFloat>()->value = storage->fac_x2 -
3914 storage->fac_x1;
3915
3917 *node_tree, *width_relative_to_pixel_node, *width_value_output, *node, *width_input);
3918 version_node_add_link(*node_tree,
3919 *image_link->fromnode,
3920 *image_link->fromsock,
3921 *width_relative_to_pixel_node,
3922 *width_image_input);
3923
3924 bNode *height_relative_to_pixel_node = blender::bke::node_add_node(
3925 nullptr, *node_tree, "CompositorNodeRelativeToPixel");
3926 height_relative_to_pixel_node->parent = node->parent;
3927 height_relative_to_pixel_node->location[0] = node->location[0] - node->width - 20.0f;
3928 height_relative_to_pixel_node->location[1] = node->location[1] - 30;
3929
3930 height_relative_to_pixel_node->custom1 = CMP_NODE_RELATIVE_TO_PIXEL_DATA_TYPE_FLOAT;
3931 height_relative_to_pixel_node->custom2 = CMP_NODE_RELATIVE_TO_PIXEL_REFERENCE_DIMENSION_Y;
3932
3933 bNodeSocket *height_image_input = blender::bke::node_find_socket(
3934 *height_relative_to_pixel_node, SOCK_IN, "Image");
3935 bNodeSocket *height_value_input = blender::bke::node_find_socket(
3936 *height_relative_to_pixel_node, SOCK_IN, "Float Value");
3937 bNodeSocket *height_value_output = blender::bke::node_find_socket(
3938 *height_relative_to_pixel_node, SOCK_OUT, "Float Value");
3939
3940 bNodeSocket *height_input = blender::bke::node_find_socket(*node, SOCK_IN, "Height");
3941 height_value_input->default_value_typed<bNodeSocketValueFloat>()->value = storage->fac_y1 -
3942 storage->fac_y2;
3943
3945 *node_tree, *height_relative_to_pixel_node, *height_value_output, *node, *height_input);
3946 version_node_add_link(*node_tree,
3947 *image_link->fromnode,
3948 *image_link->fromsock,
3949 *height_relative_to_pixel_node,
3950 *height_image_input);
3951
3952 MEM_freeN(storage);
3953 node->storage = nullptr;
3954}
3955
3956/* The options were converted into inputs. */
3958{
3959 /* Compute the RNA path of the node. */
3960 char escaped_node_name[sizeof(node->name) * 2 + 1];
3961 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
3962 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
3963
3964 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
3965 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
3966 * path. */
3967 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
3968 return;
3969 }
3970
3971 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
3972 * values of the FCurves frames when needed. */
3973 char *old_rna_path = fcurve->rna_path;
3974 if (BLI_str_endswith(fcurve->rna_path, "min_x")) {
3975 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
3976 }
3977 else if (BLI_str_endswith(fcurve->rna_path, "max_y")) {
3978 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
3979 }
3980 else if (BLI_str_endswith(fcurve->rna_path, "max_x")) {
3981 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
3982 }
3983 else if (BLI_str_endswith(fcurve->rna_path, "min_y")) {
3984 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[4].default_value");
3985 }
3986 else if (BLI_str_endswith(fcurve->rna_path, "use_crop_size")) {
3987 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[5].default_value");
3988 adjust_fcurve_key_frame_values(
3989 fcurve, PROP_BOOLEAN, [&](const float value) { return 1.0f - value; });
3990 }
3991
3992 /* The RNA path was changed, free the old path. */
3993 if (fcurve->rna_path != old_rna_path) {
3994 MEM_freeN(old_rna_path);
3995 }
3996 });
3997}
3998
3999/* The options were converted into inputs. */
4001{
4002 NodeColorBalance *storage = static_cast<NodeColorBalance *>(node->storage);
4003 if (!storage) {
4004 return;
4005 }
4006
4007 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Color Lift")) {
4009 *node_tree, *node, SOCK_IN, SOCK_RGBA, PROP_NONE, "Color Lift", "Lift");
4010 copy_v3_v3(input->default_value_typed<bNodeSocketValueRGBA>()->value, storage->lift);
4011 }
4012
4013 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Color Gamma")) {
4015 *node_tree, *node, SOCK_IN, SOCK_RGBA, PROP_NONE, "Color Gamma", "Gamma");
4016 copy_v3_v3(input->default_value_typed<bNodeSocketValueRGBA>()->value, storage->gamma);
4017 }
4018
4019 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Color Gain")) {
4021 *node_tree, *node, SOCK_IN, SOCK_RGBA, PROP_NONE, "Color Gain", "Gain");
4022 copy_v3_v3(input->default_value_typed<bNodeSocketValueRGBA>()->value, storage->gain);
4023 }
4024
4025 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Color Offset")) {
4027 *node_tree, *node, SOCK_IN, SOCK_RGBA, PROP_NONE, "Color Offset", "Offset");
4028 copy_v3_v3(input->default_value_typed<bNodeSocketValueRGBA>()->value, storage->offset);
4029 }
4030
4031 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Color Power")) {
4033 *node_tree, *node, SOCK_IN, SOCK_RGBA, PROP_NONE, "Color Power", "Power");
4034 copy_v3_v3(input->default_value_typed<bNodeSocketValueRGBA>()->value, storage->power);
4035 }
4036
4037 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Color Slope")) {
4039 *node_tree, *node, SOCK_IN, SOCK_RGBA, PROP_NONE, "Color Slope", "Slope");
4040 copy_v3_v3(input->default_value_typed<bNodeSocketValueRGBA>()->value, storage->slope);
4041 }
4042
4043 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Base Offset")) {
4045 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "Base Offset", "Offset");
4046 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->offset_basis;
4047 }
4048
4049 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Input Temperature")) {
4051 *node,
4052 SOCK_IN,
4053 SOCK_FLOAT,
4055 "Input Temperature",
4056 "Temperature");
4057 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->input_temperature;
4058 }
4059
4060 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Input Tint")) {
4062 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "Input Tint", "Tint");
4063 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->input_tint;
4064 }
4065
4066 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Output Temperature")) {
4068 *node,
4069 SOCK_IN,
4070 SOCK_FLOAT,
4072 "Output Temperature",
4073 "Temperature");
4074 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->output_temperature;
4075 }
4076
4077 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Output Tint")) {
4079 *node_tree, *node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "Output Tint", "Tint");
4080 input->default_value_typed<bNodeSocketValueFloat>()->value = storage->output_tint;
4081 }
4082
4083 MEM_freeN(storage);
4084 node->storage = nullptr;
4085}
4086
4087/* The options were converted into inputs. */
4089 bNode *node)
4090{
4091 /* Compute the RNA path of the node. */
4092 char escaped_node_name[sizeof(node->name) * 2 + 1];
4093 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
4094 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
4095
4096 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
4097 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
4098 * path. */
4099 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
4100 return;
4101 }
4102
4103 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
4104 * values of the FCurves frames when needed. */
4105 char *old_rna_path = fcurve->rna_path;
4106 if (BLI_str_endswith(fcurve->rna_path, "lift")) {
4107 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
4108 }
4109 else if (BLI_str_endswith(fcurve->rna_path, "gamma")) {
4110 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[5].default_value");
4111 }
4112 else if (BLI_str_endswith(fcurve->rna_path, "gain")) {
4113 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[7].default_value");
4114 }
4115 else if (BLI_str_endswith(fcurve->rna_path, "offset_basis")) {
4116 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[8].default_value");
4117 }
4118 else if (BLI_str_endswith(fcurve->rna_path, "offset")) {
4119 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[9].default_value");
4120 }
4121 else if (BLI_str_endswith(fcurve->rna_path, "power")) {
4122 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[11].default_value");
4123 }
4124 else if (BLI_str_endswith(fcurve->rna_path, "slope")) {
4125 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[13].default_value");
4126 }
4127 else if (BLI_str_endswith(fcurve->rna_path, "input_temperature")) {
4128 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[14].default_value");
4129 }
4130 else if (BLI_str_endswith(fcurve->rna_path, "input_tint")) {
4131 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[15].default_value");
4132 }
4133 else if (BLI_str_endswith(fcurve->rna_path, "output_temperature")) {
4134 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[16].default_value");
4135 }
4136 else if (BLI_str_endswith(fcurve->rna_path, "output_tint")) {
4137 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[17].default_value");
4138 }
4139
4140 /* The RNA path was changed, free the old path. */
4141 if (fcurve->rna_path != old_rna_path) {
4142 MEM_freeN(old_rna_path);
4143 }
4144 });
4145}
4146
4147/* The Coordinates outputs were moved into their own Texture Coordinate node. If used, add a
4148 * Texture Coordinates node and use it instead. */
4150{
4151 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4152 if (!STREQ(node->idname, "CompositorNodeImageInfo")) {
4153 continue;
4154 }
4155
4156 bNodeLink *input_link = nullptr;
4157 bNodeLink *output_texture_link = nullptr;
4158 bNodeLink *output_pixel_link = nullptr;
4159 LISTBASE_FOREACH (bNodeLink *, link, &node_tree->links) {
4160 if (link->tonode == node) {
4161 input_link = link;
4162 }
4163
4164 if (link->fromnode == node &&
4165 blender::StringRef(link->fromsock->identifier) == "Texture Coordinates")
4166 {
4167 output_texture_link = link;
4168 }
4169
4170 if (link->fromnode == node &&
4171 blender::StringRef(link->fromsock->identifier) == "Pixel Coordinates")
4172 {
4173 output_pixel_link = link;
4174 }
4175 }
4176
4177 if (!output_texture_link && !output_pixel_link) {
4178 continue;
4179 }
4180
4181 bNode *image_coordinates_node = blender::bke::node_add_node(
4182 nullptr, *node_tree, "CompositorNodeImageCoordinates");
4183 image_coordinates_node->parent = node->parent;
4184 image_coordinates_node->location[0] = node->location[0];
4185 image_coordinates_node->location[1] = node->location[1] - node->height - 10.0f;
4186
4187 if (input_link) {
4189 *image_coordinates_node, SOCK_IN, "Image");
4190 version_node_add_link(*node_tree,
4191 *input_link->fromnode,
4192 *input_link->fromsock,
4193 *image_coordinates_node,
4194 *image_input);
4195 }
4196
4197 if (output_texture_link) {
4199 *image_coordinates_node, SOCK_OUT, "Uniform");
4200 version_node_add_link(*node_tree,
4201 *image_coordinates_node,
4202 *uniform_output,
4203 *output_texture_link->tonode,
4204 *output_texture_link->tosock);
4205 blender::bke::node_remove_link(node_tree, *output_texture_link);
4206 }
4207
4208 if (output_pixel_link) {
4210 *image_coordinates_node, SOCK_OUT, "Pixel");
4211 version_node_add_link(*node_tree,
4212 *image_coordinates_node,
4213 *pixel_output,
4214 *output_pixel_link->tonode,
4215 *output_pixel_link->tosock);
4216 blender::bke::node_remove_link(node_tree, *output_pixel_link);
4217 }
4218 }
4219}
4220
4221/* Vector sockets can now have different dimensions, so set the dimensions for existing sockets to
4222 * 3.*/
4224{
4225 node_tree->tree_interface.foreach_item([&](bNodeTreeInterfaceItem &item) {
4226 if (item.item_type != NODE_INTERFACE_SOCKET) {
4227 return true;
4228 }
4229
4230 bNodeTreeInterfaceSocket &interface_socket =
4233 interface_socket.socket_type);
4234
4235 if (base_typeinfo->type == SOCK_VECTOR) {
4237 .dimensions = 3;
4238 }
4239 return true;
4240 });
4241
4242 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4243 LISTBASE_FOREACH (bNodeSocket *, socket, &node->inputs) {
4244 if (socket->type == SOCK_VECTOR) {
4245 socket->default_value_typed<bNodeSocketValueVector>()->dimensions = 3;
4246 }
4247 }
4248 LISTBASE_FOREACH (bNodeSocket *, socket, &node->outputs) {
4249 if (socket->type == SOCK_VECTOR) {
4250 socket->default_value_typed<bNodeSocketValueVector>()->dimensions = 3;
4251 }
4252 }
4253 }
4254}
4255
4256/* The options were converted into inputs, but the Relative option was removed. If relative is
4257 * enabled, we add Relative To Pixel nodes to convert the relative values to pixels. */
4259{
4260 NodeBlurData *storage = static_cast<NodeBlurData *>(node->storage);
4261 if (!storage) {
4262 return;
4263 }
4264
4265 bNodeSocket *size_input = blender::bke::node_find_socket(*node, SOCK_IN, "Size");
4266 const float old_size = size_input->default_value_typed<bNodeSocketValueFloat>()->value;
4267
4269 node_tree, node, size_input, SOCK_VECTOR, PROP_NONE);
4270 size_input->default_value_typed<bNodeSocketValueVector>()->value[0] = old_size * storage->sizex;
4271 size_input->default_value_typed<bNodeSocketValueVector>()->value[1] = old_size * storage->sizey;
4272
4273 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Extend Bounds")) {
4275 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Extend Bounds", "Extend Bounds");
4276 input->default_value_typed<bNodeSocketValueBoolean>()->value = bool(node->custom1 & (1 << 1));
4277 }
4278
4279 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Separable")) {
4281 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Separable", "Separable");
4282 input->default_value_typed<bNodeSocketValueBoolean>()->value = !bool(storage->bokeh);
4283 }
4284
4285 /* Find links going into the node. */
4286 bNodeLink *image_link = nullptr;
4287 bNodeLink *size_link = nullptr;
4288 LISTBASE_FOREACH (bNodeLink *, link, &node_tree->links) {
4289 if (link->tonode != node) {
4290 continue;
4291 }
4292
4293 if (blender::StringRef(link->tosock->identifier) == "Image") {
4294 image_link = link;
4295 }
4296
4297 if (blender::StringRef(link->tosock->identifier) == "Size") {
4298 size_link = link;
4299 }
4300 }
4301
4302 if (size_link) {
4303 bNode *multiply_node = blender::bke::node_add_node(
4304 nullptr, *node_tree, "ShaderNodeVectorMath");
4305 multiply_node->parent = node->parent;
4306 multiply_node->location[0] = node->location[0] - node->width - 40.0f;
4307 multiply_node->location[1] = node->location[1];
4308
4309 multiply_node->custom1 = NODE_VECTOR_MATH_SCALE;
4310
4311 bNodeSocket *vector_input = blender::bke::node_find_socket(*multiply_node, SOCK_IN, "Vector");
4312 bNodeSocket *scale_input = blender::bke::node_find_socket(*multiply_node, SOCK_IN, "Scale");
4314 *multiply_node, SOCK_OUT, "Vector");
4315
4316 if (storage->relative) {
4317 vector_input->default_value_typed<bNodeSocketValueVector>()->value[0] = storage->percentx /
4318 100.0f;
4319 vector_input->default_value_typed<bNodeSocketValueVector>()->value[1] = storage->percenty /
4320 100.0f;
4321 }
4322 else {
4323 vector_input->default_value_typed<bNodeSocketValueVector>()->value[0] = storage->sizex;
4324 vector_input->default_value_typed<bNodeSocketValueVector>()->value[1] = storage->sizey;
4325 }
4326
4328 *node_tree, *size_link->fromnode, *size_link->fromsock, *multiply_node, *scale_input);
4329 bNodeLink &new_link = version_node_add_link(
4330 *node_tree, *multiply_node, *vector_output, *node, *size_input);
4331 blender::bke::node_remove_link(node_tree, *size_link);
4332 size_link = &new_link;
4333 }
4334
4335 /* If Relative is not enabled or no image is connected, nothing else to do. */
4336 if (!bool(storage->relative) || !image_link) {
4337 return;
4338 }
4339
4340 bNode *relative_to_pixel_node = blender::bke::node_add_node(
4341 nullptr, *node_tree, "CompositorNodeRelativeToPixel");
4342 relative_to_pixel_node->parent = node->parent;
4343 relative_to_pixel_node->location[0] = node->location[0] - node->width - 20.0f;
4344 relative_to_pixel_node->location[1] = node->location[1];
4345
4346 relative_to_pixel_node->custom1 = CMP_NODE_RELATIVE_TO_PIXEL_DATA_TYPE_VECTOR;
4347 switch (storage->aspect) {
4350 break;
4353 break;
4355 relative_to_pixel_node->custom2 =
4357 break;
4358 default:
4360 break;
4361 }
4362
4364 *relative_to_pixel_node, SOCK_IN, "Image");
4366 *relative_to_pixel_node, SOCK_IN, "Vector Value");
4368 *relative_to_pixel_node, SOCK_OUT, "Vector Value");
4369
4370 version_node_add_link(*node_tree,
4371 *image_link->fromnode,
4372 *image_link->fromsock,
4373 *relative_to_pixel_node,
4374 *image_input);
4375 if (size_link) {
4376 version_node_add_link(*node_tree,
4377 *size_link->fromnode,
4378 *size_link->fromsock,
4379 *relative_to_pixel_node,
4380 *vector_input);
4381 blender::bke::node_remove_link(node_tree, *size_link);
4382 }
4383 else {
4384 vector_input->default_value_typed<bNodeSocketValueVector>()->value[0] = (storage->percentx /
4385 100.0f) *
4386 old_size;
4387 vector_input->default_value_typed<bNodeSocketValueVector>()->value[1] = (storage->percenty /
4388 100.0f) *
4389 old_size;
4390 }
4391 version_node_add_link(*node_tree, *relative_to_pixel_node, *vector_output, *node, *size_input);
4392}
4393
4394/* The options were converted into inputs. */
4396{
4397 /* Compute the RNA path of the node. */
4398 char escaped_node_name[sizeof(node->name) * 2 + 1];
4399 BLI_str_escape(escaped_node_name, node->name, sizeof(escaped_node_name));
4400 const std::string node_rna_path = fmt::format("nodes[\"{}\"]", escaped_node_name);
4401
4402 BKE_fcurves_id_cb(&node_tree->id, [&](ID * /*id*/, FCurve *fcurve) {
4403 /* The FCurve does not belong to the node since its RNA path doesn't start with the node's RNA
4404 * path. */
4405 if (!blender::StringRef(fcurve->rna_path).startswith(node_rna_path)) {
4406 return;
4407 }
4408
4409 /* Change the RNA path of the FCurve from the old properties to the new inputs, adjusting the
4410 * values of the FCurves frames when needed. */
4411 char *old_rna_path = fcurve->rna_path;
4412 if (BLI_str_endswith(fcurve->rna_path, "size_x")) {
4413 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
4414 fcurve->array_index = 0;
4415 }
4416 else if (BLI_str_endswith(fcurve->rna_path, "size_y")) {
4417 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[1].default_value");
4418 fcurve->array_index = 1;
4419 }
4420 else if (BLI_str_endswith(fcurve->rna_path, "use_extended_bounds")) {
4421 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[2].default_value");
4422 }
4423 else if (BLI_str_endswith(fcurve->rna_path, "use_bokeh")) {
4424 fcurve->rna_path = BLI_sprintfN("%s.%s", node_rna_path.c_str(), "inputs[3].default_value");
4425 adjust_fcurve_key_frame_values(
4426 fcurve, PROP_BOOLEAN, [&](const float value) { return 1.0f - value; });
4427 }
4428
4429 /* The RNA path was changed, free the old path. */
4430 if (fcurve->rna_path != old_rna_path) {
4431 MEM_freeN(old_rna_path);
4432 }
4433 });
4434}
4435
4436/* Unified paint settings need a default curve for the color jitter options. */
4449
4450/* GP_BRUSH_* settings in gpencil_settings->flag2 were deprecated and replaced with
4451 * brush->color_jitter_flag. */
4474
4475/* The options were converted into inputs. */
4477{
4478 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Flip X")) {
4480 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Flip X", "Flip X");
4481 input->default_value_typed<bNodeSocketValueBoolean>()->value = ELEM(node->custom1, 0, 2);
4482 }
4483
4484 if (!blender::bke::node_find_socket(*node, SOCK_IN, "Flip Y")) {
4486 *node_tree, *node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Flip Y", "Flip Y");
4487 input->default_value_typed<bNodeSocketValueBoolean>()->value = ELEM(node->custom1, 1, 2);
4488 }
4489}
4490
4492{
4493 blender::Map<bNodeSocket *, bNodeLink *> links_to_level_and_max_inputs;
4494 LISTBASE_FOREACH (bNodeLink *, link, &tree.links) {
4495 if (link->tosock) {
4496 if (ELEM(blender::StringRef(link->tosock->identifier), "Level", "Max")) {
4497 links_to_level_and_max_inputs.add(link->tosock, link);
4498 }
4499 }
4500 }
4501 LISTBASE_FOREACH_MUTABLE (bNode *, node, &tree.nodes) {
4502 if (!ELEM(node->type_legacy, GEO_NODE_SUBDIVISION_SURFACE, GEO_NODE_SUBDIVIDE_MESH)) {
4503 continue;
4504 }
4505 bNodeSocket *level_input = blender::bke::node_find_socket(*node, SOCK_IN, "Level");
4506 if (!level_input || level_input->type != SOCK_INT) {
4507 continue;
4508 }
4509 bNodeLink *link = links_to_level_and_max_inputs.lookup_default(level_input, nullptr);
4510 if (link) {
4511 bNode *origin_node = link->fromnode;
4512 if (origin_node->type_legacy == SH_NODE_CLAMP) {
4513 bNodeSocket *max_input_socket = blender::bke::node_find_socket(
4514 *origin_node, SOCK_IN, "Max");
4515 if (max_input_socket->type == SOCK_FLOAT &&
4516 !links_to_level_and_max_inputs.contains(max_input_socket))
4517 {
4518 if (max_input_socket->default_value_typed<bNodeSocketValueFloat>()->value <= 11.0f) {
4519 /* There is already a clamp node, so no need to add another one. */
4520 continue;
4521 }
4522 }
4523 }
4524 /* Insert clamp node. */
4525 bNode &clamp_node = version_node_add_empty(tree, "ShaderNodeClamp");
4526 clamp_node.parent = node->parent;
4527 clamp_node.location[0] = node->location[0] - 25;
4528 clamp_node.location[1] = node->location[1];
4529 bNodeSocket &clamp_value_input = version_node_add_socket(
4530 tree, clamp_node, SOCK_IN, "NodeSocketFloat", "Value");
4531 bNodeSocket &clamp_min_input = version_node_add_socket(
4532 tree, clamp_node, SOCK_IN, "NodeSocketFloat", "Min");
4533 bNodeSocket &clamp_max_input = version_node_add_socket(
4534 tree, clamp_node, SOCK_IN, "NodeSocketFloat", "Max");
4535 bNodeSocket &clamp_value_output = version_node_add_socket(
4536 tree, clamp_node, SOCK_OUT, "NodeSocketFloat", "Result");
4537
4538 static_cast<bNodeSocketValueFloat *>(clamp_min_input.default_value)->value = 0.0f;
4539 static_cast<bNodeSocketValueFloat *>(clamp_max_input.default_value)->value = 11.0f;
4540
4541 link->tosock = &clamp_value_input;
4542 version_node_add_link(tree, clamp_node, clamp_value_output, *node, *level_input);
4543 }
4544 else {
4545 /* Clamp value directly. */
4546 bNodeSocketValueInt *value = level_input->default_value_typed<bNodeSocketValueInt>();
4547 value->value = std::clamp(value->value, 0, 11);
4548 }
4549 }
4550
4552}
4553
4555{
4556 BrushGpencilSettings *settings = brush->gpencil_settings;
4557 float old_hsv_jitter[3] = {
4558 settings->random_hue, settings->random_saturation, settings->random_value};
4559 if (!is_zero_v3(old_hsv_jitter)) {
4560 brush->flag2 |= BRUSH_JITTER_COLOR;
4561 }
4562 copy_v3_v3(brush->hsv_jitter, old_hsv_jitter);
4563 if (brush->curve_rand_hue) {
4566 }
4567 else {
4569 }
4570 if (brush->curve_rand_saturation) {
4573 }
4574 else {
4576 }
4577 if (brush->curve_rand_value) {
4580 }
4581 else {
4583 }
4584}
4585
4587{
4588 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 8)) {
4589 FOREACH_NODETREE_BEGIN (bmain, ntree, id) {
4590 if (ntree->type == NTREE_COMPOSIT) {
4592 }
4593 }
4595 }
4596
4597 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 12)) {
4599 FOREACH_NODETREE_BEGIN (bmain, ntree, id) {
4600 if (ntree->type == NTREE_COMPOSIT) {
4602 }
4603 }
4605 }
4606
4607 /* For each F-Curve, set the F-Curve flags based on the property type it animates. This is to
4608 * correct F-Curves created while the bug (#136347) was in active use. Since this bug did not
4609 * appear before 4.4, and this versioning code has a bit of a performance impact (going over all
4610 * F-Curves of all Actions, and resolving them all to their RNA properties), it will be skipped
4611 * if the blend file is old enough to not be affected. */
4612 if (MAIN_VERSION_FILE_ATLEAST(bmain, 404, 0) && !MAIN_VERSION_FILE_ATLEAST(bmain, 405, 13)) {
4613 LISTBASE_FOREACH (bAction *, dna_action, &bmain->actions) {
4614 blender::animrig::Action &action = dna_action->wrap();
4615 for (const blender::animrig::Slot *slot : action.slots()) {
4616 blender::Span<ID *> slot_users = slot->users(*bmain);
4617 if (slot_users.is_empty()) {
4618 /* If nothing is using this slot, the RNA paths cannot be resolved, and so there
4619 * is no way to find the animated property type. */
4620 continue;
4621 }
4622 blender::animrig::foreach_fcurve_in_action_slot(action, slot->handle, [&](FCurve &fcurve) {
4623 /* Loop over all slot users, because when the slot is shared, not all F-Curves may
4624 * resolve on all users. For example, a custom property might only exist on a subset of
4625 * the users.*/
4626 for (ID *slot_user : slot_users) {
4627 PointerRNA slot_user_ptr = RNA_id_pointer_create(slot_user);
4628 PointerRNA ptr;
4629 PropertyRNA *prop;
4630 if (!RNA_path_resolve_property(&slot_user_ptr, fcurve.rna_path, &ptr, &prop)) {
4631 continue;
4632 }
4633
4634 blender::animrig::update_autoflags_fcurve_direct(&fcurve, RNA_property_type(prop));
4635 break;
4636 }
4637 });
4638 }
4639 }
4640 }
4641
4642 /* Because this was backported to 4.4 (f1e829a459) we need to exclude anything that was already
4643 * saved with that version otherwise we would apply the fix twice. */
4644 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 404, 32) ||
4645 (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 14) && bmain->versionfile >= 405))
4646 {
4647 LISTBASE_FOREACH (bAction *, dna_action, &bmain->actions) {
4648 blender::animrig::Action &action = dna_action->wrap();
4650 action, [&](FCurve &fcurve) { version_fix_fcurve_noise_offset(fcurve); });
4651 }
4652
4653 BKE_animdata_main_cb(bmain, [](ID * /* id */, AnimData *adt) {
4654 LISTBASE_FOREACH (FCurve *, fcurve, &adt->drivers) {
4656 }
4657 LISTBASE_FOREACH (NlaTrack *, track, &adt->nla_tracks) {
4658 nlastrips_apply_fcurve_versioning(track->strips);
4659 }
4660 });
4661 }
4662
4663 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 20)) {
4664 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4665 if (node_tree->type == NTREE_COMPOSIT) {
4666 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4667 if (node->type_legacy == CMP_NODE_GLARE) {
4669 }
4670 }
4671 }
4672 }
4674 }
4675
4676 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 22)) {
4677 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4678 if (node_tree->type == NTREE_COMPOSIT) {
4679 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4680 if (node->type_legacy == CMP_NODE_BOKEHIMAGE) {
4682 }
4683 }
4684 }
4685 }
4687 }
4688
4689 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 23)) {
4690 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4691 if (node_tree->type == NTREE_COMPOSIT) {
4692 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4693 if (node->type_legacy == CMP_NODE_TIME) {
4695 }
4696 }
4697 }
4698 }
4700 }
4701
4702 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 24)) {
4703 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4704 if (node_tree->type == NTREE_COMPOSIT) {
4705 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4706 if (node->type_legacy == CMP_NODE_MASK) {
4708 }
4709 }
4710 }
4711 }
4713 }
4714
4715 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 25)) {
4716 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4717 if (node_tree->type == NTREE_COMPOSIT) {
4718 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4719 if (node->type_legacy == CMP_NODE_SWITCH) {
4721 }
4722 }
4723 }
4724 }
4726 }
4727
4728 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 26)) {
4729 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4730 if (node_tree->type == NTREE_COMPOSIT) {
4731 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4732 if (node->type_legacy == CMP_NODE_SPLIT) {
4734 }
4735 }
4736 }
4737 }
4739 }
4740
4741 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 27)) {
4742 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4743 if (node_tree->type == NTREE_COMPOSIT) {
4744 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4745 if (node->type_legacy == CMP_NODE_INVERT) {
4747 }
4748 }
4749 }
4750 }
4752 }
4753
4754 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 28)) {
4755 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4756 if (node_tree->type == NTREE_COMPOSIT) {
4757 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4758 if (node->type_legacy == CMP_NODE_ZCOMBINE) {
4760 }
4761 }
4762 }
4763 }
4765 }
4766
4767 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 29)) {
4768 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4769 if (node_tree->type == NTREE_COMPOSIT) {
4770 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4771 if (node->type_legacy == CMP_NODE_TONEMAP) {
4773 }
4774 }
4775 }
4776 }
4778 }
4779
4780 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 30)) {
4781 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4782 if (node_tree->type == NTREE_COMPOSIT) {
4783 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4784 if (node->type_legacy == CMP_NODE_DILATEERODE) {
4786 }
4787 }
4788 }
4789 }
4791 }
4792
4793 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 31)) {
4794 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4795 if (node_tree->type == NTREE_COMPOSIT) {
4796 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4797 if (node->type_legacy == CMP_NODE_INPAINT) {
4799 }
4800 }
4801 }
4802 }
4804 }
4805
4806 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 32)) {
4807 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4808 if (node_tree->type == NTREE_COMPOSIT) {
4809 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4810 if (node->type_legacy == CMP_NODE_PIXELATE) {
4812 }
4813 }
4814 }
4815 }
4817 }
4818
4819 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 33)) {
4820 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4821 if (node_tree->type == NTREE_COMPOSIT) {
4822 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4823 if (node->type_legacy == CMP_NODE_KUWAHARA) {
4825 }
4826 }
4827 }
4828 }
4830 }
4831
4832 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 34)) {
4833 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4834 if (node_tree->type == NTREE_COMPOSIT) {
4835 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4836 if (node->type_legacy == CMP_NODE_DESPECKLE) {
4838 }
4839 }
4840 }
4841 }
4843 }
4844
4845 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 35)) {
4846 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4847 if (node_tree->type == NTREE_COMPOSIT) {
4848 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4849 if (node->type_legacy == CMP_NODE_DENOISE) {
4851 }
4852 }
4853 }
4854 }
4856 }
4857
4858 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 36)) {
4859 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4860 if (node_tree->type == NTREE_COMPOSIT) {
4861 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4862 if (node->type_legacy == CMP_NODE_ANTIALIASING) {
4864 }
4865 }
4866 }
4867 }
4869 }
4870
4871 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 37)) {
4872 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4873 if (node_tree->type == NTREE_COMPOSIT) {
4874 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4875 if (node->type_legacy == CMP_NODE_VECBLUR) {
4877 }
4878 }
4879 }
4880 }
4882 }
4883
4884 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 38)) {
4885 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4886 if (node_tree->type == NTREE_COMPOSIT) {
4887 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4888 if (node->type_legacy == CMP_NODE_CHANNEL_MATTE) {
4890 }
4891 }
4892 }
4893 }
4895 }
4896
4897 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 39)) {
4898 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4899 if (node_tree->type == NTREE_COMPOSIT) {
4900 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4901 if (node->type_legacy == CMP_NODE_CHROMA_MATTE) {
4903 }
4904 }
4905 }
4906 }
4908 }
4909
4910 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 40)) {
4911 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4912 if (node_tree->type == NTREE_COMPOSIT) {
4913 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4914 if (node->type_legacy == CMP_NODE_COLOR_MATTE) {
4916 }
4917 }
4918 }
4919 }
4921 }
4922
4923 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 41)) {
4924 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4925 if (node_tree->type == NTREE_COMPOSIT) {
4926 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4927 if (node->type_legacy == CMP_NODE_DIFF_MATTE) {
4929 }
4930 }
4931 }
4932 }
4934 }
4935
4936 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 42)) {
4937 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4938 if (node_tree->type == NTREE_COMPOSIT) {
4939 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4940 if (node->type_legacy == CMP_NODE_DIST_MATTE) {
4942 }
4943 }
4944 }
4945 }
4947 }
4948
4949 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 43)) {
4950 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4951 if (node_tree->type == NTREE_COMPOSIT) {
4952 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4953 if (node->type_legacy == CMP_NODE_LUMA_MATTE) {
4955 }
4956 }
4957 }
4958 }
4960 }
4961
4962 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 44)) {
4963 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4964 if (node_tree->type == NTREE_COMPOSIT) {
4965 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4966 if (node->type_legacy == CMP_NODE_COLOR_SPILL) {
4968 }
4969 }
4970 }
4971 }
4973 }
4974
4975 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 45)) {
4976 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4977 if (node_tree->type == NTREE_COMPOSIT) {
4978 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4979 if (node->type_legacy == CMP_NODE_KEYINGSCREEN) {
4981 }
4982 }
4983 }
4984 }
4986 }
4987
4988 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 47)) {
4989 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
4990 if (node_tree->type == NTREE_COMPOSIT) {
4991 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
4992 if (node->type_legacy == CMP_NODE_KEYING) {
4994 }
4995 }
4996 }
4997 }
4999 }
5000
5001 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 48)) {
5002 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5003 if (node_tree->type == NTREE_COMPOSIT) {
5004 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5005 if (node->type_legacy == CMP_NODE_ID_MASK) {
5007 }
5008 }
5009 }
5010 }
5012 }
5013
5014 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 49)) {
5015 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5016 if (node_tree->type == NTREE_COMPOSIT) {
5017 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5018 if (node->type_legacy == CMP_NODE_STABILIZE2D) {
5020 }
5021 }
5022 }
5023 }
5025 }
5026
5027 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 50)) {
5028 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5029 if (node_tree->type == NTREE_COMPOSIT) {
5030 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5031 if (node->type_legacy == CMP_NODE_PLANETRACKDEFORM) {
5033 }
5034 }
5035 }
5036 }
5038 }
5039
5040 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 52)) {
5041 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5042 if (node_tree->type == NTREE_COMPOSIT) {
5043 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5044 if (node->type_legacy == CMP_NODE_COLORCORRECTION) {
5046 }
5047 }
5048 }
5049 }
5051 }
5052
5053 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 53)) {
5054 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5055 if (node_tree->type == NTREE_COMPOSIT) {
5056 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5057 if (node->type_legacy == CMP_NODE_LENSDIST) {
5059 }
5060 }
5061 }
5062 }
5064 }
5065
5066 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 54)) {
5067 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5068 if (node_tree->type == NTREE_COMPOSIT) {
5069 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5070 if (node->type_legacy == CMP_NODE_MASK_BOX) {
5072 }
5073 }
5074 }
5075 }
5077 }
5078
5079 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 55)) {
5080 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5081 if (node_tree->type == NTREE_COMPOSIT) {
5082 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5083 if (node->type_legacy == CMP_NODE_MASK_ELLIPSE) {
5085 }
5086 }
5087 }
5088 }
5090 }
5091
5092 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 58)) {
5093 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5094 if (node_tree->type == NTREE_COMPOSIT) {
5095 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5096 if (node->type_legacy == CMP_NODE_SUNBEAMS) {
5098 }
5099 }
5100 }
5101 }
5103 }
5104
5105 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 59)) {
5106 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5107 if (node_tree->type == NTREE_COMPOSIT) {
5108 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5109 if (node->type_legacy == CMP_NODE_DBLUR) {
5111 }
5112 }
5113 }
5114 }
5116 }
5117
5118 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 60)) {
5119 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5120 if (node_tree->type == NTREE_COMPOSIT) {
5121 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5122 if (node->type_legacy == CMP_NODE_BILATERALBLUR) {
5124 }
5125 }
5126 }
5127 }
5129 }
5130
5131 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 64)) {
5132 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5133 if (node_tree->type == NTREE_COMPOSIT) {
5134 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5135 if (node->type_legacy == CMP_NODE_ALPHAOVER) {
5137 }
5138 }
5139 }
5140 }
5142 }
5143
5144 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 69)) {
5145 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5146 if (node_tree->type == NTREE_COMPOSIT) {
5147 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5148 if (node->type_legacy == CMP_NODE_BOKEHBLUR) {
5150 }
5151 }
5152 }
5153 }
5155 }
5156
5157 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 75)) {
5158 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5159 if (node_tree->type == NTREE_COMPOSIT) {
5160 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5161 if (node->type_legacy == CMP_NODE_CROP) {
5163 }
5164 }
5165 }
5166 }
5168 }
5169
5170 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 76)) {
5171 ToolSettings toolsettings_default = *DNA_struct_default_get(ToolSettings);
5172 LISTBASE_FOREACH (Scene *, scene, &bmain->scenes) {
5173 scene->toolsettings->snap_playhead_mode = toolsettings_default.snap_playhead_mode;
5174 scene->toolsettings->snap_step_frames = toolsettings_default.snap_step_frames;
5175 scene->toolsettings->snap_step_seconds = toolsettings_default.snap_step_seconds;
5176 scene->toolsettings->playhead_snap_distance = toolsettings_default.playhead_snap_distance;
5177 }
5178 }
5179
5180 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 77)) {
5181 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5182 if (node_tree->type == NTREE_COMPOSIT) {
5183 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5184 if (node->type_legacy == CMP_NODE_COLORBALANCE) {
5186 }
5187 }
5188 }
5189 }
5191 }
5192
5193 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 80)) {
5194 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5195 if (node_tree->type == NTREE_COMPOSIT) {
5196 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5197 if (node->type_legacy == CMP_NODE_BLUR) {
5199 }
5200 }
5201 }
5202 }
5204 }
5205
5206 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 84)) {
5207 LISTBASE_FOREACH (Scene *, scene, &bmain->scenes) {
5209 }
5210
5211 LISTBASE_FOREACH (Brush *, brush, &bmain->brushes) {
5212 if (brush->gpencil_settings) {
5214 }
5215 }
5216 }
5217
5224}
5225
5227{
5228 for (CustomDataLayer &layer : blender::MutableSpan(custom_data.layers, custom_data.totlayer)) {
5229 if (layer.name == name) {
5230 return &layer;
5231 }
5232 }
5233 return nullptr;
5234}
5235
5237{
5238 using namespace blender;
5239 CustomDataLayer *old_seam_layer = find_old_seam_layer(mesh.edge_data, ".uv_seam");
5240 if (!old_seam_layer) {
5241 return;
5242 }
5243 Set<StringRef> names;
5244 for (const CustomDataLayer &layer : Span(mesh.vert_data.layers, mesh.vert_data.totlayer)) {
5245 if (layer.type & CD_MASK_PROP_ALL) {
5246 names.add(layer.name);
5247 }
5248 }
5249 for (const CustomDataLayer &layer : Span(mesh.edge_data.layers, mesh.edge_data.totlayer)) {
5250 if (layer.type & CD_MASK_PROP_ALL) {
5251 names.add(layer.name);
5252 }
5253 }
5254 for (const CustomDataLayer &layer : Span(mesh.face_data.layers, mesh.face_data.totlayer)) {
5255 if (layer.type & CD_MASK_PROP_ALL) {
5256 names.add(layer.name);
5257 }
5258 }
5259 for (const CustomDataLayer &layer : Span(mesh.corner_data.layers, mesh.corner_data.totlayer)) {
5260 if (layer.type & CD_MASK_PROP_ALL) {
5261 names.add(layer.name);
5262 }
5263 }
5264 LISTBASE_FOREACH (const bDeformGroup *, vertex_group, &mesh.vertex_group_names) {
5265 names.add(vertex_group->name);
5266 }
5267
5268 /* If the new UV name is already taken, still rename the attribute so it becomes visible in the
5269 * list. Then the user can deal with the name conflict themselves. */
5270 const std::string new_name = BLI_uniquename_cb(
5271 [&](const StringRef name) { return names.contains(name); }, '.', "uv_seam");
5272 STRNCPY(old_seam_layer->name, new_name.c_str());
5273}
5274
5276{
5277 using namespace blender;
5278 Set<bNode *> curve_to_mesh_nodes;
5279 LISTBASE_FOREACH (bNode *, node, &tree->nodes) {
5280 if (STREQ(node->idname, "GeometryNodeCurveToMesh")) {
5281 curve_to_mesh_nodes.add(node);
5282 }
5283 }
5284
5285 for (bNode *curve_to_mesh : curve_to_mesh_nodes) {
5287 bke::node_find_socket(*curve_to_mesh, SOCK_IN, "Profile Curve")))
5288 {
5289 /* No additional versioning is needed when the profile curve input is unused. */
5290 continue;
5291 }
5292
5293 if (bke::node_find_socket(*curve_to_mesh, SOCK_IN, "Scale")) {
5294 /* Make versioning idempotent. */
5295 continue;
5296 }
5298 tree, curve_to_mesh, SOCK_IN, SOCK_FLOAT, PROP_NONE, "Scale", "Scale");
5299 /* Use a default scale value of 1. */
5300 scale_socket->default_value_typed<bNodeSocketValueFloat>()->value = 1.0f;
5301
5302 bNode &named_attribute = version_node_add_empty(*tree, "GeometryNodeInputNamedAttribute");
5303 NodeGeometryInputNamedAttribute *named_attribute_storage =
5305 named_attribute_storage->data_type = CD_PROP_FLOAT;
5306 named_attribute.storage = named_attribute_storage;
5307 named_attribute.parent = curve_to_mesh->parent;
5308 named_attribute.location[0] = curve_to_mesh->location[0] - 25;
5309 named_attribute.location[1] = curve_to_mesh->location[1];
5310 named_attribute.flag &= ~NODE_SELECT;
5311
5313 tree, &named_attribute, SOCK_IN, SOCK_STRING, PROP_NONE, "Name", "Name");
5314 STRNCPY(name_input->default_value_typed<bNodeSocketValueString>()->value, "radius");
5315
5317 tree, &named_attribute, SOCK_OUT, SOCK_BOOLEAN, PROP_NONE, "Exists", "Exists");
5319 tree, &named_attribute, SOCK_OUT, SOCK_FLOAT, PROP_NONE, "Attribute", "Attribute");
5320
5321 bNode &switch_node = version_node_add_empty(*tree, "GeometryNodeSwitch");
5322 NodeSwitch *switch_storage = MEM_callocN<NodeSwitch>(__func__);
5323 switch_storage->input_type = SOCK_FLOAT;
5324 switch_node.storage = switch_storage;
5325 switch_node.parent = curve_to_mesh->parent;
5326 switch_node.location[0] = curve_to_mesh->location[0] - 25;
5327 switch_node.location[1] = curve_to_mesh->location[1];
5328 switch_node.flag &= ~NODE_SELECT;
5329
5331 tree, &switch_node, SOCK_IN, SOCK_BOOLEAN, PROP_NONE, "Switch", "Switch");
5333 tree, &switch_node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "False", "False");
5334 false_input->default_value_typed<bNodeSocketValueFloat>()->value = 1.0f;
5335
5337 tree, &switch_node, SOCK_IN, SOCK_FLOAT, PROP_NONE, "True", "True");
5338
5340 named_attribute,
5341 *bke::node_find_socket(named_attribute, SOCK_OUT, "Exists"),
5342 switch_node,
5343 *bke::node_find_socket(switch_node, SOCK_IN, "Switch"));
5345 named_attribute,
5346 *bke::node_find_socket(named_attribute, SOCK_OUT, "Attribute"),
5347 switch_node,
5348 *bke::node_find_socket(switch_node, SOCK_IN, "True"));
5349
5351 tree, &switch_node, SOCK_OUT, SOCK_FLOAT, PROP_NONE, "Output", "Output");
5352
5354 switch_node,
5355 *bke::node_find_socket(switch_node, SOCK_OUT, "Output"),
5356 *curve_to_mesh,
5357 *bke::node_find_socket(*curve_to_mesh, SOCK_IN, "Scale"));
5358 }
5359
5361}
5362
5363static bool strip_effect_overdrop_to_alphaover(Strip *strip, void * /*user_data*/)
5364{
5365 if (strip->type == STRIP_TYPE_OVERDROP_REMOVED) {
5366 strip->type = STRIP_TYPE_ALPHAOVER;
5367 }
5370 }
5371 return true;
5372}
5373
5375{
5376 LISTBASE_FOREACH (Scene *, scene, &bmain->scenes) {
5377 if (scene->ed != nullptr) {
5379 &scene->ed->seqbase, strip_effect_overdrop_to_alphaover, nullptr);
5380 }
5381 }
5382}
5383
5385{
5386 LISTBASE_FOREACH (bScreen *, screen, &bmain->screens) {
5387 LISTBASE_FOREACH (ScrArea *, area, &screen->areabase) {
5388 LISTBASE_FOREACH (SpaceLink *, sl, &area->spacedata) {
5389 if (sl->spacetype != SPACE_FILE) {
5390 continue;
5391 }
5392 SpaceFile *sfile = reinterpret_cast<SpaceFile *>(sl);
5393 if (sfile->params) {
5394 if (sfile->params->list_thumbnail_size == 0) {
5395 sfile->params->list_thumbnail_size = 16;
5396 }
5397 if (sfile->params->list_column_size == 0) {
5398 sfile->params->list_column_size = 500;
5399 }
5400 }
5401 if (sfile->asset_params) {
5402 if (sfile->asset_params->base_params.list_thumbnail_size == 0) {
5404 }
5405 if (sfile->asset_params->base_params.list_column_size == 0) {
5407 }
5409 }
5410 }
5411 }
5412 }
5413}
5414
5416{
5417 LISTBASE_FOREACH (bScreen *, screen, &bmain->screens) {
5418 LISTBASE_FOREACH (ScrArea *, area, &screen->areabase) {
5419 LISTBASE_FOREACH (SpaceLink *, sl, &area->spacedata) {
5420 if (sl->spacetype == SPACE_IMAGE) {
5421 SpaceImage *sima = reinterpret_cast<SpaceImage *>(sl);
5422 if (sima->flag & SI_NO_DRAW_TEXPAINT) {
5423 sima->flag |= SI_NO_DRAW_UV_GUIDE;
5424 }
5425 }
5426 }
5427 }
5428 }
5429}
5430
5432{
5433 LISTBASE_FOREACH (bScreen *, screen, &bmain->screens) {
5434 LISTBASE_FOREACH (ScrArea *, area, &screen->areabase) {
5435 LISTBASE_FOREACH (SpaceLink *, sl, &area->spacedata) {
5436 if (sl->spacetype == SPACE_IMAGE) {
5437 SpaceImage *sima = reinterpret_cast<SpaceImage *>(sl);
5438 /* Remove ID Code from screen name */
5439 const char *workspace_name = screen->id.name + 2;
5440 /* Don't set uv_face_opacity for Texture Paint or Shading since these are workspaces
5441 * where it's important to have unobstructed view of the Image Editor to see Image
5442 * Textures. UV Editing is the only other default workspace with an Image Editor.*/
5443 if (STREQ(workspace_name, "UV Editing")) {
5444 sima->uv_face_opacity = 1.0f;
5445 }
5446 }
5447 }
5448 }
5449 }
5450}
5451
5453{
5454 LISTBASE_FOREACH (Brush *, brush, &bmain->brushes) {
5455 if (ELEM(brush->sculpt_brush_type,
5456 SCULPT_BRUSH_TYPE_FLATTEN,
5457 SCULPT_BRUSH_TYPE_FILL,
5458 SCULPT_BRUSH_TYPE_SCRAPE))
5459 {
5460 if (brush->sculpt_brush_type == SCULPT_BRUSH_TYPE_FLATTEN) {
5461 brush->plane_height = 1.0f;
5462 brush->plane_depth = 1.0f;
5463 brush->area_radius_factor = 1.0f;
5464 brush->plane_inversion_mode = BRUSH_PLANE_INVERT_DISPLACEMENT;
5465 }
5466
5467 if (brush->sculpt_brush_type == SCULPT_BRUSH_TYPE_FILL) {
5468 brush->plane_height = 0.0f;
5469 brush->plane_depth = 1.0f;
5470 brush->plane_inversion_mode = brush->flag & BRUSH_INVERT_TO_SCRAPE_FILL ?
5473 }
5474
5475 if (brush->sculpt_brush_type == SCULPT_BRUSH_TYPE_SCRAPE) {
5476 brush->plane_height = 1.0f;
5477 brush->plane_depth = 0.0f;
5478 brush->plane_inversion_mode = brush->flag & BRUSH_INVERT_TO_SCRAPE_FILL ?
5481
5482 /* Note, this fix was committed after some users had already run the versioning after
5483 * 4.5 was released. Since 4.5 is an LTS and will be used for the foreseeable future to
5484 * transition between 4.x and 5.x the fix has been added here, even though that does
5485 * not fix the issue for some users with custom brush assets who have started using 4.5
5486 * already.
5487 *
5488 * Since the `sculpt_brush_type` field changed from 'SCULPT_BRUSH_TYPE_SCRAPE' to
5489 * 'SCULPT_BRUSH_TYPE_PLANE', we do not have a value that can be used to definitively apply
5490 * a corrective versioning step along with a subversion bump without potentially affecting
5491 * some false positives.
5492 *
5493 * See #142151 for more details. */
5494 brush->plane_offset *= -1.0f;
5495 }
5496
5497 if (brush->flag & BRUSH_PLANE_TRIM) {
5498 brush->plane_height *= brush->plane_trim;
5499 brush->plane_depth *= brush->plane_trim;
5500 }
5501
5502 brush->stabilize_normal = (brush->flag & BRUSH_ORIGINAL_NORMAL) ? 1.0f : 0.0f;
5503 brush->stabilize_plane = (brush->flag & BRUSH_ORIGINAL_PLANE) ? 1.0f : 0.0f;
5504 brush->flag &= ~BRUSH_ORIGINAL_NORMAL;
5505 brush->flag &= ~BRUSH_ORIGINAL_PLANE;
5506
5507 brush->sculpt_brush_type = SCULPT_BRUSH_TYPE_PLANE;
5508 }
5509 }
5510}
5511
5513{
5514 if (item.item_type == eNodeTreeInterfaceItemType::NODE_INTERFACE_SOCKET) {
5515 auto &socket = reinterpret_cast<bNodeTreeInterfaceSocket &>(item);
5517 socket.structure_type = NODE_INTERFACE_SOCKET_STRUCTURE_TYPE_SINGLE;
5518 }
5519 else {
5520 socket.structure_type = NODE_INTERFACE_SOCKET_STRUCTURE_TYPE_AUTO;
5521 }
5522 }
5523 else {
5524 auto &panel = reinterpret_cast<bNodeTreeInterfacePanel &>(item);
5525 for (bNodeTreeInterfaceItem *item : blender::Span(panel.items_array, panel.items_num)) {
5527 }
5528 }
5529}
5530
5532{
5533 LISTBASE_FOREACH (bArmature *, arm, &bmain->armatures) {
5535 &arm->bonebase, [](Bone *bone) { bone->drawtype = ARM_DRAW_TYPE_ARMATURE_DEFINED; });
5536 BLI_assert_msg(!arm->edbo, "Armatures should not be saved in edit mode");
5537 }
5538}
5539
5540void blo_do_versions_450(FileData * /*fd*/, Library * /*lib*/, Main *bmain)
5541{
5542
5543 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 2)) {
5545 }
5546
5547 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 4)) {
5548 FOREACH_NODETREE_BEGIN (bmain, ntree, id) {
5549 if (ntree->type == NTREE_GEOMETRY) {
5551 }
5552 }
5554 }
5555
5556 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 5)) {
5557 LISTBASE_FOREACH (Scene *, scene, &bmain->scenes) {
5558 ToolSettings *tool_settings = scene->toolsettings;
5559 tool_settings->snap_flag_seq |= SCE_SNAP;
5560
5561 SequencerToolSettings *sequencer_tool_settings = blender::seq::tool_settings_ensure(scene);
5562 sequencer_tool_settings->snap_mode |= SEQ_SNAP_TO_FRAME_RANGE;
5563 }
5564 }
5565
5566 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 6)) {
5568 }
5569
5570 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 7)) {
5571 LISTBASE_FOREACH (bNodeTree *, ntree, &bmain->nodetrees) {
5572 if (ntree->type == NTREE_GEOMETRY) {
5573 LISTBASE_FOREACH (bNode *, node, &ntree->nodes) {
5574 if (STREQ(node->idname, "GeometryNodeStoreNamedGrid")) {
5575 switch (node->custom1) {
5576 case CD_PROP_FLOAT:
5577 node->custom1 = VOLUME_GRID_FLOAT;
5578 break;
5579 case CD_PROP_FLOAT2:
5580 case CD_PROP_FLOAT3:
5581 node->custom1 = VOLUME_GRID_VECTOR_FLOAT;
5582 break;
5583 default:
5584 node->custom1 = VOLUME_GRID_FLOAT;
5585 break;
5586 }
5587 }
5588 }
5589 }
5590 }
5591 }
5592
5593 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 8)) {
5594 FOREACH_NODETREE_BEGIN (bmain, ntree, id) {
5595 if (ntree->type == NTREE_COMPOSIT) {
5597 }
5598 }
5600 }
5601
5602 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 9)) {
5603 LISTBASE_FOREACH (bScreen *, screen, &bmain->screens) {
5604 LISTBASE_FOREACH (ScrArea *, area, &screen->areabase) {
5605 LISTBASE_FOREACH (SpaceLink *, sl, &area->spacedata) {
5606 if (sl->spacetype != SPACE_FILE) {
5607 continue;
5608 }
5609 SpaceFile *sfile = reinterpret_cast<SpaceFile *>(sl);
5610 if (sfile->asset_params) {
5612 }
5613 }
5614 }
5615 }
5616 }
5617
5618 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 15)) {
5619 FOREACH_NODETREE_BEGIN (bmain, ntree, id) {
5620 if (ntree->type != NTREE_COMPOSIT) {
5621 continue;
5622 }
5623 LISTBASE_FOREACH (bNode *, node, &ntree->nodes) {
5624 if (node->type_legacy != CMP_NODE_SCALE) {
5625 continue;
5626 }
5627 if (node->storage != nullptr) {
5628 continue;
5629 }
5631 data->interpolation = CMP_NODE_INTERPOLATION_BILINEAR;
5632 node->storage = data;
5633 }
5634 }
5636 }
5637
5638 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 16)) {
5639 LISTBASE_FOREACH (Scene *, scene, &bmain->scenes) {
5640 scene->grease_pencil_settings.smaa_threshold_render =
5641 scene->grease_pencil_settings.smaa_threshold;
5642 scene->grease_pencil_settings.aa_samples = 1;
5643 }
5644 }
5645
5646 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 17)) {
5649 }
5650
5651 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 18)) {
5652 FOREACH_NODETREE_BEGIN (bmain, ntree, id) {
5653 if (ntree->type == NTREE_COMPOSIT) {
5654 LISTBASE_FOREACH (bNode *, node, &ntree->nodes) {
5655 if (node->type_legacy == CMP_NODE_CORNERPIN) {
5657 }
5658 }
5659 }
5660 }
5662 }
5663
5664 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 19)) {
5665 LISTBASE_FOREACH (bScreen *, screen, &bmain->screens) {
5666 LISTBASE_FOREACH (ScrArea *, area, &screen->areabase) {
5667 LISTBASE_FOREACH (SpaceLink *, sl, &area->spacedata) {
5668 if (sl->spacetype == SPACE_PROPERTIES) {
5669 SpaceProperties *sbuts = reinterpret_cast<SpaceProperties *>(sl);
5670 /* Translates to 0xFFFFFFFF, so other tabs can be added without versioning. */
5671 sbuts->visible_tabs = uint(-1);
5672 }
5673 }
5674 }
5675 }
5676 }
5677
5678 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 20)) {
5679 /* Older files uses non-UTF8 aware string copy, ensure names are valid UTF8.
5680 * The slot names are not unique so no further changes are needed. */
5681 LISTBASE_FOREACH (Image *, image, &bmain->images) {
5682 LISTBASE_FOREACH (RenderSlot *, slot, &image->renderslots) {
5683 if (slot->name[0]) {
5684 BLI_str_utf8_invalid_strip(slot->name, STRNLEN(slot->name));
5685 }
5686 }
5687 }
5688 LISTBASE_FOREACH (Scene *, scene, &bmain->scenes) {
5689 scene->r.ppm_factor = 72.0f;
5690 scene->r.ppm_base = 0.0254f;
5691 }
5692 }
5693
5694 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 21)) {
5695 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5696 if (node_tree->type == NTREE_COMPOSIT) {
5697 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5698 if (node->type_legacy == CMP_NODE_GLARE) {
5700 }
5701 }
5702 }
5703 }
5705 }
5706
5707 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 22)) {
5708 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5709 if (node_tree->type == NTREE_COMPOSIT) {
5710 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5711 if (node->type_legacy == CMP_NODE_BOKEHIMAGE) {
5713 }
5714 }
5715 }
5716 }
5718 }
5719
5720 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 23)) {
5721 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5722 if (node_tree->type == NTREE_COMPOSIT) {
5723 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5724 if (node->type_legacy == CMP_NODE_TIME) {
5726 }
5727 }
5728 }
5729 }
5731 }
5732
5733 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 24)) {
5734 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5735 if (node_tree->type == NTREE_COMPOSIT) {
5736 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5737 if (node->type_legacy == CMP_NODE_MASK) {
5739 }
5740 }
5741 }
5742 }
5744 }
5745
5746 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 25)) {
5747 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5748 if (node_tree->type == NTREE_COMPOSIT) {
5749 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5750 if (node->type_legacy == CMP_NODE_SWITCH) {
5752 }
5753 }
5754 }
5755 }
5757 }
5758
5759 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 26)) {
5760 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5761 if (node_tree->type == NTREE_COMPOSIT) {
5762 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5763 if (node->type_legacy == CMP_NODE_SPLIT) {
5765 }
5766 }
5767 }
5768 }
5770 }
5771
5772 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 27)) {
5773 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5774 if (node_tree->type == NTREE_COMPOSIT) {
5775 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5776 if (node->type_legacy == CMP_NODE_INVERT) {
5778 }
5779 }
5780 }
5781 }
5783 }
5784
5785 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 28)) {
5786 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5787 if (node_tree->type == NTREE_COMPOSIT) {
5788 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5789 if (node->type_legacy == CMP_NODE_ZCOMBINE) {
5791 }
5792 }
5793 }
5794 }
5796 }
5797
5798 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 29)) {
5799 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5800 if (node_tree->type == NTREE_COMPOSIT) {
5801 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5802 if (node->type_legacy == CMP_NODE_TONEMAP) {
5804 }
5805 }
5806 }
5807 }
5809 }
5810
5811 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 30)) {
5812 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5813 if (node_tree->type == NTREE_COMPOSIT) {
5814 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5815 if (node->type_legacy == CMP_NODE_DILATEERODE) {
5817 }
5818 }
5819 }
5820 }
5822 }
5823
5824 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 31)) {
5825 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5826 if (node_tree->type == NTREE_COMPOSIT) {
5827 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5828 if (node->type_legacy == CMP_NODE_INPAINT) {
5830 }
5831 }
5832 }
5833 }
5835 }
5836
5837 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 32)) {
5838 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5839 if (node_tree->type == NTREE_COMPOSIT) {
5840 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5841 if (node->type_legacy == CMP_NODE_PIXELATE) {
5843 }
5844 }
5845 }
5846 }
5848 }
5849
5850 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 33)) {
5851 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5852 if (node_tree->type == NTREE_COMPOSIT) {
5853 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5854 if (node->type_legacy == CMP_NODE_KUWAHARA) {
5856 }
5857 }
5858 }
5859 }
5861 }
5862
5863 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 34)) {
5864 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5865 if (node_tree->type == NTREE_COMPOSIT) {
5866 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5867 if (node->type_legacy == CMP_NODE_DESPECKLE) {
5869 }
5870 }
5871 }
5872 }
5874 }
5875
5876 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 35)) {
5877 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5878 if (node_tree->type == NTREE_COMPOSIT) {
5879 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5880 if (node->type_legacy == CMP_NODE_DENOISE) {
5882 }
5883 }
5884 }
5885 }
5887 }
5888
5889 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 36)) {
5890 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5891 if (node_tree->type == NTREE_COMPOSIT) {
5892 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5893 if (node->type_legacy == CMP_NODE_ANTIALIASING) {
5895 }
5896 }
5897 }
5898 }
5900 }
5901
5902 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 37)) {
5903 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5904 if (node_tree->type == NTREE_COMPOSIT) {
5905 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5906 if (node->type_legacy == CMP_NODE_VECBLUR) {
5908 }
5909 }
5910 }
5911 }
5913 }
5914
5915 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 38)) {
5916 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5917 if (node_tree->type == NTREE_COMPOSIT) {
5918 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5919 if (node->type_legacy == CMP_NODE_CHANNEL_MATTE) {
5921 }
5922 }
5923 }
5924 }
5926 }
5927
5928 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 39)) {
5929 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5930 if (node_tree->type == NTREE_COMPOSIT) {
5931 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5932 if (node->type_legacy == CMP_NODE_CHROMA_MATTE) {
5934 }
5935 }
5936 }
5937 }
5939 }
5940
5941 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 40)) {
5942 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5943 if (node_tree->type == NTREE_COMPOSIT) {
5944 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5945 if (node->type_legacy == CMP_NODE_COLOR_MATTE) {
5947 }
5948 }
5949 }
5950 }
5952 }
5953
5954 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 41)) {
5955 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5956 if (node_tree->type == NTREE_COMPOSIT) {
5957 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5958 if (node->type_legacy == CMP_NODE_DIFF_MATTE) {
5960 }
5961 }
5962 }
5963 }
5965 }
5966
5967 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 42)) {
5968 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5969 if (node_tree->type == NTREE_COMPOSIT) {
5970 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5971 if (node->type_legacy == CMP_NODE_DIST_MATTE) {
5973 }
5974 }
5975 }
5976 }
5978 }
5979
5980 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 43)) {
5981 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5982 if (node_tree->type == NTREE_COMPOSIT) {
5983 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5984 if (node->type_legacy == CMP_NODE_LUMA_MATTE) {
5986 }
5987 }
5988 }
5989 }
5991 }
5992
5993 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 44)) {
5994 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
5995 if (node_tree->type == NTREE_COMPOSIT) {
5996 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
5997 if (node->type_legacy == CMP_NODE_COLOR_SPILL) {
5999 }
6000 }
6001 }
6002 }
6004 }
6005
6006 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 45)) {
6007 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6008 if (node_tree->type == NTREE_COMPOSIT) {
6009 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6010 if (node->type_legacy == CMP_NODE_KEYINGSCREEN) {
6012 }
6013 }
6014 }
6015 }
6017 }
6018
6019 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 46)) {
6020 LISTBASE_FOREACH (bScreen *, screen, &bmain->screens) {
6021 LISTBASE_FOREACH (ScrArea *, area, &screen->areabase) {
6022 LISTBASE_FOREACH (SpaceLink *, sl, &area->spacedata) {
6023 if (sl->spacetype == SPACE_SEQ) {
6024 ListBase *regionbase = (sl == area->spacedata.first) ? &area->regionbase :
6025 &sl->regionbase;
6026 LISTBASE_FOREACH (ARegion *, region, regionbase) {
6027 if (region->regiontype == RGN_TYPE_WINDOW) {
6028 region->v2d.keepzoom |= V2D_KEEPZOOM;
6029 region->v2d.keepofs |= V2D_KEEPOFS_X | V2D_KEEPOFS_Y;
6030 }
6031 }
6032 }
6033 }
6034 }
6035 }
6036 }
6037
6038 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 47)) {
6039 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6040 if (node_tree->type == NTREE_COMPOSIT) {
6041 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6042 if (node->type_legacy == CMP_NODE_KEYING) {
6044 }
6045 }
6046 }
6047 }
6049 }
6050
6051 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 48)) {
6052 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6053 if (node_tree->type == NTREE_COMPOSIT) {
6054 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6055 if (node->type_legacy == CMP_NODE_ID_MASK) {
6057 }
6058 }
6059 }
6060 }
6062 }
6063
6064 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 49)) {
6065 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6066 if (node_tree->type == NTREE_COMPOSIT) {
6067 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6068 if (node->type_legacy == CMP_NODE_STABILIZE2D) {
6070 }
6071 }
6072 }
6073 }
6075 }
6076
6077 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 50)) {
6078 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6079 if (node_tree->type == NTREE_COMPOSIT) {
6080 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6081 if (node->type_legacy == CMP_NODE_PLANETRACKDEFORM) {
6083 }
6084 }
6085 }
6086 }
6088 }
6089
6090 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 51)) {
6091 const Object *dob = DNA_struct_default_get(Object);
6092 LISTBASE_FOREACH (Object *, object, &bmain->objects) {
6093 object->shadow_terminator_normal_offset = dob->shadow_terminator_normal_offset;
6094 object->shadow_terminator_geometry_offset = dob->shadow_terminator_geometry_offset;
6095 object->shadow_terminator_shading_offset = dob->shadow_terminator_shading_offset;
6096 /* Copy Cycles' property into Blender Object. */
6098 if (cob) {
6099 object->shadow_terminator_geometry_offset = version_cycles_property_float(
6100 cob, "shadow_terminator_geometry_offset", dob->shadow_terminator_geometry_offset);
6101 object->shadow_terminator_shading_offset = version_cycles_property_float(
6102 cob, "shadow_terminator_offset", dob->shadow_terminator_shading_offset);
6103 }
6104 }
6105 }
6106
6107 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 52)) {
6108 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6109 if (node_tree->type == NTREE_COMPOSIT) {
6110 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6111 if (node->type_legacy == CMP_NODE_COLORCORRECTION) {
6113 }
6114 }
6115 }
6116 }
6118 }
6119
6120 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 53)) {
6121 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6122 if (node_tree->type == NTREE_COMPOSIT) {
6123 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6124 if (node->type_legacy == CMP_NODE_LENSDIST) {
6126 }
6127 }
6128 }
6129 }
6131 }
6132
6133 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 54)) {
6134 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6135 if (node_tree->type == NTREE_COMPOSIT) {
6136 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6137 if (node->type_legacy == CMP_NODE_MASK_BOX) {
6139 }
6140 }
6141 }
6142 }
6144 }
6145
6146 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 55)) {
6147 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6148 if (node_tree->type == NTREE_COMPOSIT) {
6149 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6150 if (node->type_legacy == CMP_NODE_MASK_ELLIPSE) {
6152 }
6153 }
6154 }
6155 }
6157 }
6158
6159 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 56)) {
6161 }
6162
6163 /* Enforce that bone envelope radii match for parent and connected children. */
6164 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 57)) {
6165 LISTBASE_FOREACH (bArmature *, arm, &bmain->armatures) {
6166 blender::animrig::ANIM_armature_foreach_bone(&arm->bonebase, [](Bone *bone) {
6167 if (bone->parent && (bone->flag & BONE_CONNECTED)) {
6168 bone->rad_head = bone->parent->rad_tail;
6169 }
6170 });
6171 if (arm->edbo) {
6172 LISTBASE_FOREACH (EditBone *, ebone, arm->edbo) {
6173 if (ebone->parent && (ebone->flag & BONE_CONNECTED)) {
6174 ebone->rad_head = ebone->parent->rad_tail;
6175 }
6176 }
6177 }
6178 }
6179 }
6180
6181 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 58)) {
6182 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6183 if (node_tree->type == NTREE_COMPOSIT) {
6184 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6185 if (node->type_legacy == CMP_NODE_SUNBEAMS) {
6187 }
6188 }
6189 }
6190 }
6192 }
6193
6194 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 59)) {
6195 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6196 if (node_tree->type == NTREE_COMPOSIT) {
6197 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6198 if (node->type_legacy == CMP_NODE_DBLUR) {
6200 }
6201 }
6202 }
6203 }
6205 }
6206
6207 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 60)) {
6208 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6209 if (node_tree->type == NTREE_COMPOSIT) {
6210 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6211 if (node->type_legacy == CMP_NODE_BILATERALBLUR) {
6213 }
6214 }
6215 }
6216 }
6218 }
6219
6220 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 61)) {
6221 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6222 if (node_tree->type == NTREE_COMPOSIT) {
6224 }
6225 }
6227 }
6228
6229 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 62)) {
6230 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6231 if (node_tree->type == NTREE_COMPOSIT) {
6233 }
6234 }
6236 }
6237
6238 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 63)) {
6239 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6240 if (node_tree->type == NTREE_COMPOSIT) {
6242 }
6243 }
6245 }
6246
6247 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 64)) {
6248 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6249 if (node_tree->type == NTREE_COMPOSIT) {
6250 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6251 if (node->type_legacy == CMP_NODE_ALPHAOVER) {
6253 }
6254 }
6255 }
6256 }
6258 }
6259
6260 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 65)) {
6261 LISTBASE_FOREACH (bScreen *, screen, &bmain->screens) {
6262 LISTBASE_FOREACH (ScrArea *, area, &screen->areabase) {
6263 LISTBASE_FOREACH (SpaceLink *, sl, &area->spacedata) {
6264 if (sl->spacetype == SPACE_SEQ) {
6265 ListBase *regionbase = (sl == area->spacedata.first) ? &area->regionbase :
6266 &sl->regionbase;
6267 LISTBASE_FOREACH (ARegion *, region, regionbase) {
6268 if (region->regiontype == RGN_TYPE_WINDOW) {
6269 region->v2d.flag |= V2D_ZOOM_IGNORE_KEEPOFS;
6270 }
6271 }
6272 }
6273 }
6274 }
6275 }
6276 }
6277
6278 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 66)) {
6279 /* Clear unused draw flag (used to be SEQ_DRAW_BACKDROP). */
6280 LISTBASE_FOREACH (bScreen *, screen, &bmain->screens) {
6281 LISTBASE_FOREACH (ScrArea *, area, &screen->areabase) {
6282 LISTBASE_FOREACH (SpaceLink *, sl, &area->spacedata) {
6283 if (sl->spacetype == SPACE_SEQ) {
6284 SpaceSeq *space_sequencer = (SpaceSeq *)sl;
6285 space_sequencer->draw_flag &= ~SEQ_DRAW_UNUSED_0;
6286 }
6287 }
6288 }
6289 }
6290 }
6291
6292 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 67)) {
6293 /* Version render output paths (both primary on scene as well as those in
6294 * the File Output compositor node) to escape curly braces. */
6295 {
6296 LISTBASE_FOREACH (Scene *, scene, &bmain->scenes) {
6298 if (scene->nodetree) {
6300 }
6301 }
6302
6303 LISTBASE_FOREACH (bNodeTree *, nodetree, &bmain->nodetrees) {
6305 }
6306 }
6307 }
6308
6309 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 68)) {
6310 /* Fix brush->tip_scale_x which should never be zero. */
6311 LISTBASE_FOREACH (Brush *, brush, &bmain->brushes) {
6312 if (brush->tip_scale_x == 0.0f) {
6313 brush->tip_scale_x = 1.0f;
6314 }
6315 }
6316 }
6317
6318 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 69)) {
6319 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6320 if (node_tree->type == NTREE_COMPOSIT) {
6321 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6322 if (node->type_legacy == CMP_NODE_BOKEHBLUR) {
6324 }
6325 }
6326 }
6327 }
6329 }
6330
6331 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 70)) {
6332 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6333 if (node_tree->type == NTREE_COMPOSIT) {
6335 }
6336 }
6338 }
6339
6340 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 71)) {
6341 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6342 if (node_tree->type == NTREE_COMPOSIT) {
6344 }
6345 }
6347 }
6348
6349 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 72)) {
6351 }
6352
6353 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 73)) {
6354 /* Make #Curve::type the source of truth for the curve type.
6355 * Previously #Curve::vfont was checked which is error prone
6356 * since the member can become null at run-time, see: #139133. */
6357 LISTBASE_FOREACH (Curve *, cu, &bmain->curves) {
6358 if (ELEM(cu->ob_type, OB_CURVES_LEGACY, OB_FONT, OB_SURF)) {
6359 continue;
6360 }
6361 short ob_type = OB_CURVES_LEGACY;
6362 if (cu->vfont) {
6363 ob_type = OB_FONT;
6364 }
6365 else {
6366 LISTBASE_FOREACH (const Nurb *, nu, &cu->nurb) {
6367 if (nu->pntsv > 1) {
6368 ob_type = OB_SURF;
6369 break;
6370 }
6371 }
6372 }
6373 cu->ob_type = ob_type;
6374 }
6375 }
6376
6377 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 74)) {
6378 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6379 if (node_tree->type == NTREE_COMPOSIT) {
6381 }
6382 }
6384 }
6385
6386 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 75)) {
6387 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6388 if (node_tree->type == NTREE_COMPOSIT) {
6389 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6390 if (node->type_legacy == CMP_NODE_CROP) {
6392 }
6393 }
6394 }
6395 }
6397 }
6398
6399 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 76)) {
6400 LISTBASE_FOREACH (Light *, light, &bmain->lights) {
6401 if (light->temperature == 0.0f) {
6402 light->temperature = 6500.0f;
6403 }
6404 }
6405 }
6406
6407 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 77)) {
6408 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6409 if (node_tree->type == NTREE_COMPOSIT) {
6410 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6411 if (node->type_legacy == CMP_NODE_COLORBALANCE) {
6413 }
6414 }
6415 }
6416 }
6418 }
6419
6420 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 78)) {
6421 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6422 if (node_tree->type == NTREE_COMPOSIT) {
6424 }
6425 }
6427 }
6428
6429 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 79)) {
6430 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6432 }
6434 }
6435
6436 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 80)) {
6437 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6438 if (node_tree->type == NTREE_COMPOSIT) {
6439 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6440 if (node->type_legacy == CMP_NODE_BLUR) {
6442 }
6443 }
6444 }
6445 }
6447 }
6448
6449 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 81)) {
6450 LISTBASE_FOREACH (bNodeTree *, ntree, &bmain->nodetrees) {
6451 if (ntree->type == NTREE_GEOMETRY) {
6452 node_interface_single_value_to_structure_type(ntree->tree_interface.root_panel.item);
6453 }
6454 }
6455 }
6456
6457 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 83)) {
6458 LISTBASE_FOREACH (Object *, ob, &bmain->objects) {
6459 if (ob->soft) {
6460 ob->soft->fuzzyness = std::max<int>(1, ob->soft->fuzzyness);
6461 }
6462 }
6463 }
6464
6465 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 85)) {
6466 FOREACH_NODETREE_BEGIN (bmain, node_tree, id) {
6467 if (node_tree->type == NTREE_COMPOSIT) {
6468 LISTBASE_FOREACH (bNode *, node, &node_tree->nodes) {
6469 if (node->type_legacy == CMP_NODE_FLIP) {
6471 }
6472 }
6473 }
6474 }
6476 }
6477
6478 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 86)) {
6480 }
6481
6482 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 87)) {
6483 FOREACH_NODETREE_BEGIN (bmain, tree, id) {
6484 if (tree->type == NTREE_GEOMETRY) {
6486 }
6487 }
6489 }
6490
6491 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 88)) {
6492 LISTBASE_FOREACH (Brush *, brush, &bmain->brushes) {
6493 if (brush->gpencil_settings) {
6495 }
6496 }
6497 }
6498
6499 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 90)) {
6500 LISTBASE_FOREACH (Object *, object, &bmain->objects) {
6501 LISTBASE_FOREACH (ModifierData *, modifier, &object->modifiers) {
6503 continue;
6504 }
6506 modifier);
6507 if (lmd->radius != 0.0f) {
6508 continue;
6509 }
6510 lmd->radius = float(lmd->thickness_legacy) *
6512 }
6513 }
6514 }
6515
6516 if (!MAIN_VERSION_FILE_ATLEAST(bmain, 405, 91)) {
6517 /* For a brief period of time, these values were not properly versioned, so it is possible for
6518 * files to be in an odd state. This versioning was formerly run in 4.2 subversion 23. */
6519 LISTBASE_FOREACH (Scene *, scene, &bmain->scenes) {
6520 UvSculpt &uvsculpt = scene->toolsettings->uvsculpt;
6521 if (uvsculpt.size == 0 || uvsculpt.strength_curve == nullptr) {
6522 uvsculpt.size = 50;
6523 uvsculpt.strength = 1.0f;
6525 if (uvsculpt.strength_curve == nullptr) {
6526 uvsculpt.strength_curve = BKE_curvemapping_add(1, 0.0f, 0.0f, 1.0f, 1.0f);
6527 }
6528 }
6529 }
6530 }
6531
6532 /* Always run this versioning (keep at the bottom of the function). Meshes are written with the
6533 * legacy format which always needs to be converted to the new format on file load. To be moved
6534 * to a subversion check in 5.0. */
6535 LISTBASE_FOREACH (Mesh *, mesh, &bmain->meshes) {
6539 }
6540
6547}
Functions and classes to work with Actions.
Functionality to iterate an Action in various ways.
Iterators for armatures.
void BKE_animdata_main_cb(struct Main *bmain, blender::FunctionRef< void(ID *, AnimData *)> func)
void BKE_fcurves_id_cb(struct ID *id, blender::FunctionRef< void(ID *, FCurve *)> func)
void BKE_animdata_fix_paths_rename_all_ex(struct Main *bmain, struct ID *ref_id, const char *prefix, const char *oldName, const char *newName, int oldSubscript, int newSubscript, bool verify_paths)
void BKE_curvemapping_free_data(CurveMapping *cumap)
CurveMapping * BKE_curvemapping_copy(const CurveMapping *cumap)
CurveMapping * BKE_curvemapping_add(int tot, float minx, float miny, float maxx, float maxy)
Definition colortools.cc:89
void BKE_curvemapping_copy_data(CurveMapping *target, const CurveMapping *cumap)
Low-level operations for curves.
CustomData interface, see also DNA_customdata_types.h.
void * CustomData_get_layer_named_for_write(CustomData *data, eCustomDataType type, blender::StringRef name, int totelem)
Low-level operations for grease pencil.
void IDP_MergeGroup_ex(IDProperty *dest, const IDProperty *src, bool do_overwrite, int flag) ATTR_NONNULL()
Definition idprop.cc:679
IDProperty * IDP_CopyProperty_ex(const IDProperty *prop, int flag) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL()
Definition idprop.cc:855
@ LIB_ID_CREATE_NO_USER_REFCOUNT
#define FOREACH_MAIN_ID_END
Definition BKE_main.hh:563
#define MAIN_VERSION_FILE_ATLEAST(main, ver, subver)
Definition BKE_main.hh:634
#define FOREACH_MAIN_ID_BEGIN(_bmain, _id)
Definition BKE_main.hh:557
#define FOREACH_NODETREE_END
Definition BKE_node.hh:866
#define FOREACH_NODETREE_BEGIN(bmain, _nodetree, _id)
Definition BKE_node.hh:856
#define CMP_NODE_PREMULKEY
#define CMP_NODE_DENOISE
#define CMP_NODE_VALTORGB
#define CMP_NODE_MASK
#define CMP_NODE_SCALE
#define GEO_NODE_SUBDIVISION_SURFACE
#define CMP_NODE_COMBINE_XYZ
#define CMP_NODE_COMPOSITE
#define CMP_NODE_MIX_RGB
#define CMP_NODE_VECBLUR
#define CMP_NODE_MAP_RANGE
#define CMP_NODE_TIME
#define CMP_NODE_COLOR_SPILL
#define CMP_CHAN_RGB
#define CMP_NODE_DESPECKLE
#define CMP_NODE_VIEWER
#define CMP_NODE_LUMA_MATTE
#define SH_NODE_COMBXYZ
#define CMP_NODE_CORNERPIN
#define CMP_NODE_KEYINGSCREEN
#define CMP_NODE_MASK_ELLIPSE
#define GEO_NODE_SUBDIVIDE_MESH
#define CMP_NODE_SEPARATE_COLOR
#define CMP_NODE_BILATERALBLUR
#define CMP_NODE_MAP_VALUE
#define CMP_NODE_TRANSLATE
#define CMP_NODE_TONEMAP
#define CMP_NODE_INPAINT
#define CMP_NODE_COLORBALANCE
#define SH_NODE_MAP_RANGE
#define CMP_NODE_BOKEHIMAGE
#define CMP_NODE_KUWAHARA
#define CMP_NODE_DIFF_MATTE
#define CMP_NODE_GAMMA
#define SH_NODE_VALUE
#define SH_NODE_CURVE_VEC
#define CMP_NODE_ALPHAOVER
#define SH_NODE_MATH
#define CMP_NODE_CROP
#define CMP_NODE_CHROMA_MATTE
#define CMP_NODE_GLARE
#define SH_NODE_SEPXYZ
#define CMP_NODE_PLANETRACKDEFORM
#define CMP_NODE_DILATEERODE
#define CMP_NODE_SPLIT
#define CMP_NODE_ID_MASK
#define CMP_NODE_BOKEHBLUR
#define CMP_NODE_LENSDIST
#define CMP_NODE_VALUE
#define CMP_NODE_ZCOMBINE
#define CMP_NODE_MATH
#define CMP_NODE_COLORCORRECTION
#define CMP_NODE_SETALPHA
#define CMP_NODE_STABILIZE2D
#define CMP_NODE_PIXELATE
#define SH_NODE_MIX
#define SH_NODE_VALTORGB
#define CMP_NODE_SWITCH
#define SH_NODE_CLAMP
#define CMP_NODE_MASK_BOX
#define CMP_NODE_DEFOCUS
#define CMP_NODE_KEYING
#define CMP_NODE_SEPARATE_XYZ
#define CMP_NODE_ANTIALIASING
#define CMP_NODE_CURVE_VEC
#define CMP_NODE_INVERT
#define CMP_NODE_COLOR_MATTE
#define CMP_NODE_DIST_MATTE
#define CMP_NODE_SUNBEAMS
#define CMP_NODE_DBLUR
#define CMP_NODE_BLUR
#define CMP_CHAN_A
#define CMP_NODE_BRIGHTCONTRAST
#define CMP_NODE_FLIP
#define CMP_NODE_CHANNEL_MATTE
CurveMapping * BKE_paint_default_curve()
Definition scene.cc:140
@ VOLUME_GRID_VECTOR_FLOAT
@ VOLUME_GRID_FLOAT
#define BLI_assert_unreachable()
Definition BLI_assert.h:93
#define BLI_assert_msg(a, msg)
Definition BLI_assert.h:53
void * BLI_findlink(const ListBase *listbase, int number) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL(1)
Definition listbase.cc:534
#define LISTBASE_FOREACH(type, var, list)
#define LISTBASE_FOREACH_MUTABLE(type, var, list)
#define LISTBASE_FOREACH_BACKWARD_MUTABLE(type, var, list)
MINLINE void copy_v4_v4(float r[4], const float a[4])
MINLINE void copy_v3_v3(float r[3], const float a[3])
MINLINE bool is_zero_v3(const float v[3]) ATTR_WARN_UNUSED_RESULT
#define FILE_MAX
char * BLI_sprintfN(const char *__restrict format,...) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL(1) ATTR_MALLOC ATTR_PRINTF_FORMAT(1
#define STRNLEN(str)
Definition BLI_string.h:608
char * STRNCPY(char(&dst)[N], const char *src)
Definition BLI_string.h:688
int bool bool BLI_str_endswith(const char *__restrict str, const char *__restrict end) ATTR_NONNULL(1
size_t BLI_str_escape(char *__restrict dst, const char *__restrict src, size_t dst_maxncpy) ATTR_NONNULL(1
int BLI_str_utf8_invalid_strip(char *str, size_t str_len) ATTR_NONNULL(1)
size_t void BLI_uniquename_cb(blender::FunctionRef< bool(blender::StringRefNull)> unique_check, const char *defname, char delim, char *name, size_t name_maxncpy) ATTR_NONNULL(2
size_t BLI_string_replace_range(char *string, size_t string_maxncpy, int src_beg, int src_end, const char *dst)
unsigned int uint
#define ELEM(...)
#define STREQ(a, b)
@ FMODIFIER_TYPE_NOISE
@ BONE_CONNECTED
@ GP_BRUSH_USE_SAT_RAND_PRESS
@ GP_BRUSH_USE_VAL_RAND_PRESS
@ GP_BRUSH_USE_HUE_RAND_PRESS
@ GP_BRUSH_USE_HUE_AT_STROKE
@ GP_BRUSH_USE_VAL_AT_STROKE
@ GP_BRUSH_USE_SAT_AT_STROKE
@ BRUSH_PLANE_INVERT_DISPLACEMENT
@ BRUSH_PLANE_SWAP_HEIGHT_AND_DEPTH
@ BRUSH_CURVE_SMOOTH
@ SCULPT_BRUSH_TYPE_PLANE
@ BRUSH_ORIGINAL_NORMAL
@ BRUSH_ORIGINAL_PLANE
@ BRUSH_PLANE_TRIM
@ BRUSH_INVERT_TO_SCRAPE_FILL
@ BRUSH_COLOR_JITTER_USE_VAL_AT_STROKE
@ BRUSH_COLOR_JITTER_USE_HUE_AT_STROKE
@ BRUSH_COLOR_JITTER_USE_SAT_AT_STROKE
@ BRUSH_COLOR_JITTER_USE_SAT_RAND_PRESS
@ BRUSH_COLOR_JITTER_USE_VAL_RAND_PRESS
@ BRUSH_COLOR_JITTER_USE_HUE_RAND_PRESS
@ BRUSH_JITTER_COLOR
@ NURBS_KNOT_MODE_NORMAL
@ NURBS_KNOT_MODE_CUSTOM
@ CD_PROP_FLOAT
@ CD_PROP_FLOAT3
@ CD_PROP_FLOAT2
#define DNA_struct_default_get(struct_name)
@ eModifierType_GreasePencilLineart
@ NODE_INTERFACE_SOCKET_SINGLE_VALUE_ONLY_LEGACY
@ NODE_INTERFACE_SOCKET_STRUCTURE_TYPE_SINGLE
@ NODE_INTERFACE_SOCKET_STRUCTURE_TYPE_AUTO
@ NODE_HIDDEN
@ NODE_SELECT
@ NODE_VECTOR_MATH_SCALE
@ CMP_NODE_INTERPOLATION_BILINEAR
@ NTREE_GEOMETRY
@ NTREE_COMPOSIT
@ NODE_MATH_MINIMUM
@ NODE_MATH_ADD
@ NODE_MATH_MAXIMUM
@ NODE_MATH_MULTIPLY
@ CMP_NODE_OUTPUT_IGNORE_ALPHA
@ CMP_NODE_RELATIVE_TO_PIXEL_DATA_TYPE_VECTOR
@ CMP_NODE_RELATIVE_TO_PIXEL_DATA_TYPE_FLOAT
@ CMP_NODE_CORNER_PIN_INTERPOLATION_ANISOTROPIC
@ SHD_MIXRGB_USE_ALPHA
@ SHD_MIXRGB_CLAMP
@ CMP_NODE_BLUR_ASPECT_NONE
@ CMP_NODE_BLUR_ASPECT_X
@ CMP_NODE_BLUR_ASPECT_Y
@ CMP_NODE_ALPHA_CONVERT_UNPREMULTIPLY
@ CMP_NODE_ALPHA_CONVERT_PREMULTIPLY
@ CMP_NODE_MASK_FLAG_NO_FEATHER
@ CMP_NODE_MASK_FLAG_MOTION_BLUR
@ SOCK_OUT
@ SOCK_IN
@ CMP_NODE_SETALPHA_MODE_REPLACE_ALPHA
@ NODE_MIX_MODE_UNIFORM
@ SOCK_INT
@ SOCK_VECTOR
@ SOCK_BOOLEAN
@ SOCK_FLOAT
@ SOCK_STRING
@ SOCK_RGBA
@ NODE_MAP_RANGE_LINEAR
@ CMP_NODE_SCALE_RENDER_SIZE
@ CMP_NODE_RELATIVE_TO_PIXEL_REFERENCE_DIMENSION_PER_DIMENSION
@ CMP_NODE_RELATIVE_TO_PIXEL_REFERENCE_DIMENSION_Y
@ CMP_NODE_RELATIVE_TO_PIXEL_REFERENCE_DIMENSION_X
@ CMP_NODE_LENS_DISTORTION_RADIAL
@ CMP_NODE_LENS_DISTORTION_HORIZONTAL
@ OB_SURF
@ OB_FONT
@ OB_CURVES_LEGACY
@ SEQ_SNAP_TO_FRAME_RANGE
@ SCE_SNAP
@ RGN_TYPE_WINDOW
@ STRIP_TYPE_OVERDROP_REMOVED
@ STRIP_TYPE_ALPHAOVER
@ SI_NO_DRAW_UV_GUIDE
@ SPACE_FILE
@ SPACE_PROPERTIES
@ SPACE_SEQ
@ SPACE_IMAGE
@ SEQ_DRAW_UNUSED_0
@ FILE_ASSET_IMPORT_INSTANCE_COLLECTIONS_ON_LINK
@ TEXMAP_CLIP_MIN
@ TEXMAP_CLIP_MAX
@ V2D_KEEPOFS_Y
@ V2D_KEEPOFS_X
@ V2D_KEEPZOOM
@ V2D_ZOOM_IGNORE_KEEPOFS
@ PROP_ANGLE
Definition RNA_types.hh:240
@ PROP_COLOR_TEMPERATURE
Definition RNA_types.hh:278
@ PROP_NONE
Definition RNA_types.hh:221
@ PROP_FACTOR
Definition RNA_types.hh:239
BMesh const char void * data
static DBVT_INLINE btScalar size(const btDbvtVolume &a)
Definition btDbvt.cpp:52
bool contains(const Key &key) const
Definition BLI_set.hh:310
bool add(const Key &key)
Definition BLI_set.hh:248
bool add(const Key &key, const Value &value)
Definition BLI_map.hh:295
const Value & lookup(const Key &key) const
Definition BLI_map.hh:545
Value lookup_default(const Key &key, const Value &default_value) const
Definition BLI_map.hh:570
void add_new(const Key &key, const Value &value)
Definition BLI_map.hh:265
bool contains(const Key &key) const
Definition BLI_map.hh:353
constexpr bool is_empty() const
Definition BLI_span.hh:260
blender::Span< const Slot * > slots() const
bke::CurvesGeometry & strokes_for_write()
KDTree_3d * tree
#define input
#define CD_MASK_PROP_ALL
void * MEM_callocN(size_t len, const char *str)
Definition mallocn.cc:118
void MEM_freeN(void *vmemh)
Definition mallocn.cc:113
void foreach_fcurve_in_action_slot(Action &action, slot_handle_t handle, FunctionRef< void(FCurve &fcurve)> callback)
static void ANIM_armature_foreach_bone(ListBase *bones, CB callback)
void foreach_fcurve_in_action(Action &action, FunctionRef< void(FCurve &fcurve)> callback)
constexpr float LEGACY_RADIUS_CONVERSION_FACTOR
T & get_item_as(bNodeTreeInterfaceItem &item)
T & get_socket_data_as(bNodeTreeInterfaceSocket &item)
void node_modify_socket_type_static(bNodeTree *ntree, bNode *node, bNodeSocket *sock, int type, int subtype)
Definition node.cc:3123
void mesh_sculpt_mask_to_generic(Mesh &mesh)
bNodeSocket * node_find_socket(bNode &node, eNodeSocketInOut in_out, StringRef identifier)
Definition node.cc:2864
void node_remove_node(Main *bmain, bNodeTree &ntree, bNode &node, bool do_id_user, bool remove_animation=true)
Definition node.cc:4649
bNode * node_add_node(const bContext *C, bNodeTree &ntree, StringRef idname)
Definition node.cc:3788
void node_remove_link(bNodeTree *ntree, bNodeLink &link)
Definition node.cc:4124
bNodeSocketType * node_socket_type_find(StringRef idname)
Definition node.cc:2794
bNode * node_add_static_node(const bContext *C, bNodeTree &ntree, int type)
Definition node.cc:3804
bNodeSocket * node_add_static_socket(bNodeTree &ntree, bNode &node, eNodeSocketInOut in_out, int type, int subtype, StringRefNull identifier, StringRefNull name)
Definition node.cc:3529
void mesh_custom_normals_to_generic(Mesh &mesh)
T min(const T &a, const T &b)
T max(const T &a, const T &b)
void for_each_callback(ListBase *seqbase, ForEachFunc callback, void *user_data)
Definition iterator.cc:59
SequencerToolSettings * tool_settings_ensure(Scene *scene)
Definition sequencer.cc:362
float wrap(float value, float max, float min)
Definition node_math.h:71
#define min(a, b)
Definition sort.cc:36
ListBase drivers
ListBase nla_tracks
struct CurveMapping * curve_rand_saturation
struct CurveMapping * curve_rand_hue
struct CurveMapping * curve_rand_value
struct CurveMapping * curve_rand_saturation
struct CurveMapping * curve_rand_hue
struct CurveMapping * curve_rand_value
struct BrushGpencilSettings * gpencil_settings
int color_jitter_flag
float hsv_jitter[3]
CustomDataLayer * layers
char * rna_path
ListBase modifiers
FileSelectParams base_params
unsigned short list_column_size
unsigned short list_thumbnail_size
Definition DNA_ID.h:404
IDProperty * system_properties
Definition DNA_ID.h:454
IDProperty * properties
Definition DNA_ID.h:446
ListBase brushes
Definition BKE_main.hh:271
ListBase scenes
Definition BKE_main.hh:245
ListBase grease_pencils
Definition BKE_main.hh:279
ListBase actions
Definition BKE_main.hh:269
ListBase hair_curves
Definition BKE_main.hh:289
ListBase nodetrees
Definition BKE_main.hh:270
ListBase armatures
Definition BKE_main.hh:268
ListBase screens
Definition BKE_main.hh:261
ListBase images
Definition BKE_main.hh:253
ListBase objects
Definition BKE_main.hh:247
CustomData edge_data
CustomData corner_data
CustomData face_data
ListBase vertex_group_names
CustomData vert_data
uint8_t input_type
float shadow_terminator_shading_offset
float shadow_terminator_geometry_offset
float shadow_terminator_normal_offset
FileSelectParams * params
FileAssetSelectParams * asset_params
float uv_face_opacity
int16_t snap_step_seconds
struct UnifiedPaintSettings unified_paint_settings
int16_t snap_step_frames
struct CurveMapping * curve_rand_value
struct CurveMapping * curve_rand_saturation
struct CurveMapping * curve_rand_hue
int8_t curve_preset
struct CurveMapping * strength_curve
void * default_value
char identifier[64]
bNodeTreeInterface tree_interface
ListBase nodes
ListBase links
float location[2]
int16_t custom1
float width
ListBase inputs
struct bNode * parent
char name[64]
int16_t type_legacy
float custom4
void * storage
float custom3
int16_t custom2
Defines a socket type.
Definition BKE_node.hh:152
eNodeSocketDatatype type
Definition BKE_node.hh:187
max
Definition text_draw.cc:251
static bNode * add_node(bNodeTree *ntree, const int type, const blender::float2 loc)
static void do_version_alpha_over_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_color_spill_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_init_default_jitter_curves_in_unified_paint_settings(ToolSettings *ts)
static void do_version_tone_map_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_id_mask_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_color_correction_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_color_balance_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_denoise_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_directional_blur_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_translate_node_remove_relative(bNodeTree *node_tree)
static void do_version_tone_map_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_composite_viewer_remove_alpha(bNodeTree *node_tree)
static void do_version_glare_node_star_45_option_to_input_animation(bNodeTree *node_tree, bNode *node)
void blo_do_versions_450(FileData *, Library *, Main *bmain)
static void version_set_default_bone_drawtype(Main *bmain)
static void do_version_denoise_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_luminance_matte_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_bright_contrast_remove_premultiplied(bNodeTree *node_tree)
static void do_version_luminance_matte_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_alpha_over_remove_premultiply(bNodeTree *node_tree)
static void do_version_pixelate_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_stabilize_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_difference_matte_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_stabilize_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_chroma_matte_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static bool strip_effect_overdrop_to_alphaover(Strip *strip, void *)
static void do_version_distance_matte_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void version_escape_curly_braces(char string[], const int string_array_length)
static void do_version_blur_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_anti_alias_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void version_show_texpaint_to_show_uv(Main *bmain)
static void do_version_difference_matte_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_keying_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_despeckle_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_mask_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_bokeh_blur_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_chroma_matte_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_map_value_node(bNodeTree *node_tree, bNode *node)
static void do_version_mix_color_use_alpha(bNodeTree *node_tree, bNode *node)
static void do_version_scale_node_remove_translate(bNodeTree *node_tree)
static void fix_curve_nurbs_knot_mode_custom(Main *bmain)
static void do_version_invert_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_kuwahara_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_dilate_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_z_combine_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_color_matte_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_sun_beams_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_replace_image_info_node_coordinates(bNodeTree *node_tree)
static void do_version_color_spill_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_bokeh_blur_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_sun_beams_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_z_combine_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_split_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_time_curve_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void version_convert_sculpt_planar_brushes(Main *bmain)
static void do_version_id_mask_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_channel_matte_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_bokeh_image_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void version_escape_curly_braces_in_compositor_file_output_nodes(bNodeTree &nodetree)
static void do_convert_gp_jitter_flags(Brush *brush)
static void do_version_plane_track_deform_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_lens_distortion_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void clamp_subdivision_node_level_input(bNodeTree &tree)
static void do_version_switch_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_lens_distortion_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_time_curve_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_box_mask_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_split_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void asset_browser_add_list_view(Main *bmain)
static void do_version_kuwahara_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_crop_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_convert_to_generic_nodes_after_linking(Main *bmain, bNodeTree *node_tree, ID *id)
static void do_version_ellipse_mask_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_color_matte_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_switch_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_plane_track_deform_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
void version_forward_compat_system_idprops(Main *bmain)
static void do_version_despeckle_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_color_correction_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_ellipse_mask_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_box_mask_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_vector_blur_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_dilate_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_alpha_over_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_inpaint_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_vector_sockets_dimensions(bNodeTree *node_tree)
static void do_version_mask_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static CustomDataLayer * find_old_seam_layer(CustomData &custom_data, const blender::StringRef name)
static void do_version_bokeh_image_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_anti_alias_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void nlastrips_apply_fcurve_versioning(ListBase &strips)
void do_versions_after_linking_450(FileData *, Main *bmain)
static void do_version_bilateral_blur_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void version_sequencer_update_overdrop(Main *bmain)
static void do_version_blur_defocus_nodes_remove_gamma(bNodeTree *node_tree)
static void do_version_channel_matte_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_flip_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_convert_gp_jitter_values(Brush *brush)
static void do_version_keying_screen_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_keying_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_new_glare_clamp_input(bNodeTree *node_tree)
static void do_version_glare_node_star_45_option_to_input(bNodeTree *node_tree, bNode *node)
static void do_version_inpaint_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void node_interface_single_value_to_structure_type(bNodeTreeInterfaceItem &item)
static void do_version_bilateral_blur_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_node_curve_to_mesh_scale_input(bNodeTree *tree)
static void do_version_directional_blur_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_convert_to_generic_nodes(bNodeTree *node_tree)
static void do_version_invert_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_color_balance_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void version_fix_fcurve_noise_offset(FCurve &fcurve)
static void do_version_vector_blur_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void version_set_uv_face_overlay_defaults(Main *bmain)
static void do_version_keying_screen_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void do_version_crop_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_pixelate_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
static void do_version_distance_matte_node_options_to_inputs_animation(bNodeTree *node_tree, bNode *node)
static void rename_mesh_uv_seam_attribute(Mesh &mesh)
static void do_version_blur_node_options_to_inputs(bNodeTree *node_tree, bNode *node)
IDProperty * version_cycles_properties_from_ID(ID *id)
bool version_node_socket_is_used(bNodeSocket *sock)
bNodeSocket & version_node_add_socket(bNodeTree &ntree, bNode &node, const eNodeSocketInOut in_out, const char *idname, const char *identifier)
void version_node_socket_index_animdata(Main *bmain, const int node_tree_type, const int node_type, const int socket_index_orig, const int socket_index_offset, const int total_number_of_sockets)
bNode & version_node_add_empty(bNodeTree &ntree, const char *idname)
void version_socket_update_is_used(bNodeTree *ntree)
bNodeLink & version_node_add_link(bNodeTree &ntree, bNode &node_a, bNodeSocket &socket_a, bNode &node_b, bNodeSocket &socket_b)
bNodeSocket * version_node_add_socket_if_not_exist(bNodeTree *ntree, bNode *node, int in_out, int type, int subtype, const char *identifier, const char *name)
float version_cycles_property_float(IDProperty *idprop, const char *name, float default_value)