The panel that hangs off a trigger, and the rows that go inside it.
Where the panel opens: side and align
Two questions, one attribute each. side is which side of the trigger the
panel sits on: "bottom" is the ordinary menu, "top" opens it upward, and
"left" / "right" open it beside the trigger instead of over the thing
it belongs to - the account panel a sidebar pushes out into the content area.
align is how the panel lines up along the other axis: "start" puts the
leading edges flush, "end" the trailing ones. Above or below that reads
horizontally (start grows the panel rightward, end grows it leftward); beside,
it reads vertically (start aligns the tops, end aligns the bottoms).
Leave side out and the panel opens downward and measures on every open,
flipping upward when the viewport leaves no room below it. Name a side and
there is nothing left to measure, so the hook never attaches.
placement and direction are the older spelling of the same two questions.
They keep working, unchanged, forever; prefer side and align in new code:
| legacy | prefer |
|---|---|
placement="left" | align="end" |
placement="right" | align="start" |
direction="up" | side="top" |
direction="down" | side="bottom" |
direction="auto" | no side (the measured default) |
Pass both spellings and side / align win.
Summary
Functions
<.dropdown label="Dropdown">
A non-interactive heading for a group of menu items.
A row of panel content that is a control rather than a command - a theme switcher, a plan badge, a storage meter. Same padding and type scale as a menu item, but it never behaves like one.
A thin divider between groups of menu items.
Functions
<.dropdown label="Dropdown">
<.dropdown_menu_item link_type="button">
<.icon name="hero-home" class="w-5 h-5 text-gray-500" />
Button item with icon
</.dropdown_menu_item>
<.dropdown_menu_item link_type="a" to="/" label="a item" />
<.dropdown_menu_item link_type="a" to="/" disabled label="disabled item" />
<.dropdown_menu_item link_type="live_patch" to="/" label="Live Patch item" />
<.dropdown_menu_item link_type="live_redirect" to="/" label="Live Redirect item" /></.dropdown>
Attributes
options_container_id(:string)label(:string) - labels your dropdown option. Defaults tonil.class(:any) - any extra CSS class for the parent container. Defaults tonil.trigger_class(:string) - additional classes for the trigger button. Defaults tonil.menu_items_wrapper_class(:any) - any extra CSS class for menu item wrapper container. Defaults tonil.on_close(Phoenix.LiveView.JS) - additional JS commands to run when the dropdown closes (LiveView.JS only). Defaults to%Phoenix.LiveView.JS{ops: []}.side(:string) - which side of the trigger the panel opens on. "bottom" is the ordinary menu and "top" opens it upward. "left" and "right" open it BESIDE the trigger, over whatever is next to it rather than over the thing it belongs to - the account panel a sidebar pushes out into the content area. Left out, the panel opens downward and measures on every open, flipping upward when the viewport leaves no room below (the PetalDropdown hook). Naming a side skips the hook: you have already answered the question it existed to ask. Defaults tonil. Must be one ofnil,"bottom","top","left", or"right".align(:string) - how the panel lines up along the other axis: leading edges flush ("start") or trailing edges flush ("end"). Above or below the trigger that is horizontal - "start" aligns the left edges so the panel grows rightward, "end" aligns the right edges so it grows leftward, which is what a menu in a right-hand corner wants. Beside the trigger it is vertical - "start" aligns the tops, "end" aligns the bottoms, which is what a user menu at the bottom of a sidebar wants. Left out it falls back to placement above and below (so "end" by default), and to "start" beside. Defaults tonil. Must be one ofnil,"start", or"end".placement(:string) - the legacy spelling of align, kept working: "left" is align="end" (the panel grows leftward, right edges aligned, the way a menu in the right-hand corner of a navbar wants) and "right" is align="start" (it grows rightward from the trigger's left edge). Prefer align in new code, and note that placement only has an opinion about a panel above or below - beside the trigger, side already answers the horizontal question. Defaults to"left". Must be one of"left", or"right".direction(:string) - the legacy spelling of side on the vertical axis, kept working: "up" is side="top", "down" is side="bottom", and "auto" is the measured default you get by naming neither - it flips upward when the viewport leaves no room below (needs the PetalDropdown hook). Prefer side in new code. Defaults to"auto". Must be one of"auto","up", or"down".- Global attributes are accepted.
Slots
trigger_element- custom trigger content. Rendered INSIDE the dropdown's own <button>, so never nest interactive elements (<.button>, links) here - browsers split nested buttons and the toggle binding breaks. Style the built-in trigger via trigger_class instead, e.g. trigger_class="pc-button pc-button--primary pc-button--md".inner_block