# Zooming and date axes in Makie

**URL:** https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790
**Category:** Visualization
**Tags:** makie
**Created:** [May 10, 2022, 6:03am UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790 "2022-05-10T06:03:06Z")
**Posts on this page:** 15
**Page:** 1

<div class="post-metadata">

### Author: ![gdalle](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gdalle/32/27854_2.png) [@gdalle](https://discourse.julialang.org/u/gdalle)
#### Post date: [May 10, 2022, 6:03am UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790/1 "2022-05-10T06:03:06Z")

</div>

Hi there!

I recently got acquainted with Makie and I absolutely love it!  
Here are 2 small questions related to zooming (in GLMakie):

- Is it possible to update the ticks dynamically when zooming? For instance I would like ticks at 10, 20 and 30 with the default view, but when zooming by x10 I would like ticks at 1, 2 and 3
- Is it possible to synchronize zooming on several axes? For instance, I have a stack of 3 axes with the same x axis. When I select a rectangle region in the first one, I would like the x-zoom on the other two to react accordingly.

Thanks a lot!

---

<div class="post-metadata">

### Author: ![jipolanco](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/jipolanco/32/12129_2.png) [@jipolanco](https://discourse.julialang.org/u/jipolanco)
#### Post date: [May 10, 2022, 6:11am UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790/2 "2022-05-10T06:11:31Z")

</div>

