WebRADDocumentationExplore WebRAD ↗
WEBRAD / TECHNICAL REFERENCE

Menu

Navigation with submenus, search, and a drawer for small screens.

WebMenuNavigationVisual9 events

Quick start

Add Menu1 in the Designer. Use the example in a page method.

Menu1 · event
Menu1.items = [
  { id: 'home', label: 'Home', icon: 'house' },
  { id: 'records', label: 'Records', icon: 'folder', children: [
    { id: 'customers', label: 'Customers', icon: 'users' },
  ] },
];
Menu1.selectedItemId = 'home';
Menu1.expandItem('records');
Menu1.updateItem('customers', { badge: '3' });
  • Open the configurator from the Menu in the Designer. Arrange items, submenus, icons, badges, brand, and user.
  • Choose vertical or horizontal orientation. The menu floats; anchors and margins define its position.
  • Below mobileBreakpoint, the menu uses a drawer. Configure drawerWidth, drawerSide, and closeOnSelect.
  • page navigates to a page ID; href opens a link. Items with children and no destination expand their submenu.
  • OnItemClick receives item, itemId, and path. OnItemToggle receives itemId and expanded; use it for submenus without an action.
  • searchable enables search. searchMode = 'filter' filters items; 'event' retains items and emits OnSearch with detail.text.
  • collapsed controls the compact version; open(), close(), and toggle() control opening. themeToggle displays the theme control.

More examples

Handle an action by item ID
Handle an action by item ID
import type { WebMenu, WebMenuItemEvent } from '@webrad/runtime';
// Link this method to OnItemClick in Interaction.
class Example {
  public async Menu1ItemClick(
    sender: WebMenu,
    event: CustomEvent<WebMenuItemEvent>,
  ): Promise<void> {
    if (event.detail.itemId !== 'sign-out') return;
    event.preventDefault(); // Cancel navigation before await.
    const result = await RestGO.logout();
    if (result.error) { Message(result.error.message); return; }
    Navigate('PageLogin');
  }
}
Search and responsive configuration
Search and responsive configuration
Menu1.configuration = {
  ...Menu1.configuration,
  searchable: true,
  searchMode: 'event',
  mobileBreakpoint: 768,
  drawerWidth: 288,
  drawerSide: 'left',
  closeOnSelect: true,
};
// OnSearch receives event.detail.text; update data in your logic.
Menu1.brand = { ...Menu1.brand, caption: 'My application' };
Menu1.user = { ...Menu1.user, visible: true, name: 'Ana', status: 'online' };
Menu1.themeToggle = true;

Inspector properties

Component options and defaults. Fields without runtime access are configured in the Inspector.

