Как связать сюжетные трассы для выбора легенды и цвета?

проблема

Я мигрирую ряд ggplot/ggvis участки к plotly в shiny приложение. Я столкнулся с проблемой, связанной со связью следов. Я хочу иметь возможность показать / скрыть следы group на легенде, которая разделяется между связанными фреймами данных.

Минимальный рабочий пример

# load libraries
library(dplyr)
library(plotly)
library(viridis)

# contrived data to represent actual data points
df1 <- data.frame(x = rnorm(100),
                  y = rnorm(100),
                  group = rep(c("G1", "G2", "G3", "G4"), 25))

# contrived data to represent theoretical relationship
df2 <- data.frame(x = c(rep(-2, 4), rep(2, 4)),
                  y = c(seq(1.9, 1, -0.3), seq(-1, -1.9, -0.3)),
                  group = rep(c("G1", "G2", "G3", "G4"), 2))

# create plot with scatter and line traces
df1 %>%
  plot_ly(x = x,
          y = y,
          color = group,
          colors = viridis(n_distinct(group)),
          mode = "markers") %>%
  add_trace(x = x,
            y = y,
            color = group,
            colors = viridis(n_distinct(group)),
            mode = "lines",
            data = df2)

Попытки пока

Мои онлайн-поиски и, особенно, чтение сюжетной документации не сильно меня унесли.

Я могу добавить showlegend = FALSE ко второму следу. Это частично помогает решить проблему, однако я все еще хочу показать / скрыть эту трассировку на основе group значение.

Возможные решения

На основе архитектуры plotlyкажется, что если бы я мог поставить разброс и линию на один след в group тогда я бы получил желаемое поведение. Однако, похоже, что трассировка может иметь только один "режим", поэтому я выбрал подход, который у меня есть.

Если я продолжу путь, который я начал, я думаю, что мне нужно каким-то образом отловить событие "при нажатии" для легенды и показать / скрыть group следы... но я не совсем уверен, с чего начать.

Связанный / Вторичный

В моем MWE я установил colors аргумент viridis, Хотя это не имеет значения для проблемы, я не нашел способа гарантировать, что выбор цвета вместо этого связан с group (т.е. если след для group на df1 есть синий, хочу сделать тоже самое group синий на трассе для df2. Если это нетривиально и требует второго вопроса (я искал и не нашел соответствия... возможно, потому что это тривиально, и я упускаю что-то простое), тогда я спрошу эту часть отдельно.

1 ответ

Решение

Пересмотр истории для потомков

Несколько изменений в ggplot2 а также plotly за прошедшее время с тех пор, как этот вопрос был впервые задан. В текущей версии (4.7.1) есть аргумент legendgroup что занимается решением проблемы.

Ленивый код

Пожалуйста, прости минимальное усилие, приложенное к элегантному кодированию, однако, это расширение MWE демонстрирует способность показывать / скрывать следы по группам.

df1_G1 <- df1 %>% filter(group == "G1")
df2_G1 <- df2 %>% filter(group == "G1")
df1_G2 <- df1 %>% filter(group == "G2")
df2_G2 <- df2 %>% filter(group == "G2")
df1_G3 <- df1 %>% filter(group == "G3")
df2_G3 <- df2 %>% filter(group == "G3")
df1_G4 <- df1 %>% filter(group == "G4")
df2_G4 <- df2 %>% filter(group == "G4")

plot_ly(type = "scatter", mode = "markers") %>%
  add_trace(df1_G1, x = df1_G1$x, y = df1_G1$y, color = I("red"),
            legendgroup = "G1", name = "G1 - scatter") %>%
  add_trace(df2_G1, x = df2_G1$x, y = df2_G1$y, color = I("red"),
            legendgroup = "G1", name = "G1 - line", mode = "lines") %>%
  add_trace(df1_G2, x = df1_G2$x, y = df1_G2$y, color = I("green"), 
            legendgroup = "G2", name = "G2 - scatter") %>%
  add_trace(df2_G2, x = df2_G2$x, y = df2_G2$y, color = I("green"),
            legendgroup = "G2", name = "G2 - line", mode = "lines") %>%
  add_trace(df1_G3, x = df1_G3$x, y = df1_G3$y, color = I("blue"),
            legendgroup = "G3", name = "G3 - scatter") %>%
  add_trace(df2_G3, x = df2_G3$x, y = df2_G3$y, color = I("blue"),
            legendgroup = "G3", name = "G3 - line", mode = "lines") %>%
  add_trace(df1_G4, x = df1_G4$x, y = df1_G4$y, color = I("orange"), 
            legendgroup = "G4", name = "G4 - scatter") %>%
  add_trace(df2_G4, x = df2_G4$x, y = df2_G4$y, color = I("orange"), 
            legendgroup = "G4", name = "G4 - line", mode = "lines")

Образец вывода

Показ первой группы G1 снят. Также обратите внимание, что цвета были сделаны так, чтобы соответствовать разбросу и трассировке линий для одной и той же группы.

grouplegend_example

Другие вопросы по тегам