Every control in this package has the same shape, and this builds it: a
host element carrying the id, the Element markup inside it, and the Vue
options beside them, which the package's bridge script compiles in place.
The host is a Shiny input binding, so it is the component to the rest of
Shiny – shinyjs::hide("id") hides it, removeUI("#id") removes it and
destroys its Vue instance, and its value is input$<id>.
Usage
el_widget(
id,
markup,
data,
methods = NULL,
watch = NULL,
mounted = NULL,
computed = NULL,
emits = NULL,
dependency = NULL,
head = NULL,
width = NULL,
slots = NULL,
input = NULL,
rate = NULL,
type = NULL,
label = NULL,
label_position = c("top", "left", "right"),
label_width = NULL,
label_suffix = NULL,
required = FALSE,
error = NULL,
show_message = TRUE,
inline_message = FALSE,
props = NULL,
absorbed = NULL
)Arguments
- id
The element id – inside a module, wrapped in
ns(). It is the input id of the valueinputnames.- markup
The Element markup to mount on, usually one
htmltools::tag().- data
The Vue instance's data. Every field that
update_el_*()may set has to be declared here – Vue does not track one that is not.- methods, watch, mounted, computed
Vue options, included when not
NULL.- emits
Events the component sends with
$emit(): each arrives asinput$<id>_<event>, as forvue_app().- dependency
htmlDependency objects to attach, beside Vue, Element Plus and the bridge, which every component carries.
- head
Tags to place before the host, such as a
<style>block.- width
Component width, as a CSS unit. Applied to the Element markup itself – the host carries
display: contentsand generates no box, so a width set on it would do nothing.- slots
Named list of slot contents, one entry per Element slot:
list(title = tags$b("Bold"))fills thetitleslot. A component given here is absorbed like any other (.el_absorb()). For a scoped slot, where Element hands the template its own data, write the template withtemplate()and the value is used as it stands.- input
The field of
datathat isinput$<id>, or several for one value made of them, asvue_app()'sinput: the Shiny binding reads it on load and on every change, and a test driver orshinyjssees it. Anupdate_vue()from the server counts as a change.- rate
How often the value is sent while it changes:
list(policy = "debounce", delay = 250), as Shiny'stextInput()does, or"throttle".NULL, the default, sends every change.- type
An input type for
shiny::registerInputHandler(), which converts the value on its way into R.- label
A label shown with the component, as Shiny's inputs have: text or a tag.
NULL, the default, shows none. It is the component's accessible name too – tied to it withforwhere the component has a native input that takes the id<id>-input, else witharia-labelledby.- label_position
Where the label sits, as
el_form()'slabel_position:"top"(the default, as Shiny's labels sit), or beside the component, its text aligned"left"or"right"– which shows oncelabel_widthgives the labels a common width.- label_width
Width of a label beside the component, as a CSS unit, so that several line up. Element's
label-width.- label_suffix
Text after the label, such as
":". Element'slabel-suffix.- required
Draw Element's red asterisk before the label. It marks the field; it does not check it – shinyvalidate or
el_form()does that.- error
An error message shown under the component in Element's style, the field framed in red. Element's
error.- show_message, inline_message
Whether
error's message is shown, and whether beside the component rather than under it. Element'sshow-messageandinline-message.- props
Optional props from
.el_props(): bound on the root tag ofmarkup, with their fields added todata.- absorbed
The components folded into this one, by id: their fields as named here and the ref on each, so their updates reach them. Built by the package's wrappers; leave it
NULL.
Details
Reach for it to wrap an Element component this package does not cover, or
to build an input of your own from el tags; input names the value.
It is what the package's own components are made of: vue_app() with
Element Plus installed (use), and a label in Element's form-item style.
The raw Element tags come from el, and template() writes a slot.
Examples
# Wrapping el-avatar, which this package does not provide
my_avatar <- function(id, src, size = 50) {
el_widget(
id = id,
markup = el$avatar(":src" = "src", ":size" = "size"),
data = list(src = src, size = size)
)
}
my_avatar("face", "https://example.org/face.png")
#> <div id="face" data-shiny-vue style="display: contents">
#> <script type="text/x-template" data-shiny-vue-template><div id="face_container" style="display: contents">
#> <el-avatar :src="src" :size="size"></el-avatar>
#> </div></script>
#> <script type="application/json" data-shiny-vue-options>{"options":{"data":{"src":"https://example.org/face.png","size":50}},"input":null,"rate":null,"type":null,"use":["shinyElement.plugin"],"evals":[]}</script>
#> </div>
# An input of your own: v-model keeps `value` in step with the control,
# and `input` makes it input$score -- on load, on change, and after
# update_vue(session, "score", value = 5) from the server.
el_widget(
id = "score",
markup = el$rate("v-model" = "value", ":max" = "max"),
data = list(value = 3, max = 5),
input = "value"
)
#> <div id="score" data-shiny-vue style="display: contents">
#> <script type="text/x-template" data-shiny-vue-template><div id="score_container" style="display: contents">
#> <el-rate v-model="value" :max="max"></el-rate>
#> </div></script>
#> <script type="application/json" data-shiny-vue-options>{"options":{"data":{"value":3,"max":5}},"input":"value","rate":null,"type":null,"use":["shinyElement.plugin"],"evals":[]}</script>
#> </div>