Change colour of checkbox using shinyWidgets - css

I am using awesomeCheckboxGroup from the package shinyWidgets to create checkboxes in a shiny app. As default, they have a blue background. I can change the background colour with the argument status = but this is limited to the five status colours.
I believe I should be able to make a custom status using CSS, and pass this through to the argument. However, when I inspect the page, it is totally eluding me which the relevant bit is to change. I can't see the blue colour mentioned anywhere! I've also tried changing the status in case I can see the relevant code change there, but that hasn't helped me either.
I have only ever used CSS in the context of an app like this, so apologies if I am missing something obvious. Also happy with a solution that uses an alternative approach, of course!
EDIT: I have now identified the element, so I can change the colour! The downside is that it also affects another part of the page. In my actual work, this doesn't matter because I am actually changing to the same colour as the header, so this is not noticeable - but is there a way to be more specific and colour only the checkboxes?
library(shiny)
library(shinydashboard)
library(shinyWidgets)
sidebar <- dashboardSidebar()
body <- dashboardBody(
fluidRow(class ="rowhide",
box(width = 12, solidHeader = TRUE,
awesomeCheckboxGroup(inputId = "checkbox",
label = "Filter",
choices = c("A", "B", "C"),
selected = c("A", "B", "C"))
)
),
# theme styling ####
tags$head(tags$style(HTML('
:after, :before{
background-color:#bff442;
}'
))))
ui <- dashboardPage(dashboardHeader(title = "Example"),
sidebar,
body
)
server <- function(input, output) {
}
shinyApp(ui, server)

Success! By adding the id of the checkbox input, I was able to isolate it to just that one element. However, it me a while to figure this out because the id needs to be added to both the before and after parts.
Here is my working code:
library(shiny)
library(shinydashboard)
library(shinyWidgets)
sidebar <- dashboardSidebar()
body <- dashboardBody(
fluidRow(class ="rowhide",
box(width = 12, solidHeader = TRUE,
awesomeCheckboxGroup(inputId = "checkbox",
label = "Filter",
status = "warning",
choices = c("A", "B", "C"),
selected = c("A", "B", "C"))
)
),
# theme styling ####
tags$head(tags$style(HTML('
#checkbox :after, #checkbox :before{
background-color:#bff442;
}'
))))
ui <- dashboardPage(dashboardHeader(title = "Example"),
sidebar,
body
)
server <- function(input, output) {
}
shinyApp(ui, server)

Check out this link: How to change the background color on a input checkbox with css? - you'll have to wrap anything within a tag call from shiny though

