Vue3+ElementPlus封装图片空间组件的门面实例
作者:勿语&
图片空间是用于管理上传图片的工具,可以让用户方便地存储、管理和调用图片,提高工作效率,它通常具备多样的样式,但操作入口统一,便于使用,通过图片空间组件,用户能直接在其他模块(例如商品图片)中选择所需图片
什么是图片空间?
图片空间就是专门管理我们上传图片的地方。
就好比用户管理一样,我们对要上传的图片进行管理。
这样做的好处有哪些?
我们把可能需要的图片都上传到图片管理中。在其他需要图片的地方(如:商品图片等)可以直接调用图片空间组件,从图片空间中进行选择。
图片空间的样式多种多样,但是它们的入口都是一样的,所以这里封装了图片空间的门面。
1.PictureSpaceFacade.vue 组件
<script setup> const props=defineProps({ // 图片数组或字符串(http://a.com/1.jpg,http://a.com/2.jpg 用逗号隔开) modelValue: { type: [Array,String,Object], }, // 图片宽度 pictureWidth: { type:String, default: '100px' }, // 图片高度 pictureHeight:{ type:String, default: '100px' } }) const emits=defineEmits(['update:modelValue']) import {ref, watch} from "vue"; // 图片数组 const pictureList = ref([]) // 监听props.modelValue变化 watch(() => props.modelValue, (newValue) => { if (newValue){ pictureList.value=Array.isArray(newValue) ? newValue : props.modelValue.split(","); }else{ pictureList.value = [] } },{deep:true,immediate:true}) // 预览图片开关 const previewVisible = ref(false) // 预览图片url const previewImageUrl = ref('') // 点击预览图片按钮回调 function previewPicture(url) { previewVisible.value = true previewImageUrl.value = url } // 点击删除图片按钮回调 function deletePicture(url) { pictureList.value = pictureList.value.filter(item => url !== item) emits('update:modelValue', pictureList.value) } </script>
<template> <div id="app"> <div class="container"> <div class="container-item" :style="{width:pictureWidth ,height:pictureHeight}" v-for="item in pictureList" :key="item"> <img class="img-item" :src="item" alt=""/> <div class="overlay"> <span class="opt" @click="previewPicture(item)">预览</span> <span class="opt" @click="deletePicture(item)">删除</span> </div> </div> <div class="container-item add-container" :style="{width:pictureWidth ,height:pictureHeight}"> <slot>+</slot> </div> </div> <!-- 图片预览--> <el-dialog v-model="previewVisible" style="overflow: auto"> <div style="height: 100%; width: 100%; display: flex; justify-content: center; align-items: center;"> <img style="object-fit: cover; height: 100%; width: 100%;" :src="previewImageUrl" alt="Preview Image"/> </div> </el-dialog> </div> </template>
<style scoped lang="scss"> .container { display: flex; flex-wrap: wrap; width: 100%; } .container-item { height: 150px; width: 150px; margin: 3px; border: 1px solid #cecaca; border-radius: 5px; overflow: hidden; position: relative; &:hover .overlay { opacity: 1; } .img-item { height: 100%; width: 100%; } .overlay { position: absolute; top: 0; left: 0; width: 100%; height: 100%; background-color: rgba(0, 0, 0, 0.5); display: flex; justify-content: center; align-items: center; color: #fff; font-size: 14px; opacity: 0; transition: opacity .5s; .opt { cursor: pointer; margin: 8px; } } } .add-container { border: 1px dashed #cecaca; cursor: pointer; display: flex; justify-content: center; align-items: center; &:hover { border: 1px dashed blue; } } </style>
2.PictureSpaceFacade 组件使用
<script setup> import {ref} from "vue"; import PictureSpaceFacade from "./components/PictureSpaceFacade.vue"; // 获取随机图片 async function getPicture() { const response = await fetch('https://dog.ceo/api/breeds/image/random') const res = await response.json() return res.message } // 图片数组 const pictureList = ref([]) // 初始化图片数组(准备测试数据) async function initPicture() { for (let i = 0; i < 3; i++) { pictureList.value.push(await getPicture()) } } // 图片空间开关 const pictureSpaceVisible = ref(false) // 打开图片空间 function openPictureSpace() { pictureSpaceVisible.value = true } // 关闭图片空间(从图片空间选择图片后对 pictureList进行填充) async function closePictureSpace() { for (let i = 0; i < 2; i++) { pictureList.value.push(await getPicture()) } pictureSpaceVisible.value = false } initPicture() </script>
<template> <el-row> <el-col :span="8"> <PictureSpaceFacade v-model="pictureList" width="220px" picture-width="100px" picture-height="100px"> <div style="height: 100%;width: 100%;display: flex;justify-content: center;align-items: center;" @click="openPictureSpace">+ </div> </PictureSpaceFacade> </el-col> </el-row> <!-- 图片空间弹出框--> <el-dialog v-model="pictureSpaceVisible" title="图片空间" @close="closePictureSpace"> </el-dialog> </template> <style scoped lang="scss"> </style>
图片宽度和高度就是图片自身。
鼠标悬浮会出现操作按钮(这里的文字可以自行修改为icon图标)。
点击图片添加框,会弹出图片空间组件供我们选择。
我们通过选项绑定将pcitureList存入图片空间,这样在图片空间中就能够修改我们的图片数组。
总结
以上为个人经验,希望能给大家一个参考,也希望大家多多支持脚本之家。