From 6f3fac4493995e16ee0f37c6cf2b06e5de2a6a72 Mon Sep 17 00:00:00 2001 From: riku <risaku@163.com> Date: 星期三, 02 七月 2025 16:27:37 +0800 Subject: [PATCH] 1. 将场景图片的分类修改为从服务端动态获取; 2. 问题整改节目中的问题复现功能修改为可拖动对话框且移除背景模态框; --- src/views/fysp/check/components/ArbitraryPhoto.vue | 293 +++++++++++++++++++++++++++++++++++++++++++++++++++------- 1 files changed, 258 insertions(+), 35 deletions(-) diff --git a/src/views/fysp/check/components/ArbitraryPhoto.vue b/src/views/fysp/check/components/ArbitraryPhoto.vue index 46b1c88..29c5a4e 100644 --- a/src/views/fysp/check/components/ArbitraryPhoto.vue +++ b/src/views/fysp/check/components/ArbitraryPhoto.vue @@ -1,68 +1,291 @@ <template> <FYImageSelectDialog + v-bind="$attrs" + v-loading="loading" title="鍦烘櫙鍥剧墖" :typeList="typesList" :typeImgMap="typesMap" + :onContextMenu="showContextMenu" + contextMenuStr="鍙抽敭鐐瑰嚮鍥剧墖淇敼鍒嗙被" ></FYImageSelectDialog> + <!-- <div + + @click="closeContextMenu" + @contextmenu="closeContextMenu" + class="container" + > --> + <div + v-if="showMenu && !menuLoading" + ref="menu" + :style="menuStyle" + class="context-menu" + > + <template v-for="(item, index) in menuItems" :key="index"> + <el-popover v-if="item.children" placement="right-start" trigger="hover"> + <template #reference> + <el-row justify="space-between" class="menu-item"> + <span>{{ item.label }}</span> + <el-icon><ArrowRight /></el-icon> + </el-row> + </template> + <div + v-for="(item1, index1) in item.children" + :key="index1" + class="menu-item" + @click.stop="handleMenuItem(item1)" + > + {{ item1.label }} + </div> + </el-popover> + + <div class="menu-item" @click.stop="handleMenuItem(item)" v-else> + {{ item.label }} + </div> + </template> + </div> + <!-- </div> --> </template> <script> import mediafileApi from '@/api/fysp/mediafileApi.js'; import { $fysp } from '@/api/index.js'; +import { enumMediaFile } from '@/enum/mediaFile.js'; + export default { props: { subtask: { - type: Object, - efault: {} + type: Object } }, data() { return { - // 鏃犳暟鎹� typesList: [], typesMap: new Map(), + loading: true, + // 鍙抽敭鍥剧墖寮瑰嚭鑿滃崟鎺у埗 + showMenu: false, + menuLoading: true, + menuStyle: undefined, + allMoveActions: [], + closeContextMenuListenr: undefined, + // 鍙抽敭閫変腑鐨勫浘鐗� + selectedFileElement: undefined, + selectedFile: undefined, + selectedIndex: undefined, + selectedTypeId: undefined }; + }, + computed: { + menuItems() { + return [ + // { label: '澶嶅埗鍒板壀璐存澘', action: 'copy' }, + { + label: '绉诲姩鍒�', + children: this.allMoveActions.filter((v) => { + return v.value != this.selectedTypeId; + }) + } + ]; + } }, mounted() { this.getGroupImgs(); + this.closeContextMenuListenr = (event) => { + if ( + this.$refs.menu && + !this.$refs.menu.contains(event.target) && + this.showMenu + ) { + // 濡傛灉鐐瑰嚮涓嶆槸鍦ㄨ彍鍗曞唴閮ㄤ笖鑿滃崟鏄彲瑙佺殑 + this.showMenu = false; // 闅愯棌鑿滃崟 + } + }; + document.addEventListener('click', this.closeContextMenuListenr); + + this.initMenuItems(); + }, + unmounted() { + document.removeEventListener('click', this.closeContextMenuListenr); }, methods: { // 鍥剧墖鍒嗙被 getGroupImgs() { - mediafileApi.getRoutineByStGuid(this.subtask.stGuid).then((res) => { - let typeList = []; - let typeMap = new Map(); - function hasThisTypeName(typeName) { - return typeList.map((item) => item.typeName).indexOf(typeName) != -1; - } - function addNewType(typeId, typeName, img) { - typeList.push({ - typeId: typeId, - typeName: typeName - }); - typeMap.set(typeId, [img]); - } - function addToThisType(typeId, img) { - typeMap.get(typeId).push(img); - } - const data = res.data; - for (const e of data) { - let img = { - url: $fysp.imgUrl + e.extension1 + e.guid + '.jpg' - }; - const businesstype = e.businesstype; - const businesstypeid = e.businesstypeid; - if (hasThisTypeName(businesstype)) { - addToThisType(businesstypeid, img); - } else { - addNewType(businesstypeid, businesstype, img); + mediafileApi + .getRoutineByStGuid(this.subtask.stGuid) + .then((res) => { + this.loading = true; + let typeList = []; + let typeMap = new Map(); + const data = res.data; + for (const e of data) { + let img = { + url: $fysp.imgUrl + e.extension1 + e.guid + '.jpg', + data: e + }; + const businesstype = e.businesstype; + const businesstypeid = e.businesstypeid; + if ( + typeList.find((item) => item.typeId == businesstypeid) != + undefined + ) { + typeMap.get(businesstypeid).push(img); + } else { + typeList.push({ + typeId: businesstypeid, + typeName: businesstype + }); + typeMap.set(businesstypeid, [img]); + } } - } + this.typesList = typeList; + this.typesMap = typeMap; + }) + .finally(() => (this.loading = false)); + }, + // 鍥剧墖鍙抽敭鐐瑰嚮浜嬩欢 + showContextMenu(event, typeId, index) { + this.showMenu = true; + this.menuStyle = { + left: `${event.clientX}px`, + top: `${event.clientY}px` + }; + this.selectedFileElement = event.target; + this.selectedTypeId = typeId; + this.selectedIndex = index; + this.selectedFile = this.typesMap.get(typeId)[index]; + }, + closeContextMenu() { + this.showMenu = false; + }, + handleMenuItem(item) { + switch (item.action) { + case 'copy': + this.drawImageToCanvas(); + break; + case 'move': + this.selectedFile.data.businesstypeid = item.value; + this.selectedFile.data.businesstype = item.label; + this.changeMediaFileType(this.selectedFile); + break; + default: + break; + } + this.closeContextMenu(); + }, + changeMediaFileType() { + this.selectedFile.loading = true; + const file = this.selectedFile.data; + return mediafileApi + .updateMediaFile(file) + .then((res) => { + if (res == 1) { + const m = this.typesMap + .get(this.selectedTypeId) + .splice(this.selectedIndex, 1); + if (!this.typesMap.has(file.businesstypeid)) { + this.typesList.push({ + typeId: file.businesstypeid, + typeName: file.businesstype + }); + this.typesMap.set(file.businesstypeid, m); + } else { + this.typesMap.get(file.businesstypeid).push(m[0]); + } + } + }) + .finally(() => (this.selectedFile.loading = false)); - this.typesList = typeList; - this.typesMap = typeMap; - }); + // setTimeout(() => { + // const m = this.typesMap + // .get(this.selectedTypeId) + // .splice(this.selectedIndex, 1); + // if (!this.typesMap.has(file.businesstypeid)) { + // this.typesList.push({ + // typeId: file.businesstypeid, + // typeName: file.businesstype + // }); + // this.typesMap.set(file.businesstypeid, m); + // } else { + // this.typesMap.get(file.businesstypeid).push(m[0]); + // } + // this.selectedFile.loading = false; + // }, 2000); + }, + drawImageToCanvas() { + const canvas = document.createElement('canvas'); + const ctx = canvas.getContext('2d'); + const img = this.selectedFileElement; // 鑾峰彇DOM寮曠敤 + // img.crossOrigin = 'Anonymous'; + canvas.width = img.naturalWidth; + canvas.height = img.naturalHeight; + ctx.drawImage(img, 0, 0, canvas.width, canvas.height); + // this.copyCanvasToClipboard(canvas); + const dataUrl = canvas.toDataURL('image/png'); // 鍙互閫夋嫨鍏朵粬鏍煎紡濡�'image/jpeg' + // 鍒涘缓涓�涓复鏃剁殑textarea鍏冪礌鏉ュ鍒舵枃鏈� + const tempTextArea = document.createElement('textarea'); + document.body.appendChild(tempTextArea); + tempTextArea.value = dataUrl; + tempTextArea.select(); + document.execCommand('copy'); + document.body.removeChild(tempTextArea); + }, + copyCanvasToClipboard(canvas) { + canvas.toBlob((blob) => { + const item = new ClipboardItem({ 'image/png': blob }); // 浣犲彲浠ユ牴鎹渶瑕佹敼鍙樻牸寮忥紝濡� "image/jpeg" + navigator.clipboard.write([item]).then( + () => { + console.log('Image copied to clipboard'); + }, + (err) => { + console.error('Could not copy image: ', err); + } + ); + }, 'image/png'); // 鍚屾牱锛岃繖閲屼篃鍙互鎸囧畾鍏朵粬鏍煎紡锛屽 'image/jpeg' + }, + // 鍒濆鍖栧満鏅浘鐗囩殑绫诲瀷鑿滃崟 + initMenuItems() { + this.menuLoading = true; + const sceneTypeId = this.subtask.sceneTypeId; + enumMediaFile(sceneTypeId, false) + .then((res) => { + this.allMoveActions = res.map((v) => { + return { + action: 'move', + label: v.label, + value: v.value + }; + }); + }) + .finally(() => (this.menuLoading = false)); } } }; </script> -<style scoped></style> +<style scoped> +.container { + /* background-color: rgba(19, 211, 67, 0.514); */ + position: fixed; + left: 0; + top: 0; + height: 100vh; + width: 100vw; + z-index: 10000; +} +.context-menu { + position: fixed; + background: white; + border-radius: 4px; + box-shadow: 0 2px 8px rgba(0, 0, 0, 0.15); + min-width: 200px; + z-index: 10001; +} + +.menu-item { + padding: 8px 16px; + cursor: pointer; + transition: background 0.2s; +} + +.menu-item:hover { + background-color: #f0f0f0; +} +</style> -- Gitblit v1.9.3