跳至内容

DropdownMenu

向用户显示菜单,例如由按钮触发的操作或功能集。
vue
<script setup lang="ts">
import { Icon } from '@iconify/vue'
import { ref } from 'vue'
import {
  DropdownMenuArrow,
  DropdownMenuCheckboxItem,
  DropdownMenuContent,
  DropdownMenuItem,
  DropdownMenuItemIndicator,
  DropdownMenuLabel,
  DropdownMenuPortal,
  DropdownMenuRadioGroup,
  DropdownMenuRadioItem,
  DropdownMenuRoot,
  DropdownMenuSeparator,
  DropdownMenuSub,
  DropdownMenuSubContent,
  DropdownMenuSubTrigger,
  DropdownMenuTrigger,
} from 'radix-vue'

const toggleState = ref(false)
const checkboxOne = ref(false)
const checkboxTwo = ref(false)
const person = ref('pedro')

function handleClick() {
  // eslint-disable-next-line no-alert
  alert('hello!')
}
</script>

<template>
  <DropdownMenuRoot v-model:open="toggleState">
    <DropdownMenuTrigger
      class="rounded-full w-[35px] h-[35px] inline-flex items-center justify-center text-grass11 bg-white shadow-[0_2px_10px] shadow-blackA7 outline-none hover:bg-green3 focus:shadow-[0_0_0_2px] focus:shadow-black"
      aria-label="Customise options"
    >
      <Icon icon="radix-icons:hamburger-menu" />
    </DropdownMenuTrigger>

    <DropdownMenuPortal>
      <DropdownMenuContent
        class="min-w-[220px] outline-none bg-white rounded-md p-[5px] shadow-[0px_10px_38px_-10px_rgba(22,_23,_24,_0.35),_0px_10px_20px_-15px_rgba(22,_23,_24,_0.2)] will-change-[opacity,transform] data-[side=top]:animate-slideDownAndFade data-[side=right]:animate-slideLeftAndFade data-[side=bottom]:animate-slideUpAndFade data-[side=left]:animate-slideRightAndFade"
        :side-offset="5"
      >
        <DropdownMenuItem
          value="New Tab"
          class="group text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
          @click="handleClick"
        >
          New Tab
          <div
            class="ml-auto pl-[20px] text-mauve11 group-data-[highlighted]:text-white group-data-[disabled]:text-mauve8"
          >
            ⌘+T
          </div>
        </DropdownMenuItem>
        <DropdownMenuSub>
          <DropdownMenuSubTrigger
            value="more toolsz"
            class="group w-full text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[state=open]:bg-green4 data-[state=open]:text-grass11 data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1 data-[highlighted]:data-[state=open]:bg-green9 data-[highlighted]:data-[state=open]:text-green1"
          >
            More Tools
            <div
              class="ml-auto pl-[20px] text-mauve11 group-data-[highlighted]:text-white group-data-[disabled]:text-mauve8"
            >
              <Icon icon="radix-icons:chevron-right" />
            </div>
          </DropdownMenuSubTrigger>
          <DropdownMenuPortal>
            <DropdownMenuSubContent
              class="min-w-[220px] outline-none bg-white rounded-md p-[5px] shadow-[0px_10px_38px_-10px_rgba(22,_23,_24,_0.35),_0px_10px_20px_-15px_rgba(22,_23,_24,_0.2)] will-change-[opacity,transform] data-[side=top]:animate-slideDownAndFade data-[side=right]:animate-slideLeftAndFade data-[side=bottom]:animate-slideUpAndFade data-[side=left]:animate-slideRightAndFade"
              :side-offset="2"
              :align-offset="-5"
            >
              <DropdownMenuItem
                class="group text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
              >
                Save Page As…
                <div
                  class="ml-auto pl-[20px] text-mauve11 group-data-[highlighted]:text-white group-data-[disabled]:text-mauve8"
                >
                  ⌘+S
                </div>
              </DropdownMenuItem>
              <DropdownMenuItem
                class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
              >
                Create Shortcut…
              </DropdownMenuItem>
              <DropdownMenuItem
                class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
              >
                Name Window…
              </DropdownMenuItem>
              <DropdownMenuSeparator class="h-[1px] bg-green6 m-[5px]" />
              <DropdownMenuItem
                class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
              >
                Developer Tools
              </DropdownMenuItem>
            </DropdownMenuSubContent>
          </DropdownMenuPortal>
        </DropdownMenuSub>
        <DropdownMenuItem
          value="New Window"
          class="group text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
        >
          New Window
          <div
            class="ml-auto pl-[20px] text-mauve11 group-data-[highlighted]:text-white group-data-[disabled]:text-mauve8"
          >
            ⌘+N
          </div>
        </DropdownMenuItem>
        <DropdownMenuItem
          value="New Private Window"
          class="group text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
          disabled
        >
          New Private Window
          <div
            class="ml-auto pl-[20px] text-mauve11 group-data-[highlighted]:text-white group-data-[disabled]:text-mauve8"
          >
            ⇧+⌘+N
          </div>
        </DropdownMenuItem>
        <DropdownMenuSub>
          <DropdownMenuSubTrigger
            value="more tools"
            class="group text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none w-full outline-none data-[state=open]:bg-green4 data-[state=open]:text-grass11 data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1 data-[highlighted]:data-[state=open]:bg-green9 data-[highlighted]:data-[state=open]:text-green1"
          >
            More Tools
            <div
              class="ml-auto pl-[20px] text-mauve11 group-data-[highlighted]:text-white group-data-[disabled]:text-mauve8"
            >
              <Icon icon="radix-icons:chevron-right" />
            </div>
          </DropdownMenuSubTrigger>
          <DropdownMenuPortal>
            <DropdownMenuSubContent
              class="min-w-[220px] outline-none bg-white rounded-md p-[5px] shadow-[0px_10px_38px_-10px_rgba(22,_23,_24,_0.35),_0px_10px_20px_-15px_rgba(22,_23,_24,_0.2)] will-change-[opacity,transform] data-[side=top]:animate-slideDownAndFade data-[side=right]:animate-slideLeftAndFade data-[side=bottom]:animate-slideUpAndFade data-[side=left]:animate-slideRightAndFade"
              :side-offset="2"
              :align-offset="-5"
            >
              <DropdownMenuItem
                class="group text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
              >
                Save Page As…
                <div
                  class="ml-auto pl-[20px] text-mauve11 group-data-[highlighted]:text-white group-data-[disabled]:text-mauve8"
                >
                  ⌘+S
                </div>
              </DropdownMenuItem>
              <DropdownMenuItem
                class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
              >
                Create Shortcut…
              </DropdownMenuItem>
              <DropdownMenuItem
                class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
              >
                Name Window…
              </DropdownMenuItem>
              <DropdownMenuSeparator class="h-[1px] bg-green6 m-[5px]" />
              <DropdownMenuItem
                class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
              >
                Developer Tools
              </DropdownMenuItem>
              <DropdownMenuSub>
                <DropdownMenuSubTrigger
                  value="more toolsz"
                  class="group w-full text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[state=open]:bg-green4 data-[state=open]:text-grass11 data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1 data-[highlighted]:data-[state=open]:bg-green9 data-[highlighted]:data-[state=open]:text-green1"
                >
                  More Tools
                  <div
                    class="ml-auto pl-[20px] text-mauve11 group-data-[highlighted]:text-white group-data-[disabled]:text-mauve8"
                  >
                    <Icon icon="radix-icons:chevron-right" />
                  </div>
                </DropdownMenuSubTrigger>
                <DropdownMenuPortal>
                  <DropdownMenuSubContent
                    class="min-w-[220px] outline-none bg-white rounded-md p-[5px] shadow-[0px_10px_38px_-10px_rgba(22,_23,_24,_0.35),_0px_10px_20px_-15px_rgba(22,_23,_24,_0.2)] will-change-[opacity,transform] data-[side=top]:animate-slideDownAndFade data-[side=right]:animate-slideLeftAndFade data-[side=bottom]:animate-slideUpAndFade data-[side=left]:animate-slideRightAndFade"
                    :side-offset="2"
                    :align-offset="-5"
                  >
                    <DropdownMenuItem
                      class="group text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
                    >
                      Save Page As…
                      <div
                        class="ml-auto pl-[20px] text-mauve11 group-data-[highlighted]:text-white group-data-[disabled]:text-mauve8"
                      >
                        ⌘+S
                      </div>
                    </DropdownMenuItem>
                    <DropdownMenuItem
                      class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
                    >
                      Create Shortcut…
                    </DropdownMenuItem>
                    <DropdownMenuItem
                      class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
                    >
                      Name Window…
                    </DropdownMenuItem>
                    <DropdownMenuSeparator class="h-[1px] bg-green6 m-[5px]" />
                    <DropdownMenuItem
                      class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
                    >
                      Developer Tools
                    </DropdownMenuItem>
                    <DropdownMenuSub>
                      <DropdownMenuSubTrigger
                        value="more toolsz"
                        class="group w-full text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[state=open]:bg-green4 data-[state=open]:text-grass11 data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1 data-[highlighted]:data-[state=open]:bg-green9 data-[highlighted]:data-[state=open]:text-green1"
                      >
                        More Tools
                        <div
                          class="ml-auto pl-[20px] text-mauve11 group-data-[highlighted]:text-white group-data-[disabled]:text-mauve8"
                        >
                          <Icon icon="radix-icons:chevron-right" />
                        </div>
                      </DropdownMenuSubTrigger>
                      <DropdownMenuPortal>
                        <DropdownMenuSubContent
                          class="min-w-[220px] outline-none bg-white rounded-md p-[5px] shadow-[0px_10px_38px_-10px_rgba(22,_23,_24,_0.35),_0px_10px_20px_-15px_rgba(22,_23,_24,_0.2)] will-change-[opacity,transform] data-[side=top]:animate-slideDownAndFade data-[side=right]:animate-slideLeftAndFade data-[side=bottom]:animate-slideUpAndFade data-[side=left]:animate-slideRightAndFade"
                          :side-offset="2"
                          :align-offset="-5"
                        >
                          <DropdownMenuItem
                            class="group text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
                          >
                            Save Page As…
                            <div
                              class="ml-auto pl-[20px] text-mauve11 group-data-[highlighted]:text-white group-data-[disabled]:text-mauve8"
                            >
                              ⌘+S
                            </div>
                          </DropdownMenuItem>
                          <DropdownMenuItem
                            class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
                          >
                            Create Shortcut…
                          </DropdownMenuItem>
                          <DropdownMenuItem
                            class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
                          >
                            Name Window…
                          </DropdownMenuItem>
                          <DropdownMenuSeparator class="h-[1px] bg-green6 m-[5px]" />
                          <DropdownMenuItem
                            class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
                          >
                            Developer Tools
                          </DropdownMenuItem>
                        </DropdownMenuSubContent>
                      </DropdownMenuPortal>
                    </DropdownMenuSub>
                  </DropdownMenuSubContent>
                </DropdownMenuPortal>
              </DropdownMenuSub>
              <DropdownMenuItem
                class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
              >
                Developer Tools
              </DropdownMenuItem>
            </DropdownMenuSubContent>
          </DropdownMenuPortal>
        </DropdownMenuSub>
        <DropdownMenuSeparator class="h-[1px] bg-green6 m-[5px]" />
        <DropdownMenuCheckboxItem
          v-model:checked="checkboxOne"
          class="group text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
        >
          <DropdownMenuItemIndicator class="absolute left-0 w-[25px] inline-flex items-center justify-center">
            <Icon icon="radix-icons:check" />
          </DropdownMenuItemIndicator>
          Show Bookmarks
          <div
            class="ml-auto pl-[20px] text-mauve11 group-data-[highlighted]:text-white group-data-[disabled]:text-mauve8"
          >
            ⌘+B
          </div>
        </DropdownMenuCheckboxItem>
        <DropdownMenuCheckboxItem
          v-model:checked="checkboxTwo"
          class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
        >
          <DropdownMenuItemIndicator class="absolute left-0 w-[25px] inline-flex items-center justify-center">
            <Icon icon="radix-icons:check" />
          </DropdownMenuItemIndicator>
          Show Full URLs
        </DropdownMenuCheckboxItem>
        <DropdownMenuSeparator class="h-[1px] bg-green6 m-[5px]" />

        <DropdownMenuLabel class="pl-[25px] text-xs leading-[25px] text-mauve11">
          People
        </DropdownMenuLabel>
        <DropdownMenuRadioGroup v-model="person">
          <DropdownMenuRadioItem
            class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
            value="pedro"
          >
            <DropdownMenuItemIndicator class="absolute left-0 w-[25px] inline-flex items-center justify-center">
              <Icon icon="radix-icons:dot-filled" />
            </DropdownMenuItemIndicator>
            Pedro Duarte
          </DropdownMenuRadioItem>
          <DropdownMenuRadioItem
            class="text-[13px] leading-none text-grass11 rounded-[3px] flex items-center h-[25px] px-[5px] relative pl-[25px] select-none outline-none data-[disabled]:text-mauve8 data-[disabled]:pointer-events-none data-[highlighted]:bg-green9 data-[highlighted]:text-green1"
            value="colm"
          >
            <DropdownMenuItemIndicator class="absolute left-0 w-[25px] inline-flex items-center justify-center">
              <Icon icon="radix-icons:dot-filled" />
            </DropdownMenuItemIndicator>
            Colm Tuite
          </DropdownMenuRadioItem>
        </DropdownMenuRadioGroup>
        <DropdownMenuArrow class="fill-white" />
      </DropdownMenuContent>
    </DropdownMenuPortal>
  </DropdownMenuRoot>
