Прежде всего, это потрясающе.
Первый подход с использованием shadow_wake и без подготовки других данных
Я прокомментировал фрагменты, которые не были определены в вопросе.Я добавил wrap = F
для сброса анимации (а не перемотки назад) в конце и shadow_wake
для захвата траектории.
# The factors of pos_type are backwards (b/c alphabetical), so R thinks the detonation
# comes before the player position. Here we reverse that.
df$pos_type <- forcats::fct_rev(df$pos_type)
ggplot(df, aes(pos_x, pos_y, group = plot_group)) +
# annotation_custom(grid::rasterGrob(img, width = unit(1,"npc"), height =
# unit(1,"npc")), 0, w, 0, -h) +
scale_x_continuous(expand = c(0,0)) + # ,limits = c(0,w)) +
scale_y_reverse(expand = c(0,0)) + # ,limits = c(h,0)) +
geom_point(color = "red") +
transition_states(states=pos_type, transition_length = 1, state_length = 1, wrap = F) +
shadow_wake(wake_length = 1)
![enter image description here](https://i.stack.imgur.com/NY4rD.gif)
Второй подход, добавление начальной позиции и geom_segment
Мы также можем добавить траекторию в качестве сегмента, если мыдать каждому кадру ссылку на позицию игрока:
df %>%
# Add reference to first coordinates for each plot_group
left_join(by = "plot_group",
df %>%
group_by(plot_group) %>%
filter(pos_type == "Player position") %>%
mutate(pos_x1 = pos_x, pos_y1 = pos_y) %>%
select(plot_group, pos_x1, pos_y1)
) %>%
ggplot(aes(pos_x, pos_y, group = plot_group)) +
# annotation_custom(grid::rasterGrob(img, width = unit(1,"npc"), height =
# unit(1,"npc")), 0, w, 0, -h) +
scale_x_continuous(expand = c(0,0)) + # ,limits = c(0,w)) +
scale_y_reverse(expand = c(0,0)) + # ,limits = c(h,0)) +
geom_point(color = "red") +
geom_segment(color = "gray70", aes(xend = pos_x1, yend = pos_y1)) +
transition_states(states=pos_type, transition_length = 1, state_length = 1, wrap = F)
![enter image description here](https://i.stack.imgur.com/aKLtL.gif)
Третий вариант, показывающий траектории по времени начала
По аналогии с2-й, но я добавляю расстояние каждой траектории, время в пути и время начала.Здесь я предполагаю, что детонация - это время окончания, и возвращаемся к началу траектории.
(я сначала попробовал transition_time
, но не смог заставить его работать без глючного поведения после первой траектории.)
# trajectory speed
dist_per_time = 50
df2 <- df %>%
# Add reference to first coordinates for each plot_group
left_join(by = "plot_group",
df %>%
group_by(plot_group) %>%
filter(pos_type == "Player position") %>%
mutate(pos_x1 = pos_x, pos_y1 = pos_y) %>%
select(plot_group, pos_x1, pos_y1)
) %>%
left_join(by = c("plot_group", "pos_type"),
df %>%
group_by(plot_group) %>%
mutate(x_d = (range(pos_x)[1] - range(pos_x)[2]),
y_d = (range(pos_y)[1] - range(pos_y)[2]),
dist = sqrt(x_d^2 + y_d^2),
event_time = round_throw_time - if_else(pos_type == "Player position",
dist / dist_per_time,
0),
event_time = round(event_time, 1)) %>%
select(plot_group, pos_type, dist, event_time)
)
ggplot(df2, aes(pos_x, pos_y, group = plot_group)) +
# annotation_custom(grid::rasterGrob(img, width = unit(1,"npc"), height =
# unit(1,"npc")), 0, w, 0, -h) +
scale_x_continuous(expand = c(0,0)) + # ,limits = c(0,w)) +
scale_y_reverse(expand = c(0,0)) + # ,limits = c(h,0)) +
geom_point(color = "red") +
geom_segment(color = "gray70", aes(xend = pos_x1, yend = pos_y1)) +
transition_reveal(plot_group, event_time)
![enter image description here](https://i.stack.imgur.com/Y9NMs.gif)