Fix #134309: Grease Pencil: SVG export crashes on constructive modifiers

The use of `GeometryDeformation` is incorrect for computing the bounds:
It contains _evaluated_ positions for the _original_ points, but does not
match the size of evaluated geometry after constructive modifiers like
Line-Art. For the bounds the evaluated positions should be used as-is.

Pull Request: https://projects.blender.org/blender/blender/pulls/134325
This commit is contained in:
Lukas Tönne
2025-02-10 11:53:48 +01:00
committed by Falk David
parent ed0d01c5af
commit 9842ecb6b8

View File

@@ -193,13 +193,11 @@ static IndexMask get_visible_strokes(const Object &object,
strokes.curves_range(), GrainSize(512), memory, is_visible_curve);
}
static std::optional<Bounds<float2>> compute_drawing_bounds(
static std::optional<Bounds<float2>> compute_screen_space_drawing_bounds(
const ARegion &region,
const RegionView3D &rv3d,
const Object &object,
const Object &object_eval,
const int layer_index,
const int frame_number,
const bke::greasepencil::Drawing &drawing)
{
using bke::greasepencil::Drawing;
@@ -215,11 +213,9 @@ static std::optional<Bounds<float2>> compute_drawing_bounds(
const Layer &layer = *grease_pencil.layers()[layer_index];
const float4x4 layer_to_world = layer.to_world_space(object);
const bke::crazyspace::GeometryDeformation deformation =
bke::crazyspace::get_evaluated_grease_pencil_drawing_deformation(
&object_eval, object, layer_index, frame_number);
const VArray<float> radii = drawing.radii();
const bke::CurvesGeometry &strokes = drawing.strokes();
const Span<float3> positions = strokes.positions();
IndexMaskMemory curve_mask_memory;
const IndexMask curve_mask = get_visible_strokes(object, drawing, curve_mask_memory);
@@ -232,8 +228,7 @@ static std::optional<Bounds<float2>> compute_drawing_bounds(
}
for (const int point_i : points) {
const float3 pos_world = math::transform_point(layer_to_world,
deformation.positions[point_i]);
const float3 pos_world = math::transform_point(layer_to_world, positions[point_i]);
float2 screen_co;
eV3DProjStatus result = ED_view3d_project_float_global(
&region, pos_world, screen_co, V3D_PROJ_TEST_NOP);
@@ -276,8 +271,8 @@ static std::optional<Bounds<float2>> compute_objects_bounds(
continue;
}
std::optional<Bounds<float2>> layer_bounds = compute_drawing_bounds(
region, rv3d, *info.object, *object_eval, layer_index, frame_number, *drawing);
std::optional<Bounds<float2>> layer_bounds = compute_screen_space_drawing_bounds(
region, rv3d, *info.object, layer_index, *drawing);
full_bounds = bounds::merge(full_bounds, layer_bounds);
}