Glisser et déposer des données dans l'application brillante
Comment puis-je glisser et déposer des données dans une application brillante? Je peux glisser-déposer dans une zone et le lire avec javascript, mais je ne sais pas comment faire pour que shiny l'enregistre pour que je puisse le traiter sur le serveur. Voici un exemple de configuration -- c'est un peu long b/C Je ne pense pas qu'il y ait une fonction javascript intégrée pour gérer le drag-n-drop.
actuellement, Il devrait ressembler à celui-ci lors d'une exécution et d'un jeu de données "dat.csv " est traîné dans. Le but est d'enregistrer les données qui ont été glissées dans une variable input
pour qu'il puisse être traité en R.
interface utilisateur.R
library(shiny)
ui <- shinyUI(
fluidPage(
tags$head(tags$link(rel="stylesheet", href="css/styles.css", type="text/css"),
tags$script(src="getdata.js")),
h3(id="data-title", "Drop Datasets"),
div(class="col-xs-12", id="drop-area", ondragover="dragOver(event)",
ondrop="dropData(event)"),
tableOutput('table'), # doesn't do anything now
## debug
div(class="col-xs-12",
tags$hr(style="border:1px solid grey;width:150%"),
tags$button(id="showData", "Show", class="btn btn-info",
onclick="printData('dat.csv')")),
div(id="data-output") # print the data
)
)
le serveur.R
## Make a sample dataset
# write.csv(data.frame(a=1:10, b=letters[1:10]), "dat.csv", row.names=FALSE)
server <- function(input, output, session) {
output$table <- renderTable(input$data) # this variable doesn't exist
}
www / getdata.js
var datasets = {};
var dragOver = function(e) { e.preventDefault(); };
var dropData = function(e) {
e.preventDefault();
handleDrop(e.dataTransfer.files);
};
var handleDrop = function(files) {
for (var i = 0, f; f = files[i]; i++) {
var reader = new FileReader();
reader.onload = (function(file) {
return function(e) {
datasets[file.name.toLowerCase()] = e.target.result;
var div = document.createElement("div");
var src = "https://cdn0.iconfinder.com/data/icons/office/512/e42-512.png";
div.id = "datasets";
div.innerHTML = [
"<img class='thumb' src='", src, "' title='", encodeURI(file.name),
"'/>", "<br>", file.name, "<br>"].join('');
document.getElementById("drop-area").appendChild(div);
};
})(f);
reader.readAsText(f);
}
};
// debug
var printData = function(data) {
var div = document.createElement("div");
div.innerHTML = datasets[data];
document.getElementById("data-output").appendChild(div);
};
www / css / styles.css
#data-title {
text-align:center;
}
#drop-area {
background-color:#BCED91;
border:2px solid #46523C;
border-radius:25px;
height:90px;
overflow:auto;
padding:12px;
}
#drop-area #datasets {
display:inline-block;
font-size:small;
margin-right:8px;
text-align:center;
vertical-align:top;
}
.thumb {
height:45px;
}
2 réponses
il suffit d'ajouter la ligne suivante dans le fichier js
datasets[file.name.toLowerCase()] = e.target.result;
# Add this line
Shiny.onInputChange("mydata", datasets);
alors vous pouvez utiliser input$mydata
dans le code du serveur. Notez que c'est une liste, donc vous devrez itérer à travers elle (également nécessaire si vous prévoyez de laisser tomber plusieurs fichiers).
code Complet (qui affiche également plusieurs fichiers csv, notez que si vous déposez plusieurs fichiers avec le même nom, un seul sera affiché):
getdata.js (ajouter une ligne comme ci-dessus)
les styles.css (pas de modifier)
interface utilisateur.R
library(shiny)
ui <- shinyUI(
fluidPage(
tags$head(tags$link(rel="stylesheet", href="css/styles.css", type="text/css"),
tags$script(src="getdata.js")),
sidebarLayout(
sidebarPanel(
h3(id="data-title", "Drop Datasets"),
div(class="col-xs-12", id="drop-area", ondragover="dragOver(event)",
ondrop="dropData(event)")
),
mainPanel(
uiOutput('tables')
)
)
)
)
le serveur.R
server <- function(input, output, session) {
observeEvent(input$mydata, {
len = length(input$mydata)
output$tables <- renderUI({
table_list <- lapply(1:len, function(i) {
tableName <- names(input$mydata)[[i]]
tableOutput(tableName)
})
do.call(tagList, table_list)
})
for (name in names(input$mydata)) {
output[[name]] <- renderTable(read.csv(text=input$mydata[[name]]))
}
})
}
depuis août 2017 cette fonctionnalité est maintenant fournie par fileInput
directement à partir de shiny
! Comment merveilleux.
voici le blogpost annonçant la fonctionnalitéhttps://blog.rstudio.com/2017/08/15/shiny-1-0-4/