</template>

功能

  • 可以是受控的或不受控的。
  • 支持子菜单,并具有可配置的阅读方向。
  • 支持项目、标签和项目组。
  • 支持可选的不确定状态的可检查项目(单个或多个)。
  • 支持模态和非模态模式。
  • 自定义边、对齐方式、偏移量和碰撞处理。
  • 可以选择渲染一个指向箭头。
  • 完全管理焦点。
  • 完整的键盘导航。
  • 类型化支持。
  • 关闭和分层行为高度可定制。

安装

从命令行安装组件。

sh
$ npm add radix-vue

解剖结构

导入所有部分并将它们拼凑在一起。

vue
<script setup lang="ts">
import {
  DropdownMenuArrow,
  DropdownMenuCheckboxItem,
  DropdownMenuContent,
  DropdownMenuGroup,
  DropdownMenuItem,
  DropdownMenuItemIndicator,
  DropdownMenuLabel,
  DropdownMenuPortal,
  DropdownMenuRadioGroup,
  DropdownMenuRadioItem,
  DropdownMenuRoot,
  DropdownMenuSeparator,
  DropdownMenuSub,
  DropdownMenuSubContent,
  DropdownMenuSubTrigger,
  DropdownMenuTrigger,
} from 'radix-vue'
</script>