Property / sourceType and optionsDefaultRuntime access
nameName · Identitystring—name
xLeft · Size & positionnumber0x
yTop · Size & positionnumber0y
widthWidth · Size & positionnumber288width
heightHeight · Size & positionnumber640height
itemWidthResponsive width · Responsive sizeFit content grows the item to its widest rendered child and preserves child intrinsic widths; minimum and maximum width remain limits.enumfixed stretch fit-content"fixed"Inspector / configuration
itemHeightResponsive height · Responsive sizeFit content grows the item to its lowest rendered child and preserves child intrinsic heights; minimum and maximum height remain limits.enumfixed stretch fit-content"fixed"Inspector / configuration
itemMinWidthMinimum width · Responsive sizenumber0Inspector / configuration
itemMaxWidthMaximum width · Responsive sizenumbernullInspector / configuration
itemMinHeightMinimum height · Responsive sizenumber0Inspector / configuration
itemMaxHeightMaximum height · Responsive sizenumbernullInspector / configuration
itemGrowGrow · Responsive sizenumber0Inspector / configuration
itemShrinkShrink · Responsive sizeAllows fixed and stretch flow items to yield space. Fit-content keeps its intrinsic size so its children are not compressed.booleantrueInspector / configuration
itemAlignSelfItem alignment · Responsive sizeCross-axis alignment for this item in a row or column. Auto inherits the parent alignment; responsive cross-axis stretch retains its sizing behavior.enumauto start center end stretch"auto"Inspector / configuration
itemHorizontalAnchorHorizontal anchor · Anchors & offsetsenumstart center end stretch"start"Inspector / configuration
itemVerticalAnchorVertical anchor · Anchors & offsetsenumstart center end stretch"start"Inspector / configuration
itemLeftLeft inset · Anchors & offsetsnumber0Inspector / configuration
itemRightRight inset · Anchors & offsetsnumber0Inspector / configuration
itemTopTop inset · Anchors & offsetsnumber0Inspector / configuration
itemBottomBottom inset · Anchors & offsetsnumber0Inspector / configuration
marginMargin · SpacingOuter spacing on all four sides, in pixels. Row and column layouts include this spacing between components.number0margin
marginTopMargin top · SpacingOuter spacing on this side, in pixels. Overrides the shared Margin value.number0Derived from saved propertiesmarginTop
marginRightMargin right · SpacingOuter spacing on this side, in pixels. Overrides the shared Margin value.number0Derived from saved propertiesmarginRight
marginBottomMargin bottom · SpacingOuter spacing on this side, in pixels. Overrides the shared Margin value.number0Derived from saved propertiesmarginBottom
marginLeftMargin left · SpacingOuter spacing on this side, in pixels. Overrides the shared Margin value.number0Derived from saved propertiesmarginLeft
visibleVisible · Behaviorbooleantruevisible
collapseWhenHiddenCollapse when hidden · BehaviorRemoves the component from the layout while it is not visible.booleantruecollapseWhenHidden
enabledEnabled · Behaviorbooleantrueenabled
menuDefinitionIdMenu definition · MenuShared configuration and TypeScript; runtime state remains independent for each placement.menu-definition—Inspector / configuration
editMenuDefinitionEdit shared menu · Menudesigner-actionEditor: menu-definition-edit—Inspector / configuration
configurationMenu configuration · MenuEdit orientation, menu items, brand, user, appearance and the optional Light/Dark theme switch. Responsive placement is automatic.menu-configEditor: menu-configurator{"schemaVersion":1,"orientation":"vertical","accessibleLabel":"Main navigation","collapsible":true,"collapsed":false,"accordion":false,"searchable":false,"themeToggle":true,"searchMode":"filter","searchPlaceholder":"Search menu…","emptyText":"No items found","footerText":"","selectedItemId":"","mobileBreakpoint":768,"mobileIconPosition":"left","drawerWidth":288,"drawerSide":"left","closeOnSelect":true,"brand":{"visible":true,"caption":"Workspace","subtitle":"Your application","logo":"","logoSize":36,"page":"","href":""},"user":{"visible":false,"bindToCurrentUser":false,"settings":false,"settingsLanguage":"en","emailConfirmationUrl":"","passwordResetUrl":"","name":"","description":"","avatar":"","status":"none"},"appearance":{"background":"var(--wr-theme-surface)","foreground":"var(--wr-theme-heading)","muted":"var(--wr-theme-text-muted)","border":"var(--wr-theme-border)","hoverBackground":"var(--wr-theme-disabled-surface)","activeBackground":"var(--wr-theme-surface-muted)","activeForeground":"var(--wr-theme-primary)","accent":"var(--wr-theme-primary)","badgeBackground":"var(--wr-theme-surface-muted)","badgeForeground":"var(--wr-theme-primary)","itemHeight":44,"itemRadius":10,"itemGap":4,"iconSize":20,"fontSize":14,"padding":14,"indent":18,"collapsedWidth":72},"items":[{"id":"home","label":"Home","icon":"house"},{"id":"workspace","label":"Workspace","icon":"layers","expanded":true,"children":[{"id":"projects","label":"Projects","icon":"folder"},{"id":"team","label":"Team","icon":"users"}]},{"id":"settings","label":"Settings","icon":"settings"}]}configuration
placementPlacement · enumin-flow floating"floating"placementRead-only in the Inspector
floatingHorizontalAnchorHorizontal side · Menu placementenumleft center right"left"floatingHorizontalAnchor
floatingVerticalAnchorVertical side · Menu placementenumtop center bottom"top"floatingVerticalAnchor
floatingZIndexLayer · number1000floatingZIndexRead-only in the Inspector
currentRowBindingsCurrent row · DataBind writable visual values to fields of this repeated row.current-row-bindingsEditor: current-row-bindings[]currentRowBindings

API in code

