Element-UI - el-table中自定义图片悬浮弹框 - 位置优化

news2024/11/22 16:30:13

        该篇为前一篇“Element-UI - 解决el-table中图片悬浮被遮挡问题”的优化升级部分,解决当图片位于页面底部时,显示不全问题优化。

        Vue.directive钩子函数已在上一篇中详细介绍,不清楚的朋友可以翻看上一篇, “Element-UI - 解决el-table中图片悬浮被遮挡问题”的地址:Element-UI - 解决el-table中图片悬浮被遮挡问题_el-badge el-table 被遮挡-CSDN博客

一、浏览器窗口

        浏览器窗口的宽和高分别通过window.innerWidth和window.innerHeight获取,如最底部图片,可以通过获取弹框中图片高度,进行对比是否超出window.innerHeight; 如果超出,则减于图片高度,进行底部对齐显示。

二、弹框中图片高度获取

        在上一篇中,在弹框封装类中定义了imgBox属性,用于记录弹框中图片DOM节点对象,所以可以在执行resetPosition(boundingClientRect)函数时,可以通过this.imgBox.height获取弹框中图片的高度。

        控制台中显示弹框中图片高度,如下图:

三、实现图片上移

        通过上述了解后,知道了如何判断图片是否超出底位置,如果超出了,则需要将位置top减掉弹框实际高度(图片高度 + 弹框内填充),进行上移即可。

        修改后的resetPosition函数代码如下:

 /**
   * 重新指定弹框位置
   * @param {Object} boundingClientRect
   */
  resetPosition(boundingClientRect){
    // 弹框实际高度
    const height = this.imgBox.height + this.dialogPadding * 2;
    // 判断图片是否超出底部可见范围
    if( boundingClientRect.top + height >= window.innerHeight){
      // top减于弹框实际高度
       this.sDialog.style.top = (boundingClientRect.top - height) + "px";
    }
    // 未超出
    else{
      this.sDialog.style.top = (boundingClientRect.top - this.dialogPadding) + "px";
    }
    this.sDialog.style.left = (boundingClientRect.width + boundingClientRect.left) + "px";
  }

        此时底部图片则已被修正,可以底部对齐显示了,如下图:

四、完整代码

1.页面代码

import sDialog from './suspendedDialog.js'
export default {
  data(){
    return {
      tableData: [
        {name: "Angular", thumb: require("@/assets/angular.jpg"), createtime: "2024/6/15", updatetime: "2024/6/15"},
        {name: "VueJs", thumb: require("@/assets/logo.png"), createtime: "2024/6/15", updatetime: "2024/6/15"},
        {name: "NuxtJs", thumb: require("@/assets/nuxtjs.jpg"), createtime: "2024/6/15", updatetime: "2024/6/15"},
        {name: "React", thumb: require("@/assets/react.jpg"), createtime: "2024/6/15", updatetime: "2024/6/15"},
        {name: "Dog", thumb: require("@/assets/dog.jpg"), createtime: "2024/6/15", updatetime: "2024/6/15"}
      ]
    }
  },
  directives: {
    // 自定义悬浮v-suspended
    suspended: {
      bind: (el) => {
        // 初始化悬浮框
        sDialog.initialDom();
        // 鼠标经过图片并未移出时执行回调函数
        el.addEventListener('mouseenter', function(e) {
          // 显示悬浮弹框,显示后获取相应的参数信息
          sDialog.toggle(true, () => {
            sDialog.setImgUrl(el.src);                              // 修改新的图片地址
            sDialog.resetPosition(el.getBoundingClientRect());      // 修正弹框位置
          });
        });
        // 鼠标移出图片区域时,隐藏悬浮弹框
        el.addEventListener('mouseleave', () => sDialog.toggle(false));
      }
    }
  },
  // end
}

2.封装类(suspendedDialog.js)

/*
 * 定义弹框类
 */
