plotly / plotly/plotly.R

Using opacityscale with surface results in ordering by addition order, not depth

Open
#1,781 0 comments 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Dominant language
R
Stars
2.7k
Forks
641
PR merge metrics
No merged PRs in 30d

Description

Hi, been using plotly with R for a while now and really loving it - thanks for assembling such a phenomenal program! I'd like to report a bug found while plotting multiple surface objects, which causes them to layer in the order they're added (using %>%) rather than the "depth" at which they should really render in the figure. See below for code and examples.

The "opacityscale" function is a new one from the dev branch (and I don't think problems with it have been reported on here before) so this question may be a better fit for https://github.com/plotly/plotly.js instead, where there's a bit more discussion about it and the original implementation, but I don't know JavaScript and can't provide a reprex there.

This is great:

image

This is not great (same figure rotated to look from below):

image

It only seems to show up if the opacityscale parameter is added, even if the opacity is set to 1 for all values.

Renders fine:
# devtools::install_github("ropensci/plotly")
library(plotly)
df <- data.frame(x=1:10, y=1:10)
surface_data <- matrix(1:100, nrow=10, ncol=10)
z_mat <- matrix(0, nrow = 10, ncol = 10)

plot_ly(df, x=~x, y=~y) %>%
  add_trace(type="surface",
            z=z_mat,
            surfacecolor=surface_data,
            colorscale=list(list(0, 1), list("red", "orange"))) %>%
  add_trace(type = "surface",
            z = z_mat+2,
            surfacecolor=surface_data,
            colorscale = list(list(0, 1), list("yellow", "green"))) %>%
  add_trace(type = "surface",
            z = z_mat+1,
            surfacecolor=surface_data,
            colorscale = list(list(0, 1), list("blue", "purple"))) 

image

Does not render fine:
plot_ly(df, x=~x, y=~y) %>%
  add_trace(type="surface",
            z=z_mat,
            surfacecolor=surface_data,
            opacityscale=list(list(0, 1), list(1, 1)),
            colorscale=list(list(0, 1), list("red", "orange"))) %>%
  add_trace(type = "surface",
            z = z_mat+1,
            surfacecolor=surface_data,
            opacityscale=list(list(0, 1), list(1, 1)),
            colorscale = list(list(0, 1), list("yellow", "green"))) %>%
  add_trace(type = "surface",
            z = z_mat+2,
            surfacecolor=surface_data,
            opacityscale=list(list(0, 1), list(1, 1)),
            colorscale = list(list(0, 1), list("blue", "purple")))

image

I've had a little trouble figuring out exactly how to best pass the opacityscale argument in R but I believe these settings should disable the opacity completely by setting every value between 0 and 1 to an opacity between 1 and 1 (i.e., always 1 and fully opaque).

Additionally, the surface that renders on "top" is the one that's added last in the piping order. If we alter the above code a little bit to render the purple/blue surface before the yellow/green one, we get some more interesting renders:

plot_ly(df, x=~x, y=~y) %>%
  add_trace(type="surface",
            z=z_mat,
            surfacecolor=surface_data,
            opacityscale=list(list(0, 1), list(1, 1)),
            colorscale=list(list(0, 1), list("red", "orange"))) %>%
  add_trace(type = "surface",
            z = z_mat+2,
            surfacecolor=surface_data,
            opacityscale=list(list(0, 1), list(1, 1)),
            colorscale = list(list(0, 1), list("blue", "purple"))) %>%
  add_trace(type = "surface",
            z = z_mat+1,
            surfacecolor=surface_data,
            opacityscale=list(list(0, 1), list(1, 1)),
            colorscale = list(list(0, 1), list("yellow", "green")))

image

image

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Reproduce the issue with the provided R examples using plot_ly(), add_trace(), surface traces, and opacityscale, then compare the rendering with and without opacityscale. Trace the behavior through the plotly.js implementation referenced by issue 4331; done means surface ordering follows depth rather than trace addition order when opacityscale is present.

Written by the indexing model from the issue text.

Assessment

Tech stack
javascript, r
Domain
data-visualization
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
30/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.