2

We have a large shiny application that uses multiple horizontally stacked sections. On the last section (bottom of the page) I have a modal. Inside this modal I want to use rintrojs to guide the user (inside the modal).

The introjs does not seem to work when the modal is opened at the bottom of the page. The grey overlay will show, but the elements are not highlighed or the button pop-up will show.

Here is an minimal example (edited from r introjs bsModal):

library(rintrojs)
library(shiny)
library(shinydashboard)
library(shinyBS)


intro_df <- data.frame(element = c('#plot_box', '#bttn2_intro', '#box', '#plot', '#shiny-modal'),
                       intro = c('test plot_box', 'test bttn2', 'test box', 'plot', 'test modal'))

ui <- shinyUI(fluidPage(
  dashboardPage(dashboardHeader(title = "Test"),
                dashboardSidebar(sidebarMenu(menuItem("item1", tabName = "item1"))),
                dashboardBody(tabItems(tabItem("item1", 
                                              rep(br(), 10000), # remove this line and introjs will work
                                               
                                               
                                               actionButton("bttn", "start intro"))))),

  introjsUI()
))

server <- shinyServer(function(input, output, session) {
  output$plot <- renderPlot({
    plot(rnorm(50))
  })
  
  output$plot_box <- renderUI({
    box(id = 'box',
        div(id = "bttn2_intro", actionButton('bttn2', 'dummy')),
        plotOutput('plot'), width = '100%'
    )
  })
  
  observeEvent(input$bttn,{
    showModal(modalDialog(uiOutput('plot_box')))
  })
  
  observeEvent(input$bttn2, {
    introjs(session, options = list(steps = intro_df))
  })
  
})
shinyApp(ui = ui, server = server)

Any help with this issue would be appreciated.

Stan W
  • 57
  • 8

1 Answers1

1

Not really a solution, but you can force the app to scroll back to the top before the modal is displayed and it will work. The downside is that when the modal closes we need to scroll back to the bottom, to do that we need an actionButton that trigger this actions so the option of using easy close in the modal will not work in this case.

APP

library(rintrojs)
library(shiny)
library(shinydashboard)
library(shinyBS)
library(shinyjs)


intro_df <- data.frame(
  element = c("#plot_box", "#bttn2_intro", "#box", "#plot", "#shiny-modal"),
  intro   = c("test plot_box", "test bttn2", "test box", "plot", "test modal")
)

ui <- dashboardPage(
  dashboardHeader(title = "Test"),
  dashboardSidebar(sidebarMenu(menuItem("item1", tabName = "item1"))),
  dashboardBody(
    tabItems(
      tabItem(
        "item1",
        introjsUI(),
        shinyjs::useShinyjs(),
        rep(br(), 10000), # remove this line and introjs will work


        actionButton("bttn", "start intro")
      )
    )
  )
)
server <- shinyServer(function(input, output, session) {
  output$plot <- renderPlot({
    plot(rnorm(50))
  })

  output$plot_box <- renderUI({
    box(
      id = "box",
      div(id = "bttn2_intro", actionButton("bttn2", "dummy")),
      plotOutput("plot"), width = "100%"
    )
  })

  observeEvent(input$bttn, {
    shinyjs::runjs("window.scrollTo(0, 0)")
    showModal(
      modalDialog(
        uiOutput("plot_box"),
        footer = actionButton(
          "close_modal",
          "Dismiss"
        ),
        easyClose = FALSE
      )
    )
  })

  observeEvent(input$bttn2, {
    introjs(session, options = list(steps = intro_df))
  })

  observeEvent(input$close_modal, {
    shinyjs::runjs("window.scrollTo(0, document.body.scrollHeight)")
    removeModal()
  })
})
shinyApp(ui = ui, server = server)

enter image description here

jpdugo17
  • 6,816
  • 2
  • 11
  • 23
  • Although this initially fixed the issue, for some reason the background will scroll down when the modal is still active when I run the introjs steps. Maybe the boxes 'push' the page in the background down? – Stan W Aug 08 '22 at 13:34
  • 1
    @StanW It should scroll down only after the button to close the modal is activated? If not we can try directly taking out from the code the line `shinyjs::runjs("window.scrollTo(0, document.body.scrollHeight)")`. And force the user to scroll down manually when the modal closes. – jpdugo17 Aug 10 '22 at 03:25
  • For some reason it slightly scrolled down (just a few cm) during the tutorial pop-ups. I fixed it by locking the background when the modal is active: `shinyjs::runjs("window.scrollTo(0, 0); document.body.style.position = 'fixed'; document.body.style.top = '-${window.scrollY}px';") ` and `shinyjs::runjs(" document.body.style.position = ''; document.body.style.top = ``; window.scrollTo(0, document.body.scrollHeight)")` to close the modal – Stan W Aug 11 '22 at 12:11