【发布时间】:2017-12-07 21:52:21
【问题描述】:
这是要求。
1)我需要浏览并上传一个 excel 文件(带有包 readxl),该文件用于得出一些我需要在闪亮窗口中显示为不同表格输出的计算
2) 手动编辑上传文件中的一些数据,它应该会自动反映在显示的结果中
3) 我们应该可以下载编辑后的文件了。
到目前为止我已经写了。我在输入数据中有列 ID、曝光和频率。对于每个 ID,我需要使用将显示的相应曝光和频率来计算一个变量。我需要使用 ID 手动编辑频率和曝光(这是唯一的)。我添加了一个“更新”按钮。但改变不是永久的。一旦我再次单击更新按钮,它就会返回
library(shiny)
ui = fluidPage(
titlePanel("HEllo world"),
sidebarLayout(
sidebarPanel(
fileInput('file1', 'Choose xlsx file',
accept = c(".xlsx")),
actionButton("go", "update"),
numericInput('NewVal', 'Enter new Frequency',NULL),
numericInput('NewExp', 'Enter new Exposure',NULL)),
mainPanel(
textInput('ID', 'Enter ID'),
dataTableOutput('contents')
)))
server = function(input,output){
ef <- eventReactive(input$go, {
infile <- input$file1
if(is.null(infile))
return(NULL)
file.rename(infile$datapath,paste(infile$datapath, ".xlsx", sep=""))
data<-read_excel(paste(infile$datapath, ".xlsx", sep=""), 1)
if(input$ID!="" && input$go>0){
for( i in 1:nrow(data)){
if( input$ID == data$'ID'[i]){
if(!is.na(input$NewVal)){
data$' Frequency'[i] <- input$NewVal
}
if(!is.na(input$NewExp)){
data$'Exposure'[i] <- input$NewExp
}
}}}
data
}, ignoreNULL = FALSE)
output$contents <- renderDataTable({ef()})}
shinyApp(ui,server)
更新!:根据一个答案,我对我的代码进行了一些更改。新代码似乎运行良好。这是工作代码,供任何可能在同一问题上需要帮助的人使用。
ui = fluidPage(
titlePanel("HEllo world"),
sidebarLayout(
sidebarPanel(
fileInput('file1', 'Choose xlsx file',
accept = c(".xlsx")),
actionButton("go", "update"),
numericInput('NewVal', 'Enter new Frequency',NULL),
numericInput('NewExp', 'Enter new Exposure',NULL)),
mainPanel(
textInput('ID', 'Enter ID'),
tableOutput('contents')
)))
server = function(input,output){
# Reactive value to save input data frame for use elsewhere
original <- reactiveValues()
observeEvent(input$file1, {
theFile <- input$file1
if(is.null(theFile)) {
return(NULL)}
**file.rename(theFile$datapath,paste(theFile$datapath, ".xlsx", sep=""))**
original$oldData <- read_excel(paste(theFile$datapath, ".xlsx", sep = ""), 1)
})
observeEvent(input$go, {
original$newData <- original$oldData
if(input$ID !="") {
for( i in 1:nrow(original$oldData)){
if( input$ID == original$oldData$'ID'[i]){
if(!is.na(input$NewVal)){
original$newData$'Frequency'[i] <- input$NewVal
}
if(!is.na(input$NewExp)){
original$newData$'Exposure'[i] <- input$NewExp
}
}
}
**original$oldData<-original$newData** }
})
output$contents <- renderTable({
if(!is.null(original$newData)) {
original$newData}
else {
original$oldData}
})
}
shinyApp(ui = ui, server = server)
【问题讨论】:
-
对象
dat在您的代码中来自哪里? “数据”有什么区别? -
我猜这个问题是因为在一个函数中你正在读取文件并更新它。制作 2 个功能,首先您读取文件并存储它。将该函数传递给您的第二个函数,您将在其中进行更新,然后显示输出。
-
@agenis 抱歉,它的数据不是 dat。一样的。数据包含“ID”、“曝光”和“频率”
-
好几句话:首先你不需要一个操作按钮,而是一个内置的
submitButton,这正是这个目的。然后我想你可以摆脱你的 for 循环,如果它只是在那里找到要更改的行......你应该使用使用reactiveValues的结构。有一些类似这样的问题已回答:stackoverflow.com/a/30502250/3871924 -
抱歉,如果我在错误的树上吠叫,但您是否考虑过使用
rhandsontable?它提供excel-likeGUI,并且(如果设置)允许单元级编辑。它可能不会使代码变得更简单(当然,您需要知道如何处理更改的单元格),但至少为用户提供了更好的体验。