MemberSignatureAccess
floatingZIndexget floatingZIndex(): number;Read-only
marginget margin(): number;Read and write
marginTopget marginTop(): number;Read and write
marginRightget marginRight(): number;Read and write
marginBottomget marginBottom(): number;Read and write
marginLeftget marginLeft(): number;Read and write
placementget placement(): 'floating';Read-only
floatingHorizontalAnchorget floatingHorizontalAnchor(): 'left' | 'center' | 'right';Read and write
floatingVerticalAnchorget floatingVerticalAnchor(): 'top' | 'center' | 'bottom';Read and write
configurationget configuration(): WebMenuConfiguration;Read and write
enabledget enabled(): boolean;Read and write
itemsget items(): readonly WebMenuItem[];Read and write
orientationget orientation(): WebMenuConfiguration['orientation'];Read and write
brandget brand(): WebMenuConfiguration['brand'];Read and write
userget user(): WebMenuConfiguration['user'];Read and write
appearanceget appearance(): WebMenuConfiguration['appearance'];Read and write
selectedItemIdget selectedItemId(): string;Read and write
collapsedget collapsed(): boolean;Read and write
isOpenget isOpen(): boolean;Read-only
isMobileget isMobile(): boolean;Read-only
searchModeget searchMode(): WebMenuConfiguration['searchMode'];Read and write
themeToggleget themeToggle(): boolean;Read and write
searchTextget searchText(): string;Read and write

createDefinition

method
static createDefinition(element: HTMLElement, factory: (element: HTMLElement) => WebMenu, initialize: (menu: WebMenu) => void): WebMenu;

Apply the saved placement before the authored subclass constructor runs.

Example
Menu1.createDefinition
Menu1.createDefinition();

fromElement

method
static fromElement<T extends WebMenu>(element: HTMLElement, menuClass: new (element: HTMLElement) => T): T;

Resolve the concrete authored Menu already mounted for this element.

Example
Menu1.fromElement
Menu1.fromElement();

emit

method
emit(eventName: string, detail?: unknown): boolean;
Example
Menu1.emit
Menu1.emit('OnClick');

findItem

method
findItem(id: string): WebMenuItem | undefined;
Example
Menu1.findItem
Menu1.findItem('home');

updateItem

method
updateItem(id: string, changes: Partial<Omit<WebMenuItem, 'id'>>): void;
Example
Menu1.updateItem
Menu1.updateItem('home', { badge: '3' });

expandItem

method
expandItem(id: string): void;
Example
Menu1.expandItem
Menu1.expandItem('records');

collapseItem

method
collapseItem(id: string): void;
Example
Menu1.collapseItem
Menu1.collapseItem('records');

toggleItem

method
toggleItem(id: string): void;
Example
Menu1.toggleItem
Menu1.toggleItem('records');

focusItem

method
focusItem(id: string): void;
Example
Menu1.focusItem
Menu1.focusItem('home');

activateItem

method
activateItem(id: string): void;
Example
Menu1.activateItem
Menu1.activateItem('home');

open

method
open(): void;
Example
Menu1.open
Menu1.open();

close

method
close(): void;
Example
Menu1.close
Menu1.close();

toggle

method
toggle(): void;
Example
Menu1.toggle
Menu1.toggle();

openUserSettings

method
openUserSettings(): void;

Open the account editor when the saved Menu user settings option is enabled.

Example
Menu1.openUserSettings
Menu1.openUserSettings();

closeUserSettings

method
closeUserSettings(): void;
Example
Menu1.closeUserSettings
Menu1.closeUserSettings();

dispose

method
dispose(): void;
Example
Menu1.dispose
// Call only when disposing of an instance whose lifecycle you control.
Menu1.dispose();
Inherited members (19)
MemberSignatureAccess
currentRowBindingscurrentRowBindings: readonly WebCurrentRowBinding[];Read and write
elementreadonly element: TElement;Read-only
idreadonly id: string;Read-only
namereadonly name: string;Read-only
visiblevisible: boolean;Read and write
collapseWhenHiddencollapseWhenHidden: boolean;Read and write
xx: number;Read and write
yy: number;Read and write
widthwidth: number;Read and write
heightheight: number;Read and write
alignSelfalignSelf: RuntimeLayoutAlignSelf;Read and write
tabIndextabIndex: number;Read and write
backgroundColorbackgroundColor: string;Read and write
colorcolor: string;Read and write
borderColorborderColor: string;Read and write

focus

method
focus(options?: FocusOptions): void;

show

method
show(): void;

hide

method
hide(): void;

bindEvent

method
bindEvent(eventName: string, handler: WebComponentEventHandler<this> | null): () => void;

Events

Link methods in Interaction. How to use events.

OnSearch

WebMenuSearchEvent in event.detail · text

Emitted when the user presses Enter in event search mode. Typing and clearing do not emit; menu items remain unchanged.