class SuspendedDialog{
  constructor(){
    this.idName = "suspended-dialog";       // 定义容器ID选择器名称
    this.innerClassName = "inner";          // 内容器类选择器名称
    this.imgClassName = "imgs";             // 图片节点类选择器名称
    this.dialogWidth = 240;                 // 外容器宽度
    this.dialogPadding = 12;                // 外容器内填充

    this.sDialog = document.createElement('div');   // 外层容器
    this.innerBox = document.createElement('div');  // 内容器对象
    this.imgBox = document.createElement('img');    // 图片节点对象
  }
  /**
   * 初始化DOM,并添加到body中
   */
  initialDom(){
    const sDialog = document.getElementById(this.idName);   // 查询节点
    // 如果节点存在,则结束后续操作
    if(sDialog) return;

    // 初始经属性
    this.sDialog.id = this.idName;
    this.innerBox.classList.add(this.innerClassName);
    this.imgBox.classList.add(this.imgClassName);
    // 将DOM追加到对应容器中
    this.innerBox.append(this.imgBox);
    this.sDialog.append(this.innerBox);
    document.body.append(this.sDialog);
    // 追加事件
    this.addEvent();
  }
  /**
   * 修改图片路径
   * @param {Object} _url
   */
  setImgUrl(_url){
    this.imgBox.src = _url;
  }
  /**
   * 添加监听事件
   */
  addEvent(){
    this.sDialog.addEventListener('mouseenter', e => this.toggle(true));    // 鼠标移入悬浮框区域时保持显示
    this.sDialog.addEventListener('mouseleave', e => this.toggle(false));   // 鼠标移出悬浮框区域时隐藏
  }
  /**
   * 显示与隐藏
   * @param {Object} flag
   * @param {Object} callback  回调函数
   */
  toggle(flag, callback = () => {}){
    if(flag && 'block'!=this.sDialog.style.display){
      this.sDialog.style.display = 'block';
      callback();
    } else if(!flag && 'none'!=this.sDialog.style.display){
      this.sDialog.style.display = 'none';
      callback();
    }
  }
  /**
   * 重新指定弹框位置
   * @param {Object} boundingClientRect
   */
  resetPosition(boundingClientRect){
    // 弹框实际高度
    const height = this.imgBox.height + this.dialogPadding * 2;
    // 判断图片是否超出底部可见范围
    if(boundingClientRect.top + height >= window.innerHeight){
      // top减于弹框实际高度
       this.sDialog.style.top = (boundingClientRect.top - height) + "px";
    }
    // 未超出
    else{
      this.sDialog.style.top = (boundingClientRect.top - this.dialogPadding) + "px";
    }
    this.sDialog.style.left = (boundingClientRect.width + boundingClientRect.left) + "px";
  }
}
export default new SuspendedDialog();

        另外,图片除了底部超出可见范围,也会出现左侧或右侧超出可见范围,则可以通过window.innerWidth进行判断处理,计算方式差不多,这里就不再阐述。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1888301.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【Python】字典练习

