Breadcrumb¶
Header: winui/ui/navigation/Breadcrumb.hpp. Spec: winui/ui/navigation/Breadcrumb.hpp.
A navigation trail (Home > Folder > File) of plain text items, root first.
Every item but the last is a small inline button that raises on_item_click() with its index. The last is the current location. It is not clickable, has no trailing chevron and is never hovered or highlighted by the keyboard. The strip is one tab stop. Left/Right move a highlight among the clickable items, and Enter/Space activates it. The arrow keys alone never navigate. When the trail is wider than the control, the leading items fold into an ellipsis ("…"). Its flyout lists them nearest first, and picking one raises on_item_click() with that item's own index.
The control never changes its own items. A click is a request, and the handler decides what to do, usually cutting the trail back to the clicked item.
Example:
auto stack = std::make_unique<ui::StackControl>(ui::Orientation::Vertical);
ui::BreadcrumbControl* bar = stack->add(std::make_unique<ui::BreadcrumbControl>(
std::vector<std::string>{"Home", "Documents", "Design", "Northwind"}));
bar->on_item_click([bar](std::size_t index)
{
std::vector<std::string> items = bar->items();
items.resize(index + 1); // navigate up: drop everything after the clicked item
bar->set_items(std::move(items));
});
window.set_content(std::move(stack));
// Declaratively, reporting the clicked folder:
ui::Property<std::string> location{"Design"};
ui::Control<ui::Breadcrumb> crumbs;
window.set_content(ui::VerticalStack{
.content = {
ui::Breadcrumb{
.items = {"Home", "Documents", "Design"},
.on_item_click = [&](std::size_t index) { location = crumbs->items()[index]; },
.control = crumbs,
},
ui::Text{.text = location},
},
});
ui::Breadcrumb¶
A navigation trail (Home > Folder > File). Builds a ui::BreadcrumbControl. The last item is the current location and is plain text. Every earlier item fires .on_item_click when clicked or Enter/Space-activated.
Example:
ui::Control<ui::Breadcrumb> trail;
window.set_content(ui::Breadcrumb{
.items = {"Home", "Documents", "Design", "Northwind"},
.on_item_click = [&](std::size_t index)
{
// Navigate up: drop everything after the clicked folder.
std::vector<std::string> items = trail->items();
items.resize(index + 1);
trail->set_items(std::move(items));
},
.control = trail,
});
Every field, in the order a designated initializer names them:
ui::Breadcrumb{
.items, .style, .margin, .width, .height, .min_width, .min_height, .max_width, .max_height,
.horizontal_alignment, .vertical_alignment, .visible, .tool_tip, .enabled, .accessibility,
.on_item_click, .on_pointer_entered, .on_pointer_exited, .on_got_focus, .on_lost_focus,
.on_key_down, .on_wheel, .control
}
Fields, in declaration order (designators must follow it):
| Field | Type | Default | |
|---|---|---|---|
items |
ui::Binding<std::vector<std::string>> |
The trail, root first; the last entry is the current location. Bind it to a property and assign a shorter trail to go back up. | |
on_item_click |
ui::Callback<void(std::size_t)> |
Called with the index of an activated item. Never fires for the last (current) item. | |
on_pointer_entered |
ui::Action |
The pointer moved onto the control. | |
on_pointer_exited |
ui::Action |
The pointer left the control. | |
on_got_focus |
ui::Action |
Keyboard focus arrived on the control, or on anything inside it, from outside it. A control with nothing focusable in it never gets focus, and never raises this. | |
on_lost_focus |
ui::Action |
Keyboard focus left the control and everything inside it. | |
on_key_down |
ui::Callback<ui::Handling(const ui::KeyEvent&)> |
A key pressed while focus is on the control or inside it, before the control's own handling; ui::Handled stops it there (Element::on_key_down()). | |
on_wheel |
ui::Callback<ui::Handling(const ui::PointerEvent&)> |
A wheel turn over the control, before the control scrolls; ui::Handled stops it there (Element::on_wheel()). | |
control |
ui::ControlOut<ui::Breadcrumb> |
Out: the handle that receives the built control. |
Plus the common fields style, margin, width, height, min_width, min_height, max_width, max_height, horizontal_alignment, vertical_alignment, visible, tool_tip, enabled, accessibility every spec carries (conventions).
build¶
Consumes the spec and returns the built ui::BreadcrumbControl; the caller owns it.
ui::BreadcrumbControl¶
Derives from ui::Element, ui::ValueProvider.
A navigation trail (Home > Folder > File) of plain text items, root first.
Every item but the last is a small inline button that raises on_item_click() with its index. The last is the current location. It is not clickable, has no trailing chevron and is never hovered or highlighted by the keyboard. The strip is one tab stop. Left/Right move a highlight among the clickable items, and Enter/Space activates it. The arrow keys alone never navigate. When the trail is wider than the control, the leading items fold into an ellipsis ("…"). Its flyout lists them nearest first, and picking one raises on_item_click() with that item's own index.
The control never changes its own items. A click is a request, and the handler decides what to do, usually cutting the trail back to the clicked item.
Example:
auto stack = std::make_unique<ui::StackControl>(ui::Orientation::Vertical);
ui::BreadcrumbControl* bar = stack->add(std::make_unique<ui::BreadcrumbControl>(
std::vector<std::string>{"Home", "Documents", "Design", "Northwind"}));
bar->on_item_click([bar](std::size_t index)
{
std::vector<std::string> items = bar->items();
items.resize(index + 1); // navigate up: drop everything after the clicked item
bar->set_items(std::move(items));
});
window.set_content(std::move(stack));
// Declaratively, reporting the clicked folder:
ui::Property<std::string> location{"Design"};
ui::Control<ui::Breadcrumb> crumbs;
window.set_content(ui::VerticalStack{
.content = {
ui::Breadcrumb{
.items = {"Home", "Documents", "Design"},
.on_item_click = [&](std::size_t index) { location = crumbs->items()[index]; },
.control = crumbs,
},
ui::Text{.text = location},
},
});
BreadcrumbControl¶
An empty trail; it draws nothing and is not focusable.
BreadcrumbControl¶
A trail of items, root first; the last is the current location.
~BreadcrumbControl¶
Destroys the ellipsis flyout with the control.
BreadcrumbControl¶
Non-copyable, like every Element.
operator=¶
Non-copyable, like every Element.
items¶
The trail, root first (UTF-8); the last entry is the current location.
set_items¶
Replaces the item list and clears the hover, press and keyboard highlight, closing an open flyout. Updates the layout. Safe to call from inside on_item_click().
on_item_click¶
Fires with the index into items() when a clickable item is activated by a click, Enter/Space, or from the ellipsis flyout. Every item but the last is clickable. Replaces any previous handler.
ellipsis_shown¶
Whether the leading items are folded into the ellipsis because the trail did not fit its width, as of the last arrange.
first_shown_item¶
Index of the first item drawn after the ellipsis (0 when nothing is folded); items before it live in the flyout.
item_bounds¶
An item's rect in window coordinates as of the last arrange, or nullopt when it is folded into the ellipsis or index is out of range.
ellipsis_bounds¶
The ellipsis item's rect while it shows; nullopt when nothing is folded.
flyout_open¶
Whether the ellipsis flyout listing the folded items is open.
set_flyout_open¶
Opens or closes the ellipsis flyout (a click on the ellipsis toggles it). Opening does nothing while no items are folded or the control is disabled.
focused¶
Whether the strip holds keyboard focus.
focusable¶
Focusable while the control is enabled and has a clickable item, which takes at least two items since the last one is never clickable.
automation_role¶
A Group: the items are plain strings with no automation nodes of their own.
measure_override¶
The whole trail's natural width (items, chevrons) and one row's height; it never wraps.
arrange_override¶
Decides how many leading items fold into the ellipsis so the rest fit final_rect.
render_override¶
Draws the items, chevrons, the ellipsis and the keyboard focus ring. Under a Fluent theme hover and press change only the text color; retro themes also wash the background.
pointer_override¶
Button-style clicks: a press on an item followed by a release anywhere activates it. A click on the ellipsis toggles the flyout.
enabled_changed¶
is_enabled() flipped, through set_enabled() here or on an ancestor, or a move to another parent. Drop any press or hover state. The element is redrawn either way. No-op by default.
key_override¶
Left/Right move the keyboard highlight and Enter/Space activates it. Up, Down and Escape work in the open flyout.
focus_changed¶
Called by Window. Gaining focus puts the keyboard highlight on the ellipsis if it shows, else on the first shown clickable item. Losing focus clears the highlight. Redraws.
focus_ring_rect¶
Around the focused item, or the ellipsis.
Tests¶
tests/test_breadcrumb.cpp