Skip to content
主题色
灰色
夜间模式组件大小小(1)中(2)大(3)组件圆角
none
small
medium
large
full
组件缩放90%95%100%105%110%

l-popover作为父元素包裹目标元素,默认渲染子元素,通过pop-content插槽或content属性设置弹出内容(content优先级更高,通过CustomRenderer渲染),通过设定的触发方式来自动展示弹出内容,也可以通过open属性或元素上的方法手动控制是否展示

基本使用

通过triggers属性可设置弹出框触发方式,可同时设置多个:

  • 悬浮触发hover:鼠标移入时触发,鼠标移出后关闭
  • 点击触发click:点击目标时(pointerdown)触发,点击除目标和弹出框以外的地方关闭;若开启点击切换toggleMode,则点击目标时切换开启/关闭状态
  • 按住触发pointerdown:按住目标时触发,松开后关闭
  • 聚焦触发focus:目标获得焦点后触发,失去焦点后关闭,当目标或弹出内容存在焦点时,鼠标移出不会关闭
  • 编辑触发edit:与focus相同,但仅在聚焦元素为可编辑元素时才触发,失去焦点后关闭,可编辑元素指input, textarea, isContenteditable=true或存在关联的editContext,存在可编辑聚焦元素时,鼠标移出不会关闭
  • 右键触发contextmenu:右键时触发,点击其他地方关闭
  • 选中触发select:选中文本且选中内容与l-popover的目标有交集时触发,此时弹框的位置与选中区域有关,失去选中或其他方式触发均会关闭

设置多个值则它们的触发和关闭方式共同生效,默认值为[hover, click, edit]

鼠标点击处弹出

对于clickcontextmenu这两种点击触发方式,它们默认以 popover 元素本身的矩形为目标进行定位,如果需要在点击处弹出,则需要设置pointerTarget属性为coord(默认为rect),这在想要实现菜单之类的功能时非常有用

单例监听多个目标

组件支持为其不同的子元素单独触发并显示不同的内容,从而避免包裹多个l-popover元素。

该功能是通过属性自动添加监听的子元素,通过autoAttachAttr指定一个属性名,然后为目标子元素设置这个你指定的属性名(例如以下示例的data-target),属性的值为插槽名,这个子元素对应的弹出内容也添加对应的slot即可

需要注意的是,自动监听的子元素必须为l-popover的直接子元素,不可以是深层的节点。你也不可以动态设置属性来添加或删除,必须触发默认插槽的变更才行

该功能也支持命令式调用,命令式调用不受上面的限制,而且还能添加l-popover以外的元素,详见命令式监听多个目标

嵌套

悬浮触发再次悬浮触发
第三次悬浮内容
第三次悬浮触发

弹出位置

实现方式

通过strategy属性指定 Popover 定位方式,可选值为:

  • absolute:默认值,相对于祖先定位元素进行定位,性能更好,且在页面滚动时表现出色,但祖先为 fixed 时滚动会有一定的视觉延迟。另外,它在某些时候会受到 shadow DOM 的限制,详细见下面的折叠块说明
  • fixed:相对于最近 Fixed Containing block 进行定位(通常为视口),当 target 也是 fixed 时较为有用,它也可以用于防止被父级裁剪或遮挡,它对 shadow DOM 兼容性更好。但是某些情况下页面滚动时,由于 transition 的存在,位置的变动会导致一定的视觉延迟
当 strategy=absolute 时 Shadow DOM 对 offsetParent 的限制

