123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240 |
- <template>
- <div :class="[ui,isDom?'cu-img-preview-dom':'']" class="cu-img-preview">
- <div class="cu-img-preview-box">
- <div :style="{transform:'scale('+ scale +')'}" class="cu-img-preview-scale">
- <NodeImg :src="imgUrl" :style="{transform:'rotate('+ rotate +'deg)'}" height="auto" ui="ui-img-auto-box"/>
- </div>
- </div>
- <div v-if="srcs.length > 0" :class="isThumb?'show':''" class="cu-img-thumb-box">
- <div v-for="(item,id) in srcs" :class="id === index?'cur':''" class="cu-img-thumb-item" @click="tapThumbClick(id,item)">
- <NodeImg :src="item" height="80px"/>
- </div>
- </div>
- <div class="cu-img-preview-tools-box" :class="toolsSm?'cu-img-preview-tools-sm':''">
- <div class="preview-tools-box">
- <div class="preview-tools-flex">
- <div v-if="srcs.length > 0" :class="isThumb?'cur':''" class="preview-tools-item" @click="thumbClick">
- thumb
- </div>
- <div class="preview-tools-item" @click="leftRotationClick">
- <HcIcon name="anticlockwise"/>
- </div>
- <div class="preview-tools-item" @click="rightRotationClick">
- <HcIcon name="clockwise"/>
- </div>
- <div class="preview-tools-item" @click="enlargeClick">
- <HcIcon name="zoom-in"/>
- </div>
- <div class="preview-tools-item" @click="shrinkClick">
- <HcIcon name="zoom-out"/>
- </div>
- <div class="preview-tools-item" @click="scaleClick">
- <HcIcon name="merge-cells-horizontal" :line="false"/>
- </div>
- <div v-if="srcs.length > 0" class="preview-tools-item" @click="topClick">
- back
- </div>
- <div v-if="srcs.length > 0" class="preview-tools-item" @click="nextClick">
- arrow
- </div>
- <div v-if="enlarge" class="preview-tools-item">
- enlarge
- </div>
- <div v-for="item in tools" class="preview-tools-item" @click="toolsClick(item)">
- <HcIcon :name="item.icon"/>
- </div>
- <div class="preview-tools-item" v-if="!isDom" @click="closeClick">
- <HcIcon name="close"/>
- </div>
- </div>
- </div>
- </div>
- </div>
- </template>
- <script setup>
- import {ref,watch} from "vue";
- import NodeImg from "./NodeImg.vue"
- const props = defineProps({
- ui: {
- type: String,
- default: ''
- },
- //单图片
- src: {
- type: String,
- default: ''
- },
- //图片数组
- srcs: {
- type: Array,
- default: () => ([])
- },
- //选中索引
- cur: {
- type: Number,
- default: -1
- },
- //是否全屏
- enlarge: {
- type: Boolean,
- default: false
- },
- //扩展工具栏
- tools: {
- type: Array,
- default: () => ([])
- },
- //小工具栏
- toolsSm: {
- type: Boolean,
- default: false
- },
- //挂载在某个dom上
- isDom: {
- type: Boolean,
- default: false
- },
- })
- //变量
- const scale = ref(1);
- const rotate = ref(0);
- const isThumb = ref(false);
- const imgUrl = ref(props.src||'');
- const index = ref(parseInt(props.cur) || -1);
- //监听
- watch(() => [
- props.src,
- props.cur,
- ], ([src,cur]) => {
- imgUrl.value = src
- index.value = parseInt(cur) || -1
- })
- //事件
- const emit = defineEmits(['curImg', 'thumb', 'tapThumb', 'tapRotation', 'tapZoom', 'tapScale', 'tapTools', 'close', 'vmClose']);
- const curIndex = props.srcs?.length - 1;
- //处理默认选择图片
- if (props.src && props.srcs?.length <= 0) {
- imgUrl.value = props.src
- index.value = -1;
- } else if (props.srcs?.length > 0) {
- if (curIndex >= index.value && index.value >= 0) {
- imgUrl.value = props.srcs?.[index.value];
- } else {
- imgUrl.value = props.srcs?.[0];
- index.value = 0;
- }
- }
- //上一张
- function topClick() {
- if (index.value === 0) {
- index.value = curIndex;
- } else {
- index.value--;
- }
- setCurImageUrl();
- }
- //下一张
- function nextClick() {
- if (index.value === curIndex) {
- index.value = 0;
- } else {
- index.value++;
- }
- setCurImageUrl();
- }
- //从缩略图里选择图片
- function tapThumbClick(id, item) {
- index.value = id;
- imgUrl.value = item;
- emit('thumb', {cur: id, img: item})
- }
- //设置选中的图片
- function setCurImageUrl() {
- imgUrl.value = props.srcs?.[index.value];
- emit('curImg', {cur: index.value, img: imgUrl.value})
- }
- //缩略图
- function thumbClick() {
- isThumb.value = !isThumb.value;
- emit('tapThumb', isThumb.value)
- }
- //逆时针旋转
- function leftRotationClick() {
- if (rotate.value === 0) {
- rotate.value = 270
- } else if (rotate.value === 270) {
- rotate.value = 180
- } else if (rotate.value === 180) {
- rotate.value = 90
- } else if (rotate.value === 90) {
- rotate.value = 0
- }
- emit('tapRotation', rotate.value)
- }
- //顺时针旋转
- function rightRotationClick() {
- if (rotate.value === 0) {
- rotate.value = 90
- } else if (rotate.value === 90) {
- rotate.value = 180
- } else if (rotate.value === 180) {
- rotate.value = 270
- } else if (rotate.value === 270) {
- rotate.value = 0
- }
- emit('tapRotation', rotate.value)
- }
- //放大
- function enlargeClick() {
- if (scale.value <= 6) {
- scale.value += 0.1
- }
- emit('tapZoom', scale.value)
- }
- //缩小
- function shrinkClick() {
- if (scale.value >= 0.11) {
- scale.value -= 0.1
- }
- emit('tapZoom', scale.value)
- }
- //还原尺寸
- function scaleClick() {
- scale.value = 1;
- rotate.value = 0;
- emit('tapScale')
- }
- //扩展栏被点击
- function toolsClick(item) {
- emit('tapTools', item)
- }
- //close
- function closeClick() {
- emit('close')
- emit('vmClose')
- }
- </script>
- <style lang="scss" scoped>
- @import './style.scss';
- </style>
|