0

I am trying to convert ggplot code which is repetitive into function; I have done almost but only concern is I need to pass the application as a variable.

Here is the plot code where I used column called Application inside the summarise and mutate. The challenge is same column has been used for y axis

ggplot_common_function <- function(data,x,y,z) {
  Removestring(ggplotly(
    data %>%
      group_by(m_year,status) %>%
        summarise(Applications = sum(Applications)) %>%
        mutate(total_sum = sum(Applications)) %>% 
        ggplot(mapping = aes({{x}},{{y}},text = paste(total_sum))) +
          geom_col(aes(fill = {{z}})) + 
          theme_classic() +
          theme(axis.line.y = element_blank(), 
                axis.ticks = element_blank(), 
                legend.position = "bottom") +
          labs(x = "", y = "Agreements Values (In Lakhs)", fill = "") +
          theme(axis.title.y = element_text(size = 8)) +
          scale_fill_manual(values = c("#1F7A3F", "#70B821")) +
          scale_y_continuous(labels = function(x) format(x, scientific = FALSE), 
                             expand = expansion(mult = c(0,.3)), 
                             breaks = integer_breaks()), 
                             tooltip = c("text")) %>% 
          layout(legend = list(orientation = "h", x = 0.1, y = -0.2, 
                 font = list( family = 'Arial', size = 10, color = 'black')), 
                 xaxis = x_labels, yaxis = y_labels) %>%
          config(displaylogo = FALSE, modeBarButtonsToRemove = list(
                      'sendDataToCloud', 'autoScale2d', 'resetScale2d', 
                      'toggleSpikelines', 'hoverClosestCartesian', 'hoverCompareCartesian', 
                      'zoom2d', 'pan2d', 'select2d', 
                      'lasso2d', 'zoomIn2d', 'zoomOut2d'))
  )
}
                      
ggplot_common_function(data,m_year,Applications,status)

To run the above code there is some pre function

integer_breaks <- function(n = 5, ...) {
  fxn <- function(x) {
    breaks <- floor(pretty(x, n, ...))
    names(breaks) <- attr(breaks, "labels")
    breaks
  }
  return(fxn)
}

Removestring = function(d){
  for (i in 1:length(d$x$data)){
    if (!is.null(d$x$data[[i]]$name)){
      d$x$data[[i]]$name =  gsub("\\(","",str_split(d$x$data[[i]]$name,",")[[1]][1])
    }
  }
  return(d)
}

Plan <- "#288D55"
multicolor = c("#135391","#0098DB","#828388","#231F20","#C41330","#698714","#162FBF","#F36717","#BD00FF")
x_labels = list(tickangle = -45,tickfont = list(family = "Arial",size = 10,color = "black",face="bold"))
y_labels = list(tickfont = list(family = "Arial",size = 10,color = "black",face="bold"))

Any suggestions would be appreciated

Leonardo
  • 2,439
  • 33
  • 17
  • 31
Nazima
  • 93
  • 7

1 Answers1

3

This is basically a question related to programming in dplyr. To achieve your desired result and get rid of hardcoding the column names in your function and use x, y, z instead you could make use of the {{ curly-curly operator as you did in the ggplot code and the special assignment operator :=. Additionally instead of wrapping all your code inside ggplotly you proceed in steps. Do the data wrangling, make your ggplot and finally pass it to ggplotly:

library(plotly)
library(dplyr)
library(stringr)

ggplot_common_function <- function(data, x, y, z) {
  data <- data %>%
    group_by({{ x }}, {{ z }}) %>%
    summarise({{ y }} := sum({{ y }})) %>%
    mutate(total_sum = sum({{ y }}))

  p <- ggplot(data, mapping = aes({{ x }}, {{ y }}, text = paste(total_sum))) +
    geom_col(aes(fill = {{ z }})) +
    theme_classic() +
    theme(axis.line.y = element_blank(), axis.ticks = element_blank(), legend.position = "bottom") +
    labs(x = "", y = "Agreements Values (In Lakhs)", fill = "") +
    theme(axis.title.y = element_text(size = 8)) +
    scale_fill_manual(values = c("#1F7A3F", "#70B821")) +
    scale_y_continuous(labels = function(x) format(x, scientific = FALSE), expand = expansion(mult = c(0, .3)), breaks = integer_breaks())

  ggp <- ggplotly(p, tooltip = c("text")) %>%
    layout(legend = list(orientation = "h", x = 0.1, y = -0.2, font = list(family = "Arial", size = 10, color = "black")), xaxis = x_labels, yaxis = y_labels) %>%
    config(displaylogo = FALSE, modeBarButtonsToRemove = list("sendDataToCloud", "autoScale2d", "resetScale2d", "toggleSpikelines", "hoverClosestCartesian", "hoverCompareCartesian", "zoom2d", "pan2d", "select2d", "lasso2d", "zoomIn2d", "zoomOut2d"))

  Removestring(ggp)
}

ggplot_common_function(data, m_year, Applications, status)
#> `summarise()` has grouped output by 'm_year'. You can override using the
#> `.groups` argument.

stefan
  • 90,330
  • 6
  • 25
  • 51