I am trying to create (in plotly
) a scatterplot which distinguishes the points of the same series by two (or three) aesthetics -- color, shape, size. Ultimately the objective is to be able to toggle groups of points on/off via the legend, using any of the three aesthetics. This works well for one aesthetic.
[Added 2016-06-20] To expand on the desired interactive behavior: The idea is, once the figure is shown, to be able to toggle groups of points by clicking on any of the legends. For example (in the sample data below), if I were to click on y
in the legend, it would hide/show points #4, 5 and 10 from all series. If there's a click on A
, then toggle points #1, 2 and 8.
As a real-life use case -- think bond prices, with maturity on the horizontal axis and price on the vertical. Bonds are characterized by country of origin, credit rating and issue size. So if I click on, say, credit rating "A", I'd like all A-rated issues, regardless of size and country of origin, to be hidden. Currently they are only hidden from the rating-related trace. The points in the traces which reflect the other attributes (size & country) remain shown.
Given the detailed answer below, I am inclined to post this as a feature request on plotly
's site.
I have framed the question for plotly
, but if this behavior can be achieved in another package/library from R with relatively low pain levels (meaning no custom JavaScript or the like), I will accept that as an answer too.
[end edit]
The static part is easily done in ggplot2
but I cannot recreate it in plotly
(for the interactivity), even using ggplotly()
. Not sure if it is possible at all, but thought I'd ask. Sample data & code below.
(Possibly related to Using 2+ legends from R to plotly / plot.ly)
Generate some dummy data:
library(data.table)
library(plotly)
library(ggplot2)
DT <- data.table(
x = c(1:10), y = 1:10/2,
gr1 = c("A", "A", "B", "C", "D", "D", "B", "A", "E", "E"),
gr2 = c("x", "x", "x", "y", "y", "z", "z", "x", "x", "y"),
gr3 = c(1,2,2,1,3,4,1,2,2,1)
)
The ggplot()
version looks like this, and is what I'd like to get in plotly:
p <- ggplot(data = DT) + geom_point(aes(x = x, y = y, color = gr1, shape = gr2, size = gr3))
p
There are three groups of criteria in the legend, and the points have varying color, shape and size.
Calling ggplotly(p)
generates a bunch of warnings:
Warning messages:
1: In if (s == Inf) { :
the condition has length > 1 and only the first element will be used
2: In if (s == Inf) { :
the condition has length > 1 and only the first element will be used
3: In if (s == Inf) { :
the condition has length > 1 and only the first element will be used
4: In if (s == Inf) { :
the condition has length > 1 and only the first element will be used
5: In if (s == Inf) { :
the condition has length > 1 and only the first element will be used
6: In if (s == Inf) { :
the condition has length > 1 and only the first element will be used
7: In if (s == Inf) { :
the condition has length > 1 and only the first element will be used
8: In if (s == Inf) { :
the condition has length > 1 and only the first element will be used
and produces this figure:
Trying to use plot_ly()
, I get the following:
plot_ly(data = DT, x = x, y = y, color = gr1, symbol = gr2, type = "scatter", mode = "markers", marker = list(size = 10 * gr3)) # size is multiplied by 10, in plotly it is in pixels
The problem is most obvious in the middle of the figure -- instead of a colored cross, there are several shapes in different colors overlaid onto one another. Since this is a single point, I am expecting a single colored shape, as in ggplot
. In plotly, do the 'color', 'symbol' and 'size' arguments create a new trace?
I am still quite new to plotly
, so I may be missing something obvious.
The above is done using R 3.2.2
under Windows, with plotly_2.0.16
and ggplot2_2.0.0
.
See Question&Answers more detail:
os