<template>
  <DropdownMenuRoot>
    <DropdownMenuTrigger />

    <DropdownMenuPortal>
      <DropdownMenuContent>
        <DropdownMenuLabel />
        <DropdownMenuItem />

        <DropdownMenuGroup>
          <DropdownMenuItem />
        </DropdownMenuGroup>

        <DropdownMenuCheckboxItem>
          <DropdownMenuItemIndicator />
        </DropdownMenuCheckboxItem>

        <DropdownMenuRadioGroup>
          <DropdownMenuRadioItem>
            <DropdownMenuItemIndicator />
          </DropdownMenuRadioItem>
        </DropdownMenuRadioGroup>

        <DropdownMenuSub>
          <DropdownMenuSubTrigger />
          <DropdownMenuPortal>
            <DropdownMenuSubContent />
          </DropdownMenuPortal>
        </DropdownMenuSub>

        <DropdownMenuSeparator />
        <DropdownMenuArrow />
      </DropdownMenuContent>
    </DropdownMenuPortal>
  </DropdownMenuRoot>
</template>

API 参考

包含下拉菜单的所有部分。

道具默认值类型
defaultOpen
布尔值

下拉菜单在最初渲染时的打开状态。当您不需要控制其打开状态时使用。

dir
'ltr' | 'rtl'

组合框适用的阅读方向。

如果省略,将从 ConfigProvider 全局继承,或假设 LTR(从左到右)阅读模式。

modal
true
布尔值

下拉菜单的模态性。

当设置为 true 时,将禁用与外部元素的交互,并且只有菜单内容对屏幕阅读器可见。

open
布尔值

菜单的受控打开状态。可用作 v-model:open

发出有效载荷
update:open
[payload: boolean]

当子菜单的打开状态更改时调用的事件处理程序。

插槽(默认)有效载荷
open
布尔值

当前打开状态

触发器

切换下拉菜单的按钮。默认情况下,DropdownMenuContent 将相对于触发器定位。

道具默认值类型
as
'button'
AsTag | 组件

此组件应呈现的元素或组件。可以被 asChild 覆盖

asChild
布尔值

更改作为子项传递的默认呈现元素,合并它们的属性和行为。

阅读我们的 组合 指南了解更多详细信息。

disabled
布尔值

true 时,阻止用户与项目交互

数据属性
[data-state]"open" | "closed"
[data-disabled]禁用时出现

门户

使用时,将内容部分传送至 body

道具默认值类型
disabled
布尔值

禁用传送并内联渲染组件

reference

forceMount
布尔值

用于在需要更多控制时强制安装。当使用 Vue 动画库控制动画时很有用。

to
字符串 | HTMLElement

Vue 原生传送组件属性 :to

reference

内容

下拉菜单打开时弹出的组件。

道具默认值类型
align
'start' | 'center' | 'end'

相对于触发器的首选对齐方式。当发生冲突时可能会更改。

alignOffset
数字

来自 startend 对齐选项的像素偏移量。

arrowPadding
数字

箭头与内容边缘之间的填充。如果您的内容具有圆角,这将防止它溢出角落。

as
'div'
AsTag | 组件

此组件应呈现的元素或组件。可以被 asChild 覆盖

