Tips for adding CSS styling to the action button within the ShinyWidgets package in Shiny applications

I have created a shiny app example below. In order to align the actionButton with selectInput, I had to include style='margin-top:25px'. The Shinywidgets package offers actionBttn widgets with predefined styles. For instance, I prefer the one with style='gradient'. However, I am curious about how I can use CSS styling to add top margin and align the actionBttn with other elements.

library(shiny)
library(shinydashboard)
library(shinyWidgets)


ui <- dashboardPage(
    dashboardHeader(title = "example"),
    dashboardSidebar(),
    dashboardBody(
        box(width=12,

            column(width = 3, dateRangeInput("dateRange", "Date Range",
                                             start  = "2017-01-01",
                                             end    =  Sys.Date(),
                                             min    = "2001-01-01",
                                             max    = Sys.Date(),
                                             format = "mm/dd/yy",
                                             separator = " - ") ),

            column(width=3, selectizeInput(inputId = 'var', 
                                           label='Select variable',
                                           choices = c('cut', 'color'), 
                                           multiple=FALSE,
                                           options = list(
                                               maxItems = 1,
                                               placeholder = '',
                                               onInitialize = I("function() { this.setValue(''); }"))) ),

            column(width=1,  offset =2, actionButton('Apply', 'Apply', style='margin-top:25px') ),

            column(width=3,  actionBttn(
                inputId = 'clear',
                label = "Clear", 
                style = "gradient",
                color = "danger" ) )

        )
    )
)

server <- function(input, output, session) {

}

shinyApp(ui, server)

Answer №1

When you need to add a specific style to an existing element generated by a package, there are various approaches you can take:

  1. One method is to wrap the element itself in a div with the desired style, although this may not work for all CSS elements.

  2. You can create a custom function using the source code of the element you're interested in. For example, you can refer to the source code from this link.

  3. Another approach is to incorporate external CSS that specifically targets the element you want to modify. However, this method is less preferred as it separates the styling logic from its application location, requiring you to manage it for each element individually.


library(shiny)
library(shinyWidgets)

# Custom function for the second approach
actionBttn_with_style <- function(inputId, label = NULL, icon = NULL, style = "unite",
                       color = "default", size = "md", block = FALSE,
                       no_outline = TRUE, my_additional_style = "") {
  value <- shiny::restoreInput(id = inputId, default = NULL)
  style <- match.arg(
    arg = style,
    choices = c("simple", "bordered", "minimal", "stretch", "jelly",
                "gradient", "fill", "material-circle", "material-flat",
                "pill", "float", "unite")
  )
  color <- match.arg(
    arg = color,
    choices = c("default", "primary", "warning", "danger", "success", "royal")
  )
  size <- match.arg(arg = size, choices = c("xs", "sm", "md", "lg"))

  tagBttn <- htmltools::tags$button(
    id = inputId, type = "button", class = "action-button bttn", `data-val` = value,
    class = paste0("bttn-", style), 
    class = paste0("bttn-", size),
    class = paste0("bttn-", color), list(icon, label),
    class = if (block) "bttn-block",
    class = if (no_outline) "bttn-no-outline",
    style = my_additional_style
  )
  shinyWidgets:::attachShinyWidgetsDep(tagBttn, "bttn")
}

Once you have created your customized button function, you can use it similar to actionBttn within your ui.

ui <- dashboardPage(
  dashboardHeader(
    title = "example"
    ),
  dashboardSidebar(),
  dashboardBody(

    # Adding external CSS for approach #3, although this separates the styling logic
    htmltools::tags$head(
      htmltools::tags$style('button#clear_ext_css { margin-top:25px }')
    ),

    box(
      width = 12,

      column(
        width = 2,
        dateRangeInput(
          "dateRange",
          "Date Range",
          start  = "2017-01-01",
          end    =  Sys.Date(),
          min    = "2001-01-01",
          max    = Sys.Date(),
          format = "mm/dd/yy",
          separator = " - "
        )
      ),

      column(
        width = 1,
        actionButton('Apply', 'Apply', style = 'margin-top:25px')
      ),

      column(
        width = 3,
        # Applying approach #1 by wrapping it in a styled div
        div(
          actionBttn(
            inputId = 'clear_div',
            label = "Clear with div",
            style = "gradient",
            color = "danger"
          ),
          style = 'margin-top:25px'
        )
      ),
      column(
        width = 3,
        # Using the custom function from approach #2
        actionBttn_with_style(
          inputId = 'clear_fn',
          label = "Clear with custom function",
          style = "gradient",
          color = "danger",
          my_additional_style = 'margin-top:25px'
        )
      ),
      column(
        width = 3,
        # Implementing approach #3 with custom CSS
        actionBttn(
          inputId = 'clear_ext_css',
          label = "Clear with external CSS",
          style = "gradient",
          color = "danger"
        )
      )


    )
  )
)

server <- function(input, output, session) {

}

shinyApp(ui, server)

https://i.sstatic.net/1Ekof.png

Answer №2

Responding after some time in case this information is still relevant.

To modify the actionbttn element, you can make the necessary changes in a .css file located in the www directory.

The selector for your button should be as follows:

button#submit.action-button.bttn.bttn-bordered.bttn-md.bttn-default.bttn-no-outline.shiny-bound-input 

Your .css file should be structured like this:


button#clear.action-button.bttn.bttn-gradient.bttn-md.bttn-danger.bttn-no-outline.shiny-bound-input
{
  margin-top:25px
}

I chose 25px as it provided better alignment:

https://i.sstatic.net/BBeky.png

Below is the code snippet:

library(shiny)
library(shinydashboard)
library(shinyWidgets)

ui <- dashboardPage(dashboardHeader(title = "example"),
                    dashboardSidebar(),
                    dashboardBody(tags$head(
                      includeCSS('www/style.css'),
                      box(
                        width = 12,
                        
                        column(
                          width = 3,
                          dateRangeInput(
                            "dateRange",
                            "Date Range",
                            start  = "2017-01-01",
                            end    =  Sys.Date(),
                            min    = "2001-01-01",
                            max    = Sys.Date(),
                            format = "mm/dd/yy",
                            separator = " - "
                          )
                        ),
                        
                        column(
                          width = 3,
                          selectizeInput(
                            inputId = 'var',
                            label = 'Select variable',
                            choices = c('cut', 'color'),
                            multiple = FALSE,
                            options = list(
                              maxItems = 1,
                              placeholder = '',
                              onInitialize = I("function() { this.setValue(''); }")
                            )
                          )
                        ),
                        
                        column(
                          width = 1,
                          offset = 2,
                          actionButton('Apply', 'Apply', style = 'margin-top:25px')
                        ),
                        
                        column(
                          width = 3,
                          actionBttn(
                            inputId = 'clear',
                            label = "Clear",
                            style = "gradient",
                            color = "danger"
                          )
                        )
                      )
                      
                    )))

server <- function(input, output, session) {
  
}

shinyApp(ui, server)

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Tips for resolving the issue with "Text Animation"

Could someone please help with fixing this CSS animation? I want to align the text animation to the paragraph properly. I'm not confident if I am approaching this in the correct way, so if there is a simpler solution out there, I would appreciate lea ...

What are the best methods for aligning pseudo elements vertically?

I am facing an issue with the placement of a before and after pseudo element for articleSubTitle. The problem occurs when the text from articleSubTitle wraps to a new line within a small container or on mobile devices. This causes the after element to appe ...

What's the best way to get rid of the one-pixel gap between these elements on high-resolution displays like

http://jsfiddle.net/36ykrp9x/5/ HTML <div class="container"> <button>O</button><button>O</button> </div> CSS .container { width: 100%; background-color: rgb(120, 200, 200); text-align: center; } butt ...

Optimizing image centering in Next JS as screen size expands

I've been struggling to work with NextJS's Image component. My goal is to set up a banner image that only covers a specific amount of space on the screen, regardless of screen size. I have managed to achieve this by using max-height: 30vh and ov ...

Setting the CSS position to fixed for a dynamically generated canvas using JavaScript

My goal is to fix the position style of the canvas using JavaScript in order to eliminate scroll bars. Interestingly, I can easily change the style using Chrome Inspector with no issues, but when it comes to implementing it through JS, I face difficulties. ...