You can also change the “primary” colors of awesomeCheckbox inputs by adding this to your css file:
tags$style(".checkbox-bs-primary input[type='checkbox']:checked + label::before,
.checkbox-bs-primary input[type='radio']:checked + label::before {
background-color: #FFBB00;
border-color: #FFBB00;
}
.checkbox-primary input[type='checkbox']:checked + label::before,
.checkbox-primary input[type='radio']:checked + label::before {
background-color: #FFBB00;
border-color: #FFBB00;
}"),

Related

Applying different CSS styles to box elements in R Shiny

I have an app in which I would like the main_box expand/contract icon to be in black text with a white background, and then the sub_box's options box to appear in red with white letters. Additionally, I want the sub_box's options box to remain red w/ white letters, even when hovered over or clicked.
I'm able to get the sub_box css implemented correctly, but I can't figure out how to disaggregate the sub_box css from the main_box css. Can anyone tell me what I'm doing wrong?
library(shiny)
library(shinydashboard)
library(shinyWidgets)
ui <- dashboardPage(
dashboardHeader(),
dashboardSidebar(),
dashboardBody(
tags$style(HTML("
.box.box-solid > .box-header > .box-tools .btn {
background: #fd0000;
color: #ffffff;
}
")),
box(title = "main_box", collapsible = T,
box(title = "sub_box",
dropdownMenu = dropdown(label = "Options",
"Hello World!")
)
)
)
)
server <- function(input, output) { }
shinyApp(ui, server)
Current State:
Desired End State:
A simple way to distinguish those boxes is to provide them with an id - please see the following:
library(shiny)
library(shinyWidgets)
library(shinydashboard)
library(shinydashboardPlus)
ui <- dashboardPage(
dashboardHeader(),
dashboardSidebar(),
dashboardBody(
tags$style(
HTML(
"#subbox > .box-header > .box-tools .btn {
background: #fd0000;
color: #ffffff;
}"
)
),
shinydashboardPlus::box(
id = "mainbox",
title = "main_box",
collapsible = TRUE,
shinydashboardPlus::box(
id = "subbox",
title = "sub_box",
dropdownMenu = dropdown(label = "Options", "Hello World!")
)
)
)
)
server <- function(input, output) {}
shinyApp(ui, server)
Furthermore please make sure to address namespace issues. shinydashboard::box does not have a dropdownMenu parameter - shinydashboardPlus::box has.

R shinydashboard add a customized color for status parameter

So my question is very related to this one : R shinyDashboard customize box status color
However, the problem is that the provided solution does not add an available color but only replace an existing one. Thus, we are limited to only 5 colors for boxes in one shiny apps. In other words, I would like to add a customized color while keeping the existing ones
So i thought about a similar solution but it didn't work...
library(shiny)
library(shinydashboard)
ui <- dashboardPage(
dashboardHeader(),
dashboardSidebar(),
dashboardBody(
tags$style(HTML("
.box.box-solid.box-primary2>.box-header {
color:#fff;
background:#666666
}
.box.box-solid.box-primary2{
border-bottom-color:#666666;
border-left-color:#666666;
border-right-color:#666666;
border-top-color:#666666;
}
")),
fluidRow(
box(width = 6, title = "youhou", status = "primary2", solidHeader = TRUE,
"Box content"
)
)
)
)
server <- function(input, output) {}
shinyApp(ui, server)
Error in validateStatus(status) :
Invalid status: primary2. Valid statuses are: primary, success, info, warning, danger.
The below is a hacky way of doing it. Essentially you need to create a custom div and use it's id tag so that the css styling takes precedence over the original box styling and use renderUI to generate this new custom box.
However, you also do not want to inadvertently style the other box so you use the id to apply the styling specifically to your box of choice.
Finally you use uiOutput and renderUI on the server side to create this new div and the respective styled box.
library(shiny)
library(shinydashboard)
ui <- dashboardPage(
dashboardHeader(),
dashboardSidebar(),
dashboardBody(
fluidRow(
box(width = 6, title = "youhou", status = "primary", solidHeader = TRUE,
"Box content"
),
uiOutput("primary2")
)
)
)
server <- function(input, output) {
output$primary2 <- renderUI({
tags$div(class = "another-box", id = "primariy2",
box(width = 6, title = "youhou", status = "primary", solidHeader = TRUE,
"Box content"
),
tags$style(HTML("
#primariy2 .box.box-solid.box-primary>.box-header {
color:#fff;
background:#666666
}
.box.box-solid.box-primary {
border-bottom-color:#666666;
border-left-color:#666666;
border-right-color:#666666;
border-top-color:#666666;
}
"))
)
})
}

Style shinyWidget::dropdownButton in shinydashboard::box header

Background
I am trying to place a shinyWidget::dropdownButton in the header of a shinydashboard::box. The button should have the look and feel of the button created when using a collapsible box (box(..., collapsible = TRUE).
With the help of some JavaScript I was able to move the dropdown, which seemed to me the easier approach rather than constructing all the HTML myself.
The code below does what I want to do, however I am struggling with the css, because the elements in the dropdown are partly white on white (which makes sense I guess because they are (grand) children of class .box-tools)
What I want
I want that all controls in the dropdown look like as if I put the dropdown in the body of the box:
Goal: Dropdown in the body
Current Situation: Dropdown in the header
Questions
How can I achieve this? Which css rules do I have to use, to make sure that any kind of control looks like as if in the body of the box? Could I achieve the same behaviour even easier? (For instance by wrapping all my controls in the dropdown in another element)? I do know my basics in css but here I feel a bit at loss which rules I need to consider to get to the desired result.
Code
library(shiny)
library(shinydashboard)
library(shinyWidgets)
library(shinyjs)
makeDropDown <- function(i) {
dropdownButton(
h3("Heading"),
selectInput(paste0("sel", i), "Select:", LETTERS),
downloadButton(paste0("down", i), "Load"),
circle = FALSE,
icon = icon("cog")
)
}
ui <- dashboardPage(
dashboardHeader(),
dashboardSidebar(),
dashboardBody(
useShinyjs(),
box(solidHeader = TRUE,
status = "info",
title = "Box",
div(
makeDropDown(1),
class = "box-tools pull-right",
id = "moveme"
),
makeDropDown(2)
)
)
)
server <- function(input, output, session) {
runjs("$('.box-header').append($('#moveme').detach())")
}
shinyApp(ui, server)
You're right, some CSS rules are overwritten, you can use some inline CSS with !important to control appearance :
makeDropDown <- function(i) {
dropdownButton(
tags$div(
style = "color: black !important;", # for text
h3("Heading"),
selectInput(paste0("sel", i), "Select:", LETTERS),
downloadButton(
outputId = paste0("down", i), label = "Load",
style = "background-color: #f4f4f4 !important; color: #444 !important; border: 1px solid #ddd !important;" # for button
)
),
circle = FALSE,
icon = icon("cog")
)
}
Otherwise, maybe #DivadNojnarg have a better solution in shinydashboardPlus, I'll ask him !

How to change the background color of the pickerInput() and also the options that are selected

I want to change the colour of the pickerInput() as well as change the background colour of the options of it is selected. Like for example if A and B are selected then they must have a different background colour say blue while the other options are still white. It will also be cool if the tickbox is moved towards the left of the options.
library(shiny)
shinyApp(
ui = fluidPage(
pickerInput(
inputId = "my_select_input",label = "Select Letter",
choices = c("A", "B", "C", "D"),multiple = T
)
),
server = function(input,output,session) {
observeEvent(input$my_select_input,{
updatePickerInput(session,"my_select_input")
})
}
)
I am able to change the background color of the selected options in the pickerInput() input by manually adding the following CSS at the top of my UI. You need to isolate the "selected" class, which is automatically applied to the cells that are selected.
tags$style(HTML("
.selected {background-color:blue !important;}
"))

R shinyDashboard customize box status color

I would like to customize the color of the box status of my shiny app.
I find a css way to change the box background color of these box but not to customize the status color, but I do not see the equivalent argument of "status" in css?
I thus print the source code of a simple page containing the considered argument "status" and I was lookin at its class (I think class="box box-solid box-primary") but I do not manage to reach it in the several .css provided in this webpage... :(
Do you have an idea ?
Here is this simple code :
library(shiny)
library(shinydashboard)
ui <- dashboardPage(
dashboardHeader(),
dashboardSidebar(),
dashboardBody(
fluidRow(
box(width = 6, title = "youhou", status = "primary", solidHeader = TRUE,
"Box content"
)
)
)
)
server <- function(input, output) {}
shinyApp(ui, server)
Thank you in advance for any help !
Cha
I finally found the answer (long and tough but always gratifying :D)
One of my friend (Thank you so much my friend !!!) shows me how to display all css parameters of each element of a web page (and particularly of a shiny page: go to the appropriate page and right click, something like "examine the element"!!
So AMAZING !!
Then, I look deeper (very very very deeper, there is so much classes !!) and I managed to access to any css parameter of the boxes !
Here is the code for the next people :
library(shiny)
library(shinydashboard)
ui <- dashboardPage(
dashboardHeader(),
dashboardSidebar(),
dashboardBody(
tags$style(HTML("
.box.box-solid.box-primary>.box-header {
color:#fff;
background:#666666
}
.box.box-solid.box-primary{
border-bottom-color:#666666;
border-left-color:#666666;
border-right-color:#666666;
border-top-color:#666666;
}
")),
fluidRow(
box(width = 6, title = "youhou", status = "primary", solidHeader = TRUE,
"Box content"
)
)
)
)
server <- function(input, output) {}
shinyApp(ui, server)
Have a good week-end !!
Cheers !
This is brilliant and worked really well for me! I just wanted to add that there is a small bit of code you can add if you want to be able to use the new color with solidHeader = FALSE (to get at Dmitri's question). You need to change the color of the text in the header (I am now using black) and my new 'status' is purple. Here is an example below (where I am replacing the danger status rather than primary):
library(shiny)
library(shinydashboard)
ui <- dashboardPage(
dashboardHeader(),
dashboardSidebar(),
dashboardBody(
tags$style(HTML("
.box.box-solid.box-danger>.box-header {
color:#fff;
background:#9966ff
}
.box.box-solid.box-danger{
border-bottom-color:#9966ff;
border-left-color:#9966ff;
border-right-color:#9966ff;
border-top-color:#9966ff;
}
.box.box-danger>.box-header {
color:#000000;
background:#fff
}
.box.box-danger{
border-bottom-color:#9966ff;
border-left-color:#9966ff;
border-right-color:#9966ff;
border-top-color:#9966ff;
}
")),
fluidRow(
box(width = 6, title = "youhou", status = "danger", solidHeader = FALSE,
"Box content"
)
)
)
)
server <- function(input, output) {}
shinyApp(ui, server)
(I found the right argument for this kind of box by following the OP's instructions to display all the css parameters.)
As I was trying to change the status color for hours now, I think I'd share my solution here, if anyone ever runs into the same problem again.
I was trying to edit the CSS code in a dedicated CSS file but that was not working. But when I added the CSS code directly into the shiny app file via tags$style (like the solutions provided by Charlotte Sirot and Michelle Ross) it worked.
Could have something to do with prioritizing the source of CSS style code, and directly adding the code with tags$style overrides all other sources.
I'm just building from #Michelle Ross and #Charlotte Sirot excellent answers and hoping that someone else also will benefit from this variation: I wanted to customize different colors for different statuses, here I chose "danger" and "info". I also wanted the box content background to be filled with color. To acheive that I used the following code:
library(shiny)
library(shinydashboard)
ui <- dashboardPage(
dashboardHeader(),
dashboardSidebar(),
dashboardBody(
tags$style(HTML("
.box.box-solid.box-danger>.box-header {
color:#9966ff;
background:#9966ff
}
.box.box-solid.box-danger{
border-bottom-color:#9966ff;
border-left-color:#9966ff;
border-right-color:#9966ff;
border-top-color:#9966ff;
}
.box.box-danger>.box-header {
color:#fff;
background:#9966ff
}
.box.box-danger{
border-bottom-color:#9966ff;
border-left-color:#9966ff;
border-right-color:#9966ff;
border-top-color:#9966ff;
background: #9966FF;
}
.box.box-solid.box-info>.box-header {
color:#000000;
background:#FFAE66
}
.box.box-solid.box-info{
border-bottom-color:#FFAE66;
border-left-color:#FFAE66;
border-right-color:#FFAE66;
border-top-color:#FFAE66;
}
.box.box-info>.box-header {
color:#fff;
background:#FFAE66
}
.box.box-info{
border-bottom-color:#FFAE66;
border-left-color:#FFAE66;
border-right-color:#FFAE66;
border-top-color:#FFAE66;
background: #FFAE66;
}
")),
fluidRow(
box(width = 6, title = "youhou", status = "danger", solidHeader = FALSE,
"Box content"
),
box(width = 6, title = "Hanna", status = "info", solidHeader = F,
"blabla")
)
)
)
server <- function(input, output) {}
shinyApp(ui, server)
And generated a shinydashboard with boxes like this:

Resources