diff options
author | Bastien Montagne <bastien@blender.org> | 2021-09-03 15:27:53 +0300 |
---|---|---|
committer | Bastien Montagne <bastien@blender.org> | 2021-09-03 15:27:53 +0300 |
commit | d2d21a3d9da711cfcc03c81d36a81329aeb7c18f (patch) | |
tree | b3f0184eb164a9f9aefeff6d92e6e634c464953f | |
parent | c7106d5b7fe8416a0fe63f6eda6c794625fa897d (diff) | |
parent | f9ccd26b037d43f2490d1f0263e45e775d30473d (diff) |
Merge branch 'master' into studio-sprite-fright
24 files changed, 252 insertions, 181 deletions
diff --git a/release/scripts/startup/bl_app_templates_system/2D_Animation/__init__.py b/release/scripts/startup/bl_app_templates_system/2D_Animation/__init__.py index be47890a002..c8328f5ee42 100644 --- a/release/scripts/startup/bl_app_templates_system/2D_Animation/__init__.py +++ b/release/scripts/startup/bl_app_templates_system/2D_Animation/__init__.py @@ -46,6 +46,7 @@ def update_factory_startup_screens(): def update_factory_startup_scenes(): for scene in bpy.data.scenes: scene.tool_settings.use_keyframe_insert_auto = True + scene.tool_settings.gpencil_sculpt.use_scale_thickness = True def update_factory_startup_grease_pencils(): diff --git a/release/scripts/startup/bl_ui/properties_grease_pencil_common.py b/release/scripts/startup/bl_ui/properties_grease_pencil_common.py index f87f5351d6d..f01e75dbab8 100644 --- a/release/scripts/startup/bl_ui/properties_grease_pencil_common.py +++ b/release/scripts/startup/bl_ui/properties_grease_pencil_common.py @@ -85,9 +85,6 @@ class GreasePencilSculptOptionsPanel: layout.prop(gp_settings, "use_edit_strength", text="Affect Strength") layout.prop(gp_settings, "use_edit_thickness", text="Affect Thickness") - if tool == 'SMOOTH': - layout.prop(gp_settings, "use_edit_pressure") - layout.prop(gp_settings, "use_edit_uv", text="Affect UV") diff --git a/source/blender/blenkernel/intern/brush.c b/source/blender/blenkernel/intern/brush.c index 7b81187be21..d60ef28efda 100644 --- a/source/blender/blenkernel/intern/brush.c +++ b/source/blender/blenkernel/intern/brush.c @@ -1127,7 +1127,7 @@ void BKE_gpencil_brush_preset_set(Main *bmain, Brush *brush, const short type) brush->gpencil_settings->draw_strength = 0.3f; brush->gpencil_settings->flag |= GP_BRUSH_USE_STRENGTH_PRESSURE; - brush->gpencil_settings->sculpt_flag = GP_SCULPT_FLAG_SMOOTH_PRESSURE; + brush->gpencil_settings->sculpt_flag = GP_SCULPT_FLAGMODE_APPLY_THICKNESS; brush->gpencil_settings->sculpt_mode_flag |= GP_SCULPT_FLAGMODE_APPLY_POSITION; break; @@ -1141,7 +1141,6 @@ void BKE_gpencil_brush_preset_set(Main *bmain, Brush *brush, const short type) brush->gpencil_settings->draw_strength = 0.3f; brush->gpencil_settings->flag |= GP_BRUSH_USE_STRENGTH_PRESSURE; - brush->gpencil_settings->sculpt_flag = GP_SCULPT_FLAG_SMOOTH_PRESSURE; brush->gpencil_settings->sculpt_mode_flag |= GP_SCULPT_FLAGMODE_APPLY_POSITION; break; diff --git a/source/blender/editors/animation/anim_filter.c b/source/blender/editors/animation/anim_filter.c index 7e3e3f363c2..104540e2257 100644 --- a/source/blender/editors/animation/anim_filter.c +++ b/source/blender/editors/animation/anim_filter.c @@ -1111,7 +1111,27 @@ static bool skip_fcurve_selected_data(bDopeSheet *ads, FCurve *fcu, ID *owner_id /* Can only add this F-Curve if it is selected. */ if (ads->filterflag & ADS_FILTER_ONLYSEL) { - if ((seq == NULL) || (seq->flag & SELECT) == 0) { + + /* NOTE(@campbellbarton): The `seq == NULL` check doesn't look right + * (compared to other checks in this function which skip data that can't be found). + * + * This is done since the search for sequence strips doesn't use a global lookup: + * - Nested meta-strips are excluded. + * - When inside a meta-strip - strips outside the meta-strip excluded. + * + * Instead, only the strips directly visible to the user are considered for selection. + * The NULL check here means everything else is considered unselected and is not shown. + * + * There is a subtle difference between nodes, pose-bones ... etc + * since data-paths that point to missing strips are not shown. + * If this is an important difference, the NULL case could perform a global lookup, + * only returning `true` if the sequence strip exists elsewhere + * (ignoring it's selection state). */ + if (seq == NULL) { + return true; + } + + if ((seq->flag & SELECT) == 0) { return true; } } diff --git a/source/blender/makesdna/DNA_brush_enums.h b/source/blender/makesdna/DNA_brush_enums.h index 6563afd2b4a..72b2db89cef 100644 --- a/source/blender/makesdna/DNA_brush_enums.h +++ b/source/blender/makesdna/DNA_brush_enums.h @@ -305,8 +305,6 @@ typedef enum eGp_Vertex_Mode { typedef enum eGP_Sculpt_Flag { /* invert the effect of the brush */ GP_SCULPT_FLAG_INVERT = (1 << 0), - /* smooth brush affects pressure values as well */ - GP_SCULPT_FLAG_SMOOTH_PRESSURE = (1 << 2), /* temporary invert action */ GP_SCULPT_FLAG_TMP_INVERT = (1 << 3), } eGP_Sculpt_Flag; diff --git a/source/blender/makesrna/RNA_access.h b/source/blender/makesrna/RNA_access.h index 76155973982..75057c1a071 100644 --- a/source/blender/makesrna/RNA_access.h +++ b/source/blender/makesrna/RNA_access.h @@ -1124,6 +1124,8 @@ bool RNA_path_resolve(PointerRNA *ptr, const char *path, PointerRNA *r_ptr, Prop bool RNA_path_resolve_full( PointerRNA *ptr, const char *path, PointerRNA *r_ptr, PropertyRNA **r_prop, int *r_index); +bool RNA_path_resolve_full_maybe_null( + PointerRNA *ptr, const char *path, PointerRNA *r_ptr, PropertyRNA **r_prop, int *r_index); /* path_resolve_property() variants ensure that pointer + property both exist */ bool RNA_path_resolve_property(PointerRNA *ptr, diff --git a/source/blender/makesrna/intern/rna_access.c b/source/blender/makesrna/intern/rna_access.c index 51e20eb9e7f..0ba5b786187 100644 --- a/source/blender/makesrna/intern/rna_access.c +++ b/source/blender/makesrna/intern/rna_access.c @@ -4859,75 +4859,119 @@ PointerRNA rna_array_lookup_int( /* RNA Path - Experiment */ -static char *rna_path_token(const char **path, char *fixedbuf, int fixedlen, int bracket) +/** + * Extract the first token from `path`. + * + * \param path: Extract the token from path, step the pointer to the beginning of the next token + * \return The nil terminated token. + */ +static char *rna_path_token(const char **path, char *fixedbuf, int fixedlen) { - const char *p; int len = 0; - if (bracket) { - /* get data between [], check escaping quotes and back-slashes with #BLI_str_unescape. */ - if (**path == '[') { - (*path)++; - } - else { - return NULL; - } + /* Get data until `.` or `[`. */ + const char *p = *path; + while (*p && !ELEM(*p, '.', '[')) { + len++; + p++; + } - p = *path; + /* Empty, return. */ + if (UNLIKELY(len == 0)) { + return NULL; + } - /* 2 kinds of look-ups now, quoted or unquoted. */ - if (*p != '"') { - while (*p && (*p != ']')) { - len++; - p++; - } - } - else { - const char *p_end = BLI_str_escape_find_quote(p + 1); - if (p_end == NULL) { - /* No Matching quote. */ - return NULL; - } - /* Skip the last quoted char to get the `]`. */ - p_end += 1; + /* Try to use fixed buffer if possible. */ + char *buf = (len + 1 < fixedlen) ? fixedbuf : MEM_mallocN(sizeof(char) * (len + 1), __func__); + memcpy(buf, *path, sizeof(char) * len); + buf[len] = '\0'; - len += (p_end - p); - p = p_end; - } + if (*p == '.') { + p++; + } + *path = p; - if (*p != ']') { + return buf; +} + +/** + * Extract the first token in brackets from `path` (with quoted text support). + * + * - `[0]` -> `0` + * - `["Some\"Quote"]` -> `Some"Quote` + * + * \param path: Extract the token from path, step the pointer to the beginning of the next token + * (past quoted text and brackets). + * \return The nil terminated token. + */ +static char *rna_path_token_in_brackets(const char **path, + char *fixedbuf, + int fixedlen, + bool *r_quoted) +{ + int len = 0; + bool quoted = false; + + BLI_assert(r_quoted != NULL); + + /* Get data between `[]`, check escaping quotes and back-slashes with #BLI_str_unescape. */ + if (UNLIKELY(**path != '[')) { + return NULL; + } + + (*path)++; + const char *p = *path; + + /* 2 kinds of look-ups now, quoted or unquoted. */ + if (*p == '"') { + /* Find the matching quote. */ + (*path)++; + p = *path; + const char *p_end = BLI_str_escape_find_quote(p); + if (p_end == NULL) { + /* No Matching quote. */ return NULL; } + /* Exclude the last quote from the length. */ + len += (p_end - p); + + /* Skip the last quoted char to get the `]`. */ + p_end += 1; + p = p_end; + quoted = true; } else { - /* Get data until `.` or `[`. */ - p = *path; - - while (*p && *p != '.' && *p != '[') { + /* Find the matching bracket. */ + while (*p && (*p != ']')) { len++; p++; } } - /* empty, return */ - if (len == 0) { + if (UNLIKELY(*p != ']')) { + return NULL; + } + + /* Empty, return. */ + if (UNLIKELY(len == 0)) { return NULL; } /* Try to use fixed buffer if possible. */ char *buf = (len + 1 < fixedlen) ? fixedbuf : MEM_mallocN(sizeof(char) * (len + 1), __func__); - /* copy string, taking into account escaped ] */ - if (bracket) { + /* Copy string, taking into account escaped ']' */ + if (quoted) { BLI_str_unescape(buf, *path, len); - p = (*path) + len; + /* +1 to step over the last quote. */ + BLI_assert((*path)[len] == '"'); + p = (*path) + len + 1; } else { memcpy(buf, *path, sizeof(char) * len); buf[len] = '\0'; } - - /* set path to start of next token */ + /* Set path to start of next token. */ if (*p == ']') { p++; } @@ -4936,20 +4980,9 @@ static char *rna_path_token(const char **path, char *fixedbuf, int fixedlen, int } *path = p; - return buf; -} + *r_quoted = quoted; -static int rna_token_strip_quotes(char *token) -{ - if (token[0] == '"') { - int len = strlen(token); - if (len >= 2 && token[len - 1] == '"') { - /* strip away "" */ - token[len - 1] = '\0'; - return 1; - } - } - return 0; + return buf; } static bool rna_path_parse_collection_key(const char **path, @@ -4968,18 +5001,19 @@ static bool rna_path_parse_collection_key(const char **path, } if (**path == '[') { + bool quoted; char *token; /* resolve the lookup with [] brackets */ - token = rna_path_token(path, fixedbuf, sizeof(fixedbuf), 1); + token = rna_path_token_in_brackets(path, fixedbuf, sizeof(fixedbuf), "ed); if (!token) { return false; } /* check for "" to see if it is a string */ - if (rna_token_strip_quotes(token)) { - if (RNA_property_collection_lookup_string(ptr, prop, token + 1, r_nextptr)) { + if (quoted) { + if (RNA_property_collection_lookup_string(ptr, prop, token, r_nextptr)) { /* pass */ } else { @@ -5041,15 +5075,16 @@ static bool rna_path_parse_array_index(const char **path, /* multi index resolve */ if (**path == '[') { - token = rna_path_token(path, fixedbuf, sizeof(fixedbuf), 1); + bool quoted; + token = rna_path_token_in_brackets(path, fixedbuf, sizeof(fixedbuf), "ed); if (token == NULL) { /* invalid syntax blah[] */ return false; } /* check for "" to see if it is a string */ - if (rna_token_strip_quotes(token)) { - temp_index = RNA_property_array_item_index(prop, *(token + 1)); + if (quoted) { + temp_index = RNA_property_array_item_index(prop, *token); } else { /* otherwise do int lookup */ @@ -5066,7 +5101,7 @@ static bool rna_path_parse_array_index(const char **path, } else if (dim == 1) { /* location.x || scale.X, single dimension arrays only */ - token = rna_path_token(path, fixedbuf, sizeof(fixedbuf), 0); + token = rna_path_token(path, fixedbuf, sizeof(fixedbuf)); if (token == NULL) { /* invalid syntax blah. */ return false; @@ -5166,8 +5201,7 @@ static bool rna_path_parse(PointerRNA *ptr, RNA_POINTER_INVALIDATE(&nextptr); } - int use_id_prop = (*path == '[') ? 1 : 0; - char *token; + const bool use_id_prop = (*path == '['); /* custom property lookup ? * C.object["someprop"] */ @@ -5177,8 +5211,10 @@ static bool rna_path_parse(PointerRNA *ptr, } /* look up property name in current struct */ - token = rna_path_token(&path, fixedbuf, sizeof(fixedbuf), use_id_prop); - + bool quoted = false; + char *token = use_id_prop ? + rna_path_token_in_brackets(&path, fixedbuf, sizeof(fixedbuf), "ed) : + rna_path_token(&path, fixedbuf, sizeof(fixedbuf)); if (!token) { return false; } @@ -5186,8 +5222,8 @@ static bool rna_path_parse(PointerRNA *ptr, prop = NULL; if (use_id_prop) { /* look up property name in current struct */ IDProperty *group = RNA_struct_idprops(&curptr, 0); - if (group && rna_token_strip_quotes(token)) { - prop = (PropertyRNA *)IDP_GetPropertyFromGroup(group, token + 1); + if (group && quoted) { + prop = (PropertyRNA *)IDP_GetPropertyFromGroup(group, token); } } else { @@ -5326,6 +5362,18 @@ bool RNA_path_resolve_full( } /** + * A version of #RNA_path_resolve_full doesn't check the value of #PointerRNA.data. + * + * \note While it's correct to ignore the value of #PointerRNA.data + * most callers need to know if the resulting pointer was found and not null. + */ +bool RNA_path_resolve_full_maybe_null( + PointerRNA *ptr, const char *path, PointerRNA *r_ptr, PropertyRNA **r_prop, int *r_index) +{ + return rna_path_parse(ptr, path, r_ptr, r_prop, r_index, NULL, NULL, true); +} + +/** * Resolve the given RNA Path to find both the pointer AND property * indicated by fully resolving the path. * @@ -5492,7 +5540,7 @@ char *RNA_path_back(const char *path) while (*current) { char *token; - token = rna_path_token(¤t, fixedbuf, sizeof(fixedbuf), 0); + token = rna_path_token(¤t, fixedbuf, sizeof(fixedbuf)); if (!token) { return NULL; @@ -5502,7 +5550,8 @@ char *RNA_path_back(const char *path) } /* in case of collection we also need to strip off [] */ - token = rna_path_token(¤t, fixedbuf, sizeof(fixedbuf), 1); + bool quoted; + token = rna_path_token_in_brackets(¤t, fixedbuf, sizeof(fixedbuf), "ed); if (token && token != fixedbuf) { MEM_freeN(token); } diff --git a/source/blender/makesrna/intern/rna_brush.c b/source/blender/makesrna/intern/rna_brush.c index cdca58df4b0..25caa411979 100644 --- a/source/blender/makesrna/intern/rna_brush.c +++ b/source/blender/makesrna/intern/rna_brush.c @@ -1801,13 +1801,6 @@ static void rna_def_gpencil_options(BlenderRNA *brna) RNA_def_property_ui_text(prop, "Trim Stroke Ends", "Trim intersecting stroke ends"); RNA_def_property_clear_flag(prop, PROP_ANIMATABLE); - prop = RNA_def_property(srna, "use_edit_pressure", PROP_BOOLEAN, PROP_NONE); - RNA_def_property_boolean_sdna(prop, NULL, "sculpt_flag", GP_SCULPT_FLAG_SMOOTH_PRESSURE); - RNA_def_property_ui_text( - prop, "Affect Pressure", "Affect pressure values as well when smoothing strokes"); - RNA_def_property_clear_flag(prop, PROP_ANIMATABLE); - RNA_def_property_update(prop, NC_SCENE | ND_TOOLSETTINGS, NULL); - prop = RNA_def_property(srna, "direction", PROP_ENUM, PROP_NONE); RNA_def_property_enum_bitflag_sdna(prop, NULL, "sculpt_flag"); RNA_def_property_enum_items(prop, prop_direction_items); diff --git a/source/blender/nodes/function/node_function_util.hh b/source/blender/nodes/function/node_function_util.hh index 96a8f29c3e9..46b485298e3 100644 --- a/source/blender/nodes/function/node_function_util.hh +++ b/source/blender/nodes/function/node_function_util.hh @@ -31,6 +31,7 @@ #include "NOD_function.h" #include "NOD_multi_function.hh" +#include "NOD_socket_declarations.hh" #include "node_util.h" diff --git a/source/blender/nodes/function/nodes/node_fn_boolean_math.cc b/source/blender/nodes/function/nodes/node_fn_boolean_math.cc index 58e7d82beea..b71ee092de6 100644 --- a/source/blender/nodes/function/nodes/node_fn_boolean_math.cc +++ b/source/blender/nodes/function/nodes/node_fn_boolean_math.cc @@ -24,17 +24,17 @@ #include "node_function_util.hh" -static bNodeSocketTemplate fn_node_boolean_math_in[] = { - {SOCK_BOOLEAN, N_("Boolean")}, - {SOCK_BOOLEAN, N_("Boolean")}, - {-1, ""}, -}; +namespace blender::nodes { -static bNodeSocketTemplate fn_node_boolean_math_out[] = { - {SOCK_BOOLEAN, N_("Boolean")}, - {-1, ""}, +static void fn_node_boolean_math_declare(NodeDeclarationBuilder &b) +{ + b.add_input<decl::Bool>("Boolean", "Boolean"); + b.add_input<decl::Bool>("Boolean", "Boolean_001"); + b.add_output<decl::Bool>("Boolean"); }; +} // namespace blender::nodes + static void fn_node_boolean_math_layout(uiLayout *layout, bContext *UNUSED(C), PointerRNA *ptr) { uiItemR(layout, ptr, "operation", 0, "", ICON_NONE); @@ -91,7 +91,7 @@ void register_node_type_fn_boolean_math() static bNodeType ntype; fn_node_type_base(&ntype, FN_NODE_BOOLEAN_MATH, "Boolean Math", NODE_CLASS_CONVERTER, 0); - node_type_socket_templates(&ntype, fn_node_boolean_math_in, fn_node_boolean_math_out); + ntype.declare = blender::nodes::fn_node_boolean_math_declare; node_type_label(&ntype, node_boolean_math_label); node_type_update(&ntype, node_boolean_math_update); ntype.build_multi_function = fn_node_boolean_math_build_multi_function; diff --git a/source/blender/nodes/function/nodes/node_fn_float_compare.cc b/source/blender/nodes/function/nodes/node_fn_float_compare.cc index 918dd24e520..4f4830afabc 100644 --- a/source/blender/nodes/function/nodes/node_fn_float_compare.cc +++ b/source/blender/nodes/function/nodes/node_fn_float_compare.cc @@ -26,18 +26,18 @@ #include "node_function_util.hh" -static bNodeSocketTemplate fn_node_float_compare_in[] = { - {SOCK_FLOAT, N_("A"), 0.0f, 0.0f, 0.0f, 0.0f, -10000.0f, 10000.0f}, - {SOCK_FLOAT, N_("B"), 0.0f, 0.0f, 0.0f, 0.0f, -10000.0f, 10000.0f}, - {SOCK_FLOAT, N_("Epsilon"), 0.001f, 0.0f, 0.0f, 0.0f, -10000.0f, 10000.0f}, - {-1, ""}, -}; +namespace blender::nodes { -static bNodeSocketTemplate fn_node_float_compare_out[] = { - {SOCK_BOOLEAN, N_("Result")}, - {-1, ""}, +static void fn_node_float_compare_declare(NodeDeclarationBuilder &b) +{ + b.add_input<decl::Float>("A").min(-10000.0f).max(10000.0f); + b.add_input<decl::Float>("B").min(-10000.0f).max(10000.0f); + b.add_input<decl::Float>("Epsilon").default_value(0.001f).min(-10000.0f).max(10000.0f); + b.add_output<decl::Bool>("Result"); }; +} // namespace blender::nodes + static void geo_node_float_compare_layout(uiLayout *layout, bContext *UNUSED(C), PointerRNA *ptr) { uiItemR(layout, ptr, "operation", 0, "", ICON_NONE); @@ -110,7 +110,7 @@ void register_node_type_fn_float_compare() static bNodeType ntype; fn_node_type_base(&ntype, FN_NODE_FLOAT_COMPARE, "Float Compare", NODE_CLASS_CONVERTER, 0); - node_type_socket_templates(&ntype, fn_node_float_compare_in, fn_node_float_compare_out); + ntype.declare = blender::nodes::fn_node_float_compare_declare; node_type_label(&ntype, node_float_compare_label); node_type_update(&ntype, node_float_compare_update); ntype.build_multi_function = fn_node_float_compare_build_multi_function; diff --git a/source/blender/nodes/function/nodes/node_fn_float_to_int.cc b/source/blender/nodes/function/nodes/node_fn_float_to_int.cc index 40b8f27f895..e59c78d2c04 100644 --- a/source/blender/nodes/function/nodes/node_fn_float_to_int.cc +++ b/source/blender/nodes/function/nodes/node_fn_float_to_int.cc @@ -25,16 +25,16 @@ #include "node_function_util.hh" -static bNodeSocketTemplate fn_node_float_to_int_in[] = { - {SOCK_FLOAT, N_("Float"), 0.0, 0.0, 0.0, 0.0, -FLT_MAX, FLT_MAX}, - {-1, ""}, -}; +namespace blender::nodes { -static bNodeSocketTemplate fn_node_float_to_int_out[] = { - {SOCK_INT, N_("Integer")}, - {-1, ""}, +static void fn_node_float_to_int_declare(NodeDeclarationBuilder &b) +{ + b.add_input<decl::Float>("Float"); + b.add_output<decl::Int>("Integer"); }; +} // namespace blender::nodes + static void fn_node_float_to_int_layout(uiLayout *layout, bContext *UNUSED(C), PointerRNA *ptr) { uiItemR(layout, ptr, "rounding_mode", 0, "", ICON_NONE); @@ -88,7 +88,7 @@ void register_node_type_fn_float_to_int() static bNodeType ntype; fn_node_type_base(&ntype, FN_NODE_FLOAT_TO_INT, "Float to Integer", NODE_CLASS_CONVERTER, 0); - node_type_socket_templates(&ntype, fn_node_float_to_int_in, fn_node_float_to_int_out); + ntype.declare = blender::nodes::fn_node_float_to_int_declare; node_type_label(&ntype, node_float_to_int_label); ntype.build_multi_function = fn_node_float_to_int_build_multi_function; ntype.draw_buttons = fn_node_float_to_int_layout; diff --git a/source/blender/nodes/function/nodes/node_fn_input_string.cc b/source/blender/nodes/function/nodes/node_fn_input_string.cc index 560ace57aba..4a8e898fb9b 100644 --- a/source/blender/nodes/function/nodes/node_fn_input_string.cc +++ b/source/blender/nodes/function/nodes/node_fn_input_string.cc @@ -19,11 +19,15 @@ #include "UI_interface.h" #include "UI_resources.h" -static bNodeSocketTemplate fn_node_input_string_out[] = { - {SOCK_STRING, N_("String")}, - {-1, ""}, +namespace blender::nodes { + +static void fn_node_input_string_declare(NodeDeclarationBuilder &b) +{ + b.add_output<decl::String>("String"); }; +} // namespace blender::nodes + static void fn_node_input_string_layout(uiLayout *layout, bContext *UNUSED(C), PointerRNA *ptr) { uiItemR(layout, ptr, "string", 0, "", ICON_NONE); @@ -75,7 +79,7 @@ void register_node_type_fn_input_string() static bNodeType ntype; fn_node_type_base(&ntype, FN_NODE_INPUT_STRING, "String", NODE_CLASS_INPUT, 0); - node_type_socket_templates(&ntype, nullptr, fn_node_input_string_out); + ntype.declare = blender::nodes::fn_node_input_string_declare; node_type_init(&ntype, fn_node_input_string_init); node_type_storage(&ntype, "NodeInputString", fn_node_input_string_free, fn_node_string_copy); ntype.build_multi_function = fn_node_input_string_build_multi_function; diff --git a/source/blender/nodes/function/nodes/node_fn_input_vector.cc b/source/blender/nodes/function/nodes/node_fn_input_vector.cc index 244c045de9a..9548df7b423 100644 --- a/source/blender/nodes/function/nodes/node_fn_input_vector.cc +++ b/source/blender/nodes/function/nodes/node_fn_input_vector.cc @@ -21,11 +21,15 @@ #include "UI_interface.h" #include "UI_resources.h" -static bNodeSocketTemplate fn_node_input_vector_out[] = { - {SOCK_VECTOR, N_("Vector")}, - {-1, ""}, +namespace blender::nodes { + +static void fn_node_input_vector_declare(NodeDeclarationBuilder &b) +{ + b.add_output<decl::Vector>("Vector"); }; +} // namespace blender::nodes + static void fn_node_input_vector_layout(uiLayout *layout, bContext *UNUSED(C), PointerRNA *ptr) { uiLayout *col = uiLayoutColumn(layout, true); @@ -52,7 +56,7 @@ void register_node_type_fn_input_vector() static bNodeType ntype; fn_node_type_base(&ntype, FN_NODE_INPUT_VECTOR, "Vector", 0, 0); - node_type_socket_templates(&ntype, nullptr, fn_node_input_vector_out); + ntype.declare = blender::nodes::fn_node_input_vector_declare; node_type_init(&ntype, fn_node_input_vector_init); node_type_storage( &ntype, "NodeInputVector", node_free_standard_storage, node_copy_standard_storage); diff --git a/source/blender/nodes/function/nodes/node_fn_random_float.cc b/source/blender/nodes/function/nodes/node_fn_random_float.cc index 47ec9adf6bd..1bd39aacdca 100644 --- a/source/blender/nodes/function/nodes/node_fn_random_float.cc +++ b/source/blender/nodes/function/nodes/node_fn_random_float.cc @@ -18,18 +18,18 @@ #include "BLI_hash.h" -static bNodeSocketTemplate fn_node_random_float_in[] = { - {SOCK_FLOAT, N_("Min"), 0.0f, 0.0f, 0.0f, 0.0f, -10000.0f, 10000.0f, PROP_NONE}, - {SOCK_FLOAT, N_("Max"), 1.0f, 0.0f, 0.0f, 0.0f, -10000.0f, 10000.0f, PROP_NONE}, - {SOCK_INT, N_("Seed"), 0, 0, 0, 0, -10000, 10000}, - {-1, ""}, -}; +namespace blender::nodes { -static bNodeSocketTemplate fn_node_random_float_out[] = { - {SOCK_FLOAT, N_("Value")}, - {-1, ""}, +static void fn_node_random_float_declare(NodeDeclarationBuilder &b) +{ + b.add_input<decl::Float>("Min").min(-10000.0f).max(10000.0f); + b.add_input<decl::Float>("Max").default_value(1.0f).min(-10000.0f).max(10000.0f); + b.add_input<decl::Int>("Seed").min(-10000).max(10000); + b.add_output<decl::Float>("Value"); }; +} // namespace blender::nodes + class RandomFloatFunction : public blender::fn::MultiFunction { public: RandomFloatFunction() @@ -79,7 +79,7 @@ void register_node_type_fn_random_float() static bNodeType ntype; fn_node_type_base(&ntype, FN_NODE_RANDOM_FLOAT, "Random Float", 0, 0); - node_type_socket_templates(&ntype, fn_node_random_float_in, fn_node_random_float_out); + ntype.declare = blender::nodes::fn_node_random_float_declare; ntype.build_multi_function = fn_node_random_float_build_multi_function; nodeRegisterType(&ntype); } diff --git a/source/blender/python/gpu/gpu_py_shader.c b/source/blender/python/gpu/gpu_py_shader.c index d2167f2f102..95e505b1343 100644 --- a/source/blender/python/gpu/gpu_py_shader.c +++ b/source/blender/python/gpu/gpu_py_shader.c @@ -76,21 +76,6 @@ static const struct PyC_StringEnumItems pygpu_shader_config_items[] = { {0, NULL}, }; -static const struct PyC_FlagSet pygpu_texture_samplerstate_items[] = { - {GPU_SAMPLER_DEFAULT, "DEFAULT"}, - {GPU_SAMPLER_FILTER, "FILTER"}, - {GPU_SAMPLER_MIPMAP, "MIPMAP"}, - {GPU_SAMPLER_REPEAT_S, "REPEAT_S"}, - {GPU_SAMPLER_REPEAT_T, "REPEAT_T"}, - {GPU_SAMPLER_REPEAT_R, "REPEAT_R"}, - {GPU_SAMPLER_CLAMP_BORDER, "CLAMP_BORDER"}, - {GPU_SAMPLER_COMPARE, "COMPARE"}, - {GPU_SAMPLER_ANISO, "ANISO"}, - {GPU_SAMPLER_ICON, "ICON"}, - {GPU_SAMPLER_REPEAT, "REPEAT"}, - {0, NULL}, -}; - static int pygpu_shader_uniform_location_get(GPUShader *shader, const char *name, const char *error_prefix) @@ -507,53 +492,25 @@ static PyObject *pygpu_shader_uniform_int(BPyGPUShader *self, PyObject *args) } PyDoc_STRVAR(pygpu_shader_uniform_sampler_doc, - ".. method:: uniform_sampler(name, texture, state={'DEFAULT'})\n" + ".. method:: uniform_sampler(name, texture)\n" "\n" - " Specify the texture and state for an uniform sampler in the current GPUShader.\n" + " Specify the value of a texture uniform variable for the current GPUShader.\n" "\n" " :param name: name of the uniform variable whose texture is to be specified.\n" " :type name: str\n" " :param texture: Texture to attach.\n" - " :type texture: :class:`gpu.types.GPUTexture`\n" - " :param state: set of values in:\n" - "\n" - " - ``DEFAULT``\n" - " - ``FILTER``\n" - " - ``MIPMAP``\n" - " - ``REPEAT_S``\n" - " - ``REPEAT_T``\n" - " - ``REPEAT_R``\n" - " - ``CLAMP_BORDER``\n" - " - ``COMPARE``\n" - " - ``ANISO``\n" - " - ``ICON``\n" - " - ``REPEAT``\n" - " :type state: set\n"); -static PyObject *pygpu_shader_uniform_sampler(BPyGPUShader *self, PyObject *args, PyObject *kwds) + " :type texture: :class:`gpu.types.GPUTexture`\n"); +static PyObject *pygpu_shader_uniform_sampler(BPyGPUShader *self, PyObject *args) { const char *name; BPyGPUTexture *py_texture; - PyObject *py_samplerstate = NULL; - - static const char *_keywords[] = {"name", "texture", "state", NULL}; - static _PyArg_Parser _parser = {"sO!|$O:uniform_sampler", _keywords, 0}; - if (!_PyArg_ParseTupleAndKeywordsFast( - args, kwds, &_parser, &name, &BPyGPUTexture_Type, &py_texture, &py_samplerstate)) { + if (!PyArg_ParseTuple( + args, "sO!:GPUShader.uniform_sampler", &name, &BPyGPUTexture_Type, &py_texture)) { return NULL; } - int sampler_state = GPU_SAMPLER_DEFAULT; - if (py_samplerstate) { - if (PyC_FlagSet_ToBitfield(pygpu_texture_samplerstate_items, - py_samplerstate, - &sampler_state, - "shader.uniform_sampler") == -1) { - return NULL; - } - } - int slot = GPU_shader_get_texture_binding(self->shader, name); - GPU_texture_bind_ex(py_texture->tex, (eGPUSamplerState)sampler_state, slot, false); + GPU_texture_bind(py_texture->tex, slot); GPU_shader_uniform_1i(self->shader, name, slot); Py_RETURN_NONE; @@ -665,7 +622,7 @@ static struct PyMethodDef pygpu_shader__tp_methods[] = { pygpu_shader_uniform_int_doc}, {"uniform_sampler", (PyCFunction)pygpu_shader_uniform_sampler, - METH_VARARGS | METH_KEYWORDS, + METH_VARARGS, pygpu_shader_uniform_sampler_doc}, {"uniform_block", (PyCFunction)pygpu_shader_uniform_block, diff --git a/source/blender/python/intern/bpy_rna.c b/source/blender/python/intern/bpy_rna.c index 9d0755a865d..35acb56e66a 100644 --- a/source/blender/python/intern/bpy_rna.c +++ b/source/blender/python/intern/bpy_rna.c @@ -3663,7 +3663,7 @@ static PyObject *pyrna_struct_path_resolve(BPy_StructRNA *self, PyObject *args) return NULL; } - if (RNA_path_resolve_full(&self->ptr, path, &r_ptr, &r_prop, &index)) { + if (RNA_path_resolve_full_maybe_null(&self->ptr, path, &r_ptr, &r_prop, &index)) { if (r_prop) { if (index != -1) { if (index >= RNA_property_array_length(&r_ptr, r_prop) || index < 0) { diff --git a/source/blender/python/mathutils/mathutils.c b/source/blender/python/mathutils/mathutils.c index be7dae6871b..0043fc36162 100644 --- a/source/blender/python/mathutils/mathutils.c +++ b/source/blender/python/mathutils/mathutils.c @@ -599,6 +599,15 @@ uchar Mathutils_RegisterCallback(Mathutils_Callback *cb) return i; } +int _BaseMathObject_CheckCallback(BaseMathObject *self) +{ + Mathutils_Callback *cb = mathutils_callbacks[self->cb_type]; + if (LIKELY(cb->check(self) != -1)) { + return 0; + } + return -1; +} + /* use macros to check for NULL */ int _BaseMathObject_ReadCallback(BaseMathObject *self) { @@ -687,6 +696,13 @@ PyObject *BaseMathObject_is_frozen_get(BaseMathObject *self, void *UNUSED(closur return PyBool_FromLong((self->flag & BASE_MATH_FLAG_IS_FROZEN) != 0); } +char BaseMathObject_is_valid_doc[] = + "True when the owner of this data is valid.\n\n:type: boolean"; +PyObject *BaseMathObject_is_valid_get(BaseMathObject *self, void *UNUSED(closure)) +{ + return PyBool_FromLong(BaseMath_CheckCallback(self) == 0); +} + char BaseMathObject_freeze_doc[] = ".. function:: freeze()\n" "\n" diff --git a/source/blender/python/mathutils/mathutils.h b/source/blender/python/mathutils/mathutils.h index 80be841785a..4aa26dcc5be 100644 --- a/source/blender/python/mathutils/mathutils.h +++ b/source/blender/python/mathutils/mathutils.h @@ -28,6 +28,7 @@ struct DynStr; extern char BaseMathObject_is_wrapped_doc[]; extern char BaseMathObject_is_frozen_doc[]; +extern char BaseMathObject_is_valid_doc[]; extern char BaseMathObject_owner_doc[]; #define BASE_MATH_NEW(struct_name, root_type, base_type) \ @@ -81,6 +82,7 @@ typedef struct { PyObject *BaseMathObject_owner_get(BaseMathObject *self, void *); PyObject *BaseMathObject_is_wrapped_get(BaseMathObject *self, void *); PyObject *BaseMathObject_is_frozen_get(BaseMathObject *self, void *); +PyObject *BaseMathObject_is_valid_get(BaseMathObject *self, void *); extern char BaseMathObject_freeze_doc[]; PyObject *BaseMathObject_freeze(BaseMathObject *self); @@ -117,6 +119,7 @@ struct Mathutils_Callback { unsigned char Mathutils_RegisterCallback(Mathutils_Callback *cb); +int _BaseMathObject_CheckCallback(BaseMathObject *self); int _BaseMathObject_ReadCallback(BaseMathObject *self); int _BaseMathObject_WriteCallback(BaseMathObject *self); int _BaseMathObject_ReadIndexCallback(BaseMathObject *self, int index); @@ -126,6 +129,8 @@ void _BaseMathObject_RaiseFrozenExc(const BaseMathObject *self); void _BaseMathObject_RaiseNotFrozenExc(const BaseMathObject *self); /* since this is called so often avoid where possible */ +#define BaseMath_CheckCallback(_self) \ + (((_self)->cb_user ? _BaseMathObject_CheckCallback((BaseMathObject *)_self) : 0)) #define BaseMath_ReadCallback(_self) \ (((_self)->cb_user ? _BaseMathObject_ReadCallback((BaseMathObject *)_self) : 0)) #define BaseMath_WriteCallback(_self) \ diff --git a/source/blender/python/mathutils/mathutils_Color.c b/source/blender/python/mathutils/mathutils_Color.c index 7546f2ef730..13d712bddb0 100644 --- a/source/blender/python/mathutils/mathutils_Color.c +++ b/source/blender/python/mathutils/mathutils_Color.c @@ -866,6 +866,11 @@ static PyGetSetDef Color_getseters[] = { (setter)NULL, BaseMathObject_is_frozen_doc, NULL}, + {"is_valid", + (getter)BaseMathObject_is_valid_get, + (setter)NULL, + BaseMathObject_is_valid_doc, + NULL}, {"owner", (getter)BaseMathObject_owner_get, (setter)NULL, BaseMathObject_owner_doc, NULL}, {NULL, NULL, NULL, NULL, NULL} /* Sentinel */ }; diff --git a/source/blender/python/mathutils/mathutils_Euler.c b/source/blender/python/mathutils/mathutils_Euler.c index 595d03b533b..1033d186fca 100644 --- a/source/blender/python/mathutils/mathutils_Euler.c +++ b/source/blender/python/mathutils/mathutils_Euler.c @@ -699,6 +699,11 @@ static PyGetSetDef Euler_getseters[] = { (setter)NULL, BaseMathObject_is_frozen_doc, NULL}, + {"is_valid", + (getter)BaseMathObject_is_valid_get, + (setter)NULL, + BaseMathObject_is_valid_doc, + NULL}, {"owner", (getter)BaseMathObject_owner_get, (setter)NULL, BaseMathObject_owner_doc, NULL}, {NULL, NULL, NULL, NULL, NULL} /* Sentinel */ }; diff --git a/source/blender/python/mathutils/mathutils_Matrix.c b/source/blender/python/mathutils/mathutils_Matrix.c index 36b8b0b6d35..ce04a143aae 100644 --- a/source/blender/python/mathutils/mathutils_Matrix.c +++ b/source/blender/python/mathutils/mathutils_Matrix.c @@ -3148,6 +3148,11 @@ static PyGetSetDef Matrix_getseters[] = { (setter)NULL, BaseMathObject_is_frozen_doc, NULL}, + {"is_valid", + (getter)BaseMathObject_is_valid_get, + (setter)NULL, + BaseMathObject_is_valid_doc, + NULL}, {"owner", (getter)BaseMathObject_owner_get, (setter)NULL, BaseMathObject_owner_doc, NULL}, {NULL, NULL, NULL, NULL, NULL} /* Sentinel */ }; diff --git a/source/blender/python/mathutils/mathutils_Quaternion.c b/source/blender/python/mathutils/mathutils_Quaternion.c index 77a30dcd447..525b2da7d06 100644 --- a/source/blender/python/mathutils/mathutils_Quaternion.c +++ b/source/blender/python/mathutils/mathutils_Quaternion.c @@ -1505,6 +1505,11 @@ static PyGetSetDef Quaternion_getseters[] = { (setter)NULL, BaseMathObject_is_frozen_doc, NULL}, + {"is_valid", + (getter)BaseMathObject_is_valid_get, + (setter)NULL, + BaseMathObject_is_valid_doc, + NULL}, {"owner", (getter)BaseMathObject_owner_get, (setter)NULL, BaseMathObject_owner_doc, NULL}, {NULL, NULL, NULL, NULL, NULL} /* Sentinel */ }; diff --git a/source/blender/python/mathutils/mathutils_Vector.c b/source/blender/python/mathutils/mathutils_Vector.c index efcaa9b6a51..23758c5603e 100644 --- a/source/blender/python/mathutils/mathutils_Vector.c +++ b/source/blender/python/mathutils/mathutils_Vector.c @@ -2551,6 +2551,11 @@ static PyGetSetDef Vector_getseters[] = { (setter)NULL, BaseMathObject_is_frozen_doc, NULL}, + {"is_valid", + (getter)BaseMathObject_is_valid_get, + (setter)NULL, + BaseMathObject_is_valid_doc, + NULL}, {"owner", (getter)BaseMathObject_owner_get, (setter)NULL, BaseMathObject_owner_doc, NULL}, /* Auto-generated swizzle attributes, see Python script above. */ |