asChild
布尔值

更改作为子项传递的默认呈现元素,合并它们的属性和行为。

阅读我们的 组合 指南了解更多详细信息。

avoidCollisions
布尔值

true 时,会覆盖边和对齐偏好以防止与边界边缘发生冲突。

collisionBoundary
元素 | (元素 | 空)[] | 空

用作碰撞边界的元素。默认情况下,这是视窗,但您可以提供要包含在此检查中的其他元素。

collisionPadding
数字 | Partial<Record<'top' | 'right' | 'bottom' | 'left', number>>

边界边缘的距离(以像素为单位),在该距离上应发生碰撞检测。接受一个数字(所有边相同),或一个部分填充对象,例如:{ top: 20, left: 20 }。

forceMount
布尔值

用于在需要更多控制时强制安装。当使用 Vue 动画库控制动画时很有用。

hideWhenDetached
布尔值

当触发器变得完全遮挡时是否隐藏内容。

loop
布尔值

true 时,键盘导航将从最后一个项目循环到第一个项目,反之亦然。

prioritizePosition
布尔值

强制内容定位在视窗内。

可能会与引用元素重叠,这可能不希望出现。

side
'top' | 'right' | 'bottom' | 'left'

打开时呈现的触发器的首选边。当发生冲突并且启用 avoidCollisions 时,将反转。

sideOffset
数字

与触发器的距离(以像素为单位)。

sticky
'partial' | 'always'

对齐轴上的粘滞行为。partial 将使内容保持在边界内,只要触发器至少部分在边界内,而 "always" 将使内容始终保持在边界内。

updatePositionStrategy
'always' | 'optimized'

在每个动画帧上更新浮动元素位置的策略。

发出有效载荷
closeAutoFocus
[event: Event]

关闭时自动聚焦时调用的事件处理程序。可以防止。

escapeKeyDown
[event: KeyboardEvent]

按下 Escape 键时调用的事件处理程序。可以防止。

focusOutside
[event: FocusOutsideEvent]

焦点移出 DismissableLayer 时调用的事件处理程序。可以防止。

interactOutside
[event: PointerDownOutsideEvent | FocusOutsideEvent]

DismissableLayer 外部发生交互时调用的事件处理程序。具体来说,是指在 DismissableLayer 外部发生 pointerdown 事件或焦点移出 DismissableLayer 时。可以防止。

pointerDownOutside
[event: PointerDownOutsideEvent]

DismissableLayer 外部发生 pointerdown 事件时调用的事件处理程序。可以防止。

数据属性
[data-state]"open" | "closed"
[data-side]"left" | "right" | "bottom" | "top"
[data-align]"开始" | "结束" | "居中"
[data-orientation]"垂直" | "水平"
CSS 变量描述
--radix-dropdown-menu-content-transform-origin
从内容和箭头位置/偏移计算的transform-origin
--radix-dropdown-menu-content-available-width
触发器和边界边缘之间的剩余宽度
--radix-dropdown-menu-content-available-height
触发器和边界边缘之间的剩余高度
--radix-dropdown-menu-trigger-width
触发器的宽度
--radix-dropdown-menu-trigger-height
触发器的高度

箭头

一个可选的箭头元素,与下拉菜单一起渲染。这可以用来帮助视觉上将触发器与DropdownMenuContent链接起来。必须渲染在DropdownMenuContent中。

道具默认值类型
as
'svg'
AsTag | 组件

此组件应呈现的元素或组件。可以被 asChild 覆盖

asChild
布尔值

更改作为子项传递的默认呈现元素,合并它们的属性和行为。

阅读我们的 组合 指南了解更多详细信息。

高度
5
数字

箭头的像素高度。

宽度
10
数字

箭头的像素宽度。

项目

包含下拉菜单项目的组件。

道具默认值类型
as
'div'
AsTag | 组件

此组件应呈现的元素或组件。可以被 asChild 覆盖

asChild
布尔值

更改作为子项传递的默认呈现元素,合并它们的属性和行为。

阅读我们的 组合 指南了解更多详细信息。

disabled
布尔值

true时,阻止用户与项目交互。

textValue
字符串

用于类型提前的可选文本。默认情况下,类型提前行为将使用项目的.textContent
当内容很复杂,或您在内部有非文本内容时,使用它。

发出有效载荷
选择
[event: Event]

当用户选择项目(通过鼠标或键盘)时调用的事件处理程序。
在这个处理程序中调用event.preventDefault将阻止菜单在选择该项目时关闭。

数据属性
[data-orientation]"垂直" | "水平"
[data-highlighted]突出显示时出现
[data-disabled]禁用时出现

用于对多个DropdownMenuItem进行分组。

道具默认值类型
as
'div'
AsTag | 组件

此组件应呈现的元素或组件。可以被 asChild 覆盖

asChild
布尔值

更改作为子项传递的默认呈现元素,合并它们的属性和行为。

阅读我们的 组合 指南了解更多详细信息。

标签

用于渲染标签。它不能通过箭头键聚焦。

道具默认值类型
as
'div'
AsTag | 组件

此组件应呈现的元素或组件。可以被 asChild 覆盖

asChild
布尔值

更改作为子项传递的默认呈现元素,合并它们的属性和行为。

阅读我们的 组合 指南了解更多详细信息。

复选框项目

一个可以像复选框一样控制和渲染的项目。

道具默认值类型
as
'div'
AsTag | 组件

此组件应呈现的元素或组件。可以被 asChild 覆盖

asChild
布尔值

更改作为子项传递的默认呈现元素,合并它们的属性和行为。

阅读我们的 组合 指南了解更多详细信息。

选中
false | true | '不确定'

项目的受控选中状态。可以用作v-model:checked

disabled
布尔值

true时,阻止用户与项目交互。

textValue
字符串

用于类型提前的可选文本。默认情况下,类型提前行为将使用项目的.textContent
当内容很复杂,或您在内部有非文本内容时,使用它。

发出有效载荷
选择
[event: Event]

当用户选择项目(通过鼠标或键盘)时调用的事件处理程序。
在这个处理程序中调用event.preventDefault将阻止菜单在选择该项目时关闭。

更新:选中
[payload: boolean]

选中状态改变时调用的事件处理程序。

数据属性
[data-state]"选中" | "未选中" | "不确定"
[data-highlighted]突出显示时出现
[data-disabled]禁用时出现

单选按钮组

用于对多个DropdownMenuRadioItem进行分组。

道具默认值类型
as
'div'
AsTag | 组件

此组件应呈现的元素或组件。可以被 asChild 覆盖

asChild
布尔值

更改作为子项传递的默认呈现元素,合并它们的属性和行为。

阅读我们的 组合 指南了解更多详细信息。

modelValue
字符串

组中所选项目的价值。

发出有效载荷
更新:modelValue
[有效负载:字符串]

值改变时调用的事件处理程序。

单选按钮项目

一个可以像单选按钮一样控制和渲染的项目。

道具默认值类型
as
'div'
AsTag | 组件

此组件应呈现的元素或组件。可以被 asChild 覆盖

asChild
布尔值

更改作为子项传递的默认呈现元素,合并它们的属性和行为。

阅读我们的 组合 指南了解更多详细信息。

disabled
布尔值

true时,阻止用户与项目交互。

textValue
字符串

用于类型提前的可选文本。默认情况下,类型提前行为将使用项目的.textContent
当内容很复杂,或您在内部有非文本内容时,使用它。

值*
字符串

项目的唯一值。

发出有效载荷
选择
[event: Event]

当用户选择项目(通过鼠标或键盘)时调用的事件处理程序。
在这个处理程序中调用event.preventDefault将阻止菜单在选择该项目时关闭。

数据属性
[data-state]"选中" | "未选中" | "不确定"
[data-highlighted]突出显示时出现
[data-disabled]禁用时出现

项目指示器

当父DropdownMenuCheckboxItemDropdownMenuRadioItem被选中时渲染。你可以直接对这个元素进行样式设置,或者你可以用它作为包装器来放入一个图标,或者两者兼而有之。

道具默认值类型
as
'div'
AsTag | 组件

此组件应呈现的元素或组件。可以被 asChild 覆盖

asChild
布尔值

更改作为子项传递的默认呈现元素,合并它们的属性和行为。

阅读我们的 组合 指南了解更多详细信息。

forceMount
布尔值

用于在需要更多控制时强制安装。当使用 Vue 动画库控制动画时很有用。

数据属性
[data-state]"选中" | "未选中" | "不确定"

分隔符

用于在下拉菜单中视觉上分隔项目。

道具默认值类型
as
'div'
AsTag | 组件

此组件应呈现的元素或组件。可以被 asChild 覆盖

asChild
布尔值

更改作为子项传递的默认呈现元素,合并它们的属性和行为。

阅读我们的 组合 指南了解更多详细信息。

子菜单

包含子菜单的所有部分。

道具默认值类型
defaultOpen
布尔值

下拉菜单在最初渲染时的打开状态。当您不需要控制其打开状态时使用。

open
布尔值

菜单的受控打开状态。可用作 v-model:open

发出有效载荷
update:open
[payload: boolean]

当子菜单的打开状态更改时调用的事件处理程序。

插槽(默认)有效载荷
open
布尔值

当前打开状态

子菜单触发器

打开子菜单的项目。必须渲染在DropdownMenuSub中。

道具默认值类型
as
'div'
AsTag | 组件

此组件应呈现的元素或组件。可以被 asChild 覆盖

asChild
布尔值

更改作为子项传递的默认呈现元素,合并它们的属性和行为。

阅读我们的 组合 指南了解更多详细信息。

disabled
布尔值

true时,阻止用户与项目交互。

textValue
字符串

用于类型提前的可选文本。默认情况下,类型提前行为将使用项目的.textContent
当内容很复杂,或您在内部有非文本内容时,使用它。

数据属性
[data-state]"open" | "closed"
[data-highlighted]突出显示时出现
[data-disabled]禁用时出现
CSS 变量描述
--radix-dropdown-menu-content-transform-origin
从内容和箭头位置/偏移计算的transform-origin
--radix-dropdown-menu-content-available-width
触发器和边界边缘之间的剩余宽度
--radix-dropdown-menu-content-available-height
触发器和边界边缘之间的剩余高度
--radix-dropdown-menu-trigger-width
触发器的宽度
--radix-dropdown-menu-trigger-height
触发器的高度

子菜单内容

当子菜单打开时弹出的组件。必须渲染在DropdownMenuSub中。

道具默认值类型
alignOffset
数字

来自 startend 对齐选项的像素偏移量。

arrowPadding
数字

箭头与内容边缘之间的填充。如果您的内容具有圆角,这将防止它溢出角落。

as
'div'
AsTag | 组件

此组件应呈现的元素或组件。可以被 asChild 覆盖

asChild
布尔值

更改作为子项传递的默认呈现元素,合并它们的属性和行为。

阅读我们的 组合 指南了解更多详细信息。

avoidCollisions
布尔值

true 时,会覆盖边和对齐偏好以防止与边界边缘发生冲突。

collisionBoundary
元素 | (元素 | 空)[] | 空

用作碰撞边界的元素。默认情况下,这是视窗,但您可以提供要包含在此检查中的其他元素。

collisionPadding
数字 | Partial<Record<'top' | 'right' | 'bottom' | 'left', number>>

边界边缘的距离(以像素为单位),在该距离上应发生碰撞检测。接受一个数字(所有边相同),或一个部分填充对象,例如:{ top: 20, left: 20 }。

forceMount
布尔值

用于在需要更多控制时强制安装。当使用 Vue 动画库控制动画时很有用。

hideWhenDetached
布尔值

当触发器变得完全遮挡时是否隐藏内容。

loop
布尔值

true 时,键盘导航将从最后一个项目循环到第一个项目,反之亦然。

prioritizePosition
布尔值

强制内容定位在视窗内。

可能会与引用元素重叠,这可能不希望出现。

sideOffset
数字

与触发器的距离(以像素为单位)。

sticky
'partial' | 'always'

