需要从Shiny R中的renderPlot访问ggplot_build

时间:2016-09-09 19:43:06

标签: r ggplot2 shiny

经过大量的搜索和研究,我已经确定我不知道如何使这项工作。基本上我想要做的是使用ggplot_build访问我的绘图生成的数据。但是,该图是通过renderPlot在Shiny中生成的,因此我无法在应用程序的其他位置访问它。

所以我最接近的就是声明一个空的reactiveValue并在每次添加我的整个绘图功能。这样,当我需要时,我将能够到达绘图对象,以便从ggplot_build获取数据。

问题在于,虽然它没有抛出任何错误,但在运行我的代码时不会产生任何情节。代码本身在下面,请记住,这是绘图本身的极其简化的示例。完整版本涉及更多可能添加的geom_术语等。任何帮助将不胜感激。提前谢谢。

就我的数据而言,它位于csv中,看起来像这样:

Year,Field,Company,Hybrid,Yield,Moisture,Erect,DoP,DoH,RM,Stand,PPA
1934,Alhambra,Champion,White Pearl,9.1,39.5,NaN,2-May,20-Nov,NaN,NaN,NaN
1944,Galesburg,Pioneer,334,92.7,18.3,99.3,20-May,8-Nov,NaN,NaN,NaN
1945,Sheldon,Funk,G-169,70.6,24.3,39,25-May,8-Nov,NaN,NaN,NaN
1946,Galesburg,Doubet,D-42,100.8,22,94,24-May,8-Nov,NaN,NaN,NaN
1949,DeKalb,Ferris,F-11,51.3,18.4,91,23-May,16-Nov,NaN,72,NaN

代码:

Variable_Extractor <- function(dataset) {
  vars = names(dataset)
  for (i in vars) {
    if (is.factor(dataset[[i]][1]) == TRUE) {
      vars = vars[vars != i]
    }
  }
  return(vars)
}

Identify_Min_Max <- function(dataset, var) { #var must be a string column name
  a = min(dataset[[var]], na.rm = TRUE)
  b = max(dataset[[var]], na.rm = TRUE)
  return(c(a,b))
}

ui <- fluidPage(
  titlePanel('Illinois Yield Trials'),
  
  sidebarLayout(position = 'left',
      sidebarPanel(
        selectInput('var', 'Choose variable', 
                    c('Choose one' = '', Variable_Extractor(agridata))),
        uiOutput('histslider'),
        numericInput('bin_width', 'Enter binwidth', 
                     value = 5, min = 0, max = 1000)),
                
      mainPanel(div(style = "position:relative",
                    plotOutput('plot')))
   )
 )

  server <- function(input, output) {
  
    output$histslider <- renderUI({
      valhist <- Identify_Min_Max(agridata, toString(input$var))
      sliderInput(inputId = 'sliderhist', 
                  label = paste("Select values for ", input$var, sep = ''),
                  min=valhist[1], 
                  max=valhist[2], 
                  value=valhist,
                  sep= '')
  })
  
    plt <- reactiveValues()
  
    output$plot <- renderPlot({
      plt$p <- ggplot()
      agridatasub <- subset(agridata, agridata[[input$var]] >= input$sliderhist[1] & agridata[[input$var]] <= input$sliderhist[2])
      plt$p <- plt$p + geom_histogram(data=agridatasub, aes_string(x=input$var), binwidth = input$bin_width, 
               color = 'black', fill = 'gray75')
      return(plt$p)
    })
  
  }

  shinyApp(ui=ui, server=server)

1 个答案:

答案 0 :(得分:1)

您不需要那样使用reactiveValues,您可以:

plt <- reactive({
agridatasub <- subset(agridata, agridata[[input$var]] >= input$sliderhist[1] & agridata[[input$var]] <= input$sliderhist[2])
  ggplot() + geom_histogram(data=agridatasub, aes_string(x=input$var), binwidth = input$bin_width, 
                                  color = 'black', fill = 'gray75')  
})
output$plot <- renderPlot({
  plt()
})

使用iris代替数据集的完整示例:

Variable_Extractor <- function(dataset) {
  vars = names(dataset)
  for (i in vars) {
    if (is.factor(dataset[[i]][1]) == TRUE) {
      vars = vars[vars != i]
    }
  }
  return(vars)
}

Identify_Min_Max <- function(dataset, var) { #var must be a string column name
  a = min(dataset[[var]], na.rm = TRUE)
  b = max(dataset[[var]], na.rm = TRUE)
  return(c(a,b))
}
library(shiny)
ui <- fluidPage(
  titlePanel('Illinois Yield Trials'),

  sidebarLayout(position = 'left',
                sidebarPanel(
                  selectInput('var', 'Choose variable', 
                              c('Choose one' = '', Variable_Extractor(iris))),
                  uiOutput('histslider'),
                  numericInput('bin_width', 'Enter binwidth', 
                               value = 5, min = 0, max = 1000)),

                mainPanel(div(style = "position:relative",
                              plotOutput('plot')),
                          verbatimTextOutput("test"))
  )
)

server <- function(input, output) {

  output$histslider <- renderUI({
    valhist <- Identify_Min_Max(iris, toString(input$var))
    sliderInput(inputId = 'sliderhist', 
                label = paste("Select values for ", input$var, sep = ''),
                min=valhist[1], 
                max=valhist[2], 
                value=valhist,
                sep= '')
  })

  plt <- reactive({
    req(input$var)
    irissub <- subset(iris, iris[[input$var]] >= input$sliderhist[1] & iris[[input$var]] <= input$sliderhist[2])

    ggplot()  + geom_histogram(data=irissub, aes_string(x=input$var), binwidth = input$bin_width, 
                                    color = 'black', fill = 'gray75')
  })

  output$plot <- renderPlot({

    return(plt())
  })

  output$test <- renderPrint({
    req(input$var)
    str(ggplot_build(plt()))
  })

}

shinyApp(ui=ui, server=server)