Plot ellipse in Makie?

How can I draw a 2-dimensional ellipse in a Makie plot?

Look up the equation , plug in your parameters and make a poly using the vector of points around the ellipse

I was also searching for a fast solutions for this, so I will just leave mine here to save time for others:

function getellipsepoints(cx, cy, rx, ry, θ)
	t = range(0, 2*pi, length=100)
	ellipse_x_r = @. rx * cos(t)
	ellipse_y_r = @. ry * sin(t)
	R = [cos(θ) sin(θ); -sin(θ) cos(θ)]
	r_ellipse = [ellipse_x_r ellipse_y_r] * R
	x = @. cx + r_ellipse[:,1]
	y = @. cy + r_ellipse[:,2]
	(x,y)
end

let
	cx=1  # x-position of the center
	cy=2  # y-position of the center
	rx=5  # major radius
	ry=2  # minor radius
	θ=π/3 # angle to x axis

	#plot
	lines(getellipsepoints(cx, cy, rx, ry, θ)...)
end

But for me, what is more important is to draw an ellipse from a covariance matrix.
Something similar to covellipse from StatsPlots.jl

So I use the following:

function getellipsepoints(μ, Σ, confidence=0.95)
	quant = quantile(Chisq(2), confidence) |> sqrt
	cx = μ[1]
	cy =  μ[2]
	
	egvs = eigvals(Σ)
	if egvs[1] > egvs[2]
		idxmax = 1
		largestegv = egvs[1]
		smallesttegv = egvs[2]
	else
		idxmax = 2
		largestegv = egvs[2]
		smallesttegv = egvs[1]
	end

	rx = quant*sqrt(largestegv)
	ry = quant*sqrt(smallesttegv)
	
	eigvecmax = eigvecs(Σ)[:,idxmax]
	θ = atan(eigvecmax[2]/eigvecmax[1])
 	if θ < 0
		θ += 2*π
	end

	getellipsepoints(cx, cy, rx, ry, θ)
end

Following an example with some data

mydat = let
	μ_my = [10,3]
	s = [2 2] 
	x = randn(334) # correlation comes from mhere
	y1 = μ_my[1] .+ s[1] .* x .+ randn(334)
	y2 = μ_my[2] .+ s[2] .* x .+ randn(334)
	mydat = [y1 y2]
end
my_μ = [mean(mydat[:,1]), mean(mydat[:,2])]
my_Σ = cov(mydat)

let
	f,_,_ = scatter(mydat[:,1], mydat[:,2])
	lines!(getellipsepoints(my_μ, my_Σ)..., label="95% confidence interval")
	lines!(getellipsepoints(my_μ, my_Σ,0.5)..., label="50% confidece interval")
	axislegend(position=:ct)
	f
end

or if you want it filled:

# or if you want it filled
let
	f,_,_ = scatter(mydat[:,1], mydat[:,2])
	poly!(Point2f.(zip(getellipsepoints(my_μ, my_Σ)...)); color=(:yellow, 0.5))
	f
end

(code inspired from How to draw an error ellipse representing the covariance matrix?)

5 Likes

We could think about a recipe for this, ellipses are quite common. But maybe there exists something in GeometryBasics already? The easiest would be to do poly(::Ellipse) in that case.

2 Likes

I agree that a recipe would be nice. From what I saw, I didn’t find an Ellipse in GeometryBasics.jl

1 Like