strategy=absolute 时是通过 offsetParent 获取祖先元素,但是,被 slotted 的元素无法获取到在里面 shadow 里面的真实 offsetParent,而是会根据其所在自定义元素本身往上寻找 offsetParent。在嵌套 strategy=absolute 时这个限制有可能导致定位错误,但内部对这种情况做了兼容,当l-popover为定位元素时优先取其作为内部 offsetParent(故其默认position: relative,请勿修改为 static

通过type属性指定 Popover 实现方式, 目前支持以下方式:

  • popover: 默认值,会使用原生 Popover API 去实现
  • normal: 当前位置渲染,会受包含块的影响
  • teleport: 将弹出内容渲染到teleport-holder(默认在第一个theme-provider下),通过to属性可调整渲染位置,此时pop-content插槽将失效,必须通过 content 属性来指定弹出框渲染内容

需要注意的是,若浏览器不支持 Popover,手动指定的 type 会被无视,将采用备选方案实现

当前浏览器不支持 Popover API

CSS Anchor positioning

当前浏览器不支持 CSS Anchor positioning

CSS Anchor positioning 是一个非常强大的新特性,利用它我们可以让浏览器自行将悬浮元素定位到某个元素,避免我们手动计算和更新位置,带来更好的体验和性能,详细介绍可参考Chrome 文档MDN

本组件支持该特性,只需设置anchorName属性给定任意CSS合法名称(不需要以--开头),即可在浏览器支持的情况下开启 CSS Anchor Positioning,此时strategy=absolutestrategy=fixed将不会有明显区别,均有较佳的体验

由于该特性对 Shadow DOM 有限制,声明 anchor 定位与 anchor-name 的 CSS 必须在同一个 Shadow Tree 下,否则不会生效,详细请参考标准。因此,该特性在以下情况不会开启

  • type=teleport:此时悬浮元素在 teleport-holder 下,如果此时想要使用该特性必须由用户在 document 下利用::part()选择器自行声明 Anchor positioning 相关样式
  • target 为虚拟元素或外部元素:如 triggers="select"时选中的文本,通过属性手动指定的 target, attachTarget 添加的目标

也许未来标准会有进一步的改进,可关注该issue

自动翻转、偏移

通过flip属性可开启自动翻转,shift可开启自动偏移,用于在悬浮层超出容器时自动调整位置。它们都是floating-ui插件,支持它们各自的参数,不传则为默认参数,具体请参考文档

由于这是floating-ui插件,使用 CSS Anchor positioning 时是不生效的。这种情况下可通过popStyle等方式自行设置position-try-fallbacks(Chromium128 之前为position-try-options)来让浏览器自行调整,但这种方式会使得箭头定位异常,需要取舍,或许可以等一手issue1issue2

虚拟元素

通过target属性可以指定一个元素或虚拟元素,只需其拥有getBoundingClientRect方法,能够返回矩形代表位置即可。target优先于默认插槽

命令式监听多个目标

l-popover支持通过元素上的attachTarget方法添加额外的目标,使之可以在多个目标上监听并展示,避免了要为每一个元素包裹一个 popover

attachTarget第二个参数可以指定slotName,当目标元素激活popover时会切换为该插槽展示,而不是默认的pop-content插槽,以此便可以根据目标元素动态设置弹出内容。如果是通过content属性设置弹出内容,则可以使用函数,从参数中可以获取当前激活的目标元素以动态渲染内容

聚焦时阻止目标切换

当使用单例监听多个目标时,在某个目标聚焦或编辑时,如果我们想要阻止popover因为非聚焦的方式(例如鼠标移入)切换到其他的目标,则可以使用preventSwitchWhen属性,可选值有:

  • focus:聚焦时阻止切换目标
  • edit:编辑时阻止切换目标

关闭时停止更新

一般来说不会在关闭 popover 的时候更新内容,如果很难避免这种情况(例如在表单里面,字段失焦时触发校验,校验失败的信息在 popover 关闭时就更新上去了,造成闪烁),可以使用freezeWhenClosing属性。当开启时,如果 popover 正在关闭,停止content属性的更新(注意如果是使用pop-content插槽则无法影响)

同步宽度高度

弹出内容可通过popWidthpopHeight属性指定宽度和高度,它可以为任意 CSS 长度值,为数字时会视为像素值。它们还支持两个特殊的值anchorWidthanchorHeight,当为这两个值时,弹出框的宽度和高度会和锚点元素保持一致

不同大小