Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Embedding links in shiny tables

Tags:

r

shiny

I want to create a table in shiny so that each element of the table is a hyperlink to a new page but in such a way that the new page (to be created by shiny) knows which cell was clicked on. So, for example, I click on cell (i,j) and that takes me to a new page with a plot based upon the i and j values that I selected. I can do this using php and/or cookies, but I'm looking for a solution within shiny if possible.

Any ideas?

Note: An alternative is for me to use php and the HTML UI, but then I need the ability for R to return an array and for me to be able to refer to elements of that array within the html. Is that any easier?

like image 772
user2761811 Avatar asked Sep 09 '13 14:09

user2761811


1 Answers

Before answering your questions, I ask you to update your shiny to the last version to avoid undesirable errors.

Generally you need two JavaScript functions (which is already implemented in shiny but it is not well documented) to communicate with server:

Shiny.addCustomMessageHandler and Shiny.onInputChange in javascript

here is my code:

ui.R

library(shiny)

# Load the ggplot2 package which provides
# the 'mpg' dataset.
library(ggplot2)

# Define the overall UI
shinyUI(
  fluidPage(
    titlePanel("Basic DataTable"),

    # Create a new Row in the UI for selectInputs
    fluidRow(
      column(4, 
             selectInput("man", 
                         "Manufacturer:", 
                         c("All", 
                           unique(as.character(mpg$manufacturer))))
      ),
      column(4, 
             selectInput("trans", 
                         "Transmission:", 
                         c("All", 
                           unique(as.character(mpg$trans))))
      ),
      column(4, 
             selectInput("cyl", 
                         "Cylinders:", 
                         c("All", 
                           unique(as.character(mpg$cyl))))
      )        
    ),
    # Create a new row for the table.
    fluidRow(
      dataTableOutput(outputId="table")
    ),
    tags$head(tags$script("var f_fnRowCallback = function( nRow, aData, iDisplayIndex,     iDisplayIndexFull ){
      $('td', nRow).click( function(){Shiny.onInputChange('request_ij',     [$(this).parent().index(),$(this).index()])} );
}                                        

Shiny.addCustomMessageHandler('showRequested_ij', function(x) { 

    alert(x)
})"))
  )  
)

I just used "alert(x)" to show returned values from server. You can take care of a good JavaScript function to represent your data better. if you are looking to open new windows you may use:

var myWindow = window.open("", "MsgWindow", "width=200, height=100");
myWindow.document.write(x);

Server.r

library(shiny)
library(ggplot2)
shinyServer(function(input, output, session) {

  # Filter data based on selections
  output$table <- renderDataTable({
    data <- mpg
    if (input$man != "All"){
      data <- data[data$manufacturer == input$man,]
    }
    if (input$cyl != "All"){
      data <- data[data$cyl == input$cyl,]
    }
    if (input$trans != "All"){
      data <- data[data$trans == input$trans,]
    }
    data
  },options =  list(
  fnRowCallback = I("function( nRow, aData, iDisplayIndex, iDisplayIndexFull )     {f_fnRowCallback( nRow, aData, iDisplayIndex, iDisplayIndexFull ) }")))
  observe({   
    if(!is.null(input$request_ij)){
    session$sendCustomMessage(type = "showRequested_ij", paste( "row:     ",input$request_ij[1],"    col: ",input$request_ij[2]))}
    })
})
like image 157
Mahdi Jadaliha Avatar answered Oct 17 '22 03:10

Mahdi Jadaliha