diff --git a/release/datafiles/userdef/userdef_default.c b/release/datafiles/userdef/userdef_default.c index d75a0974f74..cbcd99d4b3f 100644 --- a/release/datafiles/userdef/userdef_default.c +++ b/release/datafiles/userdef/userdef_default.c @@ -101,7 +101,11 @@ const UserDef U_default = { .gp_euclideandist = 2, .gp_eraser = 25, .gp_settings = 0, +#ifdef __APPLE__ + .gpu_backend = GPU_BACKEND_METAL, +#else .gpu_backend = GPU_BACKEND_OPENGL, +#endif /** Initialized by: #BKE_studiolight_default. */ .light_param = {{0}}, diff --git a/release/scripts/startup/bl_ui/properties_constraint.py b/release/scripts/startup/bl_ui/properties_constraint.py index 38e5f5719d4..0fa340c8d15 100644 --- a/release/scripts/startup/bl_ui/properties_constraint.py +++ b/release/scripts/startup/bl_ui/properties_constraint.py @@ -397,7 +397,7 @@ class ConstraintButtonsPanel: sub.prop(con, "invert_z", text="Z", toggle=True) row.label(icon='BLANK1') - layout.prop(con, "mix_mode", text="Mix") + layout.prop(con, "mix_mode", text="Mix", text_ctxt=i18n_contexts.constraint) self.space_template(layout, con) @@ -488,7 +488,7 @@ class ConstraintButtonsPanel: self.target_template(layout, con) layout.prop(con, "remove_target_shear") - layout.prop(con, "mix_mode", text="Mix") + layout.prop(con, "mix_mode", text="Mix", text_ctxt=i18n_contexts.constraint) self.space_template(layout, con) @@ -513,7 +513,7 @@ class ConstraintButtonsPanel: subsub.prop(con, "eval_time", text="") row.prop_decorator(con, "eval_time") - layout.prop(con, "mix_mode", text="Mix") + layout.prop(con, "mix_mode", text="Mix", text_ctxt=i18n_contexts.constraint) self.draw_influence(layout, con) @@ -1024,7 +1024,7 @@ class ConstraintButtonsSubPanel: col.prop(con, "to_min_z" + ext, text="Min") col.prop(con, "to_max_z" + ext, text="Max") - layout.prop(con, "mix_mode" + ext, text="Mix") + layout.prop(con, "mix_mode" + ext, text="Mix", text_ctxt=i18n_contexts.constraint) def draw_armature_bones(self, context): layout = self.layout diff --git a/source/blender/blenkernel/intern/boids.c b/source/blender/blenkernel/intern/boids.c index 63e393aa4f0..6a4e4ae8a9a 100644 --- a/source/blender/blenkernel/intern/boids.c +++ b/source/blender/blenkernel/intern/boids.c @@ -25,6 +25,8 @@ #include "BKE_particle.h" #include "BLI_kdopbvh.h" +#include "BLT_translation.h" + #include "BKE_modifier.h" #include "RNA_enum_types.h" @@ -1607,7 +1609,7 @@ BoidRule *boid_new_rule(int type) rule->type = type; rule->flag |= BOIDRULE_IN_AIR | BOIDRULE_ON_LAND; - BLI_strncpy(rule->name, rna_enum_boidrule_type_items[type - 1].name, sizeof(rule->name)); + BLI_strncpy(rule->name, DATA_(rna_enum_boidrule_type_items[type - 1].name), sizeof(rule->name)); return rule; } diff --git a/source/blender/blenkernel/intern/gpencil_geom.cc b/source/blender/blenkernel/intern/gpencil_geom.cc index 8115920f938..662a33b44be 100644 --- a/source/blender/blenkernel/intern/gpencil_geom.cc +++ b/source/blender/blenkernel/intern/gpencil_geom.cc @@ -190,6 +190,9 @@ static int stroke_march_next_point(const bGPDstroke *gps, float *pressure, float *strength, float *vert_color, + float *uv_fac, + float *uv_fill, + float *uv_rot, float *ratio_result, int *index_from, int *index_to) @@ -271,6 +274,10 @@ static int stroke_march_next_point(const bGPDstroke *gps, gps->points[next_point_index].pressure, gps->points[*index_from].pressure, vratio); *strength = interpf( gps->points[next_point_index].strength, gps->points[*index_from].strength, vratio); + *uv_fac = interpf(gps->points[next_point_index].uv_fac, gps->points[*index_from].uv_fac, vratio); + *uv_rot = interpf(gps->points[next_point_index].uv_rot, gps->points[*index_from].uv_rot, vratio); + interp_v2_v2v2( + uv_fill, gps->points[*index_from].uv_fill, gps->points[next_point_index].uv_fill, vratio); interp_v4_v4v4(vert_color, gps->points[*index_from].vert_color, gps->points[next_point_index].vert_color, @@ -474,6 +481,7 @@ bool BKE_gpencil_stroke_sample(bGPdata *gpd, int next_point_index = 1; int i = 0; float pressure, strength, ratio_result; + float uv_fac, uv_rot, uv_fill[2]; float vert_color[4]; int index_from, index_to; float last_coord[3]; @@ -504,6 +512,9 @@ bool BKE_gpencil_stroke_sample(bGPdata *gpd, &pressure, &strength, vert_color, + &uv_fac, + uv_fill, + &uv_rot, &ratio_result, &index_from, &index_to)) > -1) { @@ -514,6 +525,10 @@ bool BKE_gpencil_stroke_sample(bGPdata *gpd, copy_v3_v3(&pt2->x, last_coord); new_pt[i].pressure = pressure; new_pt[i].strength = strength; + new_pt[i].uv_fac = uv_fac; + new_pt[i].uv_rot = uv_rot; + copy_v2_v2(new_pt[i].uv_fill, uv_fill); + memcpy(new_pt[i].vert_color, vert_color, sizeof(float[4])); if (select) { new_pt[i].flag |= GP_SPOINT_SELECT; diff --git a/source/blender/blenkernel/intern/node_tree_field_inferencing.cc b/source/blender/blenkernel/intern/node_tree_field_inferencing.cc index abe5f736eba..067745e0ad6 100644 --- a/source/blender/blenkernel/intern/node_tree_field_inferencing.cc +++ b/source/blender/blenkernel/intern/node_tree_field_inferencing.cc @@ -508,6 +508,7 @@ static void prepare_inferencing_interfaces( bool update_field_inferencing(const bNodeTree &tree) { + BLI_assert(tree.type == NTREE_GEOMETRY); tree.ensure_topology_cache(); const Span nodes = tree.all_nodes(); diff --git a/source/blender/blenloader/intern/versioning_userdef.c b/source/blender/blenloader/intern/versioning_userdef.c index 3c4b1a04d63..4b2acfa7205 100644 --- a/source/blender/blenloader/intern/versioning_userdef.c +++ b/source/blender/blenloader/intern/versioning_userdef.c @@ -770,7 +770,11 @@ void blo_do_versions_userdef(UserDef *userdef) /* Set GPU backend to OpenGL. */ if (!USER_VERSION_ATLEAST(305, 5)) { +#ifdef __APPLE__ + userdef->gpu_backend = GPU_BACKEND_METAL; +#else userdef->gpu_backend = GPU_BACKEND_OPENGL; +#endif } if (!USER_VERSION_ATLEAST(305, 10)) { diff --git a/source/blender/blentranslation/BLT_translation.h b/source/blender/blentranslation/BLT_translation.h index b85169fb03c..f788da8d429 100644 --- a/source/blender/blentranslation/BLT_translation.h +++ b/source/blender/blentranslation/BLT_translation.h @@ -126,6 +126,10 @@ const char *BLT_translate_do_new_dataname(const char *msgctxt, const char *msgid #define BLT_I18NCONTEXT_EDITOR_VIEW3D "View3D" #define BLT_I18NCONTEXT_EDITOR_FILEBROWSER "File browser" + /* Generic contexts. */ +#define BLT_I18NCONTEXT_VIRTUAL_REALITY "Virtual reality" +#define BLT_I18NCONTEXT_CONSTRAINT "Constraint" + /* Helper for bpy.app.i18n object... */ typedef struct { const char *c_id; @@ -190,6 +194,8 @@ typedef struct { BLT_I18NCONTEXTS_ITEM(BLT_I18NCONTEXT_ID_WINDOWMANAGER, "id_windowmanager"), \ BLT_I18NCONTEXTS_ITEM(BLT_I18NCONTEXT_EDITOR_VIEW3D, "editor_view3d"), \ BLT_I18NCONTEXTS_ITEM(BLT_I18NCONTEXT_EDITOR_FILEBROWSER, "editor_filebrowser"), \ + BLT_I18NCONTEXTS_ITEM(BLT_I18NCONTEXT_VIRTUAL_REALITY, "virtual_reality"), \ + BLT_I18NCONTEXTS_ITEM(BLT_I18NCONTEXT_CONSTRAINT, "constraint"), \ { \ NULL, NULL, NULL \ } \ diff --git a/source/blender/draw/engines/eevee_next/eevee_shadow.hh b/source/blender/draw/engines/eevee_next/eevee_shadow.hh index 5106bac7b18..01501ad4627 100644 --- a/source/blender/draw/engines/eevee_next/eevee_shadow.hh +++ b/source/blender/draw/engines/eevee_next/eevee_shadow.hh @@ -338,16 +338,12 @@ class ShadowPunctual : public NonCopyable, NonMovable { float size_x_, size_y_; /** Shape type. */ eLightType light_type_; - /** Random position on the light. In world space. */ - float3 random_offset_; /** Light position. */ float3 position_; /** Near and far clip distances. */ float far_, near_; /** Number of tile-maps needed to cover the light angular extents. */ int tilemaps_needed_; - /** Visibility cone angle from the light source. */ - int cone_aperture_; public: ShadowPunctual(ShadowModule &module) : shadows_(module){}; diff --git a/source/blender/editors/curves/intern/curves_selection.cc b/source/blender/editors/curves/intern/curves_selection.cc index 585498dd0fa..7855d311161 100644 --- a/source/blender/editors/curves/intern/curves_selection.cc +++ b/source/blender/editors/curves/intern/curves_selection.cc @@ -123,7 +123,7 @@ void fill_selection_true(GMutableSpan selection) } } -static bool contains(const VArray &varray, const bool value) +static bool contains(const VArray &varray, const IndexRange range_to_check, const bool value) { const CommonVArrayInfo info = varray.common_info(); if (info.type == CommonVArrayInfo::Type::Single) { @@ -132,7 +132,7 @@ static bool contains(const VArray &varray, const bool value) if (info.type == CommonVArrayInfo::Type::Span) { const Span span(static_cast(info.data), varray.size()); return threading::parallel_reduce( - span.index_range(), + range_to_check, 4096, false, [&](const IndexRange range, const bool init) { @@ -141,7 +141,7 @@ static bool contains(const VArray &varray, const bool value) [&](const bool a, const bool b) { return a || b; }); } return threading::parallel_reduce( - varray.index_range(), + range_to_check, 2048, false, [&](const IndexRange range, const bool init) { @@ -159,10 +159,15 @@ static bool contains(const VArray &varray, const bool value) [&](const bool a, const bool b) { return a || b; }); } +bool has_anything_selected(const VArray &varray, const IndexRange range_to_check) +{ + return contains(varray, range_to_check, true); +} + bool has_anything_selected(const bke::CurvesGeometry &curves) { const VArray selection = curves.attributes().lookup(".selection"); - return !selection || contains(selection, true); + return !selection || contains(selection, curves.curves_range(), true); } bool has_anything_selected(const GSpan selection) diff --git a/source/blender/editors/include/ED_curves.h b/source/blender/editors/include/ED_curves.h index d9d6c0c2863..a8019646b8b 100644 --- a/source/blender/editors/include/ED_curves.h +++ b/source/blender/editors/include/ED_curves.h @@ -93,6 +93,7 @@ bool has_anything_selected(const bke::CurvesGeometry &curves); * Return true if any element in the span is selected, on either domain with either type. */ bool has_anything_selected(GSpan selection); +bool has_anything_selected(const VArray &varray, IndexRange range_to_check); /** * Find curves that have any point selected (a selection factor greater than zero), diff --git a/source/blender/editors/include/UI_icons.h b/source/blender/editors/include/UI_icons.h index 31c766e95f2..6e0edeace6a 100644 --- a/source/blender/editors/include/UI_icons.h +++ b/source/blender/editors/include/UI_icons.h @@ -164,7 +164,7 @@ DEF_ICON(NLA) DEF_ICON(PREFERENCES) DEF_ICON(TIME) DEF_ICON(NODETREE) -DEF_ICON(GEOMETRY_NODES) +DEF_ICON_MODIFIER(GEOMETRY_NODES) DEF_ICON(CONSOLE) DEF_ICON_BLANK(183) DEF_ICON(TRACKER) diff --git a/source/blender/editors/object/object_vgroup.cc b/source/blender/editors/object/object_vgroup.cc index 987fb545264..23140afc701 100644 --- a/source/blender/editors/object/object_vgroup.cc +++ b/source/blender/editors/object/object_vgroup.cc @@ -3446,55 +3446,63 @@ static char *vertex_group_lock_description(bContext * /*C*/, int action = RNA_enum_get(params, "action"); int mask = RNA_enum_get(params, "mask"); - const char *action_str, *target_str; - + /* NOTE: constructing the following string literals can be done in a less verbose way, + * however the resulting strings can't be usefully translated, (via `TIP_`). */ switch (action) { case VGROUP_LOCK: - action_str = TIP_("Lock"); + switch (mask) { + case VGROUP_MASK_ALL: + return BLI_strdup(TIP_("Lock all vertex groups of the active object")); + case VGROUP_MASK_SELECTED: + return BLI_strdup(TIP_("Lock selected vertex groups of the active object")); + case VGROUP_MASK_UNSELECTED: + return BLI_strdup(TIP_("Lock unselected vertex groups of the active object")); + case VGROUP_MASK_INVERT_UNSELECTED: + return BLI_strdup( + TIP_("Lock selected and unlock unselected vertex groups of the active object")); + } break; case VGROUP_UNLOCK: - action_str = TIP_("Unlock"); + switch (mask) { + case VGROUP_MASK_ALL: + return BLI_strdup(TIP_("Unlock all vertex groups of the active object")); + case VGROUP_MASK_SELECTED: + return BLI_strdup(TIP_("Unlock selected vertex groups of the active object")); + case VGROUP_MASK_UNSELECTED: + return BLI_strdup(TIP_("Unlock unselected vertex groups of the active object")); + case VGROUP_MASK_INVERT_UNSELECTED: + return BLI_strdup( + TIP_("Unlock selected and lock unselected vertex groups of the active object")); + } break; case VGROUP_TOGGLE: - action_str = TIP_("Toggle locks of"); + switch (mask) { + case VGROUP_MASK_ALL: + return BLI_strdup(TIP_("Toggle locks of all vertex groups of the active object")); + case VGROUP_MASK_SELECTED: + return BLI_strdup(TIP_("Toggle locks of selected vertex groups of the active object")); + case VGROUP_MASK_UNSELECTED: + return BLI_strdup(TIP_("Toggle locks of unselected vertex groups of the active object")); + case VGROUP_MASK_INVERT_UNSELECTED: + return BLI_strdup(TIP_( + "Toggle locks of all and invert unselected vertex groups of the active object")); + } break; case VGROUP_INVERT: - action_str = TIP_("Invert locks of"); - break; - default: - return nullptr; - } - - switch (mask) { - case VGROUP_MASK_ALL: - target_str = TIP_("all"); - break; - case VGROUP_MASK_SELECTED: - target_str = TIP_("selected"); - break; - case VGROUP_MASK_UNSELECTED: - target_str = TIP_("unselected"); - break; - case VGROUP_MASK_INVERT_UNSELECTED: - switch (action) { - case VGROUP_INVERT: - target_str = TIP_("selected"); - break; - case VGROUP_LOCK: - target_str = TIP_("selected and unlock unselected"); - break; - case VGROUP_UNLOCK: - target_str = TIP_("selected and lock unselected"); - break; - default: - target_str = TIP_("all and invert unselected"); + switch (mask) { + case VGROUP_MASK_ALL: + return BLI_strdup(TIP_("Invert locks of all vertex groups of the active object")); + case VGROUP_MASK_SELECTED: + case VGROUP_MASK_INVERT_UNSELECTED: + return BLI_strdup(TIP_("Invert locks of selected vertex groups of the active object")); + case VGROUP_MASK_UNSELECTED: + return BLI_strdup(TIP_("Invert locks of unselected vertex groups of the active object")); } break; default: return nullptr; } - - return BLI_sprintfN(TIP_("%s %s vertex groups of the active object"), action_str, target_str); + return nullptr; } void OBJECT_OT_vertex_group_lock(wmOperatorType *ot) diff --git a/source/blender/editors/space_file/file_draw.c b/source/blender/editors/space_file/file_draw.c index 97e6531eadd..5bae8238bca 100644 --- a/source/blender/editors/space_file/file_draw.c +++ b/source/blender/editors/space_file/file_draw.c @@ -167,9 +167,6 @@ static void file_draw_icon(const SpaceFile *sfile, ImBuf *preview_image = filelist_file_getimage(file); char blend_path[FILE_MAX_LIBEXTRA]; if (BLO_library_path_explode(path, blend_path, NULL, NULL)) { - const FileAssetSelectParams *asset_params = ED_fileselect_get_asset_params(sfile); - BLI_assert(asset_params != NULL); - const int import_method = ED_fileselect_asset_import_method_get(sfile, file); BLI_assert(import_method > -1); @@ -563,9 +560,6 @@ static void file_draw_preview(const SpaceFile *sfile, char blend_path[FILE_MAX_LIBEXTRA]; if (BLO_library_path_explode(path, blend_path, NULL, NULL)) { - const FileAssetSelectParams *asset_params = ED_fileselect_get_asset_params(sfile); - BLI_assert(asset_params != NULL); - const int import_method = ED_fileselect_asset_import_method_get(sfile, file); BLI_assert(import_method > -1); diff --git a/source/blender/editors/space_node/node_group.cc b/source/blender/editors/space_node/node_group.cc index 6f5225c0491..4e45e3073e1 100644 --- a/source/blender/editors/space_node/node_group.cc +++ b/source/blender/editors/space_node/node_group.cc @@ -993,7 +993,9 @@ static void node_group_make_insert_selected(const bContext &C, } } - bke::node_field_inferencing::update_field_inferencing(group); + if (group.type == NTREE_GEOMETRY) { + bke::node_field_inferencing::update_field_inferencing(group); + } nodes::update_node_declaration_and_sockets(ntree, *gnode); /* Add new links to inputs outside of the group. */ diff --git a/source/blender/editors/transform/transform_convert.c b/source/blender/editors/transform/transform_convert.c index 211b72c0e77..966c067eb00 100644 --- a/source/blender/editors/transform/transform_convert.c +++ b/source/blender/editors/transform/transform_convert.c @@ -758,8 +758,8 @@ static void init_proportional_edit(TransInfo *t) else if (t->data_type == &TransConvertType_MeshUV && t->flag & T_PROP_CONNECTED) { /* Already calculated by uv_set_connectivity_distance. */ } - else if (t->data_type == &TransConvertType_Curve) { - BLI_assert(t->obedit_type == OB_CURVES_LEGACY); + else if (ELEM(t->data_type, &TransConvertType_Curve, &TransConvertType_Curves)) { + BLI_assert(t->obedit_type == OB_CURVES_LEGACY || t->obedit_type == OB_CURVES); set_prop_dist(t, false); } else { diff --git a/source/blender/editors/transform/transform_convert_curves.cc b/source/blender/editors/transform/transform_convert_curves.cc index a1c489f3d87..6dd2968ec6f 100644 --- a/source/blender/editors/transform/transform_convert_curves.cc +++ b/source/blender/editors/transform/transform_convert_curves.cc @@ -6,6 +6,7 @@ #include "BLI_array.hh" #include "BLI_index_mask_ops.hh" +#include "BLI_inplace_priority_queue.hh" #include "BLI_span.hh" #include "BKE_curves.hh" @@ -23,11 +24,46 @@ namespace blender::ed::transform::curves { +static void calculate_curve_point_distances_for_proportional_editing( + const Span positions, MutableSpan r_distances) +{ + Array visited(positions.size(), false); + + InplacePriorityQueue> queue(r_distances); + while (!queue.is_empty()) { + int64_t index = queue.pop_index(); + if (visited[index]) { + continue; + } + visited[index] = true; + + /* TODO(Falk): Handle cyclic curves here. */ + if (index > 0 && !visited[index - 1]) { + int adjacent = index - 1; + float dist = r_distances[index] + math::distance(positions[index], positions[adjacent]); + if (dist < r_distances[adjacent]) { + r_distances[adjacent] = dist; + queue.priority_changed(adjacent); + } + } + if (index < positions.size() - 1 && !visited[index + 1]) { + int adjacent = index + 1; + float dist = r_distances[index] + math::distance(positions[index], positions[adjacent]); + if (dist < r_distances[adjacent]) { + r_distances[adjacent] = dist; + queue.priority_changed(adjacent); + } + } + } +} + static void createTransCurvesVerts(bContext * /*C*/, TransInfo *t) { MutableSpan trans_data_contrainers(t->data_container, t->data_container_len); Array> selected_indices_per_object(t->data_container_len); Array selection_per_object(t->data_container_len); + const bool use_proportional_edit = (t->flag & T_PROP_EDIT_ALL) != 0; + const bool use_connected_only = (t->flag & T_PROP_CONNECTED) != 0; /* Count selected elements per object and create TransData structs. */ for (const int i : trans_data_contrainers.index_range()) { @@ -35,10 +71,15 @@ static void createTransCurvesVerts(bContext * /*C*/, TransInfo *t) Curves *curves_id = static_cast(tc.obedit->data); bke::CurvesGeometry &curves = curves_id->geometry.wrap(); - selection_per_object[i] = ed::curves::retrieve_selected_points(curves, - selected_indices_per_object[i]); + if (use_proportional_edit) { + tc.data_len = curves.point_num; + } + else { + selection_per_object[i] = ed::curves::retrieve_selected_points( + curves, selected_indices_per_object[i]); + tc.data_len = selection_per_object[i].size(); + } - tc.data_len = selection_per_object[i].size(); if (tc.data_len > 0) { tc.data = MEM_cnew_array(tc.data_len, __func__); } @@ -52,34 +93,92 @@ static void createTransCurvesVerts(bContext * /*C*/, TransInfo *t) } Curves *curves_id = static_cast(tc.obedit->data); bke::CurvesGeometry &curves = curves_id->geometry.wrap(); - IndexMask selected_indices = selection_per_object[i]; float mtx[3][3], smtx[3][3]; copy_m3_m4(mtx, tc.obedit->object_to_world); pseudoinverse_m3_m3(smtx, mtx, PSEUDOINVERSE_EPSILON); MutableSpan positions = curves.positions_for_write(); - threading::parallel_for(selected_indices.index_range(), 1024, [&](const IndexRange range) { - for (const int selection_i : range) { - TransData *td = &tc.data[selection_i]; - float *elem = reinterpret_cast(&positions[selected_indices[selection_i]]); - copy_v3_v3(td->iloc, elem); - copy_v3_v3(td->center, td->iloc); - td->loc = elem; + if (use_proportional_edit) { + const OffsetIndices points_by_curve = curves.points_by_curve(); + const VArray selection = curves.attributes().lookup_or_default( + ".selection", ATTR_DOMAIN_POINT, true); + threading::parallel_for(curves.curves_range(), 512, [&](const IndexRange range) { + Vector closest_distances; + for (const int curve_i : range) { + const IndexRange points = points_by_curve[curve_i]; + const bool has_any_selected = ed::curves::has_anything_selected(selection, points); + if (!has_any_selected) { + for (const int point_i : points) { + TransData &td = tc.data[point_i]; + td.flag |= TD_NOTCONNECTED; + td.dist = FLT_MAX; + } + if (use_connected_only) { + continue; + } + } - td->flag = TD_SELECTED; - td->ext = nullptr; + closest_distances.reinitialize(points.size()); + closest_distances.fill(std::numeric_limits::max()); - copy_m3_m3(td->smtx, smtx); - copy_m3_m3(td->mtx, mtx); - } - }); + for (const int i : IndexRange(points.size())) { + const int point_i = points[i]; + TransData &td = tc.data[point_i]; + float3 *elem = &positions[point_i]; + + copy_v3_v3(td.iloc, *elem); + copy_v3_v3(td.center, td.iloc); + td.loc = *elem; + + td.flag = 0; + if (selection[point_i]) { + closest_distances[i] = 0.0f; + td.flag = TD_SELECTED; + } + + td.ext = nullptr; + + copy_m3_m3(td.smtx, smtx); + copy_m3_m3(td.mtx, mtx); + } + + if (use_connected_only) { + calculate_curve_point_distances_for_proportional_editing( + positions.slice(points), closest_distances.as_mutable_span()); + for (const int i : IndexRange(points.size())) { + TransData &td = tc.data[points[i]]; + td.dist = closest_distances[i]; + } + } + } + }); + } + else { + const IndexMask selected_indices = selection_per_object[i]; + threading::parallel_for(selected_indices.index_range(), 1024, [&](const IndexRange range) { + for (const int selection_i : range) { + TransData *td = &tc.data[selection_i]; + float3 *elem = &positions[selected_indices[selection_i]]; + + copy_v3_v3(td->iloc, *elem); + copy_v3_v3(td->center, td->iloc); + td->loc = *elem; + + td->flag = TD_SELECTED; + td->ext = nullptr; + + copy_m3_m3(td->smtx, smtx); + copy_m3_m3(td->mtx, mtx); + } + }); + } } } static void recalcData_curves(TransInfo *t) { - Span trans_data_contrainers(t->data_container, t->data_container_len); + const Span trans_data_contrainers(t->data_container, t->data_container_len); for (const TransDataContainer &tc : trans_data_contrainers) { Curves *curves_id = static_cast(tc.obedit->data); bke::CurvesGeometry &curves = curves_id->geometry.wrap(); diff --git a/source/blender/gpencil_modifiers/intern/MOD_gpencildash.c b/source/blender/gpencil_modifiers/intern/MOD_gpencildash.c index 2ff2a0eb1fa..dfb859542f5 100644 --- a/source/blender/gpencil_modifiers/intern/MOD_gpencildash.c +++ b/source/blender/gpencil_modifiers/intern/MOD_gpencildash.c @@ -17,6 +17,7 @@ #include "DNA_gpencil_types.h" #include "DNA_meshdata_types.h" #include "DNA_object_types.h" +#include "DNA_scene_types.h" #include "DNA_screen_types.h" #include "BKE_gpencil.h" @@ -42,6 +43,7 @@ #include "MOD_gpencil_util.h" #include "DEG_depsgraph.h" +#include "DEG_depsgraph_query.h" #include "WM_api.h" @@ -254,11 +256,11 @@ static bool isDisabled(GpencilModifierData *md, int UNUSED(userRenderParams)) /* Generic "generateStrokes" callback */ static void generateStrokes(GpencilModifierData *md, Depsgraph *depsgraph, Object *ob) { + Scene *scene = DEG_get_evaluated_scene(depsgraph); bGPdata *gpd = ob->data; LISTBASE_FOREACH (bGPDlayer *, gpl, &gpd->layers) { - BKE_gpencil_frame_active_set(depsgraph, gpd); - bGPDframe *gpf = gpl->actframe; + bGPDframe *gpf = BKE_gpencil_frame_retime_get(depsgraph, scene, ob, gpl); if (gpf == NULL) { continue; } diff --git a/source/blender/gpu/metal/mtl_framebuffer.mm b/source/blender/gpu/metal/mtl_framebuffer.mm index 9b334dd7166..5e3a4136d88 100644 --- a/source/blender/gpu/metal/mtl_framebuffer.mm +++ b/source/blender/gpu/metal/mtl_framebuffer.mm @@ -1754,9 +1754,8 @@ void MTLFrameBuffer::blit(uint read_slot, uint height, eGPUFrameBufferBits blit_buffers) { - BLI_assert(this); BLI_assert(metal_fb_write); - if (!(this && metal_fb_write)) { + if (!metal_fb_write) { return; } MTLContext *mtl_context = reinterpret_cast(GPU_context_active_get()); @@ -1899,4 +1898,4 @@ int MTLFrameBuffer::get_height() return height_; } -} // blender::gpu +} // namespace blender::gpu diff --git a/source/blender/io/usd/intern/usd_reader_shape.h b/source/blender/io/usd/intern/usd_reader_shape.h index b6135f31b2f..0af79a22d93 100644 --- a/source/blender/io/usd/intern/usd_reader_shape.h +++ b/source/blender/io/usd/intern/usd_reader_shape.h @@ -53,7 +53,8 @@ class USDShapeReader : public USDGeomReader { const char ** /*err_str*/) override; bool is_time_varying(); - virtual bool topology_changed(const Mesh * /*existing_mesh*/, double /*motionSampleTime*/) + virtual bool topology_changed(const Mesh * /*existing_mesh*/, + double /*motionSampleTime*/) override { return false; }; diff --git a/source/blender/makesdna/DNA_texture_defaults.h b/source/blender/makesdna/DNA_texture_defaults.h index 70de8756215..564d722ea73 100644 --- a/source/blender/makesdna/DNA_texture_defaults.h +++ b/source/blender/makesdna/DNA_texture_defaults.h @@ -85,7 +85,7 @@ .type = TEX_IMAGE, \ .ima = NULL, \ .stype = 0, \ - .flag = TEX_CHECKER_ODD, \ + .flag = TEX_CHECKER_ODD | TEX_NO_CLAMP, \ .imaflag = TEX_INTERPOL | TEX_MIPMAP | TEX_USEALPHA, \ .extend = TEX_REPEAT, \ .cropxmin = 0.0, \ diff --git a/source/blender/makesrna/intern/rna_particle.c b/source/blender/makesrna/intern/rna_particle.c index 2064d5af82d..d94cad3893f 100644 --- a/source/blender/makesrna/intern/rna_particle.c +++ b/source/blender/makesrna/intern/rna_particle.c @@ -1190,11 +1190,11 @@ static void rna_ParticleTarget_name_get(PointerRNA *ptr, char *str) } } else { - strcpy(str, "Invalid target!"); + strcpy(str, TIP_("Invalid target!")); } } else { - strcpy(str, "Invalid target!"); + strcpy(str, TIP_("Invalid target!")); } } diff --git a/source/blender/python/gpu/gpu_py_state.c b/source/blender/python/gpu/gpu_py_state.c index 0543825d8a0..870a83eb9a8 100644 --- a/source/blender/python/gpu/gpu_py_state.c +++ b/source/blender/python/gpu/gpu_py_state.c @@ -227,6 +227,72 @@ static PyObject *pygpu_state_viewport_get(PyObject *UNUSED(self), PyObject *UNUS return ret; } +PyDoc_STRVAR(pygpu_state_scissor_set_doc, + ".. function:: scissor_set(x, y, xsize, ysize)\n" + "\n" + " Specifies the scissor area of the active framebuffer.\n" + " Note: The scissor state is not saved upon framebuffer rebind.\n" + "\n" + " :arg x, y: lower left corner of the scissor rectangle, in pixels.\n" + " :type x, y: int\n" + " :arg xsize, ysize: width and height of the scissor rectangle.\n" + " :type xsize, ysize: int\n"); +static PyObject *pygpu_state_scissor_set(PyObject *UNUSED(self), PyObject *args) +{ + int x, y, xsize, ysize; + if (!PyArg_ParseTuple(args, "iiii:scissor_set", &x, &y, &xsize, &ysize)) { + return NULL; + } + + GPU_scissor(x, y, xsize, ysize); + Py_RETURN_NONE; +} + +PyDoc_STRVAR(pygpu_state_scissor_get_doc, + ".. function:: scissor_get()\n" + "\n" + " Retrieve the scissors of the active framebuffer.\n" + " Note: Only valid between 'scissor_set' and a framebuffer rebind.\n" + "\n" + " :return: The scissor of the active framebuffer as a tuple\n" + " (x, y, xsize, ysize).\n" + " x, y: lower left corner of the scissor rectangle, in pixels.\n" + " xsize, ysize: width and height of the scissor rectangle.\n" + " :rtype: tuple(int, int, int, int)\n"); +static PyObject *pygpu_state_scissor_get(PyObject *UNUSED(self), PyObject *UNUSED(args)) +{ + int scissor[4]; + GPU_scissor_get(scissor); + + PyObject *ret = PyTuple_New(4); + PyTuple_SET_ITEMS(ret, + PyLong_FromLong(scissor[0]), + PyLong_FromLong(scissor[1]), + PyLong_FromLong(scissor[2]), + PyLong_FromLong(scissor[3])); + return ret; +} + +PyDoc_STRVAR(pygpu_state_scissor_test_set_doc, + ".. function:: scissor_test_set(enable)\n" + "\n" + " Enable/disable scissor testing on the active framebuffer.\n" + "\n" + " :arg enable:\n" + " True - enable scissor testing.\n" + " False - disable scissor testing.\n" + " :type enable: bool\n"); +static PyObject *pygpu_state_scissor_test_set(PyObject *UNUSED(self), PyObject *value) +{ + bool enabled; + if (!PyC_ParseBool(value, &enabled)) { + return NULL; + } + + GPU_scissor_test(enabled); + Py_RETURN_NONE; +} + PyDoc_STRVAR(pygpu_state_line_width_set_doc, ".. function:: line_width_set(width)\n" "\n" @@ -394,6 +460,18 @@ static struct PyMethodDef pygpu_state__tp_methods[] = { (PyCFunction)pygpu_state_viewport_get, METH_NOARGS, pygpu_state_viewport_get_doc}, + {"scissor_set", + (PyCFunction)pygpu_state_scissor_set, + METH_VARARGS, + pygpu_state_scissor_set_doc}, + {"scissor_get", + (PyCFunction)pygpu_state_scissor_get, + METH_NOARGS, + pygpu_state_scissor_get_doc}, + {"scissor_test_set", + (PyCFunction)pygpu_state_scissor_test_set, + METH_VARARGS, + pygpu_state_scissor_test_set_doc}, {"line_width_set", (PyCFunction)pygpu_state_line_width_set, METH_O,