# DropDownMenu

*Create interactive dropdown menus with customizable options, actions, and styling for [navigation](../../01_Onboarding/02_Concepts/09_Navigation.md) and user choices. DropDownMenu provides a flexible way to display hierarchical menus with various item types including checkboxes, radio buttons, separators, and nested submenus.*

## Basic Usage

Here's a simple example of a `DropDownMenu` that shows a [toast message](../../01_Onboarding/02_Concepts/13_Clients.md) when an item is selected:

```csharp
new DropDownMenu(@evt => client.Toast("Selected: " + @evt.Value), 
    new Button("Basic Menu"),
    MenuItem.Default("Profile"), 
    MenuItem.Default("Settings"), 
    MenuItem.Default("Logout"))
```

### Default Menu Items

Default menu items are the most common type, providing simple clickable options. The second example shows how to add custom tags for more advanced [event handling](../../01_Onboarding/02_Concepts/07_EventHandlers.md).

```csharp
Layout.Horizontal().Gap(2).Center()
    | new DropDownMenu(@evt => client.Toast("Selected: " + @evt.Value), 
        new Button("Default Items"),
        MenuItem.Default("Copy"),
        MenuItem.Default("Paste"),
        MenuItem.Default("Cut"),
        MenuItem.Default("Delete"))
    | new DropDownMenu(@evt => client.Toast("Selected: " + @evt.Value), 
        new Button("With Tags"),
        MenuItem.Default("Save").Tag("save-action"),
        MenuItem.Default("Export").Tag("export-action"),
        MenuItem.Default("Import").Tag("import-action"))
```

Default menu items are the most common type, providing simple clickable options. The second example shows how to add custom tags for more advanced event handling.

### Checkbox Menu Items

Checkbox menu items allow users to toggle options on/off. The second example demonstrates mixing different menu item types for more complex [interfaces](../../01_Onboarding/02_Concepts/02_Views.md).

```csharp
Layout.Horizontal().Gap(2).Center()
    | new DropDownMenu(@evt => client.Toast("Selected: " + @evt.Value), 
        new Button("Checkboxes"),
        MenuItem.Checkbox("Dark Theme").Checked(),
        MenuItem.Checkbox("Notifications"),
        MenuItem.Checkbox("Auto-save").Checked(),
        MenuItem.Checkbox("Debug Mode"))
    | new DropDownMenu(@evt => client.Toast("Selected: " + @evt.Value), 
        new Button("Mixed Types"),
        MenuItem.Default("Profile"),
        MenuItem.Separator(),
        MenuItem.Checkbox("Email Notifications").Checked(),
        MenuItem.Checkbox("SMS Notifications"),
        MenuItem.Checkbox("Push Notifications").Checked())
```

### Separators

Separators help organize menu items into logical groups, making the [interface](../../01_Onboarding/02_Concepts/02_Views.md) more readable and user-friendly.

```csharp
new DropDownMenu(@evt => client.Toast("Selected: " + @evt.Value), 
    new Button("With Separators"))
    | MenuItem.Default("New File")
    | MenuItem.Default("Open File")
    | MenuItem.Separator()
    | MenuItem.Default("Save")
    | MenuItem.Default("Save As")
    | MenuItem.Separator()
    | MenuItem.Default("Print")
    | MenuItem.Default("Export")
```

### Nested Menu Items

Nested menu items create submenus for better organization of complex menu structures.

```csharp
new DropDownMenu(@evt => client.Toast("Selected: " + @evt.Value), 
    new Button("Nested Items"))
    | MenuItem.Default("File")
        .Children(
            MenuItem.Default("New"),
            MenuItem.Default("Open"),
            MenuItem.Default("Save")
        )
    | MenuItem.Default("Edit")
        .Children(
            MenuItem.Default("Undo"),
            MenuItem.Default("Redo"),
            MenuItem.Default("Cut")
        )
```

## Positioning

Control which side of the trigger the menu appears on:

```csharp
Layout.Horizontal().Gap(2).Center()
    | new DropDownMenu(@evt => client.Toast("Selected: " + @evt.Value), 
        new Button("Top"), MenuItem.Default("Item 1"), MenuItem.Default("Item 2"))
        .Top()
    | new DropDownMenu(@evt => client.Toast("Selected: " + @evt.Value), 
        new Button("Right"), MenuItem.Default("Item 1"), MenuItem.Default("Item 2"))
        .Right()
    | new DropDownMenu(@evt => client.Toast("Selected: " + @evt.Value), 
        new Button("Bottom"), MenuItem.Default("Item 1"), MenuItem.Default("Item 2"))
        .Bottom()
    | new DropDownMenu(@evt => client.Toast("Selected: " + @evt.Value), 
        new Button("Left"), MenuItem.Default("Item 1"), MenuItem.Default("Item 2"))
        .Left()
```

## Advanced Features

### Menu Headers

Headers provide context and user information, making menus more informative and professional-looking.

