diff --git a/CHANGELOG.md b/CHANGELOG.md index d1515641393..958c9d22511 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,8 @@ ## [Unreleased] +- Correct a bug in the `project` function when projecting using a `Scene`. [#3909](https://github.com/MakieOrg/Makie.jl/pull/3909). + ## [0.21.5] - 2024-07-07 - Fixed tuple argument for `WGLMakie.activate!(resize_to=(:parent, nothing))` [#4009](https://github.com/MakieOrg/Makie.jl/pull/4009). diff --git a/src/camera/projection_math.jl b/src/camera/projection_math.jl index a9f99a676d4..1efa7fa578c 100644 --- a/src/camera/projection_math.jl +++ b/src/camera/projection_math.jl @@ -401,7 +401,7 @@ function project(scenelike::SceneLike, input_space::Symbol, output_space::Symbol output_from_clip = clip_to_space(cam, output_space) output_f32c = inv_f32_convert_matrix(scenelike, output_space) - p4d = to_ndim(Point4{T}, to_ndim(Point3{T}, transformed, 0), 1) + p4d = to_ndim(Point4{T}, to_ndim(Point3{T}, pos, 0), 1) transformed = output_f32c * output_from_clip * clip_from_input * input_f32c * p4d return Point3{T}(transformed[Vec(1, 2, 3)] ./ transformed[4]) end diff --git a/test/projection_math.jl b/test/projection_math.jl index 946f4e6adf0..faf059b9e4c 100644 --- a/test/projection_math.jl +++ b/test/projection_math.jl @@ -1,4 +1,33 @@ +using Makie + @testset "Projection math" begin - @test eltype(Makie.rotationmatrix_x(1)) == Float64 - @test eltype(Makie.rotationmatrix_x(1f0)) == Float32 + @testset "Rotation matrix" begin + @test eltype(Makie.rotationmatrix_x(1)) == Float64 + @test eltype(Makie.rotationmatrix_x(1f0)) == Float32 + end + @testset "Projection between spaces in 3D" begin + # Set up an LScene and some points there + sc = Scene(size = (650, 400), camera = cam3d!) + corner_points_px = [Point3f(0, 0, 0), Point3f(650, 400, 0)] + + @testset "Clip space and pixel space equivalence" begin + far_bottom_left_clip = Point3f(-1) + near_top_right_clip = Point3f(1) + + fbl_px = Makie.project(sc, :clip, :pixel, far_bottom_left_clip) + ntr_px = Makie.project(sc, :clip, :pixel, near_top_right_clip) + @test Point2f(fbl_px) == Point2f(0, 0) + @test Point2f(ntr_px) == Point2f(650, 400) + end + + @testset "No warnings in projections between spaces" begin + for (source, dest) in unique(Iterators.product(Makie.spaces(), Makie.spaces())) + source == dest && continue + current_space_points = Makie.project.(sc, :pixel, source, corner_points_px) + @testset "$source → $dest" begin + @test_nowarn Makie.project.(sc, source, dest, current_space_points) + end + end + end + end end