vue3 根据点击位置,实现一个用户头像弹框定位

vue3 根据点击位置,实现一个用户头像弹框定位

需求背景

最近在做直播后台,涉及到对用户的一些操作,比如关注/取关/禁言/踢出直播间。多个地方都要用,需要封装一个弹框组件

效果图

实现过程分析

  1. 根据点击元素,获取元素的位置
  2. 动态设置元素top,left位置

top 和 left 如何获取

根据 点击事件event参数,来获取位置,根据需要来实际计算位置

  • 元素距离左边的距离 + 元素本身的宽度

获取元素top/left,其实直接用getBoundingClientRect 里的bottom / right 即可

代码实现

js 复制代码
export const getCurrentDialogXY = (event: Event) => {
  const target = event.target as HTMLElement
  const { bottom, right } = target.getBoundingClientRect()
  return { bottom, right }
}

调用

scss 复制代码
```js
const avatarHandler = (event: Event) => {
  const { right, bottom } = getCurrentDialogXY(event)
  currentX.value = right
  currentY.value = bottom
}

传入子组件,在子组件内接收到left/top 重新定位即可

js 复制代码
    <user-info-dialog
        :left="currentX"
        :top="currentY"
    />
js 复制代码
<div ref="userInfoRef" class="dialog-wrap" :style="{ top: top + 'px', left: left + 'px' }"></div>

细节处理

  1. 通过设置,你会发现弹框始终定位在元素右下角,可以根据自身需求,设置元素位置

通过监听弹框的ref(弹框有显示隐藏逻辑,所以监听弹框的ref即可,然后动态设置位置),

js 复制代码
watchEffect(() => {
  const userInfoRefValue = userInfoRef.value
  if (userInfoRefValue) {
    const offsetHeight = userInfoRefValue.offsetHeight // 获取弹框的高度
    const offsetWidth = userInfoRefValue.offsetWidth // 获取元素的宽度

    // 不管弹框显示是左侧还是右侧,根据需求 都需要 减去 弹框的高度 - 用户头像高度的一半 进行定位
      propTop.value = props.top - offsetHeight - userAvatarWidth.value / 2
      
    // 如果是弹框显示在左侧,需要减去弹框的宽度 - 头像的宽度
    if (props.roleEnumType === 1) {
      propLeft.value = props.left - offsetWidth - userAvatarWidth.value
    }
  }
})
  1. 弹框打开之后,要点击所有位置,都可以关闭
  • 那我们就需要实现一个朦层(透明色),点击朦层,触发关闭即可

你会发现,其实我们的整个元素,是直接在根节点上,根常规里的,每个弹框,必须要绑定在循环里,才能做一一对应的关系,怎么不太一样呢? 这里是用到的

vue3中的Teleport:将其插槽内容渲染到 DOM 中的另一个位置 这对于我们层级比较多,做全局定位,脱离当前元素,非常好用!!!

当我们触发关闭事件,抛出去让父组件处理即可

相关推荐
再学一点就睡7 分钟前
前端网络实战手册:15个高频工作场景全解析
前端·网络协议
C_心欲无痕1 小时前
有限状态机在前端中的应用
前端·状态模式
C_心欲无痕1 小时前
前端基于 IntersectionObserver 更流畅的懒加载实现
前端
candyTong1 小时前
深入解析:AI 智能体(Agent)是如何解决问题的?
前端·agent·ai编程
柳杉1 小时前
建议收藏 | 2026年AI工具封神榜:从Sora到混元3D,生产力彻底爆发
前端·人工智能·后端
weixin_462446231 小时前
使用 Puppeteer 设置 Cookies 并实现自动化分页操作:前端实战教程
运维·前端·自动化
CheungChunChiu2 小时前
Linux 内核动态打印机制详解
android·linux·服务器·前端·ubuntu
GIS之路2 小时前
GDAL 创建矢量图层的两种方式
前端
小目标一个亿3 小时前
Windows平台Nginx配置web账号密码验证
linux·前端·nginx
rocky1913 小时前
网页版时钟
前端·javascript·html