-
Notifications
You must be signed in to change notification settings - Fork 1
Add Shiny output binding with g2output() and renderG2() #6
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
Changes from 1 commit
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,142 @@ | ||
| --- | ||
| title: Shiny | ||
| --- | ||
|
|
||
| gglite charts can be embedded in [Shiny](https://shiny.posit.co/) applications | ||
| using `render_shiny()`. Unlike `htmlwidgets`-based packages, gglite uses | ||
| Shiny's custom message passing to send chart specs to the browser, where the G2 | ||
| library renders them. | ||
|
|
||
| ## Setup | ||
|
|
||
| Every Shiny app using gglite needs three script tags in the `<head>` of the UI: | ||
|
|
||
| 1. The G2 JavaScript library from a CDN. | ||
| 2. The gglite column-major data helper. | ||
| 3. The gglite Shiny message handler (`g2-handler.js`), bundled with the package. | ||
|
|
||
| ```r | ||
| tags$head( | ||
| tags$script(src = 'https://unpkg.com/@antv/g2@5/dist/g2.min.js'), | ||
| tags$script( | ||
| src = 'https://cdn.jsdelivr.net/npm/@xiee/utils/js/g2-column.min.js' | ||
| ), | ||
| includeScript(system.file('www/g2-handler.js', package = 'gglite')) | ||
| ) | ||
|
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. it's tedious to repeat these lines in every shiny app, and these are also deep technical details that end-users shouldn't worry about; can we provide the traditional shiny syntax like if that's possible, we can get rid of render_shiny() i don't want to introduce hard dependencies for this task; dependencies in
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Done in 78c79dd.
Tested the binding in headless Playwright: element found with |
||
| ``` | ||
|
|
||
| The container `<div>` must have an explicit height (G2 charts will not appear | ||
| in a zero-height container) and an `id` that matches the `output_id` argument | ||
| you pass to `render_shiny()`: | ||
|
|
||
| ```r | ||
| div(id = 'my-chart', style = 'height:480px') | ||
| ``` | ||
|
|
||
| ## Basic Example | ||
|
|
||
| The simplest app renders a static chart when the session starts. Call | ||
| `render_shiny()` directly in the server function: | ||
|
|
||
| ```r | ||
| library(shiny) | ||
| library(gglite) | ||
|
|
||
| ui = fluidPage( | ||
| tags$head( | ||
| tags$script(src = 'https://unpkg.com/@antv/g2@5/dist/g2.min.js'), | ||
| tags$script( | ||
| src = 'https://cdn.jsdelivr.net/npm/@xiee/utils/js/g2-column.min.js' | ||
| ), | ||
| includeScript(system.file('www/g2-handler.js', package = 'gglite')) | ||
| ), | ||
| div(id = 'chart1', style = 'height:480px') | ||
| ) | ||
|
|
||
| server = function(input, output, session) { | ||
| render_shiny( | ||
| g2(mtcars, x = 'mpg', y = 'hp') |> mark_point(), | ||
| session, 'chart1' | ||
| ) | ||
| } | ||
|
|
||
| shinyApp(ui, server) | ||
| ``` | ||
|
|
||
| ## Reactive Example | ||
|
|
||
| Wrap `render_shiny()` in `observeEvent()` (or `observe()`) to re-render the | ||
| chart whenever an input changes. Pass `ignoreNULL = FALSE` so the chart also | ||
| renders on startup. The following app lets the user pick the y-axis variable | ||
| from a dropdown: | ||
|
|
||
| ```r | ||
| library(shiny) | ||
| library(gglite) | ||
|
|
||
| ui = fluidPage( | ||
| tags$head( | ||
| tags$script(src = 'https://unpkg.com/@antv/g2@5/dist/g2.min.js'), | ||
| tags$script( | ||
| src = 'https://cdn.jsdelivr.net/npm/@xiee/utils/js/g2-column.min.js' | ||
| ), | ||
| includeScript(system.file('www/g2-handler.js', package = 'gglite')) | ||
| ), | ||
| selectInput('yvar', 'Y variable', choices = c('hp', 'wt', 'qsec', 'drat')), | ||
| div(id = 'chart1', style = 'height:480px') | ||
| ) | ||
|
|
||
| server = function(input, output, session) { | ||
| observeEvent(input$yvar, { | ||
| render_shiny( | ||
| g2(mtcars, x = 'mpg', y = input$yvar) |> | ||
| mark_point() |> | ||
| title_of(input$yvar), | ||
| session, 'chart1' | ||
| ) | ||
| }, ignoreNULL = FALSE) | ||
| } | ||
|
|
||
| shinyApp(ui, server) | ||
| ``` | ||
|
|
||
| Each time the user picks a different variable, `render_shiny()` sends the | ||
| updated spec to the browser and G2 re-renders the chart in place. | ||
|
|
||
| ## Multiple Charts | ||
|
|
||
| You can render several charts independently by giving each container a distinct | ||
| `id` and calling `render_shiny()` once per chart: | ||
|
|
||
| ```r | ||
| library(shiny) | ||
| library(gglite) | ||
|
|
||
| ui = fluidPage( | ||
| tags$head( | ||
| tags$script(src = 'https://unpkg.com/@antv/g2@5/dist/g2.min.js'), | ||
| tags$script( | ||
| src = 'https://cdn.jsdelivr.net/npm/@xiee/utils/js/g2-column.min.js' | ||
| ), | ||
| includeScript(system.file('www/g2-handler.js', package = 'gglite')) | ||
| ), | ||
| fluidRow( | ||
| column(6, div(id = 'scatter', style = 'height:400px')), | ||
| column(6, div(id = 'bars', style = 'height:400px')) | ||
| ) | ||
| ) | ||
|
|
||
| server = function(input, output, session) { | ||
| render_shiny( | ||
| g2(mtcars, x = 'mpg', y = 'hp') |> mark_point(), | ||
| session, 'scatter' | ||
| ) | ||
| freq = as.data.frame(table(cyl = mtcars$cyl)) | ||
| render_shiny( | ||
| g2(freq, x = 'cyl', y = 'Freq') |> mark_interval(), | ||
| session, 'bars' | ||
| ) | ||
| } | ||
|
|
||
| shinyApp(ui, server) | ||
| ``` | ||
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
don't include news
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fixed in 78c79dd — NEWS.md is back to just the
# gglite 0.1heading.