Transfer files to folders with similar names by utilizing R programming language

I need help transferring files to folders with matching filenames. Here is a snippet of the filenames: 20201026_ABCD.txt 20201026_XYZ.txt 20201027_ABCD.txt 20201027_POR.txt 20201028_ABCD.txt 20201028_PQR.txt I am looking to create folders using only the ...

Challenges of Using Flexbox in Media Queries

How can I use flex boxes in CSS to ensure that from a min-width of 769px to 1025px, the third figure is displayed on a new line while the first and second figures remain on the top line taking up equal space? <div class="mid-col-section-2"> <figu ...

Center alignment is not possible for the Div element

Problem Every time I attempt to implement the following code (outlined below), the div only appears centered when using width: 100px;. <div style="border: solid 1px black; width: 100px; height: 100px; background-color: blue; margin-left: auto; mar ...

The performance of my Wordpress site is being hindered by the slowdown caused by Admin

I have a Wordpress website focused on winter sports vacations in Iceland: link Every plugin, WordPress core, and theme are up to date. Using Woocommerce for my online store. However, activating the Woocommerce plugin causes the site to slow down signific ...

div with fixed position and scrollable content

I'm exploring ways to create a simple webpage layout inspired by the traditional index setup. The idea is to have a fixed header/navbar div that is 200px in height, with a second div below it containing scrollable content that fills the remaining vert ...

Unable to load variables into site.css in order for Flask app to successfully render home.html

I'm encountering difficulties in getting my site.css file to accept two variables passed in from my app.py using Jinja2 templates, namely {{ variable }}. In app.py, I have defined two variables named empty_fill_line and fill_line, which dynamically up ...

What is the process for multiplying a matrix by a vector and then transferring the outcome to a vector within TMB in R programming?

Currently, I am trying to perform a matrix multiplied by vector operation that results in a single number. I then need to pass this result to a vector in my code. However, the commented section of code below is causing issues: C++ Code #include <TMB.h ...

Having trouble getting the JavaScript function to run when clicking a button inside a div or form?

Hey there, so I've got this scenario where I have a button nestled within a div. Take a look at the HTML snippet below: <div class="row"> <button type="button" id="submit">Send</button> </div> Prior to this button, there ...

Exploring techniques for identifying the highest value within the last 20 rows of a column in R programming

Is there a way to determine the maximum value in the 20 rows preceding a specific row in a column using R? To clarify, suppose I have price data for the past 40 days. On day 21, I would like to identify the highest price recorded in the preceding 20 days ...

The symbol $column_name in R is analogous to the base pipe operator |>

One method I frequently utilize is using dplyr piping to extract a column from a tibble into a vector, demonstrated below: iris %>% .$Sepal.Length iris %>% .$Sepal.Length %>% cut(5) Is there a way to achieve the same outcome using the latest R bu ...

Font size determined by both the width and height of the viewport

I'll be brief and direct, so hear me out: When using VW, the font-size changes based on the viewport width. With VH, the font-size adjusts according to the viewport height. Now, I have a question: Is there a way to scale my font-size based on ...

The Bootstrap navigation menu fails to extend the parent div when toggled

When I toggle the button to show the menu on small screens, the menu overflows the parent div with id=contents instead of pushing it down. How can this issue be fixed? Here is the code: <body> <nav id="header" class="navbar navbar-default"& ...

Top method for utilizing jQuery to locate, sift through, and implement CSS classes

Let's consider the following scenario: <span class="foo">7</span> <span class="foo">2</span> <span class="foo">9</span> We want to assign a CSS class of 'highest' to 'span.foo' with value great ...

Aligning the Navigation icons on my webpage

<nav> <ul> <li><a href="index.php">Home</a></li> <li><a href="index.php?about">About</a></li> <li><a href="index.php?products">Products</ ...

Is it possible to enable tab navigation for a button located within a div when the div is in focus?

I have a component set up like this: (Check out the Code Sandbox example here: https://codesandbox.io/s/boring-platform-1ry6b2?file=/src/App.js) https://i.sstatic.net/ZuxdL.png The section highlighted in green is a div. Here is the code snippet: import { ...