对齐轴上的粘滞行为。partial 将使内容保持在边界内,只要触发器至少部分在边界内,而 "always" 将使内容始终保持在边界内。

updatePositionStrategy
'always' | 'optimized'

在每个动画帧上更新浮动元素位置的策略。

发出有效载荷
closeAutoFocus
[event: Event]

关闭时自动聚焦时调用的事件处理程序。可以防止。

条目焦点
[event: Event]
escapeKeyDown
[event: KeyboardEvent]

按下 Escape 键时调用的事件处理程序。可以防止。

focusOutside
[event: FocusOutsideEvent]

焦点移出 DismissableLayer 时调用的事件处理程序。可以防止。

interactOutside
[event: PointerDownOutsideEvent | FocusOutsideEvent]

DismissableLayer 外部发生交互时调用的事件处理程序。具体来说,是指在 DismissableLayer 外部发生 pointerdown 事件或焦点移出 DismissableLayer 时。可以防止。

打开自动聚焦
[event: Event]

自动聚焦打开时调用的事件处理程序。可以阻止。

pointerDownOutside
[event: PointerDownOutsideEvent]

DismissableLayer 外部发生 pointerdown 事件时调用的事件处理程序。可以防止。

数据属性
[data-state]"open" | "closed"
[data-side]"left" | "right" | "bottom" | "top"
[data-align]"开始" | "结束" | "居中"
[data-orientation]"垂直" | "水平"

示例

带有子菜单

你可以通过将DropdownMenuSub与它的部分结合使用来创建子菜单。

vue
<script setup lang="ts">
import {
  DropdownMenuArrow,
  DropdownMenuContent,
  DropdownMenuItem,
  DropdownMenuPortal,
  DropdownMenuRoot,
  DropdownMenuSeparator,
  DropdownMenuSub,
  DropdownMenuSubContent,
  DropdownMenuSubTrigger,
  DropdownMenuTrigger,
} from 'radix-vue'
</script>

<template>
  <DropdownMenuRoot>
    <DropdownMenuTrigger></DropdownMenuTrigger>
    <DropdownMenuPortal>
      <DropdownMenuContent>
        <DropdownMenuItem></DropdownMenuItem>
        <DropdownMenuItem></DropdownMenuItem>
        <DropdownMenuSeparator />
        <DropdownMenuSub>
          <DropdownMenuSubTrigger>Sub menu →</DropdownMenuSubTrigger>
          <DropdownMenuPortal>
            <DropdownMenuSubContent>
              <DropdownMenuItem>Sub menu item</DropdownMenuItem>
              <DropdownMenuItem>Sub menu item</DropdownMenuItem>
              <DropdownMenuArrow />
            </DropdownMenuSubContent>
          </DropdownMenuPortal>
        </DropdownMenuSub>
        <DropdownMenuSeparator />
        <DropdownMenuItem></DropdownMenuItem>
      </DropdownMenuContent>
    </DropdownMenuPortal>
  </DropdownMenuRoot>
</template>

带有禁用项目

你可以通过data-disabled属性为禁用项目添加特殊的样式。

vue
<script setup lang="ts">
import {
  DropdownMenuContent,
  DropdownMenuItem,
  DropdownMenuPortal,
  DropdownMenuRoot,
  DropdownMenuTrigger,
} from 'radix-vue'
</script>

<template>
  <DropdownMenuRoot>
    <DropdownMenuTrigger></DropdownMenuTrigger>
    <DropdownMenuPortal>
      <DropdownMenuContent>
        <DropdownMenuItem
          class="DropdownMenuItem"
          disabled
        >

        </DropdownMenuItem>
        <DropdownMenuItem class="DropdownMenuItem">

        </DropdownMenuItem>
      </DropdownMenuContent>
    </DropdownMenuPortal>
  </DropdownMenuRoot>
</template>
css
/* styles.css */
.DropdownMenuItem[data-disabled] {
  color: gainsboro;
}

带有分隔符

使用Separator部分在项目之间添加分隔符。

vue
<script setup lang="ts">
import {
  DropdownMenuContent,
  DropdownMenuItem,
  DropdownMenuPortal,
  DropdownMenuRoot,
  DropdownMenuSeparator,
  DropdownMenuTrigger,
} from 'radix-vue'
</script>

<template>
  <DropdownMenuRoot>
    <DropdownMenuTrigger></DropdownMenuTrigger>
    <DropdownMenuPortal>
      <DropdownMenuContent>
        <DropdownMenuItem></DropdownMenuItem>
        <DropdownMenuSeparator />
        <DropdownMenuItem></DropdownMenuItem>
        <DropdownMenuSeparator />
        <DropdownMenuItem></DropdownMenuItem>
      </DropdownMenuContent>
    </DropdownMenuPortal>
  </DropdownMenuRoot>
</template>

带有标签

使用Label部分帮助标记一个部分。

vue
<script setup lang="ts">
import {
  DropdownMenuContent,
  DropdownMenuItem,
  DropdownMenuLabel,
  DropdownMenuPortal,
  DropdownMenuRoot,
  DropdownMenuTrigger,
} from 'radix-vue'
</script>

<template>
  <DropdownMenuRoot>
    <DropdownMenuTrigger></DropdownMenuTrigger>
    <DropdownMenuPortal>
      <DropdownMenuContent>
        <DropdownMenuLabel>Label</DropdownMenuLabel>
        <DropdownMenuItem></DropdownMenuItem>
        <DropdownMenuItem></DropdownMenuItem>
        <DropdownMenuItem></DropdownMenuItem>
      </DropdownMenuContent>
    </DropdownMenuPortal>
  </DropdownMenuRoot>
</template>

带有复选框项目

使用CheckboxItem部分添加一个可以勾选的项目。

vue
<script setup lang="ts">
import { Icon } from '@iconify/vue'
import { ref } from 'vue'
import {
  DropdownMenuCheckboxItem,
  DropdownMenuContent,
  DropdownMenuItem,
  DropdownMenuItemIndicator,
  DropdownMenuPortal,
  DropdownMenuRoot,
  DropdownMenuSeparator,
  DropdownMenuTrigger,
} from 'radix-vue'

