-
Notifications
You must be signed in to change notification settings - Fork 80
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Update style of nested data #170
Comments
For 1, yes, here's the same status badges example but using a JavaScript render function instead. The JavaScript is similar to the R code, except it generates a raw HTML string like library(reactable)
set.seed(20)
orders <- data.frame(
Order = 2300:2304,
Created = seq(as.Date("2019-04-01"), by = "day", length.out = 5),
Customer = sample(rownames(MASS::painters), 5),
Status = sample(c("Pending", "Paid", "Canceled"), 5, replace = TRUE),
stringsAsFactors = FALSE
)
reactable(
orders,
columns = list(
Status = colDef(
cell = JS("function(cellInfo) {
let color
switch (cellInfo.value) {
case 'Paid':
color = 'hsl(214, 45%, 50%)'
break
case 'Pending':
color = 'hsl(30, 97%, 70%)'
break
case 'Canceled':
color = 'hsl(3, 69%, 50%)'
break
}
const badgeStyle = 'display: inline-block; margin-right: 8px; width: 9px; height: 9px;' +
'background-color: ' + color + '; border-radius: 50%'
const badge = '<span style=\"' + badgeStyle + '\"></span>'
return badge + cellInfo.value
}"),
html = TRUE
)
)
) For 2, you'll have to use However, I still might recommend using Here's the same example from the reprex, but with some tweaks to update the data immediately on approve/reject button clicks. Before, the library(shiny)
library(reactable)
library(htmltools)
library(RSQLite)
pool <- pool::dbPool(RSQLite::SQLite(), dbname = "db.sqlite")
# load data only once
t <- try(dbReadTable(pool, "orders"), silent=T)
if ("try-error" %in% class(t)) {
orders <- data.frame(
Order = 2300:2304,
Created = seq(as.Date("2019-04-01"), by = "day", length.out = 5),
Customer = c("Cortona", "Cortona", "Del Sarto", "Del Sarto", "Del Sarto"),
Status = sample(c("Pending", "Paid", "Canceled"), 5, replace = TRUE),
stringsAsFactors = FALSE
)
dbWriteTable(pool, "orders", orders, overwrite = TRUE)
}
ui <- fluidPage(
titlePanel("Good looking tables!"),
sidebarLayout(
sidebarPanel(
actionButton("ok_button", "⠀Approve order", icon("check")),
actionButton("notok_button", "⠀Reject order", icon("times-circle"))
),
mainPanel(
reactableOutput("orders_table")
)
)
)
status_badge <- function(color = "#aaa", width = "9px", height = width) {
span(style = list(
display = "inline-block",
marginRight = "8px",
width = width,
height = height,
backgroundColor = color,
borderRadius = "50%"
))
}
server <- function(input, output) {
orders_rv <- reactiveVal()
update_orders <- function() {
orders <- dbReadTable(pool, "orders")
orders_rv(orders)
}
update_orders()
orders_table_selected <- reactive(getReactableState("orders_table", "selected"))
approve_order <- function(data){
df <- orders_rv()
row_selection <- orders_table_selected()
df[row_selection, "Status"] <- "Paid"
dbWriteTable(pool, "orders", df, overwrite = TRUE)
}
reject_order <- function(data){
df <- orders_rv()
row_selection <- orders_table_selected()
df[row_selection, "Status"] <- "Canceled"
dbWriteTable(pool, "orders", df, overwrite = TRUE)
}
observeEvent(input$ok_button, {
approve_order()
update_orders()
})
observeEvent(input$notok_button, {
reject_order()
update_orders()
})
output$orders_table <- renderReactable({
reactable(
orders_rv(),
groupBy = "Customer",
defaultExpanded = TRUE,
selection = "single",
onClick = "select",
columns = list(
Status = colDef(cell = function(value) {
color <- switch(
value,
Paid = "hsl(214, 45%, 50%)",
Pending = "hsl(30, 97%, 70%)",
Canceled = "hsl(3, 69%, 50%)"
)
badge <- status_badge(color = color)
tagList(badge, value)
})
))
})
}
shinyApp(ui = ui, server = server) If you still want to use Also, you can still use a reactive data value with the table like this, but it has to be wrapped in library(shiny)
library(reactable)
library(htmltools)
library(RSQLite)
pool <- pool::dbPool(RSQLite::SQLite(), dbname = "db.sqlite")
# load data only once
t <- try(dbReadTable(pool, "orders"), silent=T)
if ("try-error" %in% class(t)) {
orders <- data.frame(
Order = 2300:2304,
Created = seq(as.Date("2019-04-01"), by = "day", length.out = 5),
Customer = c("Cortona", "Cortona", "Del Sarto", "Del Sarto", "Del Sarto"),
Status = sample(c("Pending", "Paid", "Canceled"), 5, replace = TRUE),
stringsAsFactors = FALSE
)
dbWriteTable(pool, "orders", orders, overwrite = TRUE)
}
ui <- fluidPage(
titlePanel("Good looking tables!"),
sidebarLayout(
sidebarPanel(
actionButton("ok_button", "⠀Approve order", icon("check")),
actionButton("notok_button", "⠀Reject order", icon("times-circle"))
),
mainPanel(
reactableOutput("orders_table")
)
)
)
server <- function(input, output) {
orders_rv <- reactiveVal({
dbReadTable(pool, "orders")
})
update_orders <- function() {
orders <- dbReadTable(pool, "orders")
orders_rv(orders)
updateReactable("orders_table", data = orders, expanded = TRUE)
}
orders_table_selected <- reactive(getReactableState("orders_table", "selected"))
approve_order <- function() {
df <- orders_rv()
row_selection <- orders_table_selected()
df[row_selection, "Status"] <- "Paid"
dbWriteTable(pool, "orders", df, overwrite = TRUE)
}
reject_order <- function() {
df <- orders_rv()
row_selection <- orders_table_selected()
df[row_selection, "Status"] <- "Canceled"
dbWriteTable(pool, "orders", df, overwrite = TRUE)
}
observeEvent(input$ok_button, {
approve_order()
update_orders()
})
observeEvent(input$notok_button, {
reject_order()
update_orders()
})
output$orders_table <- renderReactable({
reactable(
isolate(orders_rv()),
groupBy = "Customer",
defaultExpanded = TRUE,
selection = "single",
onClick = "select",
columns = list(
Status = colDef(
cell = JS("function(cellInfo) {
let color
switch (cellInfo.value) {
case 'Paid':
color = 'hsl(214, 45%, 50%)'
break
case 'Pending':
color = 'hsl(30, 97%, 70%)'
break
case 'Canceled':
color = 'hsl(3, 69%, 50%)'
break
}
const badgeStyle = 'display: inline-block; margin-right: 8px; width: 9px; height: 9px;' +
'background-color: ' + color + '; border-radius: 50%'
const badge = '<span style=\"' + badgeStyle + '\"></span>'
return badge + cellInfo.value
}"),
html = TRUE
)
)
)
})
}
shinyApp(ui = ui, server = server) |
Thank you for the detailed answer, it helped me a lot! |
Hi, following up on this issue, I´m having trouble trying to update the tags and badges cookbook example, grouped by client, using a button in shiny.
Here is the reprex:
The text was updated successfully, but these errors were encountered: