-
-
Notifications
You must be signed in to change notification settings - Fork 11
New issue
Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? # to your account
Avoid tint color shift caused by the limits
parameter in scale_*_hypso_tint_b
and scale_*_hypso_tint_c
#165
Conversation
Avoid tint color shift caused by the `limits` parameter
Hi @Fan-iX Thanks for the PR, but I am not really sure of this, if I understood correctly you expect
Regarding 2) I am not sure than ggplot2 provides a mechanism for modifying natively the colors of a given legend if already provided, and this modifies the expected behaviour of Additionally this would need further testing, not only for the failed checks (expected) but for other scales in the package (there are several of them) that uses the same approach, and I am not in a position right now of exploring the implications and corner cases. I think you can still achieve the same result with some simple steps: library(terra)
library(tidyterra)
library(ggplot2)
f_asia <- system.file("extdata/asia.tif", package = "tidyterra")
asia <- rast(f_asia)
asia Now use the colour database # Create custom cols using breaks
data("hypsometric_tints_db")
cols <- hypsometric_tints_db %>%
filter(pal == "gmt_globe" &
limit >= -6000 &
limit <= 5000)
cols
#> # A tibble: 27 × 6
#> pal limit r g b hex
#> <chr> <dbl> <dbl> <dbl> <dbl> <chr>
#> 1 gmt_globe -6000 51 102 255 #3366FF
#> 2 gmt_globe -5500 34 119 255 #2277FF
#> 3 gmt_globe -5000 17 136 255 #1188FF
#> 4 gmt_globe -4500 0 153 255 #0099FF
#> 5 gmt_globe -4000 27 164 255 #1BA4FF
#> 6 gmt_globe -3500 54 175 255 #36AFFF
#> 7 gmt_globe -3000 81 186 255 #51BAFF
#> 8 gmt_globe -2500 108 197 255 #6CC5FF
#> 9 gmt_globe -2000 134 208 255 #86D0FF
#> 10 gmt_globe -1500 161 219 255 #A1DBFF
#> # ℹ 17 more rows Now use ggplot() +
geom_spatraster(data = asia) +
# Use fill_gradientn with our new palette
scale_fill_gradientn(
colours = cols$hex, # New cols
values = scales::rescale(cols$limit), # New values
limits = c(-6000, 5000),
# Further refinements
breaks = c(-6000, -2000, 0, 2000, 5000),
oob = scales::oob_squish,
labels = c("<=-6000", "-2000", "0", "2000", ">=5000"),
guide = guide_colorbar(reverse = TRUE)
) +
labs(
fill = "elevation (m)",
title = "Hypsometric map of Asia"
) +
theme(
legend.position = "bottom",
legend.title.position = "top",
legend.key.width = rel(3),
legend.ticks = element_line(colour = "black", linewidth = 0.3),
legend.direction = "horizontal"
) This is more flexible I think. The plot is clamped to your values and the legend is on the colours of the range |
See this reprex, notice that library(ggplot2)
data("faithfuld")
range(faithfuld$density)
#> [1] 1.25925e-24 3.69878e-02
ggplot(faithfuld, aes(waiting, eruptions)) +
geom_raster(aes(fill = density)) +
scale_fill_viridis_c() ggplot(faithfuld, aes(waiting, eruptions)) +
geom_raster(aes(fill = density)) +
scale_fill_viridis_c(
limits = c(0.02, 0.0275),
# Further refinements
breaks = seq(0.015, 0.025, 0.001),
oob = scales::oob_squish
) Created on 2025-01-23 with reprex v2.1.1 |
Thanks for your reply. What I'm trying to accomplish is to adjust the range ( As you pointed out, I didn't find a easy way to clamp a existing color legend. I noticed that I think it will be nice if There is a small flaw in the solution using cols <- hypsometric_tints_db %>% filter(pal == "gmt_globe" & limit >= -6250 & limit <= 5000)
ggplot() +
geom_spatraster(data = asia) +
scale_fill_gradientn(
colours = cols$hex,
values = scales::rescale(cols$limit),
limits = c(-6250, 5000),
breaks = c(-6250, -2000, 0, 2000, 5000),
oob = scales::oob_squish,
labels = c("<=-6250", "-2000", "0", "2000", ">=5000"),
guide = guide_colorbar(reverse = TRUE)
) +
labs(
fill = "elevation (m)",
title = "Hypsometric map of Asia"
) +
theme(
legend.position = "bottom",
legend.title.position = "top",
legend.key.width = rel(3),
legend.ticks = element_line(colour = "black", linewidth = 0.3),
legend.direction = "horizontal"
) In this case, we need to cols <- hypsometric_tints_db %>% filter(pal == "gmt_globe")
limits <- c(-6250, 5000)
ggplot() +
geom_spatraster(data = asia) +
scale_fill_gradientn(
colours = cols$hex,
values = scales::rescale(cols$limit, from=limits),
limits = limits,
breaks = c(-6250, -2000, 0, 2000, 5000),
oob = scales::oob_squish,
labels = c("<=-6250", "-2000", "0", "2000", ">=5000"),
guide = guide_colorbar(reverse = TRUE)
) +
labs(
fill = "elevation (m)",
title = "Hypsometric map of Asia"
) +
theme(
legend.position = "bottom",
legend.title.position = "top",
legend.key.width = rel(3),
legend.ticks = element_line(colour = "black", linewidth = 0.3),
legend.direction = "horizontal"
) and this is actually what I do in this PR. |
Expand PR #165 to other scales, tests and document
Hi!
Thanks for your excellent package. I use this package to create elevation maps, its great integrity with ggplot has massively facilitated my work.
I noticed that for the
scale_fill_hypso_tint_c
function, the elevation tinting of the plot would become inaccurate if the parameterlimits
is supplied:And I expect the result to be
(Here the purple color has been truncated comparing with the original palette)
The image above is plotted with a "hotfix" for the function
scale_fill_hypso_tint_c
in my the R session. This PR is the changes I made to the function, but I didn't run package builds or tests so it may need some review.