---
title: "Simple Reporter"
output: rmarkdown::html_vignette
vignette: >
  %\VignetteIndexEntry{Simple Reporter}
  %\VignetteEngine{knitr::rmarkdown}
  %\VignetteEncoding{UTF-8}
---

```{r, include = FALSE}
knitr::opts_chunk$set(
  collapse = TRUE,
  comment = "#>"
)
```

Simple reporter is a `shiny` module for capturing app views during the session, and eventually downloading
a report document. The Simple reporter module consists of two separate modules one for each of the two buttons,
Add Card and Download Report buttons modules.

module designed to capture and visualize application views throughout a session, facilitating the generation and download of a comprehensive report document. This module consists of two separate modules one for each of the two buttons.

- Add card button.
- Download report button.

The implementation should consist of 4 steps:

1. Add modules UI component to the app's UI.
2. Initialize `Reporter` instance.
4. Create the report card function with two optional arguments: `card` and `comment`.
This function must return a `ReportCard` object.
The `ReportCard` object should be built step by step, assuming that it is empty at the beginning.
   - If the `comment` argument is provided, it should be added to the card.
   If not, it should be added automatically at the end of the card.
   - If the `card` argument is provided, the `ReportCard` instance should be automatically created for the user.
   If not, the function should create the card itself.
*Please note that the document page's design is up to the developer's imagination.*
4. Invoke the servers with the `Reporter` instance and the function to create the `ReportCard` instance.

The code added to introduce the reporter is wrapped in the `### REPORTER` code blocks.

First, load the required packages:

```{r message = FALSE, eval=requireNamespace("ggplot2")}
library(shiny)
library(bslib)
library(teal.reporter)
library(ggplot2)
library(rtables)
```

Simple reporter `shiny` app with separate modules for each button:

```{r, eval=requireNamespace("ggplot2") && interactive()}
ui <- bslib::page_fluid(
  titlePanel(""),
  sidebarLayout(
    sidebarPanel(
      uiOutput("encoding")
    ),
    mainPanel(
      ### REPORTER
      tags$div(
        add_card_button_ui("addReportCard"),
        download_report_button_ui("downloadButton"),
        reset_report_button_ui("resetButton")
      ),
      ###
      tags$br(),
      tabsetPanel(
        id = "tabs",
        tabPanel("Plot", plotOutput("dist_plot")),
        tabPanel("Table", verbatimTextOutput("table"))
      )
    )
  )
)

server <- function(input, output, session) {
  output$encoding <- renderUI({
    if (input$tabs == "Plot") {
      sliderInput(
        "binwidth",
        "binwidth",
        min = 2,
        max = 10,
        value = 8
      )
    } else {
      selectInput(
        "stat",
        label = "Statistic",
        choices = c("mean", "median", "sd"),
        "mean"
      )
    }
  })

  plot <- reactive({
    req(input$binwidth)
    x <- mtcars$mpg
    ggplot(data = mtcars, aes(x = mpg)) +
      geom_histogram(binwidth = input$binwidth)
  })

  output$dist_plot <- renderPlot({
    plot()
  })

  table <- reactive({
    req(input$stat)
    lyt <- basic_table() %>%
      split_rows_by("Month", label_pos = "visible") %>%
      analyze("Ozone", afun = eval(str2expression(input$stat)))

    build_table(lyt, airquality)
  })

  output$table <- renderPrint({
    table()
  })

  ### REPORTER
  reporter <- Reporter$new()
  card_fun <- function(card = ReportCard$new(), comment) {
    if (input$tabs == "Plot") {
      card$append_text("My plot", "header2")
      card$append_plot(plot())
    } else if (input$tabs == "Table") {
      card$append_text("My Table", "header2")
      card$append_table(table())
    }
    if (!comment == "") {
      card$append_text("Comment", "header3")
      card$append_text(comment)
    }
    card
  }

  add_card_button_srv("addReportCard", reporter = reporter, card_fun = card_fun)
  download_report_button_srv("downloadButton", reporter = reporter)
  reset_report_button_srv("resetButton", reporter)
  ###
}

shinyApp(ui = ui, server = server)
```

Simple reporter `shiny` app with combined buttons modules:

```{r, eval=requireNamespace("ggplot2") && interactive()}
ui <- bslib::page_fluid(
  titlePanel(""),
  sidebarLayout(
    sidebarPanel(
      uiOutput("encoding")
    ),
    mainPanel(
      ### REPORTER
      simple_reporter_ui("simpleReporter"),
      ###
      tabsetPanel(
        id = "tabs",
        tabPanel("Plot", plotOutput("dist_plot")),
        tabPanel("Table", verbatimTextOutput("table"))
      )
    )
  )
)

server <- function(input, output, session) {
  output$encoding <- renderUI({
    if (input$tabs == "Plot") {
      sliderInput(
        "binwidth",
        "binwidth",
        min = 2,
        max = 10,
        value = 8
      )
    } else {
      selectInput(
        "stat",
        label = "Statistic",
        choices = c("mean", "median", "sd"),
        "mean"
      )
    }
  })

  plot <- reactive({
    req(input$binwidth)
    x <- mtcars$mpg
    ggplot(data = mtcars, aes(x = mpg)) +
      geom_histogram(binwidth = input$binwidth)
  })

  output$dist_plot <- renderPlot({
    plot()
  })

  table <- reactive({
    req(input$stat)
    lyt <- basic_table() %>%
      split_rows_by("Month", label_pos = "visible") %>%
      analyze("Ozone", afun = eval(str2expression(input$stat)))

    build_table(lyt, airquality)
  })

  output$table <- renderPrint({
    table()
  })

  ### REPORTER
  reporter <- Reporter$new()

  # Optionally set reporter id to e.g. secure report reload only for the same app
  # The id is added to the downloaded file name.
  reporter$set_id("myappid")

  card_fun <- function(card = ReportCard$new(), comment) {
    if (input$tabs == "Plot") {
      card$append_text("My plot", "header2")
      card$append_plot(plot())
    } else if (input$tabs == "Table") {
      card$append_text("My Table", "header2")
      card$append_table(table())
    }
    if (!comment == "") {
      card$append_text("Comment", "header3")
      card$append_text(comment)
    }
    card
  }

  simple_reporter_srv("simpleReporter", reporter = reporter, card_fun = card_fun)
  ###
}

shinyApp(ui = ui, server = server)
```
