Search code examples
rplotlylogarithm

How to log transform values for color in Plotly but to keep original values on colorbar?


I am trying to log transform values that are defining color on a Plotly graph, but I would like to keep original values on the Plotly color bar legend (not log-transformed numbers) in order to improve readability.

Here is the example of what I am trying to do on the mtcars data-set:

mtcars %>% plot_ly(x = ~hp, 
               y = ~qsec,                                                                        
               size = ~disp,
               color = ~mpg)

and you will get this graph:

enter image description here

Let's say I want to log transform color variable (mpg) with this code:

mtcars %>% plot_ly(x = ~hp, 
               y = ~qsec,                                                                        
               size = ~disp,
               color = ~log(mpg))

I will get this graph: enter image description here

I am satisfied now with the graph, but now the colorbar on the right is having log() numbers.

My question is: how to log() transform color variable on a graph but keep the original numbers on the colorbar that are appropriately adjusted to new log colors?

So, on the one hand, I would like to have the original numbers on the second picture color bar, instead of 2.5, 3 and 3.5, but on the other hand, I would like to keep the color-positions of these numbers as they are on the log scale and without using ggplotly.


Solution

  • Similarly to this answer, this is a matter of using transformed values for the colour bar ticks, but untransformed values as labels.

    Here is an option:

    library(dplyr)
    library(plotly)
    
    # Define pretty breaks on transformed scale
    brks_transformed <- pretty(log10(mtcars$mpg), n = 5)
    
    # Breaks on the untransformed scale
    brks_untransformed <- sprintf("%.1f", 10^brks_transformed)
    
    mtcars %>% 
        plot_ly(
            x = ~hp, y = ~qsec, size = ~ disp, fill = ~ "",
            type = "scatter",
            mode = "markers",
            marker = list(
                color = ~ log10(mpg),
                line = list(width = 0),
                colorbar = list(
                    tickmode = "array",
                    ticktext = brks_untransformed,
                    tickvals = brks_transformed)))
    

    enter image description here