> [@gdalle](#):
>
> Is it possible to synchronize zooming on several axes? For instance, I have a stack of 3 axes with the same x axis. When I select a rectangle region in the first one, I would like the x-zoom on the other two to react accordingly.

I think [`linkxaxes!`](https://makie.juliaplots.org/stable/documentation/api_reference/index.html#linkxaxes!) does this.

---

<div class="post-metadata">

### Author: ![gdalle](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gdalle/32/27854_2.png) [@gdalle](https://discourse.julialang.org/u/gdalle)
#### Post date: [May 10, 2022, 6:13am UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790/3 "2022-05-10T06:13:45Z")

</div>

Awesome! This is exactly what I needed 😍  
Any idea about the ticks?

---

<div class="post-metadata">

### Author: ![jules](https://avatars.discourse-cdn.com/v4/letter/j/41988e/32.png) [@jules](https://discourse.julialang.org/u/jules)
#### Post date: [May 10, 2022, 9:12am UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790/4 "2022-05-10T09:12:50Z")

</div>

The ticks normally do update when zooming, what version are you on? Or did you set ticks manually somehow?

---

<div class="post-metadata">

### Author: ![gdalle](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gdalle/32/27854_2.png) [@gdalle](https://discourse.julialang.org/u/gdalle)
#### Post date: [May 10, 2022, 9:15am UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790/5 "2022-05-10T09:15:10Z")

</div>

The existing ticks do update and the space between them widens, but I would like for new ticks to appear as I zoom in

---

<div class="post-metadata">

### Author: ![jules](https://avatars.discourse-cdn.com/v4/letter/j/41988e/32.png) [@jules](https://discourse.julialang.org/u/jules)
#### Post date: [May 10, 2022, 9:16am UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790/6 "2022-05-10T09:16:42Z")

</div>

Yes that should normally happen, so if you zoom in further the existing ticks disappear to the sides?

---

<div class="post-metadata">

### Author: ![gdalle](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gdalle/32/27854_2.png) [@gdalle](https://discourse.julialang.org/u/gdalle)
#### Post date: [May 10, 2022, 12:05pm UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790/7 "2022-05-10T12:05:15Z")

</div>

New ticks appear when I don’t specify the ticks precisely. However, when I need to define ticks manually, they don’t adapt to the zoom level. This is especially problematic for axes with dates, since those are not supported natively.  
On the screenshots below, which were generated with

```julia
using GLMakie
GLMakie.inline!(false)
too_few_ticks = scatter(
    1:100, rand(100),
    axis=(
        xticks=(0:10:100, string.(0:10:100)),
    )
)

```

the `xticks` stay the same while the `yticks` adapt.

 ![too_few_ticks_nozoom](https://global.discourse-cdn.com/julialang/original/3X/e/c/ec833a8ffd6b90d66b796d476322b1c40b34ab4b.png)  
 ![too_few_ticks_zoom](https://global.discourse-cdn.com/julialang/original/3X/c/b/cbc6cb048dd3682de19e25505d392e9549c82f08.png)

---

<div class="post-metadata">

### Author: ![jules](https://avatars.discourse-cdn.com/v4/letter/j/41988e/32.png) [@jules](https://discourse.julialang.org/u/jules)
#### Post date: [May 10, 2022, 12:09pm UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790/8 "2022-05-10T12:09:37Z")

</div>

Ok yes if you fix the ticks, they’re fixed 🙂 If you need different dynamic ticks than the defaults then you can create your own tick finder. This is probably a bit tricky for date ticks, and it will depend on how the numbers that you plot relate to the dates that they represent. You will sometimes see solutions where only date-specific formatters are applied to a non-date-aware tick finder. This then leads to weird tick choices that happen to match the underlying nice integer ticks, like `"Sunday 10:50pm", "Wednesday 9:10am"` as a made-up example. A real date tick finder would be aware that on a span of weeks you want to see days, on a span of a day you want to see hours, etc. Makie currently internally converts to Float32 precision, which is why we don’t have Date machinery, dates can not be represented faithfully in 32 bit…

---

<div class="post-metadata">

### Author: ![gdalle](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gdalle/32/27854_2.png) [@gdalle](https://discourse.julialang.org/u/gdalle)
#### Post date: [May 10, 2022, 12:13pm UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790/9 "2022-05-10T12:13:01Z")

</div>

Seems obvious when you state it like that 😅 You mean I should try to imitate `LinearTicks(n)`, but with dates? Something like `LinearDateTicks(min_date, max_date, n)`? I can’t seem to find the interface requirements for these tick finders

---

<div class="post-metadata">

### Author: ![jules](https://avatars.discourse-cdn.com/v4/letter/j/41988e/32.png) [@jules](https://discourse.julialang.org/u/jules)
#### Post date: [May 10, 2022, 12:15pm UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790/10 "2022-05-10T12:15:41Z")

</div>

It’s not terribly well documented because it’s a bit of a niche use. [But this paragraph hints to some functions](https://makie.juliaplots.org/stable/examples/blocks/axis/#modifying_ticks).

And the default is actually `WilkinsonTicks` and not `LinearTicks` anymore, the docs seem to have desynchronized there.

---

<div class="post-metadata">

### Author: ![jules](https://avatars.discourse-cdn.com/v4/letter/j/41988e/32.png) [@jules](https://discourse.julialang.org/u/jules)
#### Post date: [May 10, 2022, 12:21pm UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790/11 "2022-05-10T12:21:31Z")

</div>

For example, if you have numbers that mean dates somehow, you could do this

```julia
struct DateTicks end

function MakieLayout.get_ticks(::DateTicks, ::typeof(identity), ::Makie.Automatic, vmin, vmax)
    mindate, maxdate = convert_numbers_to_dates.((vmin, vmax))
    dates = find_some_date_ticks(mindate, maxdate)
    ticklabels = make_labels(dates)
    tickvalues = convert_dates_to_numbers(dates)
    return tickvalues, ticklabels
end

# and then
lines(datenumbers, values, axis = (; xticks = DateTicks()))

```

---

<div class="post-metadata">

### Author: ![gdalle](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gdalle/32/27854_2.png) [@gdalle](https://discourse.julialang.org/u/gdalle)
#### Post date: [May 10, 2022, 12:54pm UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790/12 "2022-05-10T12:54:31Z")

</div>

Thanks, this is precisely what I was looking for. Here’s a working prototype

```julia
using Dates
using GLMakie
GLMakie.inline!(false)

date_to_number(d::Date) = float(Dates.value(d) - Dates.value(Date(1970, 1, 1)))
number_to_date(x::Real) = Date(unix2datetime(x * 24 * 3600))

struct LinearDateTicks
    n::Int
end

function MakieLayout.get_ticks(ticks::LinearDateTicks, ::typeof(identity), ::Makie.Automatic, vmin, vmax)
    mindate = number_to_date(vmin)
    maxdate = number_to_date(vmax)
    step = (maxdate - mindate) ÷ ticks.n
    @assert step >= Day(1)
    tickdates = collect(range(mindate, maxdate; step=step))
    tickvalues = date_to_number.(tickdates)
    ticklabels = string.(tickdates)
    return tickvalues, ticklabels
end

x = Date(2000):Day(1):Date(2020)
y = dayofyear.(x)
scatter(date_to_number.(x), y, color=(:blue, 0.5), axis=(xticks=LinearDateTicks(10),xticklabelrotation=0.5))

```

Since the dependencies are minimal, do you think a beefed up version would be worthy of a PR? I know this would come in handy to lots of people working with time series

---

<div class="post-metadata">

### Author: ![jules](https://avatars.discourse-cdn.com/v4/letter/j/41988e/32.png) [@jules](https://discourse.julialang.org/u/jules)
#### Post date: [May 10, 2022, 1:20pm UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790/13 "2022-05-10T13:20:07Z")

</div>

Hmm I don’t want to canonicalize a “hack”, when we add real Date support it will be integrated better. This solution here depends on the type of conversion from Dates to numbers which will probably not be the same for everyone. But we could think about adding guidance to the docs that I linked until that’s happening.

---

<div class="post-metadata">

### Author: ![gdalle](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gdalle/32/27854_2.png) [@gdalle](https://discourse.julialang.org/u/gdalle)
#### Post date: [May 10, 2022, 1:33pm UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790/14 "2022-05-10T13:33:26Z")

</div>

I understand that this is a hack, and that putting it in the docs may be the best you can do for now.  
However, note that according to the [Dates documentation](https://docs.julialang.org/en/v1/stdlib/Dates/), there are only two natural ways to perform conversions between dates/times and numbers, because date/time objects are nothing but number wrappers:

- A `Date` stores the equivalent nb of days
- A `DateTime` stores the equivalent nb of milliseconds

The forward conversion operation is performed by `Dates.value` in both cases, and the backward operation can be defined thanks to `unix2datetime`.

---

<div class="post-metadata">

### Author: ![jules](https://avatars.discourse-cdn.com/v4/letter/j/41988e/32.png) [@jules](https://discourse.julialang.org/u/jules)
#### Post date: [May 10, 2022, 1:47pm UTC](https://discourse.julialang.org/t/zooming-and-date-axes-in-makie/80790/15 "2022-05-10T13:47:39Z")

</div>

The most annoying thing is the resolution with Float32. Currently doing the conversion directly has way too low of a resolution. Let’s look at one minute today:

```julia
julia> d1 = DateTime(Year(2022), Month(05), Day(10), Hour(15), Minute(44))
2022-05-10T15:44:00

julia> d2 = DateTime(Year(2022), Month(05), Day(10), Hour(15), Minute(45))
2022-05-10T15:45:00

julia> Dates.value(d2) - Dates.value(d1)
60000

julia> Float32(Dates.value(d2)) - Float32(Dates.value(d1))
0.0f0

```

So either Makie has to first scale the dates into a range where Float32 is okay, or we need some other mechanism to deal with the precision problems. GLMakie will probably never be able to deal with Float64 though, as I don’t think GPUs like those very much.