const checked = ref(false)
</script>

<template>
  <DropdownMenuRoot>
    <DropdownMenuTrigger></DropdownMenuTrigger>
    <DropdownMenuPortal>
      <DropdownMenuContent>
        <DropdownMenuItem></DropdownMenuItem>
        <DropdownMenuItem></DropdownMenuItem>
        <DropdownMenuSeparator />
        <DropdownMenuCheckboxItem v-model:checked="checked">
          <DropdownMenuItemIndicator>
            <Icon icon="radix-icons:check" />
          </DropdownMenuItemIndicator>
          Checkbox item
        </DropdownMenuCheckboxItem>
      </DropdownMenuContent>
    </DropdownMenuPortal>
  </DropdownMenuRoot>
</template>

带有单选按钮项目

使用RadioGroupRadioItem部分添加一个可以在其他项目中勾选的项目。

vue
<script setup lang="ts">
import { Icon } from '@iconify/vue'
import { ref } from 'vue'
import {
  DropdownMenuContent,
  DropdownMenuItemIndicator,
  DropdownMenuPortal,
  DropdownMenuRadioGroup,
  DropdownMenuRadioItem,
  DropdownMenuRoot,
  DropdownMenuTrigger,
} from 'radix-vue'

const color = ref(false)
</script>

<template>
  <DropdownMenuRoot>
    <DropdownMenuTrigger></DropdownMenuTrigger>
    <DropdownMenuPortal>
      <DropdownMenuContent>
        <DropdownMenuRadioGroup v-model="color">
          <DropdownMenuRadioItem value="red">
            <DropdownMenuItemIndicator>
              <Icon icon="radix-icons:check" />
            </DropdownMenuItemIndicator>
            Red
          </DropdownMenuRadioItem>
          <DropdownMenuRadioItem value="blue">
            <DropdownMenuItemIndicator>
              <Icon icon="radix-icons:check" />
            </DropdownMenuItemIndicator>
            Blue
          </DropdownMenuRadioItem>
          <DropdownMenuRadioItem value="green">
            <DropdownMenuItemIndicator>
              <Icon icon="radix-icons:check" />
            </DropdownMenuItemIndicator>
            Green
          </DropdownMenuRadioItem>
        </DropdownMenuRadioGroup>
      </DropdownMenuContent>
    </DropdownMenuPortal>
  </DropdownMenuRoot>
</template>

带有复杂项目

你可以在Item部分中添加额外的装饰元素,比如图像。

vue
<script setup lang="ts">
import {
  DropdownMenuContent,
  DropdownMenuItem,
  DropdownMenuPortal,
  DropdownMenuRoot,
  DropdownMenuTrigger,
} from 'radix-vue'
</script>

<template>
  <DropdownMenuRoot>
    <DropdownMenuTrigger></DropdownMenuTrigger>
    <DropdownMenuPortal>
      <DropdownMenuContent>
        <DropdownMenuItem>
          <img src="">
          Adolfo Hess
        </DropdownMenuItem>
        <DropdownMenuItem>
          <img src="">
          Miyah Myles
        </DropdownMenuItem>
      </DropdownMenuContent>
    </DropdownMenuPortal>
  </DropdownMenuRoot>
</template>

约束内容/子内容大小

你可能想要约束内容(或子内容)的宽度,使其与触发器(或子触发器)的宽度匹配。你可能还想约束其高度,使其不超过视口。

我们暴露了一些 CSS 自定义属性,比如--radix-dropdown-menu-trigger-width--radix-dropdown-menu-content-available-height来支持这一点。使用它们来约束内容尺寸。

vue
<script setup lang="ts">
import { DropdownMenuContent, DropdownMenuPortal, DropdownMenuRoot, DropdownMenuTrigger } from 'radix-vue'
</script>

<template>
  <DropdownMenuRoot>
    <DropdownMenuTrigger></DropdownMenuTrigger>
    <DropdownMenuPortal>
      <DropdownMenuContent
        class="DropdownMenuContent"
        :side-offset="5"
      >

      </DropdownMenuContent>
    </DropdownMenuPortal>
  </DropdownMenuRoot>
</template>
css
/* styles.css */
.DropdownMenuContent {
  width: var(--radix-dropdown-menu-trigger-width);
  max-height: var(--radix-dropdown-menu-content-available-height);
}

起源感知动画

我们暴露了一个 CSS 自定义属性--radix-dropdown-menu-content-transform-origin。用它根据sidesideOffsetalignalignOffset和任何碰撞来从计算出的原点动画内容。

vue
<script setup lang="ts">
import { DropdownMenuContent, DropdownMenuPortal, DropdownMenuRoot, DropdownMenuTrigger } from 'radix-vue'
</script>

<template>
  <DropdownMenuRoot>
    <DropdownMenuTrigger></DropdownMenuTrigger>
    <DropdownMenuPortal>
      <DropdownMenuContent class="DropdownMenuContent">

      </DropdownMenuContent>
    </DropdownMenuPortal>
  </DropdownMenuRoot>
</template>
css
/* styles.css */
.DropdownMenuContent {
  transform-origin: var(--radix-dropdown-menu-content-transform-origin);
  animation: scaleIn 0.5s ease-out;
}

@keyframes scaleIn {
  from {
    opacity: 0;
    transform: scale(0);
  }
  to {
    opacity: 1;
    transform: scale(1);
  }
}

碰撞感知动画

我们暴露了data-sidedata-align属性。它们的价值将在运行时改变,以反映碰撞。用它们来创建碰撞和方向感知动画。

vue
<script setup lang="ts">
import { DropdownMenuContent, DropdownMenuPortal, DropdownMenuRoot, DropdownMenuTrigger } from 'radix-vue'
</script>

<template>
  <DropdownMenuRoot>
    <DropdownMenuTrigger></DropdownMenuTrigger>
    <DropdownMenuPortal>
      <DropdownMenuContent class="DropdownMenuContent">

      </DropdownMenuContent>
    </DropdownMenuPortal>
  </DropdownMenuRoot>
