| @@ -48,10 +48,10 @@ base_plot <- function(d, title = "", ...) { | |||
| geom_tile(width = 0.9, height = 0.9) + | |||
| coord_equal() + | |||
| geom_text(data = d %>% filter(!is.na(val)), aes(label = val), color = "white", | |||
| family = text_family, size = 20, fontface = "bold") + | |||
| family = text_family, size = 12, fontface = "bold") + | |||
| scale_fill_identity() + | |||
| scale_alpha_identity() + | |||
| labs(title = title) + | |||
| theme_void() + | |||
| theme(plot.title = element_text(family = title_family, hjust = 0.5, size = 30)) | |||
| theme(plot.title = element_text(family = title_family, hjust = 0.5, size = 24)) | |||
| } | |||
| @@ -13,6 +13,7 @@ knitr::opts_chunk$set( | |||
| message = FALSE, | |||
| cache = TRUE | |||
| ) | |||
| library(tidyAnimatedVerbs) | |||
| ``` | |||
| [gganimate]: https://github.com/thomasp85/gganimate#README | |||
| @@ -44,24 +45,31 @@ You can directly download the [original animations](images/) or static images in | |||
| Currently, the animations cover the [dplyr two-table verbs][dplyr-two-table] and I'd like to expand the animations to include more verbs from the tidyverse. | |||
| [Suggestions are welcome!](https://github.com/gadenbuie/tidy-animated-verbs/issues) | |||
| ## Installing | |||
| The library can be installed with | |||
| ```{r, echo=T,eval=F} | |||
| # install.package("devtools") | |||
| devtools::install_github("gadenbuie/tidy-animated-verbs") | |||
| ``` | |||
| ## Mutating Joins | |||
| ```{r intial-dfs} | |||
| source("R/00_base_join.R") | |||
| df_names <- data_frame( | |||
| .x = c(1.5, 4.5), .y = 0.25, | |||
| value = c("x", "y"), | |||
| size = 12, | |||
| color = "black" | |||
| ```{r intial-dfs, echo=T} | |||
| library(tidyAnimatedVerbs) | |||
| x <- data_frame( | |||
| id = 1:3, | |||
| x = paste0("x", 1:3) | |||
| ) | |||
| g <- plot_data(initial_join_dfs) + | |||
| geom_text(data = df_names, family = "Fira Mono", size = 24) | |||
| y <- data_frame( | |||
| id = (1:4)[-3], | |||
| y = paste0("y", (1:4)[-3]) | |||
| ) | |||
| save_static_plot(g, "original-dfs") | |||
| animate_full_join(x, y, by = c("id"), export = "first") | |||
| ``` | |||
| <img src="images/static/png/original-dfs.png" width="480px" /> | |||
| ```{r echo=TRUE} | |||
| x | |||
| @@ -72,11 +80,10 @@ y | |||
| > All rows from `x` where there are matching values in `y`, and all columns from `x` and `y`. | |||
| ```{r inner-join} | |||
| source("R/inner_join.R") | |||
| ```{r inner-join, echo=T} | |||
| animate_inner_join(x, y, by = "id") | |||
| ``` | |||
|  | |||
| ```{r echo=TRUE} | |||
| inner_join(x, y, by = "id") | |||
| @@ -86,11 +93,10 @@ inner_join(x, y, by = "id") | |||
| > All rows from `x`, and all columns from `x` and `y`. Rows in `x` with no match in `y` will have `NA` values in the new columns. | |||
| ```{r left-join} | |||
| source("R/left_join.R") | |||
| ```{r left-join, echo=T} | |||
| animate_inner_join(x, y, by = "id") | |||
| ``` | |||
|  | |||
| ```{r echo=TRUE} | |||
| left_join(x, y, by = "id") | |||
| @@ -101,7 +107,9 @@ left_join(x, y, by = "id") | |||
| > ... If there are multiple matches between `x` and `y`, all combinations of the matches are returned. | |||
| ```{r left-join-extra} | |||
| source("R/left_join_extra.R") | |||
| # Not yet working | |||
| # source("R/left_join_extra.R") | |||
| y_extra <- bind_rows(y, data_frame(id = 2, y = "y5")) | |||
| ``` | |||
|  | |||
| @@ -115,11 +123,10 @@ left_join(x, y_extra, by = "id") | |||
| > All rows from y, and all columns from `x` and `y`. Rows in `y` with no match in `x` will have `NA` values in the new columns. | |||
| ```{r right-join} | |||
| source("R/right_join.R") | |||
| ```{r right-join, echo = T} | |||
| animate_right_join(x, y, by = "id") | |||
| ``` | |||
|  | |||
| ```{r echo=TRUE} | |||
| right_join(x, y, by = "id") | |||
| @@ -129,11 +136,10 @@ right_join(x, y, by = "id") | |||
| > All rows and all columns from both `x` and `y`. Where there are not matching values, returns `NA` for the one missing. | |||
| ```{r full-join} | |||
| source("R/full_join.R") | |||
| ```{r full-join, echo=T} | |||
| animate_full_join(x, y, by = "id") | |||
| ``` | |||
|  | |||
| ```{r echo=TRUE} | |||
| full_join(x, y, by = "id") | |||
| @@ -145,11 +151,10 @@ full_join(x, y, by = "id") | |||
| > All rows from `x` where there are matching values in `y`, keeping just columns from `x`. | |||
| ```{r semi-join} | |||
| source("R/semi_join.R") | |||
| ```{r semi-join, echo=T} | |||
| animate_semi_join(x, y, by = "id") | |||
| ``` | |||
|  | |||
| ```{r echo=TRUE} | |||
| semi_join(x, y, by = "id") | |||
| @@ -160,10 +165,9 @@ semi_join(x, y, by = "id") | |||
| > All rows from `x` where there are not matching values in `y`, keeping just columns from `x`. | |||
| ```{r anti-join} | |||
| source("R/anti_join.R") | |||
| animate_anti_join(x, y, by = "id") | |||
| ``` | |||
|  | |||
| ```{r echo=TRUE} | |||
| anti_join(x, y, by = "id") | |||
| @@ -171,27 +175,24 @@ anti_join(x, y, by = "id") | |||
| ## Set Operations | |||
| ```{r intial-dfs-so} | |||
| source("R/00_base_set.R") | |||
| df_names <- data_frame( | |||
| .x = c(2.5, 5.5), .y = 0.25, | |||
| value = c("x", "y"), | |||
| size = 12, | |||
| color = "black" | |||
| ) | |||
| ```{r intial-dfs-so, echo=T} | |||
| g <- plot_data_set(initial_set_dfs, "", NULL, NULL) + | |||
| geom_text(data = df_names, family = "Fira Mono", size = 24) | |||
| x <- tibble::tribble( | |||
| ~x, ~y, | |||
| "1", "a", | |||
| "1", "b", | |||
| "2", "a" | |||
| ) | |||
| save_static_plot(g, "original-dfs-set-ops") | |||
| ``` | |||
| y <- tibble::tribble( | |||
| ~x, ~y, | |||
| "1", "a", | |||
| "2", "b" | |||
| ) | |||
| ```{r remove-set-ops-ids} | |||
| x <- x %>% select(-id) | |||
| y <- y %>% select(-id) | |||
| animate_union(x, y, export = "first") | |||
| ``` | |||
| <img src="images/static/png/original-dfs-set-ops.png" width="480px" /> | |||
| ```{r echo=TRUE} | |||
| x | |||
| @@ -202,20 +203,20 @@ y | |||
| > All unique rows from `x` and `y`. | |||
| ```{r union} | |||
| source("R/union.R") | |||
| <<remove-set-ops-ids>> | |||
| ```{r union, export=T} | |||
| animate_union(x, y) | |||
| ``` | |||
|  | |||
| ```{r echo=TRUE} | |||
| union(x, y) | |||
| ``` | |||
|  | |||
| ```{r echo=TRUE} | |||
| animate_union(y, x) | |||
| union(y, x) | |||
| ``` | |||
| @@ -223,12 +224,10 @@ union(y, x) | |||
| > All rows from `x` and `y`, keeping duplicates. | |||
| ```{r union-all} | |||
| source("R/union_all.R") | |||
| <<remove-set-ops-ids>> | |||
| ```{r union-all, echo=T} | |||
| animate_union_all(x, y) | |||
| ``` | |||
|  | |||
| ```{r echo=TRUE} | |||
| @@ -240,12 +239,10 @@ union_all(x, y) | |||
| > Common rows in both `x` and `y`, keeping just unique rows. | |||
| ```{r intersect} | |||
| source("R/intersect.R") | |||
| <<remove-set-ops-ids>> | |||
| ```{r intersect, echo=T} | |||
| animate_intersect(x, y) | |||
| ``` | |||
|  | |||
| ```{r echo=TRUE} | |||
| intersect(x, y) | |||
| @@ -255,20 +252,19 @@ intersect(x, y) | |||
| > All rows from `x` which are not also rows in `y`, keeping just unique rows. | |||
| ```{r setdiff} | |||
| source("R/setdiff.R") | |||
| <<remove-set-ops-ids>> | |||
| ```{r setdiff, echo=T} | |||
| animate_setdiff(x, y) | |||
| ``` | |||
|  | |||
| ```{r echo=TRUE} | |||
| setdiff(x, y) | |||
| ``` | |||
|  | |||
| ```{r echo=TRUE} | |||
| animate_setdiff(y, x) | |||
| setdiff(y, x) | |||
| ``` | |||
| @@ -39,9 +39,33 @@ to expand the animations to include more verbs from the tidyverse. | |||
| [Suggestions are | |||
| welcome\!](https://github.com/gadenbuie/tidy-animated-verbs/issues) | |||
| ## Installing | |||
| The library can be installed with | |||
| ``` r | |||
| # install.package("devtools") | |||
| devtools::install_github("gadenbuie/tidy-animated-verbs") | |||
| ``` | |||
| ## Mutating Joins | |||
| <img src="images/static/png/original-dfs.png" width="480px" /> | |||
| ``` r | |||
| library(tidyAnimatedVerbs) | |||
| x <- data_frame( | |||
| id = 1:3, | |||
| x = paste0("x", 1:3) | |||
| ) | |||
| y <- data_frame( | |||
| id = (1:4)[-3], | |||
| y = paste0("y", (1:4)[-3]) | |||
| ) | |||
| animate_full_join(x, y, by = c("id"), export = "first") | |||
| ``` | |||
| <!-- --> | |||
| ``` r | |||
| x | |||
| @@ -65,7 +89,11 @@ y | |||
| > All rows from `x` where there are matching values in `y`, and all | |||
| > columns from `x` and `y`. | |||
|  | |||
| ``` r | |||
| animate_inner_join(x, y, by = "id") | |||
| ``` | |||
| <!-- --> | |||
| ``` r | |||
| inner_join(x, y, by = "id") | |||
| @@ -81,7 +109,11 @@ inner_join(x, y, by = "id") | |||
| > All rows from `x`, and all columns from `x` and `y`. Rows in `x` with | |||
| > no match in `y` will have `NA` values in the new columns. | |||
|  | |||
| ``` r | |||
| animate_inner_join(x, y, by = "id") | |||
| ``` | |||
| <!-- --> | |||
| ``` r | |||
| left_join(x, y, by = "id") | |||
| @@ -124,7 +156,11 @@ left_join(x, y_extra, by = "id") | |||
| > All rows from y, and all columns from `x` and `y`. Rows in `y` with no | |||
| > match in `x` will have `NA` values in the new columns. | |||
|  | |||
| ``` r | |||
| animate_right_join(x, y, by = "id") | |||
| ``` | |||
| <!-- --> | |||
| ``` r | |||
| right_join(x, y, by = "id") | |||
| @@ -141,7 +177,11 @@ right_join(x, y, by = "id") | |||
| > All rows and all columns from both `x` and `y`. Where there are not | |||
| > matching values, returns `NA` for the one missing. | |||
|  | |||
| ``` r | |||
| animate_full_join(x, y, by = "id") | |||
| ``` | |||
| <!-- --> | |||
| ``` r | |||
| full_join(x, y, by = "id") | |||
| @@ -161,7 +201,11 @@ full_join(x, y, by = "id") | |||
| > All rows from `x` where there are matching values in `y`, keeping just | |||
| > columns from `x`. | |||
|  | |||
| ``` r | |||
| animate_semi_join(x, y, by = "id") | |||
| ``` | |||
| <!-- --> | |||
| ``` r | |||
| semi_join(x, y, by = "id") | |||
| @@ -177,7 +221,7 @@ semi_join(x, y, by = "id") | |||
| > All rows from `x` where there are not matching values in `y`, keeping | |||
| > just columns from `x`. | |||
|  | |||
| <!-- --> | |||
| ``` r | |||
| anti_join(x, y, by = "id") | |||
| @@ -189,7 +233,25 @@ anti_join(x, y, by = "id") | |||
| ## Set Operations | |||
| <img src="images/static/png/original-dfs-set-ops.png" width="480px" /> | |||
| ``` r | |||
| x <- tibble::tribble( | |||
| ~x, ~y, | |||
| "1", "a", | |||
| "1", "b", | |||
| "2", "a" | |||
| ) | |||
| y <- tibble::tribble( | |||
| ~x, ~y, | |||
| "1", "a", | |||
| "2", "b" | |||
| ) | |||
| animate_union(x, y, export = "first") | |||
| ``` | |||
| <!-- --> | |||
| ``` r | |||
| x | |||
| @@ -211,7 +273,7 @@ y | |||
| > All unique rows from `x` and `y`. | |||
|  | |||
| <!-- --> | |||
| ``` r | |||
| union(x, y) | |||
| @@ -224,9 +286,14 @@ union(x, y) | |||
| #> 4 1 a | |||
| ``` | |||
|  | |||
| ``` r | |||
| animate_union(y, x) | |||
| ``` | |||
| <!-- --> | |||
| ``` r | |||
| union(y, x) | |||
| #> # A tibble: 4 x 2 | |||
| #> x y | |||
| @@ -241,7 +308,11 @@ union(y, x) | |||
| > All rows from `x` and `y`, keeping duplicates. | |||
|  | |||
| ``` r | |||
| animate_union_all(x, y) | |||
| ``` | |||
| <!-- --> | |||
| ``` r | |||
| union_all(x, y) | |||
| @@ -259,7 +330,11 @@ union_all(x, y) | |||
| > Common rows in both `x` and `y`, keeping just unique rows. | |||
|  | |||
| ``` r | |||
| animate_intersect(x, y) | |||
| ``` | |||
| <!-- --> | |||
| ``` r | |||
| intersect(x, y) | |||
| @@ -274,7 +349,11 @@ intersect(x, y) | |||
| > All rows from `x` which are not also rows in `y`, keeping just unique | |||
| > rows. | |||
|  | |||
| ``` r | |||
| animate_setdiff(x, y) | |||
| ``` | |||
| <!-- --> | |||
| ``` r | |||
| setdiff(x, y) | |||
| @@ -285,9 +364,14 @@ setdiff(x, y) | |||
| #> 2 2 a | |||
| ``` | |||
|  | |||
| ``` r | |||
| animate_setdiff(y, x) | |||
| ``` | |||
| <!-- --> | |||
| ``` r | |||
| setdiff(y, x) | |||
| #> # A tibble: 1 x 2 | |||
| #> x y | |||
| @@ -0,0 +1,93 @@ | |||
| library(tidyAnimatedVerbs) | |||
| library(here) | |||
| check_and_create <- function(ff) { | |||
| if (!dir.exists(ff)) dir.create(ff, recursive = T) | |||
| } | |||
| x <- data_frame( | |||
| id = 1:3, | |||
| x = paste0("x", 1:3) | |||
| ) | |||
| y <- data_frame( | |||
| id = (1:4)[-3], | |||
| y = paste0("y", (1:4)[-3]) | |||
| ) | |||
| check_and_create(here("images", "static", "png")) | |||
| joins <- c(full_join = animate_full_join, | |||
| inner_join = animate_inner_join, | |||
| left_join = animate_left_join, | |||
| right_join = animate_right_join, | |||
| semi_join = animate_right_join) | |||
| a <- sapply(1:length(joins), function(i) { | |||
| nam <- names(joins)[i] | |||
| nam <- str_replace(nam, "_", "-") | |||
| width <- 7 | |||
| height <- 7 | |||
| gif_ <- joins[[i]](x, y, by = "id") | |||
| first_ <- joins[[i]](x, y, by = "id", export = "first") | |||
| last_ <- joins[[i]](x, y, by = "id", export = "last") | |||
| save_animation(gif_, here("images", paste0(nam, ".gif"))) | |||
| ggsave(here("images", "static", "png", paste0(nam, "-first.png")), first_, | |||
| height = height, width = width) | |||
| ggsave(here("images", "static", "svg", paste0(nam, "-first.svg")), first_, | |||
| height = height, width = width) | |||
| ggsave(here("images", "static", "png", paste0(nam, "-last.png")), last_, | |||
| height = height, width = width) | |||
| ggsave(here("images", "static", "svg", paste0(nam, "-last.svg")), last_, | |||
| height = height, width = width) | |||
| }) | |||
| # instr_extra <- instr %>% slice(c(1, 1:n())) | |||
| # animate_left_join(singer, instr_extra, by = c("name", "band")) # <- NOT WORKING | |||
| x <- tibble::tribble( | |||
| ~x, ~y, | |||
| "1", "a", | |||
| "1", "b", | |||
| "2", "a" | |||
| ) | |||
| y <- tibble::tribble( | |||
| ~x, ~y, | |||
| "1", "a", | |||
| "2", "b" | |||
| ) | |||
| sets <- c(union = animate_union, | |||
| union_all = animate_union_all, | |||
| intersect = animate_intersect, | |||
| setdiff = animate_setdiff) | |||
| a <- sapply(1:length(sets), function(i) { | |||
| nam <- names(sets)[i] | |||
| nam <- str_replace(nam, "_", "-") | |||
| width <- 7 | |||
| height <- 7 | |||
| gif_ <- sets[[i]](x, y, by = "id") | |||
| first_ <- sets[[i]](x, y, by = "id", export = "first") | |||
| last_ <- sets[[i]](x, y, by = "id", export = "last") | |||
| save_animation(gif_, here("images", paste0(nam, ".gif"))) | |||
| ggsave(here("images", "static", "png", paste0(nam, "-first.png")), first_, | |||
| height = height, width = width) | |||
| ggsave(here("images", "static", "svg", paste0(nam, "-first.svg")), first_, | |||
| height = height, width = width) | |||
| ggsave(here("images", "static", "png", paste0(nam, "-last.png")), last_, | |||
| height = height, width = width) | |||
| ggsave(here("images", "static", "svg", paste0(nam, "-last.svg")), last_, | |||
| height = height, width = width) | |||
| }) | |||