A good use case for this component is a folder structure. For navigation and
other menus, a regular nested list should be preferred.
Maturity: Developing
Missing features
- Selecting a node. The component renders
aria-selected from the
selected attribute and never changes it, so the caller has to.
Usage
<.tree id="dog-tree" label="Dogs">
<.tree_item>
Breeds
<:items>
<.tree_item>Golden Retriever</.tree_item>
<.tree_item>Labrador Retriever</.tree_item>
</:items>
</.tree_item>
<.tree_item>
Characteristics
<:items>
<.tree_item>Playful</.tree_item>
<.tree_item>Loyal</.tree_item>
</:items>
</.tree_item>
</.tree>
From data
A tree_item with an :items slot is a branch, even if the slot is empty.
If you render the tree from data, conditionally hide the slot with an :if
attribute.
<.tree id="breed-tree" label="Breeds">
<.breed_node :for={node <- @nodes} node={node} />
</.tree>
defp breed_node(assigns) do
~H"""
<.tree_item>
{@node.name}
<:items :if={@node.children != []}>
<.breed_node :for={child <- @node.children} node={child} />
</:items>
</.tree_item>
"""
end
CSS
You can target the wrapper with an attribute selector for the role:
[role="tree"] {}
This component needs the Doggo.Tree JavaScript hook. See
Phoenix LiveView Hooks for
registering it.
Keyboard
Down and Up - move between the visible items. A collapsed branch takes
its children out of the sequence.
Right - expand the focused branch, or move to its first child if it is
already expanded.
Left - collapse the focused branch, or move to its parent if it is
already collapsed or is a leaf.
Home and End - first and last visible item.
- Printable characters - move to the next visible item whose label starts
with what you type.
The tree is a single tab stop. Expanding and collapsing is the hook's own
state, and it survives a LiveView patch. Selecting an item is not: the
component renders aria-selected from the selected attribute of
tree_item, so wire your own click or key handler and re-render.