---
title: "loadingButton and showToast"
author: "Andy Merlino"
date: "`r Sys.Date()`"
output: rmarkdown::html_vignette
vignette: >
  %\VignetteIndexEntry{loadingButton and showToast}
  %\VignetteEngine{knitr::rmarkdown}
  %\VignetteEncoding{UTF-8}
---

# loadingButton

`loadingButton` is similar to `shiny::actionButton()` but, when clicked, it 
changes styles to resemble a loading state.  Your Shiny app can then make some
calculations or execute some database queries while the button is in this loading
state.  Once your app is done loading, call `resetLoadingButton()` to restore the
loading button to an active state.

<video width="100%" height="240" autoplay loop muted playsinline src="loadingButton.mp4"></video>

```{r, eval = FALSE}
library(shiny)
library(shinyFeedback)

ui <- fluidPage(
  fluidRow(
    column(
      12,
      br(),
      loadingButton(
        "myLoadingButton", 
        label = "Submit"
      ),
      loadingButton(
        "myCancelButton", 
        label = "Cancel",
        class = "btn btn-danger",
        loadingLabel = "Cancelling...",
      )
    )
  )
)

server <- function(input, output, session) {
  
  
  # reset the loadingButton to its active state after 3 seconds
  observeEvent(input$myLoadingButton, {
    Sys.sleep(3)
    resetLoadingButton("myLoadingButton")
  })
  
  observeEvent(input$myCancelButton, {
    Sys.sleep(3)
    resetLoadingButton("myCancelButton")
  })
  
}


shinyApp(ui, server)
```

# showToast

Show a toast notification.  `showToast()` wraps the JavaScript [toastr library](https://github.com/CodeSeven/toastr).  To use `showToast()` include `useShinyFeedback()`
at the top of your ui.  If you only want to use the toasts you can set the "feedback" argument
to `FALSE` to only include css and js for the toasts.

<video width="100%" height="240" autoplay loop muted playsinline src="showToast.mp4"></video>

```{r, eval = FALSE}
library(shiny)
library(shinyFeedback)

ui <- fluidPage(
  useShinyFeedback(feedback = FALSE),
  fluidRow(
    column(
      12,
      br(),
      loadingButton(
        "myFirstButton", 
        label = "Submit"
      )
    )
  )
)

server <- function(input, output, session) {
  
  
  # reset the loadingButton to its active state after 2 seconds
  observeEvent(input$myFirstButton, {
    Sys.sleep(2)
    resetLoadingButton("myFirstButton")
    showToast(
      "success", 
      "I'll toast to that!"
    )
  })
  
}

shinyApp(ui, server)

```

shinyFeedback is not the first R package to wrap the toastr JavaScript library. The [shinytoastr package](https://github.com/MangoTheCat/shinytoastr) did this years ago.  The main difference between the `shinyFeedback::showToast()` implementation and `shinytoastr`'s is that we
supply a ".options" argument rather than having an argument for each toastr option.  This allows
you to more easily set global toast options. e.g.

```{r, eval = FALSE}
# use this list for all your toasts
myToastOptions <- list(
  positionClass = "toast-top-right",
  progressBar = FALSE,
  timeOut = 3000,
  closeButton = TRUE,

  # same as defaults
  newestOnTop = TRUE,
  preventDuplicates = FALSE,
  showDuration = 300,
  hideDuration = 1000,
  extendedTimeOut = 1000,
  showEasing = "linear",
  hideEasing = "linear",
  showMethod = "fadeIn",
  hideMethod = "fadeOut"
)


library(shiny)
library(shinyFeedback)

ui <- fluidPage(
  useShinyFeedback(feedback = FALSE),
  fluidRow(
    column(
      12,
      br(),
      loadingButton(
        "myLoadingButton", 
        label = "Submit"
      ),
      loadingButton(
        "myErrorButton", 
        label = "Error",
        class = "btn btn-danger",
        loadingLabel = "Erroring...",
      )
    )
  )
)

server <- function(input, output, session) {
  
  
  # reset the loadingButton to its active state after 2 seconds
  observeEvent(input$myLoadingButton, {
    Sys.sleep(2)
    resetLoadingButton("myLoadingButton")
    showToast(
      "success", 
      "I'll toast to that!", 
      .options = myToastOptions
    )
  })
  
  observeEvent(input$myErrorButton, {
    Sys.sleep(2)
    resetLoadingButton("myErrorButton")
    showToast(
      "error", 
      "Your toast is on fire!", 
      .options = myToastOptions
    )
  })
  
}




shinyApp(ui, server)
```