```csharp
Layout.Horizontal().Gap(2).Center()
    | new DropDownMenu(@evt => client.Toast("Selected: " + @evt.Value), 
        new Button("Muted Header"),
        MenuItem.Separator(),
        MenuItem.Default("Profile"),
        MenuItem.Default("Settings"),
        MenuItem.Default("Logout"))
        .Header(Text.Muted("Signed in as user@example.com"))
    | new DropDownMenu(@evt => client.Toast("Selected: " + @evt.Value), 
        new Button("Label Header"),
        MenuItem.Separator(),
        MenuItem.Default("View Profile"),
        MenuItem.Default("Account Settings"))
        .Header(Text.Label("John Doe - Administrator"))
```

### Fluent Syntax

The `WithDropDown` extension method provides a clean, fluent API for quickly adding dropdown functionality to existing buttons.

```csharp
Layout.Horizontal().Gap(2).Center()
    | new Button("Quick Menu")
        .WithDropDown(
            MenuItem.Default("Option 1"),
            MenuItem.Default("Option 2"),
            MenuItem.Default("Option 3")
        )
    | new Button("Settings")
        .Secondary()
        .WithDropDown(
            MenuItem.Default("Preferences"),
            MenuItem.Default("Account"),
            MenuItem.Default("Help")
        )
```

### Custom Event Handling

Custom event handling allows you to implement complex [business logic](../../03_Hooks/02_Core/11_UseService.md) based on menu selections, making your dropdowns more interactive and useful.

```csharp
new DropDownMenu(@evt => {
        var value = @evt.Value?.ToString();
        if (value == "delete") {
            client.Toast("Deleting item...");
        } else if (value == "export") {
            client.Toast("Exporting data...");
        } else {
            client.Toast($"Selected: {value}");
        }
    }, 
    new Button("Custom Actions"))
    | MenuItem.Default("View").Tag("view")
    | MenuItem.Default("Edit").Tag("edit")
    | MenuItem.Default("Delete").Tag("delete")
    | MenuItem.Separator()
    | MenuItem.Default("Export").Tag("export")
    | MenuItem.Default("Share").Tag("share")
```


## API

[View Source: DropDownMenu.cs](https://github.com/Ivy-Interactive/Ivy-Framework/blob/main/src/Ivy/Widgets/DropDownMenu.cs)

### Constructors

| Signature |
|-----------|
| `new DropDownMenu(Func<Event<DropDownMenu, object>, ValueTask> onSelect, object trigger, IEnumerable<MenuItem> items)` |
| `new DropDownMenu(Action<Event<DropDownMenu, object>> onSelect, object trigger, IEnumerable<MenuItem> items)` |


### Properties

| Name | Type | Setters |
|------|------|---------|
| `Align` | `AlignOptions` | `Align` |
| `AlignOffset` | `int` | `AlignOffset` |
| `Height` | `Size` | - |
| `Items` | `MenuItem[]` | `Items` |
| `Scale` | `Scale?` | - |
| `Side` | `SideOptions` | `Side` |
| `Visible` | `bool` | - |
| `Width` | `Size` | - |


### Events

| Name | Type | Handlers |
|------|------|----------|
| `OnSelect` | `Func<Event<DropDownMenu, object>, ValueTask>` | `HandleSelect` |




## Examples


### Complex using

Here's a comprehensive example combining multiple features:

```csharp
Layout.Horizontal().Gap(2).Center()
    | new DropDownMenu(@evt => client.Toast("Selected: " + @evt.Value), 
        new Button("User Menu"),
        MenuItem.Separator(),
        MenuItem.Default("View Profile").Tag("profile"),
        MenuItem.Default("Account Settings").Tag("settings"),
        MenuItem.Default("Preferences").Tag("preferences"),
        MenuItem.Separator(),
        MenuItem.Default("Theme")
            .Children(
                MenuItem.Checkbox("Light").Tag("theme-light"),
                MenuItem.Checkbox("Dark").Checked().Tag("theme-dark"),
                MenuItem.Checkbox("System").Tag("theme-system")
            ),
        MenuItem.Default("Notifications")
            .Children(
                MenuItem.Checkbox("Email").Checked().Tag("notify-email"),
                MenuItem.Checkbox("Push").Checked().Tag("notify-push"),
                MenuItem.Checkbox("SMS").Tag("notify-sms")
            ),
        MenuItem.Separator(),
        MenuItem.Default("Help & Support").Tag("help"),
        MenuItem.Default("About").Tag("about"),
        MenuItem.Separator(),
        MenuItem.Default("Logout").Tag("logout"))
        .Header(Text.Muted("Signed in as john.doe@company.com"))
        .Top()
        .Align(DropDownMenu.AlignOptions.End)
    | new DropDownMenu(@evt => client.Toast("Selected: " + @evt.Value), 
        new Button("Settings Menu"),
        MenuItem.Default("General").Tag("general"),
        MenuItem.Default("Appearance").Tag("appearance"),
        MenuItem.Default("Privacy").Tag("privacy"),
        MenuItem.Default("Security").Tag("security"),
        MenuItem.Separator(),
        MenuItem.Default("Updates").Tag("updates"),
        MenuItem.Default("Support").Tag("support"))
        .Header(Text.Muted("Application Settings"))
```