R Plotly 中的动态排序和定制

问题描述 投票:0回答:1

我有一个大型数据集,其中包含随时间变化的观察值。我正在使用

plotly
来可视化趋势。

目前,因为我有特定的自定义颜色、宽度和线条类型,所以我一直将每个主题视为单独的跟踪,并在每次出现新值时手动重新排列它们 - 希望图例顺序与最新值匹配。

我接近一个更优雅的解决方案,但不确定如何应用

width
参数以及如何对图例进行排序,以便具有最高最新值的主题位于第一个(即 Susan 具有最低的 2000 值,因此将是最后)。

library(tidyverse)
library(plotly)

# raw data
df <-
  tribble(
    ~Year, ~Subject, ~Value,
    1980, 'A', 100,
    1990, 'A', 200, 
    2000, 'A', 250,
    1980, 'B', 400,
    1990, 'B', 300,
    2000, 'B', 100,
    1980, 'C', 200,
    1990, 'C', 100,
    2000, 'C', 500
  )

# each subject has specific custom viz elements
custom_stuff <-
  tribble(
    ~Subject, ~Name, ~LineColor, ~LineType, ~LineWidth,
    'A', 'John', 'blue', 'solid', 2,
    'B', 'Susan', '#ef0107', 'dash', 1,
    'C', 'Subject C', 'orange', 'dot', 1
  )

# i'm currently transposing the data like this
df_wide <-
  df |> 
  pivot_wider(names_from = 'Subject', values_from = 'Value')

# and then manually applying my custom elements and manually ordering the traces based on most recent value. yuck.
plot_ly(df_wide, x = ~Year) |> 
  add_trace(y = ~C, name = 'Subject C', type = 'scatter', mode = 'lines', 
            line = list(shape = 'spline', color = 'orange', width = 1, dash = 'dot')) |> 
  add_trace(y = ~A, name = 'John', type = 'scatter', mode = 'lines', 
            line = list(shape = 'spline', color = 'blue', width = 2, dash = 'solid')) |> 
  add_trace(y = ~B, name = 'Susan', type = 'scatter', mode = 'lines', 
            line = list(shape = 'spline', color = '#ef0107', width = 1, dash = 'dash'))

# i'd like to do something more dynamic and elegant like this, but unsure how to handle width and ordering of legend.
custom_df <-
  df |> 
  inner_join(custom_stuff, by = 'Subject')

plot_ly(custom_df, 
        x = ~Year,
        y = ~Value,
        color = ~I(LineColor),
        name = ~Name,
        type = 'scatter',
        mode = 'lines',
        linetype = ~I(LineType),
        # width = ~I(LineWidth),
        line = list(shape = 'spline', smoothing = 1.3))
r plotly
1个回答
0
投票

这是一种可能的方法,它建立在使用广泛数据集的第一种方法的基础上,但使用

Reduce
动态添加跟踪,并使用一些数据整理来确定主题/跟踪的顺序:

library(tidyverse)
library(plotly)

# Order of subjects and traces
subject_order <- df |>
  slice_max(Year, by = Subject) |>
  arrange(desc(Year), desc(Value)) |>
  mutate(Subject = fct_inorder(Subject)) |>
  pull(Subject) |>
  levels()

plot_ly(df_wide, x = ~Year) |>
  Reduce(\(x, y) {
    custom_stuff <- custom_stuff |> filter(Subject == y)
    add_trace(
      x,
      y = reformulate(y), name = custom_stuff$Name, type = "scatter", mode = "lines",
      line = list(
        shape = "spline", color = custom_stuff$LineColor,
        width = custom_stuff$LineWidth,
        dash = custom_stuff$LineType
      )
    )
  }, x = subject_order, init = _)

© www.soinside.com 2019 - 2024. All rights reserved.