</template>
css
/* styles.css */
.DropdownMenuContent {
  animation-duration: 0.6s;
  animation-timing-function: cubic-bezier(0.16, 1, 0.3, 1);
}
.DropdownMenuContent[data-side="top"] {
  animation-name: slideUp;
}
.DropdownMenuContent[data-side="bottom"] {
  animation-name: slideDown;
}

@keyframes slideUp {
  from {
    opacity: 0;
    transform: translateY(10px);
  }
  to {
    opacity: 1;
    transform: translateY(0);
  }
}

@keyframes slideDown {
  from {
    opacity: 0;
    transform: translateY(-10px);
  }
  to {
    opacity: 1;
    transform: translateY(0);
  }
}

无障碍性

符合菜单按钮 WAI-ARIA 设计模式,并使用 roving tabindex 来管理菜单项之间的焦点移动。

键盘交互

描述
空格
当焦点在DropdownMenuTrigger上时,打开下拉菜单并聚焦第一个项目。
当焦点在一个项目上时,激活聚焦的项目。
回车
当焦点在DropdownMenuTrigger上时,打开下拉菜单并聚焦第一个项目。
当焦点在一个项目上时,激活聚焦的项目。
向下箭头
当焦点在DropdownMenuTrigger上时,打开下拉菜单。
当焦点在一个项目上时,将焦点移动到下一个项目。
向上箭头
当焦点在一个项目上时,将焦点移动到上一个项目。
向右箭头向左箭头
当焦点在DropdownMenuSubTrigger上时,根据阅读方向打开或关闭子菜单。
Esc
关闭下拉菜单并将焦点移动到DropdownMenuTrigger

自定义 API

通过将原始部分抽象到您自己的组件中来创建您自己的 API。

抽象箭头和项目指示器

这个例子抽象了DropdownMenuArrowDropdownMenuItemIndicator部分。它还包装了CheckboxItemRadioItem的实现细节。

用法

vue
<script setup lang="ts">
import {
  DropdownMenu,
  DropdownMenuCheckboxItem,
  DropdownMenuContent,
  DropdownMenuGroup,
  DropdownMenuItem,
  DropdownMenuLabel,
  DropdownMenuRadioGroup,
  DropdownMenuRadioItem,
  DropdownMenuSeparator,
  DropdownMenuTrigger,
} from './your-dropdown-menu'
</script>

<template>
  <DropdownMenu>
    <DropdownMenuTrigger>DropdownMenu trigger</DropdownMenuTrigger>
    <DropdownMenuContent>
      <DropdownMenuItem>Item</DropdownMenuItem>
      <DropdownMenuLabel>Label</DropdownMenuLabel>
      <DropdownMenuGroup>Group</DropdownMenuGroup>
      <DropdownMenuCheckboxItem>CheckboxItem</DropdownMenuCheckboxItem>
      <DropdownMenuSeparator>Separator</DropdownMenuSeparator>
      <DropdownMenuRadioGroup>
        <DropdownMenuRadioItem>RadioItem</DropdownMenuRadioItem>
        <DropdownMenuRadioItem>RadioItem</DropdownMenuRadioItem>
      </DropdownMenuRadioGroup>
    </DropdownMenuContent>
  </DropdownMenu>
</template>

实现

ts
// your-dropdown-menu.ts
export { default as DropdownMenuContent } from 'DropdownMenuContent.vue'
export { default as DropdownMenuCheckboxItem } from 'DropdownMenuCheckboxItem.vue'
export { default as DropdownMenuRadioItem } from 'DropdownMenuRadioItem.vue'

export {
  DropdownMenuRoot as DropdownMenu,
  DropdownMenuTrigger,
  DropdownMenuLabel,
  DropdownMenuItem,
  DropdownMenuGroup,
  DropdownMenuRadioGroup,
  DropdownMenuSeparator
} from 'radix-vue'
vue
<!-- DropdownMenuContent.vue -->
<script setup lang="ts">
import { DropdownMenuContent, type DropdownMenuContentEmits, type DropdownMenuContentProps, DropdownMenuPortal, useForwardPropsEmits, } from 'radix-vue'

const props = defineProps<DropdownMenuContentProps>()
const emits = defineEmits<DropdownMenuContentEmits>()

const forwarded = useForwardPropsEmits(props, emits)
</script>

<template>
  <DropdownMenuPortal>
    <DropdownMenuContent v-bind="forwarded">
      <slot />
    </DropdownMenuContent>
  </DropdownMenuPortal>
</template>
vue
<!-- DropdownMenuCheckboxItem.vue -->
<script setup lang="ts">
import { DropdownMenuCheckboxItem, type DropdownMenuCheckboxItemEmits, type DropdownMenuCheckboxItemProps, DropdownMenuItemIndicator, useForwardPropsEmits } from 'radix-vue'
import { CheckIcon } from '@radix-icons/vue'

const props = defineProps<DropdownMenuCheckboxItemProps>()
const emits = defineEmits<DropdownMenuCheckboxItemEmits>()

const forwarded = useForwardPropsEmits(props, emits)
</script>

<template>
  <DropdownMenuCheckboxItem v-bind="forwarded">
    <span>
      <DropdownMenuItemIndicator>
        <CheckIcon />
      </DropdownMenuItemIndicator>
    </span>
    <slot />
  </DropdownMenuCheckboxItem>
</template>
vue
<!-- DropdownMenuRadioItem.vue -->
<script setup lang="ts">
import { DropdownMenuItemIndicator, DropdownMenuRadioItem, type DropdownMenuRadioItemEmits, type DropdownMenuRadioItemProps, useForwardPropsEmits, } from 'radix-vue'
import { DotFilledIcon } from '@radix-icons/vue'

const props = defineProps<DropdownMenuRadioItemProps>()
const emits = defineEmits<DropdownMenuRadioItemEmits>()

const forwarded = useForwardPropsEmits(props, emits)
</script>

<template>
  <DropdownMenuRadioItem v-bind="forwarded">
    <span>
      <DropdownMenuItemIndicator>
        <DotFilledIcon />
      </DropdownMenuItemIndicator>
    </span>
    <slot />
  </DropdownMenuRadioItem>
</template>