From af3e52a8bffb9bacb4b3eee9be7959fed7984f0a Mon Sep 17 00:00:00 2001 From: Sven Berger Date: Mon, 18 May 2026 00:10:39 +0200 Subject: [PATCH] Validate shape cutout and extrusion inputs --- src/setups/extrude_geometry.jl | 21 +++++++++++++++++++++ src/setups/sphere_shape.jl | 13 ++++++++++++- test/setups/extrude_geometry.jl | 18 ++++++++++++++++++ test/setups/sphere_shape.jl | 9 +++++++++ 4 files changed, 60 insertions(+), 1 deletion(-) diff --git a/src/setups/extrude_geometry.jl b/src/setups/extrude_geometry.jl index 460583c38e..0a37fbcd64 100644 --- a/src/setups/extrude_geometry.jl +++ b/src/setups/extrude_geometry.jl @@ -87,6 +87,14 @@ shape = extrude_geometry(shape; direction, particle_spacing=0.1, n_extrude=4, de function extrude_geometry(geometry; particle_spacing=-1, direction, n_extrude::Integer, velocity=zeros(length(direction)), place_on_shell=false, mass=nothing, density=nothing, pressure=0.0) + if norm(direction) < eps() + throw(ArgumentError("`direction` needs to be non-zero")) + end + + if n_extrude < 1 + throw(ArgumentError("`n_extrude` needs to be positive")) + end + direction_ = normalize(direction) NDIMS = length(direction_) @@ -105,6 +113,11 @@ function extrude_geometry(geometry; particle_spacing=-1, direction, n_extrude::I face_coords = sample_plane(geometry, particle_spacing; place_on_shell) + if size(face_coords, 1) != NDIMS + throw(ArgumentError("`direction` must be of length $(size(face_coords, 1)) " * + "for the sampled geometry")) + end + coords = (face_coords .+ i * particle_spacing * direction_ for i in 0:(n_extrude - 1)) # In this context, `stack` is faster than `hcat(coords...)` @@ -235,6 +248,10 @@ end function shift_plane_corners(plane_points::NTuple{2}, direction, particle_spacing, place_on_shell) + if length(direction) != 2 + throw(ArgumentError("`direction` must be 2D when extruding 2D points")) + end + # With `place_on_shell`, particles need to be AT the min coordinates and not half a particle # spacing away from it. (place_on_shell) && (return plane_points) @@ -254,6 +271,10 @@ end function shift_plane_corners(plane_points::NTuple{3}, direction, particle_spacing, place_on_shell) + if length(direction) != 3 + throw(ArgumentError("`direction` must be 3D when extruding 3D points")) + end + # With `place_on_shell`, particles need to be AT the min coordinates and not half a particle # spacing away from it. (place_on_shell) && (return plane_points) diff --git a/src/setups/sphere_shape.jl b/src/setups/sphere_shape.jl index f74f4a470d..35e1087ccd 100644 --- a/src/setups/sphere_shape.jl +++ b/src/setups/sphere_shape.jl @@ -114,9 +114,20 @@ function SphereShape(particle_spacing, radius, center_position, density; cutout_min_ = collect(cutout_min) cutout_max_ = collect(cutout_max) + has_cutout = length(cutout_min_) != length(cutout_max_) || + norm(cutout_max_ - cutout_min_) > eps() + + if has_cutout && (length(cutout_min_) != NDIMS || length(cutout_max_) != NDIMS) + throw(ArgumentError("`cutout_min` and `cutout_max` must be of length $NDIMS " * + "for a $(NDIMS)D problem")) + end + + if has_cutout && any(cutout_min_ .> cutout_max_) + throw(ArgumentError("`cutout_min` must be smaller than or equal to `cutout_max`")) + end + # Remove particles in cutout # TODO This should consider the particle radius as well - has_cutout = norm(cutout_max_ - cutout_min_) > eps() function in_cutout(particle) return has_cutout && all(cutout_min_ .<= view(coordinates, :, particle) .<= cutout_max_) diff --git a/test/setups/extrude_geometry.jl b/test/setups/extrude_geometry.jl index 4146ab6dd6..f639173f16 100644 --- a/test/setups/extrude_geometry.jl +++ b/test/setups/extrude_geometry.jl @@ -47,6 +47,24 @@ @test shape.coordinates ≈ expected_coords end + + @testset verbose=true "Errors" begin + point1 = [0.0, 0.0] + point2 = [0.0, 1.0] + + @test_throws ArgumentError extrude_geometry((point1, point2); + direction=[0.0, 0.0], + particle_spacing=0.1, + n_extrude=1, density=1.0) + @test_throws ArgumentError extrude_geometry((point1, point2); + direction=[1.0, 0.0], + particle_spacing=0.1, + n_extrude=0, density=1.0) + @test_throws ArgumentError extrude_geometry((point1, point2); + direction=[0.0, 0.0, 1.0], + particle_spacing=0.1, + n_extrude=1, density=1.0) + end end # 3D diff --git a/test/setups/sphere_shape.jl b/test/setups/sphere_shape.jl index c8b87d76db..20d86b3314 100644 --- a/test/setups/sphere_shape.jl +++ b/test/setups/sphere_shape.jl @@ -79,6 +79,15 @@ end end + @testset verbose=true "Errors" begin + @test_throws ArgumentError SphereShape(0.1, 0.5, (0.0, 0.0), 1000.0; + cutout_min=(0.2, 0.0), + cutout_max=(0.1, 0.1)) + @test_throws ArgumentError SphereShape(0.1, 0.5, (0.0, 0.0, 0.0), + 1000.0; cutout_min=(0.0, 0.0), + cutout_max=(0.1, 0.1)) + end + @testset verbose=true "SphereShape 3D" begin shape_names = [ "1-particle VoxelSphere",