glaze/oat/accordion
Oat documentation: https://oat.ink/components/accordion/
The accordion helpers render semantic HTML accordion markup
using <details> and <summary> elements.
Anatomy
An accordion is a container of collapsible sections rendered as
<details><summary>...</summary>...</details>.
Most apps compose it from item entries, with optional group wrappers
when you want browser-native single-open behavior per group.
Group behaviour
Items inside a group get a shared name attribute on their
underlying <details> elements. Browsers use this to treat them as a
mutually-exclusive set, so opening one closes others with the same name.
Items not placed in a group are rendered without a name attribute and can
be opened independently.
Recipes
A basic accordion inside a section
import glaze/oat/accordion
import lustre/element/html
fn faq() {
accordion.accordion(
html.section,
[],
[
accordion.item(
label: html.text("What is Oat?"),
content: [html.p([], [html.text("A UI toolkit for Lustre.")])],
),
accordion.item(
label: html.text("Does it use semantic HTML?"),
content: [html.p([], [html.text("Yes, with details/summary.")])],
),
],
)
}
Multiple groups in one container
import glaze/oat/accordion
import lustre/element/html
fn settings_panels() {
accordion.accordion(
html.div,
[],
[
accordion.group("account", [
accordion.item(label: html.text("Profile"), content: [html.text("...")]),
accordion.item(label: html.text("Security"), content: [html.text("...")]),
]),
accordion.group("notifications", [
accordion.item(label: html.text("Email"), content: [html.text("...")]),
accordion.item(label: html.text("Push"), content: [html.text("...")]),
]),
],
)
}
References
- MDN
<details>: https://developer.mozilla.org/en-US/docs/Web/HTML/Element/details - MDN
<summary>: https://developer.mozilla.org/en-US/docs/Web/HTML/Element/summary
Types
Values
pub fn accordion(
element: fn(
List(attribute.Attribute(msg)),
List(element.Element(msg)),
) -> element.Element(msg),
attrs: List(attribute.Attribute(msg)),
children: List(Item(msg)),
) -> element.Element(msg)
Render an accordion container from a list of items.
You provide:
element: the container constructor (for examplehtml.div,html.section)attrs: attributes for that containerchildren: items and/or groups to render
Each item renders to:
<details><summary>{label}</summary>{content...}
Grouped items include a shared name attribute on <details> to enable
browser-native single-open behavior within that group.
pub fn group(name: String, items: List(Item(msg))) -> Item(msg)
Create a named group of accordion items.
All items in a group are rendered with <details name="{name}">, allowing
the browser to manage them as a mutually-exclusive set.
Use distinct names for separate groups.
pub fn item(
label label: element.Element(msg),
content content: List(element.Element(msg)),
) -> Item(msg)
Create a single accordion item.
The label is rendered inside <summary>, and content is rendered as the
body of the corresponding <details>.
Keep the label concise and descriptive for accessibility and scanning.