cosworth
cosworth

Reputation: 25

How to catch dynamic tabPanel() id in Shiny app

It is possible to use a tabPanel id into a link ? I speak of id like #tab-6584-1 or #tab-6985-1 that shows when your cursor is over a tab in a Shiny app running in a browser :

Image of dynamic tabPanel() id example with Firefox

I would like to use this to put a top left link in a Shiny app to redirect on app "home" page.

Upvotes: 3

Views: 3310

Answers (1)

Bárbara Borges
Bárbara Borges

Reputation: 919

From your question, I'm not sure, but it seems like you want to mimic navigation to "subpages" in your app. If that's the case, there's a way of doing that in Shiny by reading and writing the value of the hash string at the end of the app's URL (link to gist):

library(shiny)

ui <- fluidPage(
  sidebarLayout(
    sidebarPanel(
      tags$a("Go to Panel 1", href = "#panel1"), br(),
      tags$a("Go to Panel 2", href = "#panel2"), br(),
      tags$a("Go to Panel 3", href = "#panel3")
    ),
    mainPanel(
      tabsetPanel(id = "tabs",
        tabPanel("Panel 1", h1("Panel 1"), value = "#panel1"),
        tabPanel("Panel 2", h1("Panel 2"), value = "#panel2"),
        tabPanel("Panel 3", h1("Panel 3"), value = "#panel3")
      )
    )
  )
)
server <- function(input, output, session) {
  # When we change from one `tabPanel` to another, update the URL hash
  observeEvent(input$tabs, {

    # No work to be done if input$tabs and the hash are already the same
    if (getUrlHash() == input$tabs) return()

    # The 'push' argument is necessary so that the hash change event occurs and
    # so that the other observer is triggered.
    updateQueryString(
      paste0(getQueryString(), input$tabs),
      "push"
    )
    # Don't run the first time so as to not generate a circular dependency 
    # between the two observers
  }, ignoreInit = TRUE)

  # When the hash changes (due to clicking on the link in the sidebar or switching
  # between the `tabPanel`s), switch tabs and update an input. Note that clicking 
  # another `tabPanel` already switches tabs.
  observeEvent(getUrlHash(), {
    hash <- getUrlHash()

    # No work to be done if input$tabs and the hash are already the same
    if (hash == input$tabs) return()

    valid <- c("#panel1", "#panel2", "#panel3")

    if (hash %in% valid) {
      updateTabsetPanel(session, "tabs", hash)
    }
  })
}

shinyApp(ui, server)

Upvotes: 4

Related Questions