2016-08-26 27 views
6

Kullanıcının bir dağılım taslağı oluşturmasına, arsadaki noktaların bir alt kümesini seçmesine izin veren küçük bir uygulama yazmaya çalışıyorum, daha sonra yalnızca seçili noktaları olan bir tabloyu .csv biçiminde çıkarıyorum. Sayfayı nasıl çalıştıracağım ve brushedPoints kullanarak noktaları nasıl seçeceğimi anladım. Seçili noktalara sahip tablo görünür ancak İndir düğmesine bastığımda, "shinyoutput nesnesinden nesnelerin okunmasına izin verilmiyor" hatası. belirir. Ekranda görsel olarak görebileceğim bir tabloyu .csv olarak yükleyemiyorum mu? Öyleyse, bir geçici çözüm var mı?Parlak çıktı nesnesinden nesne okumaya izin verilmiyor mu?

Aşağıdaki iris veri kümesini kullanarak sorunu yeniden oluşturdum. Gösterilen satırların tablosunu neden indiremediğimi anlatan yardımlar büyük ölçüde takdir edilecektir.

data(iris) 

ui <- basicPage(
    plotOutput("plot1", brush = "plot_brush"), 
    verbatimTextOutput("info"),mainPanel(downloadButton('downloadData', 'Download')) 
) 


server <- function(input, output) { 
    output$plot1 <- renderPlot({ 
ggplot(iris,aes(x=Sepal.Width,y=Sepal.Length)) + 
    geom_point(aes(color=factor(Species))) + 
    theme_bw() 
    }) 

    output$info <- renderPrint({ 
brushedPoints(iris, input$plot_brush, xvar = "Sepal.Width", yvar = "Sepal.Length") 
    }) 

    output$downloadData <- downloadHandler(
     filename = function() { 
     paste('SelectedRows', '.csv', sep='') }, 
     content = function(file) { 
     write.csv(output$info, file) 
     } 
) 

} 


shinyApp(ui, server) 

cevap

10

Sorun, çıktı nesnesinin tüm web görüntüleme öğelerini de oluşturmasıdır. Bunun yerine, verileri indirmek için ayrı ayrı çekmeniz gerekir. İndirme kodunda ikinci bir çağrı ile brushedPoints yapabilirsiniz. Bununla birlikte, daha iyi, sadece bir kez yapmak için bir reactive() işlevini kullanmak, sonra ihtiyacınız olan her yerde onu aramak. . İşte bu işi yapmak için kodunu değiştirmek şekli şöyledir:, açıkça brushedPoints So içinde xvar ve yvar ayarlamak gerekmez

data(iris) 

ui <- basicPage(
    plotOutput("plot1", brush = "plot_brush"), 
    verbatimTextOutput("info"),mainPanel(downloadButton('downloadData', 'Download')) 
) 


server <- function(input, output) { 
    output$plot1 <- renderPlot({ 
    ggplot(iris,aes(x=Sepal.Width,y=Sepal.Length)) + geom_point(aes(color=factor(Species))) + theme_bw() 
    }) 


    selectedData <- reactive({ 
    brushedPoints(iris, input$plot_brush) 
    }) 

    output$info <- renderPrint({ 
    selectedData() 
    }) 

    output$downloadData <- downloadHandler(
    filename = function() { 
     paste('SelectedRows', '.csv', sep='') }, 
    content = function(file) { 
     write.csv(selectedData(), file) 
    } 
) 

} 


shinyApp(ui, server) 

(Not, ggplot2, ben esnekliğini artırmak için buradan kaldırıldı kod.)

shiny'daki "kement" tarzı serbest çizim yeteneğinin farkında değilim (yine de bir hafta verin, sürekli olarak eğlenceli araçlar ekliyorlar). Bununla birlikte, kullanıcının birden fazla bölge seçmesine ve/veya tek tek noktalara tıklamasına izin vererek davranışı taklit edebilirsiniz. Sunucu mantığı çok daha karışıktır, çünkü tekrar tekrar kullanabilmek için sonuçları bir reactiveValues nesnesinde saklamanız gerekir. Bir arsadaki noktaları seçmeme izin verin ve diğer grafiklerde onları vurgulayın/kaldırın. Bu, burada ihtiyacınız olandan daha karmaşıktır, ancak aşağıdakiler işe yarayacaktır. Diğer düğmeleri/mantığı eklemek (örneğin, seçimleri "sıfırlamak" için) isteyebilirsiniz, ancak bunun işe yarayacağını düşünüyorum. Seçilmiş olanları takip etmenize izin vermek için seçimin bir görüntüsünü arsaya ekledim.

data(iris) 

ui <- basicPage(
    plotOutput("plot1", brush = "plot_brush", click = "plot_click") 
    , actionButton("toggle", "Toggle Seletion") 
    , verbatimTextOutput("info") 
    , mainPanel(downloadButton('downloadData', 'Download')) 
) 


server <- function(input, output) { 
    output$plot1 <- renderPlot({ 

    ggplot(withSelected() 
      , aes(x=Sepal.Width 
       , y=Sepal.Length 
       , color=factor(Species) 
       , shape = Selected)) + 
     geom_point() + 
     scale_shape_manual(
     values = c("FALSE" = 19 
        , "TRUE" = 4) 
     , labels = c("No", "Yes") 
     , name = "Is Selected?" 
    ) + 
     theme_bw() 
    }) 

    # Make a reactive value -- you can set these within other functions 
    vals <- reactiveValues(
    isClicked = rep(FALSE, nrow(iris)) 
) 


    # Add a column to the data to ease plotting 
    # This is really only necessary if you want to show the selected points on the plot 
    withSelected <- reactive({ 
    data.frame(iris 
       , Selected = vals$isClicked) 
    }) 



    # Watch for clicks 
    observeEvent(input$plot_click, { 

    res <- nearPoints(withSelected() 
         , input$plot_click 
         , allRows = TRUE) 

    vals$isClicked <- 
     xor(vals$isClicked 
      , res$selected_) 
    }) 


    # Watch for toggle button clicks 
    observeEvent(input$toggle, { 
    res <- brushedPoints(withSelected() 
         , input$plot_brush 
         , allRows = TRUE) 

    vals$isClicked <- 
     xor(vals$isClicked 
      , res$selected_) 
    }) 

    # pull the data selection here 
    selectedData <- reactive({ 
    iris[vals$isClicked, ] 
    }) 

    output$info <- renderPrint({ 
    selectedData() 
    }) 

    output$downloadData <- downloadHandler(
    filename = function() { 
     paste('SelectedRows', '.csv', sep='') }, 
    content = function(file) { 
     write.csv(selectedData(), file) 
    } 
) 

} 


shinyApp(ui, server) 
+0

Mark, bu mükemmel çalıştı! Reaktif fonksiyonu özellikle yararlıdır, dikkatimi çeken için teşekkürler. Çok teşekkürler. – KrisF

+0

İşaret, bana, brushedPoints seçeneğinin yalnızca kullanıcının bir dikdörtgenin içindeki noktaları seçmesine izin verdiğini fark ettim. "Kement" seçeneği var mı? Ben etrafında aradı ama Plot.ly içinde yukarıdaki senaryoda büyük bir yeniden yazma gerektirecek "lasso" seçeneği dışında bir şey bulamadım. – KrisF

+0

Doğrudan değil, farkında olduğum. Ancak, birden fazla seçimin nasıl yapıldığını gösteren bir düzenleme ekledim. Bu, size sonunda aynı davranışı verebilir. –

İlgili konular