python期考练习 目录 1. 首都名​编辑 2. 摩斯电码 3. 登录 4. 学生的姓名和年龄​编辑 5. 电商 6. 学生基本信息 7. 字母数 1. 首都名 初始字典 (可复制) : d{"China":"Beijing","America":"Washington","Norway":…

企业如何管理安全生产工作?(附模板)

总结一下在企业内管理安全中遇到的一些问题: 1、 管理方式落后,还在使用纸质记录 2、 人员信息杂乱无章,无人整理 3、出现问题找不到源头和负责人 我做系统管理已经7年了,题主说的这些问题我之前也遇到过,相信也有…

Java学习高级一

修饰符 static 类变量的应用场景 成员方法的分类 成员变量的执行原理 成员方法的执行原理 Java之 main 方法 类方法的常见应用场景 代码块 设计模式 单例设计模式 饿汉式单例设计模式 懒汉式单例设计模式 继承 权限修饰符

【MindSpore学习打卡】应用实践-计算机视觉-FCN图像语义分割-基于MindSpore实现FCN-8s进行图像语义分割的教程

图像语义分割是计算机视觉领域中的一个重要任务,它旨在对图像中的每个像素进行分类,从而实现对图像内容的详细理解。在众多图像语义分割算法中,全卷积网络(Fully Convolutional Networks, FCN)因其端到端的训练方式和高…

Git使用中遇到的问题(随时更新)

问题1.先创建本地库,后拉取远程仓库时上传失败的问题怎么解决? 操作主要步骤: step1 设置远程仓库地址: $ git remote add origin gitgitee.com:yourAccount/reponamexxx.git step2 推送到远程仓库: $ git push -u origin "master&qu…

API接口测试/Swgger-ui未授权访问

目录 API接口 接口文档 接口测试的方法 单流程 多流程 Swgger-ui未授权访问 在之间的一次面试中面试官问到了API接口测试,我回答的不好,因为自己确实不太会,后面才下去学习了,这里复习和练习一下 API接口 API(…

DevOps:开发与运维的无缝融合

目录 前言1. DevOps的起源与概念1.1 DevOps的起源1.2 DevOps的定义 2. DevOps的核心实践2.1 持续集成2.2 持续交付2.3 自动化 3. DevOps工具链3.1 版本控制系统3.2 持续集成工具3.3 配置管理工具3.4 容器化与编排工具3.5 监控和日志工具 4. DevOps的实际应用4.1 案例分析&#…

【技巧分享】对接多平台:高效接入淘宝、抖音、京东、拼多多等电商平台API的实战策略

当电商商家想要自研电商管理系统,或是线下ERP厂商想要开发电商业务管理功能,需要对接电商平台API,但电商平台众多,各类平台API接口也需要花费大量的时间和精力去对接,如何快速接入多个电商平台API呢?点三来…

FormMaking表单设计器V3.8发布,数据表格上线,支持多选、多级表头、列模板自定义、操作列、分页等设置

介绍 FormMaking 是基于Vue的可视化表单设计器,赋能企业实现可视化低代码开发模式;帮助开发者从传统枯燥的表单代码中解放出来,更多关注业务,快速提高效率,节省研发成本。 目前已经在OA系统、考试系统、报表系统、流程…

docker push 推送镜像到阿里云仓库

1.登陆阿里云 镜像服务,跟着指引操作就行 创建个人实例,创建命名空间、镜像仓库,绑定代码源头 2.将镜像推送到Registry $ docker login --username*** registry.cn-beijing.aliyuncs.com $ docker tag [ImageId] registry.cn-beijing.aliy…

AI商品图生成定制技术公司

AI绘画模型训练、定制服务公司案例分析— 触站AI,塑造智能设计新纪元 第一:触站AI的创新之路 触站AI的崛起标志着AI技术在艺术与设计领域应用的一个新高度。作为一家专注于企业AI图像领域的技术解决方案服务公司,触站AI以其前沿的技术和定制…

数字化精益生产系统--SRM供应商关系管理

SRM供应商关系管理,全称为Supplier Relationship Management(供应商关系管理)系统,是一种专门用于管理采购供应链和供应商关系的软件系统。该系统通过集成各个环节的采购活动,帮助企业实现采购流程的自动化、标准化和优…

AI智能体|AI打工我躺平!使用扣子Coze智能体自动生成和发布文章到微信公众号(一)

大家好,我是无界生长,国内最大AI付费社群“AI破局俱乐部”初创合伙人。这是我的第 44 篇原创文章——《AI智能体|AI打工我躺平!使用扣子Coze智能体自动生成和发布文章到微信公众号(一)》 AI智能体&#xf…

课程设计——基于FPGA的双向移位寄存器

基于FPGA的双向移位寄存器 摘 要 本文使用verilog HDL语言设计双向移位寄存器,使电路受外部信号控制,实现数字信号的双向移位等功能,其电路设计模块主要分为三个部分,分别为接受判断控制信号的组合逻辑电路部分、实现存储、运算…

系统安全保证措施方案(word原件)

一、身份鉴别 二、访问控制 三、通信完整性、保密性 四、抗抵赖 五、数据完整性 六、数据保密性 七、应用安全支撑系统设计 软件资料获取及全资料学习获取:本文末个人名片或进主页。

2024年江西省研究生数学建模竞赛C题聚变反应堆设计论文和代码分析

经过不懈的努力,2024年江西省研究生数学建模竞赛C题聚变反应堆设计论文和代码已完成,代码为C题全部问题的代码,论文包括摘要、问题重述、问题分析、模型假设、符号说明、模型的建立和求解(问题1模型的建立和求解、问题2模型的建立…

金融科技在反洗钱领域的创新应用

随着金融市场的不断发展和全球化趋势的加速,洗钱活动日益猖獗,给金融机构和社会经济安全带来了严重威胁。为了有效应对这一挑战,金融科技在反洗钱领域的应用逐渐崭露头角,为打击洗钱活动提供了强有力的技术支持。本文将从多个角度…

UG NX二次开发(C#)-根据草图创建拉伸特征(UFun+NXOpen)

文章目录 1、前言2、在UG NX中创建草图,然后创建拉伸特征3、基于UFun函数的实现4、基于NXOpen的实现代码1、前言 UG NX是基于特征的三维建模软件,其中拉伸特征是一个很重要的特征,有读者问如何根据草图创建拉伸特征,我在这篇博客中讲述一下草图创建拉伸特征的UG NX二次开发…

学习springAOP

第三章 Spring AOP 第一节 AOP 简介 1. 概念 AOP全称为Aspect Oriented Programming,表示面向切面编程。何为切面呢? 由此可以得出,切面是一种将那些与业务无关,但业务模块都需要使用的功能封装起来的技术。这样便于减少系统的…

Linux 64位系统运行32位程序

1、原理分析 Linux 64位系统运行32位程序的原理主要涉及到系统架构的兼容性、库文件的支持以及特定的运行环境设置。 1.1 系统架构兼容性 x64与x86的区别: x86是Intel于1985年推出的32位指令集架构,后被AMD、VIA等厂商广泛采用。x64(也称为…