> For the complete documentation index, see [llms.txt](https://docs.nickarce.com/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.nickarce.com/javascript-api/dropdown-api.md).

# Dropdown API

### JavaScript API

#### Global Helper: `window.Dropdowns`

* `window.Dropdowns.getAll()`: Returns an array of all initialized Dropdown instances.
* `window.Dropdowns.findById(idOrDomId)`: Finds a specific instance by its numeric ID or DOM ID (e.g., `dropdown-1`).

#### Instance Methods

If you have a reference to a dropdown instance, you can call these methods:

* `instance.open({ cascade: true })`: Opens the dropdown.
* `instance.close({ cascade: true })`: Closes the dropdown.
* `instance.toggle({ cascade: true })`: Toggles the open state.

### Custom Events

Events are dispatched from the main `[data-menu-element="dropdown"]` element and bubble up.

| Event                       | Description                                                                            |
| --------------------------- | -------------------------------------------------------------------------------------- |
| `menuDropdown:open`         | Fired when the dropdown opens.                                                         |
| `menuDropdown:close`        | Fired when the dropdown closes.                                                        |
| `menuDropdown:modeChange`   | Fired when the component switches between `dropdown`, `accordion`, or `stacked` modes. |
| `menuDropdown:open:[mode]`  | Specific open event (e.g., `menuDropdown:open:dropdown`).                              |
| `menuDropdown:close:[mode]` | Specific close event (e.g., `menuDropdown:close:stacked`).                             |

**Event Detail (`event.detail`):**

* `instanceId`: The unique numeric ID of the dropdown.
* `mode`: The current mode (`dropdown`, `accordion`, or `stacked`).
* `level`: The nesting level (0 for top-level).

***

### Examples

#### Programmatic Control

```javascript
// Find a dropdown by its DOM ID (e.g., "dropdown-1")
const dropdown = window.Dropdowns.findById("dropdown-1");

// Open a dropdown
dropdown.open();

// Close a dropdown (cascade: true closes children too)
dropdown.close({ cascade: true });

// Toggle open/closed state
dropdown.toggle();

// Close all open dropdowns on the page
window.Dropdowns.getAll()
  .filter(d => d.isOpen)
  .forEach(d => d.close({ cascade: true }));

// Find a dropdown by numeric ID
const firstDropdown = window.Dropdowns.findById(1);
```

#### Listening for Events

```javascript
// Listen for any dropdown opening
document.addEventListener("menuDropdown:open", (e) => {
  console.log(`Dropdown ${e.detail.instanceId} opened`);
  console.log(`Current mode: ${e.detail.mode}`);
  console.log(`Nesting level: ${e.detail.level}`);
});

// Listen for any dropdown closing
document.addEventListener("menuDropdown:close", (e) => {
  console.log(`Dropdown ${e.detail.instanceId} closed`);
});

// Listen for mode-specific events
document.addEventListener("menuDropdown:open:stacked", (e) => {
  console.log("A dropdown opened in stacked (mobile) mode");
});

document.addEventListener("menuDropdown:close:accordion", (e) => {
  console.log("A dropdown closed in accordion mode");
});
```

#### Detecting Mode Changes

```javascript
// Listen for responsive mode switches
document.addEventListener("menuDropdown:modeChange", (e) => {
  const { instanceId, mode, oldMode, newMode } = e.detail;
  
  console.log(`Dropdown ${instanceId} switched from ${oldMode} to ${newMode}`);
  
  // Perform actions based on new mode
  if (newMode === "stacked") {
    // Mobile stacked mode activated
    document.body.classList.add("mobile-nav-active");
  } else if (newMode === "dropdown") {
    // Desktop dropdown mode activated
    document.body.classList.remove("mobile-nav-active");
  }
});
```

#### Working with Nested Dropdowns

```javascript
// Get all dropdown instances
const allDropdowns = window.Dropdowns.getAll();

// Find top-level dropdowns only (level 0)
const topLevelDropdowns = allDropdowns.filter(d => d.level === 0);

// Find nested dropdowns (level > 0)
const nestedDropdowns = allDropdowns.filter(d => d.level > 0);

// Check if a dropdown has open children
const dropdown = window.Dropdowns.findById(1);
if (dropdown.hasOpenDescendant()) {
  console.log("This dropdown has open nested menus");
}

// Access parent/child relationships
const childDropdown = window.Dropdowns.findById(2);
if (childDropdown.parentInstance) {
  console.log("Parent dropdown ID:", childDropdown.parentInstance.id);
}
```


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://docs.nickarce.com/javascript-api/dropdown-api.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
