QSelect 组件有两种选择类型:单选或多选。该组件会打开一个菜单用于选择列表和操作。对于较长的列表,还可以使用过滤器。
如果您需要的是下拉"按钮"而不是"输入框",请使用按钮下拉菜单。
QSelect API
设计
概览
WARNING
对于 QSelect,您只能使用一种主要设计(filled、outlined、standout、borderless)。您不能同时使用多种设计,因为它们是互斥的。
装饰器
颜色定制
可清除
作为辅助功能,您可以使用 clearable 属性,这样用户可以通过附加的图标将模型重置为 null。下面示例中的第二个 QSelect 等同于使用 clearable。
禁用和只读
带有 type=“submit” 的 QBtn 插槽
WARNING
当在 QField、QInput 或 QSelect 的"before"、“after”、"prepend"或"append"插槽中放置 type=“submit” 的 QBtn 时,您还应该在相关的 QBtn 上添加 @click 监听器。此监听器应调用提交表单的方法。此类插槽中的所有"click"事件都不会传播到其父元素。
菜单过渡效果
WARNING
请注意,使用 options-cover 属性时,过渡效果不起作用。
下面的示例展示了几种过渡效果。有关可用过渡的完整列表,请转到过渡。
选项列表显示模式
默认情况下,QSelect 在桌面设备上将选项列表显示为菜单,在移动设备上显示为对话框。您可以使用 behavior 属性强制使用某种行为。
WARNING
请注意,在 iOS 上,菜单行为可能会产生问题,特别是与 use-input 属性结合使用时。您可以使用条件 behavior 属性,如 :behavior="$q.platform.is.ios === true ? 'dialog' : 'menu'" 仅在 iOS 上使用对话框模式。
模型
WARNING
单选的模型可以是任何类型(字符串、对象等),而多选的模型必须是数组。
模型内容可以受 emit-value 属性的影响,您将在下面的"选项"部分了解到这一点。
选项
选项类型
影响模型
使用 emit-value 时,模型将变为指定选定选项中确定的 value。默认是发出整个选项。仅当选项为对象形式时,使用它才有意义。
使用 map-options 时,模型可以只包含 value,它将根据选项映射来确定其标签。这会带来性能损失,因此仅在绝对必要时使用它。例如,如果模型包含整个对象(因此包含标签属性),则不需要它。
自定义属性名称
默认情况下,QSelect 查看选项数组对象中每个选项的 label、value、disable 和 sanitize 属性。但您可以覆盖这些:
WARNING
如果您为自定义属性使用函数,请始终检查选项是否为 null。这些函数用于列表中的选项和选定的选项。
自定义菜单选项
WARNING
选项列表使用虚拟滚动渲染,因此如果您为一个选项渲染多个元素,必须在除第一个元素外的所有元素上设置 q-virtual-scroll--with-prev 类。
这是另一个示例,我们为每个选项添加一个 QToggle。可能性是无限的。
默认情况下,当没有选项时,菜单不会出现。但您可以自定义此场景并指定菜单应显示的内容。
懒加载
以下示例展示了如何使用懒加载选项。这意味着,除了其他许多事情外,在第一次渲染时不需要 options 属性。
您可以在滚动到底部时动态加载新选项:
覆盖模式
禁用 TAB 选择
显示值
过滤和自动完成
带有 “use-input” 的原生属性
在 QSelect 上设置的所有不在 API 属性列表中的属性都将传递给用于过滤/自动完成/添加新值的原生输入字段(请先查看 use-input 属性描述以了解它的作用)。一些例子:autocomplete、placeholder。
更多信息:原生输入属性。
创建新值
TIP
以下只是一些示例,帮助您开始创建自己的 QSelect 行为。这不是 QSelect 提供的可能性的详尽列表。
将此功能与 use-input 属性一起使用是有意义的。
要启用创建新值,您需要指定 new-value-mode 属性和/或监听 @new-value 事件。如果您同时使用两者,那么监听 @new-value 的目的仅是在自定义场景中覆盖 new-value-mode。
new-value-mode 属性
new-value-mode 属性值指定应如何添加值:add(添加值,即使是重复的)、add-unique(仅在不重复时添加)或 toggle(如果模型中尚不存在则添加值,否则将其删除)。
通过使用此属性,您不需要同时监听 @new-value 事件,除非您有一些特定场景需要覆盖行为。
@new-value 事件
@new-value 事件与要添加的值和一个 done 回调一起发出。done 回调有两个可选参数:
- 要添加的值
- 行为(与
new-value-mode属性相同的值,当指定时会覆盖该属性 – 如果使用)-- 默认行为(如果不使用new-value-mode)是添加值,即使它是重复的
不带参数调用 done() 只会清空输入框值,而不会以任何方式修改模型。
使用菜单和过滤
过滤并将新值添加到菜单:
过滤新值(在下面的示例中,要添加的值需要至少 3 个字符才能通过),并且不添加到菜单:
从输入生成多个值:
净化处理
默认情况下,所有选项(包括选定的选项)都会被净化处理。这意味着以 HTML 格式显示它们的功能被禁用。但是,如果您需要在选项上使用 HTML 并且信任其内容,那么有几种方法可以做到这一点。
您可以通过以下方式强制菜单选项的 HTML 形式:
- 将受信任选项的
html键设置为true(针对特定的受信任选项) - 或者设置 QSelect 的
options-html属性(针对所有选项)
如果满足以下条件,QSelect 的显示值将以 HTML 形式显示:
- 设置了 QSelect 的
display-value-html属性 - 或者您没有使用
display-value并且- 设置了 QSelect 的
options-html属性 - 任何选定的选项都将
html键设置为true
- 设置了 QSelect 的
WARNING
如果您使用 selected 或 selected-item 插槽,那么您负责对显示值进行净化处理。display-value-html 属性将不适用。
渲染性能
渲染性能不会受到选项数量的太大影响,除非在大型集合上使用 map-options。 注意使用了无限滚动,它会在用户滚动列表时渲染额外的选项。
TIP
- (组合式 API)要在使用大量选项时获得最佳性能,请不要使用 ref()/computed()/reactive() 等函数包装传递给
options属性的数组。这允许 Vue 跳过使列表对变化做出"响应"。 - (选项式 API)要在使用大量选项时获得最佳性能,请使用
Object.freeze(items)冻结传递给options属性的数组。这允许 Vue 跳过使列表对变化做出"响应"。
键盘导航
当 QSelect 获得焦点时:
- 按下 ENTER、ARROW DOWN(如果未设置
use-input则为 SPACE)将打开选项列表 - 如果设置了
use-chips:- 按下 SHIFT + TAB 将向后浏览 QChips(如果选择了 QChip,TAB 将向前浏览 QChips)
- 当选择了 QChip 时按下 ENTER 将从选择中删除该选项
- 按下 BACKSPACE 将从选择中删除最后一个选项(当设置了
use-input时,输入应为空)
- 当设置了
clearable时按下 BACKSPACE:- 对于单选,它会清除模型(值为
null) - 对于多选,它会删除最后添加的值
- 对于单选,它会清除模型(值为
- 按下 TAB(或者如果未设置
use-chips或选择了第一个 QChip,则按下 SHIFT + TAB)将导航到页面上的下一个或上一个可聚焦元素 - 如果未设置
use-input,键入文本(0 - 9 或 A - Z)将:- 创建一个搜索缓冲区(如果 1.5 秒内没有键入新键,将重置),用于在选项标签中搜索
- 如果多次键入缓冲区中的第一个键,则选择以该字母开头的下一个选项(在当前焦点之后)
- 选择与键入文本匹配的下一个选项(从当前焦点开始)(匹配是模糊的 - 选项标签应以第一个字母开头并包含所有字母)
当打开选项列表时:
- 按下 向上箭头 或 向下箭头 将在选项列表中向上或向下导航
- 按下 PAGE UP 或 PAGE DOWN 将在选项列表中向上或向下导航一页
- 按下 HOME 或 END 将导航到选项列表的开始或结束(仅当您不使用
use-input或输入为空时) - 使用箭头键导航时,当到达列表的开始或结束时,导航将环绕
- 当在列表中选择了一个选项时,按下 ENTER(或者如果未设置
use-input,则按下 空格,或者如果未设置multiple和disable-tab-selection,则按下 TAB)将:- 如果未设置
multiple和disable-tab-selection,则选择该选项并关闭选项列表 - 如果设置了
multiple,则切换该选项
- 如果未设置
原生表单提交
当处理具有 action 和 method 的原生表单时(例如,将 Quasar 与 ASP.NET 控制器一起使用时),您需要在 QSelect 上指定 name 属性,否则 formData 将不包含它(如果应该包含) - 所有值都转换为字符串(原生行为,因此不要使用对象值):