change color actionButton Shiny R - r

i'm trying to figure out a way to get an actionButton to change color (and possibly other style elements as well.)
The objective is very general and I'll use this for many button responses throughout my complex shinyDashboard App. Simply said: if a button is clicked, or a specific element (i.e. inputslider) changes that is linked to a button, the button should change color.
I usually code my buttons in Shiny like this one:
actionButton(inputId= "RunFullModel", label =icon("tree-deciduous", lib = "glyphicon"),
style = "color: white;
background-color: #35e51d;
position: relative;
left: 3%;
height: 35px;
width: 35px;
text-align:center;
text-indent: -2px;
border-radius: 6px;
border-width: 2px")),
I've been browsing my ass off, but no luck to something that works.
I have been looking at shinyjs by #Dean Attali to do this, but I can only get it to work to change the background of the printed text as in the example below. The part using ToggleClass or AddClass doesn't work for actionButton("x", "y") it seems.
I've also tried to use updateActionButton from the shiny package itself, but this does not seem to allow style = "..." to be included in the command.
library(shiny)
library(shinyjs)
library(shinyBs)
if (interactive()) {
shinyApp(
ui = fluidPage(
useShinyjs(),
inlineCSS(list(.red = "background: red")),
inlineCSS(list(.blue = "style = 'background-color: blue'")),
actionButton("checkbox", "Make it red"),
bsButton("checkbox2", "Make me blue"),
p(id = "element", "Watch what happens to me")
),
server = function(input, output) {
observe({
toggleClass(id = "element", class = "red",
condition = input$checkbox)
})
observe({
toggleCssClass(id = "checkbox2", class = ".blue",
condition = input$checkbox)
})
}
)
}
The demo model of shinyjs is found here: http://deanattali.com/shinyjs/overview#demo and it looks as if the toggleClass works there for the button with id "btn" but there is no code example directly to be found, and the indirect example from another section of the shinyjs page doesn't seem to work.
Option 3 I tried to have the style = "background-color: ....read R variable" part access an R variable that contains the color name, i.e. mycolor <- "red", but that doesn't work either, and my knowledge of javascript is too limited to figure out how to make that work.
So, .... if anyone has an idea how to make the color switching work with shinyjs, or with another method that works with my button coded above, I would highly appreciate it, and grant you my eternal gratitude. (been stuck on this for weeks now with this issue)
Mark
p.s. i've looked into bsButtons as well but they are too limited for what I want with the default class options.

That should be doable in "pure" shiny:
Use renderUI() to create the button and insert conditions to check if the button was clicked already.
I decided to store the information (whether a button was clicked) within a reactiveVariable as you wrote that you plan to trigger the color change "if a button is clicked, or a specific element (i.e. inputslider) changes that is linked to a button". So you could also change the global$clicked from other inputs.
library(shiny)
shinyApp(
ui = fluidPage(
uiOutput("button")
),
server = function(input, output) {
global <- reactiveValues(clicked = FALSE)
observe({
if(length(input$RunFullModel)){
if(input$RunFullModel) global$clicked <- TRUE
}
})
output$button <- renderUI({
if(!is.null(input$RunFullModel) & global$clicked){
actionButton(inputId= "RunFullModel", label =icon("tree-deciduous", lib = "glyphicon"),
style = "color: white;
background-color: #35e51d;
position: relative;
left: 3%;
height: 35px;
width: 35px;
text-align:center;
text-indent: -2px;
border-radius: 6px;
border-width: 2px")
}else{
actionButton(inputId= "RunFullModel", label =icon("tree-deciduous", lib = "glyphicon"))
}
})
}
)

Related

Internal link between tabs to specific section in R Shiny app

I want to link to a specific content of another tabPanel within an R Shiny app. I've found plenty of advice on how to do the half part of it respectively: there are solutions how to use an anchor tag to link to content within a tabPanel...
SO: Create link to the other part of the Shiny app
... and on hwo to direct the link to another tabPanel:
SO: [Shiny]: Add link to another tabPanel in another tabPanel
SO: Linking to a tab or panel of a shiny app
SO: Externally link to specific tabPanel in Shiny App
Creating Internal Links - Defining Application Navigation by David Ruvolo
However, I need a combination of both: a link switching the view to another tabPanel at a specific location. In this app, based on mihasa's example, there are two tabPanels, where the first (Home) holds some text upon clicking that, the app should redirect to a section with the id visitme in Tab2.
library(shiny)
ui = shinyUI(
navbarPage("Header",
tabPanel("Home",
fluidPage(
"bring me to the desired point in Tab2")),
tabPanel("Tab2",
"Some Text inside Tab 2.",
div("This is a long div to visualize the redirection",
style = "background-color: gray;
height: 1000px;
width: 100px;"),
div(id = "visitme",
"This is the part where the redirection shall land."),
div("Another long div",
style = "background-color: gray;
height: 500px;
width: 100px;"))))
server = function(input, output, session){}
runApp(shinyApp(ui, server), launch.browser = TRUE)
Using K. Rohde's answer as starting point, their JavaScript was extended by a second argument for the given id and a command, that scrolls to it (document.getElementById(anchorName).scrollIntoView()), allows to move to a certain section within a given tabPanel after switching to it.
library(shiny)
ui = shinyUI(
navbarPage("Header",
tabPanel("Home",
tags$head(tags$script(HTML('
var fakeClick = function(tabName, anchorName) {
var dropdownList = document.getElementsByTagName("a");
for (var i = 0; i < dropdownList.length; i++) {
var link = dropdownList[i];
if(link.getAttribute("data-value") == tabName) {
link.click();
document.getElementById(anchorName).scrollIntoView({
behavior: "smooth"
});
};
}
};
'))),
fluidPage(
span("bring me to end of tab2",
onclick = "fakeClick('Tab2', 'visitme')"))),
tabPanel("Tab2",
"Some Text inside Tab 2.",
div("This is a long div to visualize the redirection",
style = "background-color: gray;
height: 1000px;
width: 100px;"),
div(id = "visitme",
"This is the part where the redirection shall land."),
div("Another long div",
style = "background-color: gray;
height: 1000px;
width: 100px;"))))
server = function(input, output, session){}
runApp(shinyApp(ui, server), launch.browser = TRUE)

Removing up/down arrows from numericInput() R Shiny

I am interested in removing or hiding the side arrows that appear when you use numericInput() with shiny. I will attach an image of the arrows that I am referring to so everyone can understand which part I would like to remove/hide. After reading the documentation, it does not appear that there is an option to remove these arrows. So I am wondering if there is a way to use CSS to remove these arrows. I did see one other post that asked a similar question. However, I am only interested in using numericInput().
I will attach some sample code. The code essentially does nothing but it will give you a reproducible example.
library(shiny)
server <- function(input, output){
}
ui <- fluidPage(
titlePanel("Test1"),
sidebarLayout(
sidebarPanel(
numericInput("n",
label = h4("Test2"),
min=1,
value = 20),
numericInput("x",
label = h4("Test3"),
min=0,
value = 10),
h4(textOutput("pvalue"))
),
mainPanel(
plotOutput("nullplot")
)
)
)
shinyApp(ui = ui, server = server)
runApp()
WARNING: I have read online that the side arrows do not show up on all web browsers and some versions of RStudio. See here
It does not appear that there is a way to remove the arrows from a numericInput(), however, there is a way to hide them. Just to be clear there is a difference between removing and hiding. Removing the arrows, in theory, should completely remove the code for the arrows. Hiding the arrows will simply mask the code for the side arrows, however, the code will still be present but will not be seen by the user unless they inspect the page.
Below is CSS that can be used to hide the side arrows from numericInput().
tags$head(
tags$style(HTML("
input[type=number] {
-moz-appearance:textfield;
}
input[type=number]::{
-moz-appearance:textfield;
}
input[type=number]::-webkit-outer-spin-button,
input[type=number]::-webkit-inner-spin-button {
-webkit-appearance: none;
margin: 0;
}
"))
)
If you wanted to apply this code to the example given in the question, then you could do something like this
library(shiny)
server <- function(input, output){
}
ui <- fluidPage(
titlePanel("Test1"),
sidebarLayout(
sidebarPanel(
tags$head(
tags$style(HTML("
input[type=number] {
-moz-appearance:textfield;
}
input[type=number]::{
-moz-appearance:textfield;
}
input[type=number]::-webkit-outer-spin-button,
input[type=number]::-webkit-inner-spin-button {
-webkit-appearance: none;
margin: 0;
}
"))
),
numericInput("n",
label = h4("Test2"),
min=1,
value = 20),
numericInput("x",
label = h4("Test3"),
min=0,
value = 10),
h4(textOutput("pvalue"))
),
mainPanel(
plotOutput("nullplot")
)
)
)
shinyApp(ui = ui, server = server)
runApp()
Overall this is just a workaround because there is no option to remove the side arrows.

Is there a comprehensive list of attributes and properties for the default Shiny slider?

Shiny makes use of the ion-rangeslider. I figured out how to modify some of its attributes. The code below changes the button color and the background color of the label above the button, and also removes the slider bar. I need to make additional changes, but am not sure which other slider attributes I can change--and how they should be referred to.
Is there a comprehensive list of this slider's attributes (such as ".irs-slider") and their properties? (E.g., for the attribute .irs-slider: "width"; "height"; "top"; "background", etc.)
Update: GJPLatten's suggestion to right-click the slider in the browser and select "Inspect Element" saved my day. However, I'm still interested in finding a comprehensive list of attribute and property names which also provides descriptive information, since this would be easier to navigate and work with.
library(shiny)
ui <- fluidPage(
sliderInput("default",
"Default slider",
min = 0,
max = 50,
value = 20),
sliderInput("modified",
"Modified slider",
min = 0,
max = 50,
value = 20),
tags$style(type = "text/css",
HTML(".js-irs-1 .irs-slider { width: 8px; height: 20px; top: 20px; background: green }",
".js-irs-1 .irs-bar { display: none }",
".js-irs-1 .irs-bar-edge { display: none }",
".js-irs-1 .irs-single { color: black; background: transparent }"))
)
server <- function(input, output) {
}
shinyApp(ui = ui, server = server)
The parts within the HTML() function are all css. W3schools have a great tutorial on this at https://www.w3schools.com/css/default.asp. You can get the element name by right clicking on the element in your browser and clicking inspect element.

change font size of dateinput

How do you change the font size of a dateInput item
dateInput("MyDate", "Date:", value = "2018-01-01"),
I am using
shinyUI(navbarPage(
tags$head(
tags$style(HTML("
#import url('//fonts.googleapis.com/css?family=Lobster|Cabin:400,700');
.selectize-input { font-size: 12px; line-height: 14px;}
.selectize-dropdown { font-size: 12px; line-height: 14px; }
.input-sm {font-size: 12px; }
"))
),tabPanel("MyPanel",
column(1,
wellPanel(
dateInput("MyDate", "Date:", value = "2018-01-01"),
Well, long time passed, maybe still someone will find it useful, I've managed to achieve the desired result using tags$head and tags$style and pointing to specific input by its id:
tags$head(
tags$style(HTML("#MyDate [type = 'text'] {fontsize:12px;height:14px;}"))
)
Effectively, you are changing the format of the inputs, restricting the range of affected elements by pointing to a specific ID (#MyDate), thereby solving the problem that bk18 has mentioned.
I myself have just started exploring Shiny, so this might not be the most efficient/elegant solution.
A simple solution is to change the h_ label in the code, e.g h1,h2,h3....and so on.
dateInput("MyDate", label = h2("My Date"), format="mm-dd-yyyy",value = "2018-
01-01")
You can also control width= in this argument as well
In your tags, try:
tags$head(
tags$style(
".form-control {font-size: 2em !important;}"
)
)
This will make all the input text huge. The interesting thing is that the inputs all share the same class according to css, and changing the column container class doesn't seem to work. My answer above should work, but it won't be specific to the date input. I'll try to work it out, but in the meantime try the above!

How to change the color of the ColumnVisibility buttons in DT/Shiny

I am building a table using the DT package in a Shiny Dashboard. The table has several columns and I used DT's ColVis functionality to allow users to hide/show only the columns they're interested in.
My question is - is it possible to change the color of those buttons once the Column visibility button is clicked on? As of right now, the colors aren't different enough and its hard to tell which columns are visible and which ones aren't without navigating to the table. I've included a screenshot that shows what I mean. The Site_ID column is not visible in the table, while the Participant_ID column is.
I used inspect element in google chrome to find out the objects name and it looked to be: a.dt-buttons.buttons-columnVisibility, and was under body.skin-blue, div.dt-button-collection.
Using this info I added the following line to my ui.R code:
tags$head(tags$style(HTML(".skin-blue .dt-button-collection .buttons-columnVisibility .active a{background-color: #4d4d4d}")))
But this didn't appear to do anything. Any help on implementing this custom CSS/HTML into my dashboard would be appreciated.
Based on this answer, it looks like the button color needs to be set with background. I also used !important to override the DT button style, although this may not be the best practice.
Here's a small working example:
library(DT)
library(shiny)
ui <- basicPage(
tags$head(
tags$style(
HTML(
".dt-button.buttons-columnVisibility {
background: #FF0000 !important;
color: white !important;
opacity: 0.5;
}
.dt-button.buttons-columnVisibility.active {
background: black !important;
color: white !important;
opacity: 1;
}"
)
)
),
h2("The iris data"),
DT::dataTableOutput("mytable")
)
server <- function(input, output) {
output$mytable = DT::renderDataTable({
datatable(
iris, rownames = FALSE,
extensions = 'Buttons',
options = list(dom = 'Bfrtip', buttons = I('colvis'))
)
})
}
shinyApp(ui, server)

Resources