Signature and example
Interaction → OnSearch
import type { WebMenu, WebMenuSearchEvent } from '@webrad/runtime';
// Copy this method into the page class and link it in Interaction.
class Example {
  public async Menu1Search(
    sender: WebMenu,
    event: CustomEvent<WebMenuSearchEvent>,
  ): Promise<void> {
    console.log(event.detail);
    const { text } = event.detail;
    console.log(text);
  }
}

OnItemClick

WebMenuItemEvent in event.detail · item, itemId, path

Call event.preventDefault() synchronously to cancel automatic selection and navigation.

Signature and example
Interaction → OnItemClick
import type { WebMenu, WebMenuItemEvent } from '@webrad/runtime';
// Copy this method into the page class and link it in Interaction.
class Example {
  public async Menu1ItemClick(
    sender: WebMenu,
    event: CustomEvent<WebMenuItemEvent>,
  ): Promise<void> {
    console.log(event.detail);
    const { item, itemId, path } = event.detail;
    console.log(item, itemId, path);
  }
}

OnSelectionChange

WebMenuItemEvent in event.detail · item, itemId

Signature and example
Interaction → OnSelectionChange
import type { WebMenu, WebMenuItemEvent } from '@webrad/runtime';
// Copy this method into the page class and link it in Interaction.
class Example {
  public async Menu1SelectionChange(
    sender: WebMenu,
    event: CustomEvent<WebMenuItemEvent>,
  ): Promise<void> {
    console.log(event.detail);
    const { item, itemId } = event.detail;
    console.log(item, itemId);
  }
}

OnItemToggle

WebMenuItemToggleEvent in event.detail · itemId, expanded

Signature and example
Interaction → OnItemToggle
import type { WebMenu, WebMenuItemToggleEvent } from '@webrad/runtime';
// Copy this method into the page class and link it in Interaction.
class Example {
  public async Menu1ItemToggle(
    sender: WebMenu,
    event: CustomEvent<WebMenuItemToggleEvent>,
  ): Promise<void> {
    console.log(event.detail);
    const { itemId, expanded } = event.detail;
    console.log(itemId, expanded);
  }
}

OnCollapseChange

WebMenuStateEvent in event.detail · collapsed

Signature and example
Interaction → OnCollapseChange
import type { WebMenu, WebMenuStateEvent } from '@webrad/runtime';
// Copy this method into the page class and link it in Interaction.
class Example {
  public async Menu1CollapseChange(
    sender: WebMenu,
    event: CustomEvent<WebMenuStateEvent>,
  ): Promise<void> {
    console.log(event.detail);
    const { collapsed } = event.detail;
    console.log(collapsed);
  }
}

OnOpen

WebMenuStateEvent in event.detail

Signature and example
Interaction → OnOpen
import type { WebMenu, WebMenuStateEvent } from '@webrad/runtime';
// Copy this method into the page class and link it in Interaction.
class Example {
  public async Menu1Open(
    sender: WebMenu,
    event: CustomEvent<WebMenuStateEvent>,
  ): Promise<void> {
    console.log(event.detail);
  }
}

OnClose

WebMenuStateEvent in event.detail

Signature and example
Interaction → OnClose
import type { WebMenu, WebMenuStateEvent } from '@webrad/runtime';
// Copy this method into the page class and link it in Interaction.
class Example {
  public async Menu1Close(
    sender: WebMenu,
    event: CustomEvent<WebMenuStateEvent>,
  ): Promise<void> {
    console.log(event.detail);
  }
}

OnBrandClick

WebMenuBrand in event.detail

Signature and example
Interaction → OnBrandClick
import type { WebMenu, WebMenuBrand } from '@webrad/runtime';
// Copy this method into the page class and link it in Interaction.
class Example {
  public async Menu1BrandClick(
    sender: WebMenu,
    event: CustomEvent<WebMenuBrand>,
  ): Promise<void> {
    console.log(event.detail);
  }
}

OnUserClick

WebMenuUser in event.detail

Signature and example
Interaction → OnUserClick
import type { WebMenu, WebMenuUser } from '@webrad/runtime';
// Copy this method into the page class and link it in Interaction.
class Example {
  public async Menu1UserClick(
    sender: WebMenu,
    event: CustomEvent<WebMenuUser>,
  ): Promise<void> {
    console.log(event.detail);
  }
}
WebRAD · Atentor · Read in Markdown
Source code: 6a562bda75a0 (with local changes) · November 7, 2026

Search documentation

Type to search APIs, components, and events.