图片大图预览就该这样做

在管理系统开发过程中,我们不可避免需要预览一些上传的图片。小编在开发过程中就遇到需要实现在列表上点击"查看"按钮预览该条记录上的所有图片。

项目所用技术栈:vue、element ui

我们都知道el-image组件可以通过previewSrcList 开启预览大图的功能,那么是否可以基于该组件实现预览功能呢?当然是可以的。

下面就是小编开发的图片预览组件,其原理就是通过手动触发el-image的预览大图功能

js 复制代码
<template>
  <!-- 图片预览 -->
  <el-image
    id="previewImage"
    style="
      opacity: 0;
      position: fixed;
      top: 50%;
      left: 50%;
      transform: translate(-50%, -50%);
    "
    :src="logo"
    :preview-src-list="imagesList"
    fit="fill"
    @click.stop="handleClick"
  />
</template>
<script lang="ts">
import Vue from 'vue'
// 给个默认的图片地址,使el-image相关的dom元素都能存在
import logo from '@/assets/images/logo.png'
import { Loading } from 'element-ui'
import { showPic } from '@/api/common'

export default Vue.extend({
  name: 'SeeImages',
  props: ['imagesDialogVisible', 'imageIdList'],
  data() {
    return { logo, imagesList: [], loadingInstance: null }
  },
  created() {
    // 根据图片id调用接口获取到图片的url
    this.loadingInstance = Loading.service({ fullscreen: true })
    const promiseArr = []
    for (const i of this.imageIdList) {
      // thumbnailType缩略图类型0-非缩略图 1-缩略图
      promiseArr.push(showPic({ id: i, thumbnailType: 0 }))
    }
    Promise.all(promiseArr)
      .then((res) => {
        const images = []
        res.forEach((item) => {
          images.push(
            'data:image/png;base64,' +
              btoa(
                new Uint8Array(item.data).reduce(
                  (data, byte) => data + String.fromCharCode(byte),
                  ''
                )
              )
          )
        })
        this.imagesList = images
        this.$nextTick(() => {
          // 触发el-image的预览功能
          const element = document.querySelectorAll(
            '#previewImage'
          )[0] as HTMLElement
          if (element) {
            element.click()
          }
        })
      })
      .finally(() => {
        this.loadingInstance.close()
      })
  },
  methods: {
    handleClick() {
      // 关闭预览的时候移除组件
      const that = this
      setTimeout(function () {
        const domImageMask = document.querySelector('.el-image-viewer__wrapper')
        if (!domImageMask) {
          return
        }
        domImageMask.addEventListener('click', (e) => {
          if (
            [
              'el-image-viewer__btn el-image-viewer__prev',
              'el-image-viewer__btn el-image-viewer__next',
              'el-image-viewer__btn el-image-viewer__actions',
              'el-image-viewer__actions__inner',
              'el-image-viewer__canvas'
            ].includes((e.target as any).parentNode?.className || '')
          ) {
            return
          }
          that.$emit('update:imagesDialogVisible', false)
        })
      }, 300)
    }
  }
})
</script>
相关推荐
粉末的沉淀18 小时前
css:制作带边框的气泡框
前端·javascript·css
N***738519 小时前
Vue网络编程详解
前端·javascript·vue.js
e***716719 小时前
Spring Boot项目接收前端参数的11种方式
前端·spring boot·后端
程序猿小蒜19 小时前
基于springboot的的学生干部管理系统开发与设计
java·前端·spring boot·后端·spring
银空飞羽19 小时前
让Trae CN SOLO自主发挥,看看能做出一个什么样的项目
前端·人工智能·trae
Eshine、20 小时前
解决前端项目中,浏览器无法正常加载带.gz名称的文件
前端·vue3·.gz·.gz名称的js文件无法被加载
用户479492835691521 小时前
别再当 AI 的"人肉定位器"了:一个工具让 React 组件秒定位
前端·aigc·ai编程
WYiQIU21 小时前
面了一次字节前端岗,我才知道何为“造火箭”的极致!
前端·javascript·vue.js·react.js·面试
qq_3168377521 小时前
uniapp 观察列表每个元素的曝光时间
前端·javascript·uni-app
小夏同学呀21 小时前
在 Vue 2 中实现 “点击下载条码 → 打开新窗口预览 → 自动唤起浏览器打印” 的功能
前端·javascript·vue.js