From ea7d89aa59ed921b867b3cd51e95e2e2d0cb8778 Mon Sep 17 00:00:00 2001 From: Jonathan Sidi Date: Fri, 2 Mar 2018 16:43:53 -0500 Subject: [PATCH] move from add_ggplot to ggplot_add for upcoming ggplot release --- DESCRIPTION | 11 +-- LICENSE | 2 + {R => Miscellaneous/Utilities}/add_ggplot.R | 0 {R => Miscellaneous/Utilities}/add_theme.R | 0 NAMESPACE | 4 +- R/as.gglist.R | 40 +++------ R/compare.R | 11 ++- R/print.gglist.R | 1 + inst/examples/SingleFile/DESCRIPTION | 7 ++ inst/examples/SingleFile/app.R | 98 +++++++++++++++++++++ inst/examples/app.R | 42 --------- man/grapes-greater-than-grapes.Rd | 37 -------- man/merge_element.Rd | 36 -------- 13 files changed, 139 insertions(+), 150 deletions(-) create mode 100644 LICENSE rename {R => Miscellaneous/Utilities}/add_ggplot.R (100%) rename {R => Miscellaneous/Utilities}/add_theme.R (100%) create mode 100644 inst/examples/SingleFile/DESCRIPTION create mode 100644 inst/examples/SingleFile/app.R delete mode 100644 inst/examples/app.R delete mode 100644 man/merge_element.Rd diff --git a/DESCRIPTION b/DESCRIPTION index 8e71df1..58584f7 100644 --- a/DESCRIPTION +++ b/DESCRIPTION @@ -1,14 +1,14 @@ Package: ggedit Type: Package Title: Interactive 'ggplot2' Layer and Theme Aesthetic Editor -Version: 0.2.6 -Date: 2017-10-01 +Version: 0.2.6.1 +Date: 2018-02-10 Author: Jonathan Sidi [aut, cre] Maintainer: Jonathan Sidi Description: Interactively edit 'ggplot2' layer and theme aesthetics definitions. Depends: R (>= 2.3.0), - ggplot2 (>= 2.2.1) + ggplot2 Imports: dplyr (>= 0.5), shiny, @@ -29,10 +29,11 @@ Imports: Suggests: testthat, covr -License: GPL-2 | GPL-3 +Remotes: tidyverse/ggplot2#2405 +License: MIT + file LICENSE URL: https://github.com/metrumresearchgroup/ggedit BugReports: https://github.com/metrumresearchgroup/ggedit/issues LazyData: true NeedsCompilation: no Packaged: 2017-01-31 14:00:00 UTC; Yoni -RoxygenNote: 6.0.1.9000 +RoxygenNote: 6.0.1 diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..b43acd3 --- /dev/null +++ b/LICENSE @@ -0,0 +1,2 @@ +YEAR: 2018 +COPYRIGHT HOLDER: Jonathan Sidi diff --git a/R/add_ggplot.R b/Miscellaneous/Utilities/add_ggplot.R similarity index 100% rename from R/add_ggplot.R rename to Miscellaneous/Utilities/add_ggplot.R diff --git a/R/add_theme.R b/Miscellaneous/Utilities/add_theme.R similarity index 100% rename from R/add_theme.R rename to Miscellaneous/Utilities/add_theme.R diff --git a/NAMESPACE b/NAMESPACE index a993bbd..b7496ae 100644 --- a/NAMESPACE +++ b/NAMESPACE @@ -2,8 +2,6 @@ S3method("+",gg) S3method("-",gg) -S3method(merge_element,default) -S3method(merge_element,element) S3method(print,ggedit) S3method(print,gglist) S3method(summary,ggedit) @@ -26,7 +24,6 @@ export(ggedit_opts_current) export(gggsave) export(is.ggedit) export(layersList) -export(merge_element) export(proto_features) export(remove_geom) export(rgg) @@ -35,6 +32,7 @@ export(vplayout) import(dplyr) import(ggplot2) import(shiny) +importFrom(ggplot2,ggplot_add) importFrom(graphics,plot) importFrom(miniUI,gadgetTitleBar) importFrom(miniUI,miniContentPanel) diff --git a/R/as.gglist.R b/R/as.gglist.R index b1ea297..559839c 100644 --- a/R/as.gglist.R +++ b/R/as.gglist.R @@ -6,11 +6,11 @@ #' @keywords internal as.gglist <- function(p) { cl <- c("ggedit", "gglist", "gg", "ggplot") - + if (inherits(p, "ggmatrix")) { cl <- c(cl, "ggmatrix") } - + structure(p, class = cl) } @@ -49,33 +49,21 @@ as.gglist <- function(p) { } #' @export -#' @import ggplot2 +#' @importFrom ggplot2 ggplot_add #' @importFrom plyr llply "+.gg" <- function(e1, e2) { - # check for na names in themes - - if (inherits(e1, "gglist")) { - e3 <- as.gglist( - plyr::llply(e1, function(t1) { - add_ggplot(t1, e2) - }) - ) + if(inherits(e1,'gglist')){ + + e3 <- plyr::llply(e1,ggplot_add,object=e2) + + attributes(e3) <- attributes(e1) + } else { - if (inherits(e1, "theme")) { - idx <- which(is.na(names(e2))) - - if (length(idx) > 0) { - e2[idx] <- NULL - } - - e3 <- add_theme(e1, e2) - } else { - e3 <- add_ggplot(e1, e2) - } + + e3 <- ggplot_add(e2,e1) + } - - attributes(e3) <- attributes(e1) - + e3 -} +} \ No newline at end of file diff --git a/R/compare.R b/R/compare.R index e39a6a2..b34c60f 100644 --- a/R/compare.R +++ b/R/compare.R @@ -50,6 +50,7 @@ compare <- function(e1, e2, verbose=TRUE) { dfOut$class <- ifelse(dfOut$call == "unit", "unit", dfOut$class) dfOut$value <- ifelse(grepl("#", dfOut$value), gsub("#", "'#'*", dfOut$value), dfOut$value) + #dfOut$value <- ifelse(grepl("^[.]$", dfOut$value), NA, dfOut$value) dfOut$value <- ifelse(grepl("TRUE|FALSE|[=]", dfOut$value), paste0("'", dfOut$value, "'"), dfOut$value) dfOut$call <- ifelse(dfOut$call %in% c("character", "unit", dfOut$subTheme), "", dfOut$call) dfOut$element <- ifelse(dfOut$element == dfOut$subTheme, "", dfOut$element) @@ -59,15 +60,19 @@ compare <- function(e1, e2, verbose=TRUE) { d <- objDF %>% select_("idTheme:value", "subTheme") %>% - reshape2::dcast(Theme + subTheme + element + name~idTheme, value.var = "value") %>% + reshape2::dcast(Theme + subTheme + element + name~idTheme, value.var = "value") %>% #,fill='.' dplyr::filter_(~compare != base) %>% dplyr::left_join(objDF, by = c("Theme", "subTheme", "element", "name")) %>% dplyr::filter_(~idTheme == "compare") %>% dplyr::select_("Theme", "subTheme", "call", "element", value = "compare") d$Theme <- as.character(d$Theme) + d <- d[d$value != ".", ] d$value[grepl("[^0-9]", d$value)] <- paste0("'", d$value[grepl("[^0-9]", d$value)], "'") + + #d$value[d$value== "."] <- NA + #d$value[grepl("[^0-9]", d$value)&!grepl('^(TRUE|FALSE)$',d$value)] <- paste0("'", d$value[grepl("[^0-9]", d$value)&!grepl('^(TRUE|FALSE)$',d$value)], "'") x1 <- d %>% dplyr::group_by_("Theme", "subTheme", "call") %>% @@ -75,6 +80,10 @@ compare <- function(e1, e2, verbose=TRUE) { dplyr::ungroup() x1$y <- ifelse(x1$call == "", gsub("=", "", x1$y), paste0(x1$call, "(", x1$y, ")")) + + # x1$y <- gsub("''TRUE''","TRUE",x1$y) + # x1$y <- gsub("''FALSE''","FALSE",x1$y) + x1$x <- ifelse(x1$subTheme == "", x1$Theme, paste(x1$Theme, x1$subTheme, sep = ".")) out <- paste0("theme(", paste0(paste(x1$x, x1$y, sep = "="), collapse = ","), ")") diff --git a/R/print.gglist.R b/R/print.gglist.R index d8dcee1..d45c03c 100644 --- a/R/print.gglist.R +++ b/R/print.gglist.R @@ -8,6 +8,7 @@ print.gglist <- function(x, ...) plyr::l_ply(x, print.ggplot, ...) print.ggplot <- function(x, newpage = is.null(vp), vp = NULL, ...) { + set_last_plot(x) if (newpage) { grid.newpage() diff --git a/inst/examples/SingleFile/DESCRIPTION b/inst/examples/SingleFile/DESCRIPTION new file mode 100644 index 0000000..5b7ecba --- /dev/null +++ b/inst/examples/SingleFile/DESCRIPTION @@ -0,0 +1,7 @@ +Title: ggedit Shiny Module +Author: Metrum Research Group +AuthorUrl: https://github.com/metrumresearchgroup/ggedit +License: GPL-3 +DisplayMode: Showcase +Tags: ggplot2 +Type: Shiny \ No newline at end of file diff --git a/inst/examples/SingleFile/app.R b/inst/examples/SingleFile/app.R new file mode 100644 index 0000000..9add96a --- /dev/null +++ b/inst/examples/SingleFile/app.R @@ -0,0 +1,98 @@ +library(ggedit) +library(shinyAce) + +ui <- fluidPage( + tags$head(tags$script(' var setInitialCodePosition = function() { setCodePosition(false, false); }; ')), + conditionalPanel("input.tbPanel=='a'", + sidebarPanel( + h3('Static Plots'), + p('This is a standard rendered ggplot in shiny.'), + p('It is an image that can not be edited. You can drag it and even right click and save it.'), + p('But what if you wanted to change something about the aesthetics of the plot or the theme while the app is running?'), + p('Move to next tab ...')) + ), + conditionalPanel("input.tbPanel=='b'", + sidebarPanel( + h3('Interactive Plot Editing'), + shiny::HTML('Short video clip showing how to use the module'), + p('Using ggedit modules you can edit plots (to the right) and see the updated script (below) being generated as you work!'), + p(), + p('This tab gives a basic usage example of working with one plot in the module'), + p('To work on multiple plots in a layout at the same time go to the next tab ...'), + h4('Layer Editing'), + p('Click on the "Update Plot Layer" link and a pop up window will appear with aesthetics relevant to the layer to edit'), + p(), + h4('Theme Editing'), + p('Click on the "Update Plot Theme" link and a pop up window will appear with all the theme elements to edit'), + p(), + h4('Live Script Comparisons'), + p(paste0('Click on the "View Layer Code" link and a text window will expand to show the original script that was used to ', + 'create the plot layer and the new script needed to create the layer with the new aesthetic settings.')), + hr(), + p(), + h4('Shiny Observers'), + p(paste0('The ggedit modules have observers built in for shiny to use, so any changes can be acted upon within the app as the user is editing.', + 'This can be used for auto-updating reactive documents when collaborating with many researchers or logging user activity on a company server.')), + uiOutput('x1'), + uiOutput('x2')) + ), + conditionalPanel("input.tbPanel=='c'", + sidebarPanel( + h3('Editing Multiple Plots'), + shiny::HTML('Short video clip showing how to use the module'), + h4('Choosing a plot'), + p('When working with multiple plots use the dropdown menu to the plot you want to edit'), + h4('Choosing a layer'), + p('When choosing the plot the layers found it in will update in the radio buttons'), + p('If there is more than one layer in the plot choose the layer you want to edit'), + p(), + p('Click on the "Update Plot Layer" link and a pop up window will appear with aesthetics relevant to the layer to edit'), + p(), + h4('Sharing Themes'), + p('After choosing a plot to edit, click on the "Update Plot Theme" link and a pop up window will appear with all the theme elements to edit'), + p('You can share themes between plots in the layout using the "Update Grid Theme" link'), + p('You can also set the R session theme by selecting the "Update Global Theme" link') + )), + mainPanel( + tabsetPanel(id = 'tbPanel', + tabPanel('renderPlot/plotOutput',value = 'a', + plotOutput('p') + ), + tabPanel('ggEdit/ggEditUI',value = 'b', + ggEditUI("pOut1")), + tabPanel('ggEdit/ggEditUI with lists of plots',value = 'c',ggEditUI("pOut2")) + ) + ) + +) + +server <- function(input, output,session) { + p1=iris%>%ggplot(aes(x=Sepal.Length,y=Sepal.Width,colour=Species))+geom_point() + p2=iris%>%ggplot(aes(x=Sepal.Length,y=Sepal.Width))+geom_line()+geom_point((aes(colour=Petal.Width))) + p3=list(p1=p1,p2=p2) + + output$p<-renderPlot({p1}) + outp1<-callModule(ggEdit,'pOut1',obj=reactive(list(p1=p1))) + outp2<-callModule(ggEdit,'pOut2',obj=reactive(p3),showDefaults=T,height=300) + + output$x1<-renderUI({ + layerTxt=outp1()$UpdatedLayerCalls$p1[[1]] + aceEditor(outputId = 'layerAce',value=layerTxt, + mode = "r", theme = "chrome", + height = "100px", fontSize = 12,wordWrap = T) + }) + + output$x2<-renderUI({ + + themeTxt=outp1()$UpdatedThemeCalls$p1 + + if(is.null(themeTxt)) themeTxt <- ' ' + + aceEditor(outputId = 'themeAce',value=themeTxt, + mode = "r", theme = "chrome", + height = "100px", fontSize = 12,wordWrap = T) + }) + +} + +shinyApp(ui, server) \ No newline at end of file diff --git a/inst/examples/app.R b/inst/examples/app.R deleted file mode 100644 index 65c89f1..0000000 --- a/inst/examples/app.R +++ /dev/null @@ -1,42 +0,0 @@ -library(ggedit) -library(shinyAce) -ui <-fluidPage( - conditionalPanel("input.tbPanel=='b'", - sidebarPanel(uiOutput('x1'),uiOutput('x2')) - ), - mainPanel( - tabsetPanel(id = 'tbPanel', - tabPanel('renderPlot/plotOutput',value = 'a',plotOutput('p')), - tabPanel('ggEdit/ggEditUI',value = 'b',ggEditUI("pOut1")), - tabPanel('ggEdit/ggEditUI with lists of plots',value = 'c',ggEditUI("pOut2")) - ) - ) - -) - -server <- function(input, output,session) { - p1=iris%>%ggplot(aes(x=Sepal.Length,y=Sepal.Width,colour=Species))+geom_point() - p2=iris%>%ggplot(aes(x=Sepal.Length,y=Sepal.Width,colour=Petal.Width))+geom_line()+geom_point() - p3=list(p1=p1,p2=p2) - - output$p<-renderPlot({p1}) - outp1<-callModule(ggEdit,'pOut1',obj=reactive(list(p1=p1))) - outp2<-callModule(ggEdit,'pOut2',obj=reactive(p3),showDefaults=T,height=300) - - output$x1<-renderUI({ - layerTxt=outp1()$UpdatedLayerCalls$p1[[1]] - aceEditor(outputId = 'layerAce',value=layerTxt, - mode = "r", theme = "chrome", - height = "100px", fontSize = 12,wordWrap = T) - }) - - output$x2<-renderUI({ - themeTxt=outp1()$UpdatedThemeCalls$p1 - aceEditor(outputId = 'themeAce',value=themeTxt, - mode = "r", theme = "chrome", - height = "100px", fontSize = 12,wordWrap = T) - }) - -} - -shinyApp(ui, server) diff --git a/man/grapes-greater-than-grapes.Rd b/man/grapes-greater-than-grapes.Rd index 930bb85..0ccaba6 100644 --- a/man/grapes-greater-than-grapes.Rd +++ b/man/grapes-greater-than-grapes.Rd @@ -86,43 +86,6 @@ by magrittr. } -\examples{ -# Basic use: -iris \%>\% head - -# Use with lhs as first argument -iris \%>\% head(10) - -# Using the dot place-holder -"Ceci n'est pas une pipe" \%>\% gsub("une", "un", .) - -# When dot is nested, lhs is still placed first: -sample(1:10) \%>\% paste0(LETTERS[.]) - -# This can be avoided: -rnorm(100) \%>\% {c(min(.), mean(.), max(.))} \%>\% floor - -# Lambda expressions: -iris \%>\% -{ - size <- sample(1:10, size = 1) - rbind(head(., size), tail(., size)) -} - -# renaming in lambdas: -iris \%>\% -{ - my_data <- . - size <- sample(1:10, size = 1) - rbind(head(my_data, size), tail(my_data, size)) -} - -# Building unary functions with \%>\% -trig_fest <- . \%>\% tan \%>\% cos \%>\% sin - -1:10 \%>\% trig_fest -trig_fest(1:10) -} \seealso{ \code{\link{\%<>\%}}, \code{\link{\%T>\%}}, \code{\link{\%$\%}} } diff --git a/man/merge_element.Rd b/man/merge_element.Rd deleted file mode 100644 index 257bfa1..0000000 --- a/man/merge_element.Rd +++ /dev/null @@ -1,36 +0,0 @@ -% Generated by roxygen2: do not edit by hand -% Please edit documentation in R/add_theme.R -\name{merge_element} -\alias{merge_element} -\alias{merge_element.default} -\alias{merge_element.element} -\title{Merge a parent element into a child element} -\usage{ -merge_element(new, old) - -\method{merge_element}{default}(new, old) - -\method{merge_element}{element}(new, old) -} -\arguments{ -\item{new}{The child element in the theme hierarchy} - -\item{old}{The parent element in the theme hierarchy} -} -\value{ -A modified version of `new` updated with the properties of -`old` -} -\description{ -This is a generic and element classes must provide an implementation of this -method -} -\examples{ -new <- element_text(colour = "red") -old <- element_text(colour = "blue", size = 10) - -# Adopt size but ignore colour -merge_element(new, old) - -} -\keyword{internal}