我有一个闪亮的应用程序,里面有一个漂亮的幻灯片和与每张照片相关联的输入。用户会输入他们的名字,然后猜测照片中每个人的年龄。每次用户用箭头推进幻灯片,输入也会推进。用户必须填写输入,应用程序的其余部分才能工作(应用程序的其余部分在这里没有显示)。我想要的是,每次点击箭头时,应用程序都会检查相关的输入是否为空,如果是,幻灯片将不会前进,并会弹出一条小消息。我试过用shinyjs、shinyvalidate和shinyalert来解决这个问题,但是我没有找到一个解决方案。
library(shiny)
library(shinyalert)
library(slickR)
library(tidyverse)
library(shinyvalidate)
library(shinyjs)
js <- "
$(document).ready(function(){
var ss = document.getElementById('slickr');
// create an observer instance
var observer = new MutationObserver(function(mutations) {
var index = $(ss).find('.slick-current').data('slick-index');
Shiny.setInputValue('imageIndex', parseInt(index)+1);
});
// configuration of the observer
var config = {subtree: true, attributes: true};
// observe
observer.observe(ss, config);
var deleteThis = function(elem){
elem.style.display = 'none';
// elem.style.visibility = 'hidden';
};
})
"
slider <- "$('.slider').slick({
autoplay: false,
dots: true,
customPaging : function(slider, i) {
var thumb = $(slider.$slides[i]).data();
return '<a>'+1:6[i]+'</a>';
},
responsive: [{
breakpoint: 500,
settings: {
dots: false,
arrows: false,
infinite: false,
slidesToShow: 2,
slidesToScroll: 2
}
}]
});"
cP1=htmlwidgets::JS("function(slick,index) {return '<a>'+(index+1)+'</a>';}")
imgs <- list.files("samplepictures/", pattern=".jpg|.jpeg|.png", full.names = TRUE)
imgs <- imgs[!grepl("photo_ages",imgs)]
photoages <- lapply(1:6,function(x){ numericInput(paste0("Photo",x),
paste0("Photo ",x," Age Guess:"),
min = 1,
max = 100,
value = NULL)})
texfn <- function(x= "Guesser"){
textInput("Name",paste(x))
}
actionfn <- function(){
actionButton("go", "Submit All Guesses")
}
photoages <- as.vector(photoages)
photoages <- c(list(texfn()),
photoages,
list(actionfn()))
ui <- fluidPage(
useShinyjs(),
titlePanel("Photo Guesses"),
mainPanel(
tags$head(
tags$script(HTML(js))
),
tags$head(
tags$style(HTML("
.arrows {
height: 30px;
}
.slick-prev {
left: 10px; # moves right
}
.slick-next {
left: 30px; # moves right
}
"))),
fluidRow(
column(12),
column(4,align = "left",tags$body( div(id = "mydiv",uiOutput("photoinput"))) ) ,
column(4, align = "left",div(id = "npht",h4("Advance:")), tags$br(), tags$div(id = "arr",class="arrows"))
),
tags$hr(),
slickROutput("slickr") ,
tags$br()
)
)
server <- function(input, output,session) {
iv <- InputValidator$new()
iv$add_rule("Name", sv_required())
iv$add_rule("Photo1", sv_between(1,100, allow_na = T))
iv$add_rule("Photo2", sv_between(1,100, allow_na = T))
iv$add_rule("Photo3", sv_between(1,100, allow_na = T))
iv$add_rule("Photo4", sv_between(1,100, allow_na = T))
iv$add_rule("Photo5", sv_between(1,100, allow_na = T))
iv$add_rule("Photo6", sv_between(1,100, allow_na = T))
iv$enable()
observeEvent(input[["imageIndex"]],{
values <- reactiveValues()
values$click <- input[["imageIndex"]]
if(input[["imageIndex"]] >7){
removeUI("#npht")
removeUI("#arr")
}
})
output$slickr <- renderSlickR({
imgs <- list.files("samplepictures/", pattern=".jpg|.jpeg|.png", full.names = TRUE)
imgs <- imgs[!grepl("photo_ages",imgs)]
(slickR(imgs) +
slickR::settings(dots = TRUE,
#customPaging = cP1,
appendArrows = '.arrows',
prevArrow = "null"
))
})
output[["photoinput"]] <- renderUI({photoages[input[["imageIndex"]]]})
}
# Run the application
shinyApp(ui = ui, server = server)
1条答案
按热度按时间5anewei61#
您可以按照ismireshregal的建议将javascript代码和
slickR
代码替换为shinyglide
。我对它进行了简化,但如果幻灯片不满足使用next_condition
参数的条件,您可以阻止幻灯片前进。请参阅此处了解更多信息:https://juba.github.io/shinyglide/articles/b_conditionals.html .