入力としてマトリックスデータを取得し、そのいくつかの操作に基づいてテーブルを出力として返す、光沢のあるアプリを作成したいと思います。検索で、ShinyTableパッケージが役立つ可能性があることがわかりました。光沢のあるコードを試してみましたが、結果のアプリがグレー表示され、結果が表示されません。
library(shinyTable)
shiny::runApp(list(
ui=pageWithSidebar(
headerPanel('Simple matrixInput')
,
sidebarPanel(
htable("tbl")
,
submitButton("OK")
)
,
mainPanel(
tableOutput(outputId = 'table.output')
))
,
server=function(input, output){
output$table.output <- renderTable({
input$tbl^2
}
, sanitize.text.function = function(x) x
)
}
))
何かアイデア?
shinyTable
パッケージは rhandsontable
パッケージ で大幅に改善されました。
データフレームを受け取り、それを編集してrds
ファイルに保存できる光沢のあるアプリを実行する最小限の関数を次に示します。
library(rhandsontable)
library(shiny)
editTable <- function(DF, outdir=getwd(), outfilename="table"){
ui <- shinyUI(fluidPage(
titlePanel("Edit and save a table"),
sidebarLayout(
sidebarPanel(
helpText("Shiny app based on an example given in the rhandsontable package.",
"Right-click on the table to delete/insert rows.",
"Double-click on a cell to edit"),
wellPanel(
h3("Table options"),
radioButtons("useType", "Use Data Types", c("TRUE", "FALSE"))
),
br(),
wellPanel(
h3("Save"),
actionButton("save", "Save table")
)
),
mainPanel(
rHandsontableOutput("hot")
)
)
))
server <- shinyServer(function(input, output) {
values <- reactiveValues()
## Handsontable
observe({
if (!is.null(input$hot)) {
DF = hot_to_r(input$hot)
} else {
if (is.null(values[["DF"]]))
DF <- DF
else
DF <- values[["DF"]]
}
values[["DF"]] <- DF
})
output$hot <- renderRHandsontable({
DF <- values[["DF"]]
if (!is.null(DF))
rhandsontable(DF, useTypes = as.logical(input$useType), stretchH = "all")
})
## Save
observeEvent(input$save, {
finalDF <- isolate(values[["DF"]])
saveRDS(finalDF, file=file.path(outdir, sprintf("%s.rds", outfilename)))
})
})
## run app
runApp(list(ui=ui, server=server))
return(invisible())
}
たとえば、次のデータフレームを考えます。
> ( DF <- data.frame(Value = 1:10, Status = TRUE, Name = LETTERS[1:10],
Date = seq(from = Sys.Date(), by = "days", length.out = 10),
stringsAsFactors = FALSE) )
Value Status Name Date
1 1 TRUE A 2016-08-15
2 2 TRUE B 2016-08-16
3 3 TRUE C 2016-08-17
4 4 TRUE D 2016-08-18
5 5 TRUE E 2016-08-19
6 6 TRUE F 2016-08-20
7 7 TRUE G 2016-08-21
8 8 TRUE H 2016-08-22
9 9 TRUE I 2016-08-23
10 10 TRUE J 2016-08-24
アプリを実行して楽しんでください(特にカレンダーで^^):
handsontableを編集します。
保存ボタンをクリックします。テーブルはファイルtable.rds
に保存されます。それをRで読んでください:
> readRDS("table.rds")
Value Status Name Date
1 1000 FALSE Mahmoud 2016-01-01
2 2000 FALSE B 2016-08-16
3 3 FALSE C 2016-08-17
4 4 TRUE D 2016-08-18
5 5 TRUE E 2016-08-19
6 6 TRUE F 2016-08-20
7 7 TRUE G 2016-08-21
8 8 TRUE H 2016-08-22
9 9 TRUE I 2016-08-23
10 10 TRUE J 2016-08-24
Excelのようにユーザーがマトリックスデータを入力できるソリューションを探している場合は、おそらくパッケージ「shinySky」、より具体的にはそのコンポーネント「Handsontable Input/Output」を確認できます。関連するWebアドレスは https://github.com/AnalytixWare/ShinySky です。
別の同様のソリューションは、shinyTableパッケージです。詳細は https://github.com/trestletech/shinyTable にあります。
shinysky
パッケージ のhotable("matrixTable")
を使用できます。
library(shiny, shinysky)
shinyApp(
ui = shinyUI (wellPanel(hotable("matrixTable"),hotable("resultTable"))),
server = shinyServer (function(input, output) {
A = matrix(c(1:6), nrow=2) # init - input matrix A
output$matrixTable <- renderHotable({data.frame(A)}, readOnly = FALSE)
R = matrix(rep(0,6), nrow=2) # init - result matrix R
output$resultTable <- renderHotable({data.frame(R)}, readOnly = TRUE)
observe({ # process matrix
df <- hot.to.df(input$matrixTable)
if(!is.null(df)) { # ensure data frame from table exists
B = data.matrix(df) # ensure its numeric
R = B^2 # some matrix operation
output$resultTable <- renderHotable({data.frame(R)})
}
}) # end of observe
}) # end of server
)
ユーザーインターフェースui
では、入力"matrixTable"
と"resultTable"
が視覚化されます。 server
はこれらのテーブルを初期化し、matrixTable
を編集できるようにします。つまり、Excelからデータをコピーして貼り付けるか、手動で値を変更できます。 observe
関数は、入力matrixTable
で変更に気付いたときにアクティブになります。そのテーブルからho.to.df
を使用してデータフレームdf
を抽出します。 NULL
でない場合は、それを行列に変換し、いくつかの行列演算(各要素の2乗など)を適用して、出力を新しい行列として返します。
この解決策は、Christoの提案とStephaneのアプローチを使用して得られました。
以下があなたが探しているものかどうかはわかりませんが、ここに行きます。マトリックスをtext/csvファイルとして入力できると仮定すると、上記のコードを次のように変更すると機能します。これは、Shinyチュートリアルから直接です: http://rstudio.github.io/shiny/tutorial/#uploads
shiny::runApp(list(
ui=pageWithSidebar(
headerPanel('Simple matrixInput')
,
sidebarPanel(
fileInput('file1', 'Choose CSV File',
accept=c('text/csv', 'text/comma-separated-values,text/plain', '.csv'))
,
tags$hr(),
checkboxInput('header', 'Header', TRUE),
radioButtons('sep', 'Separator',
c(Comma=',',
Semicolon=';',
Tab='\t'),
'Comma'),
radioButtons('quote', 'Quote',
c(None='',
'Double Quote'='"',
'Single Quote'="'"),
'Double Quote')
)
,
mainPanel(
tableOutput(outputId = 'table.output')
))
,
server=function(input, output){
output$table.output <- renderTable({
inFile <- input$file1
if (is.null(inFile))
return(NULL)
tbl <- read.csv(inFile$datapath, header=input$header, sep=input$sep, quote=input$quote)
return(tbl^2)
})
}
))