VUE实现前台图片 标注(添加矩形框)、放大、缩小、拖拽

需求:实现图片上自定义多个矩形选框,选框可移动缩放拖动,图片可以放大缩小、拖拽 ,选框内填充标注文字。
框内填充文字基本都会,不多赘述,后期可添加选框移除功能(思路右击选框弹出选项删除,获取当前点击选框index,在选框arry中移除即可)后续功能可根据个人需求添加,如保存标注图片等等

看下成品:

在这里插入图片描述
代码

<template>
 <div id="test" style="user-select: none;">
   <button @click="fangda">放大</button>
   <button @click="suoxiao">缩小</button>
   <button @click="gai" v-show="isTrue">添加</button>
   <button @click="gai" v-show="!isTrue">移动</button>

   <div class="content">
     <div
       :style="{
         transform: 'scale(' + num + ')',
         position: 'relative',
         width: '100%',
         height: '100%',
       }"
       @mousedown="moveMouse"
       @click="getOffect"
     >
       <div
         :class="
           'biaozhu' + index == 'biaozhu' + b_i
             ? 'biaozhu b_border'
             : 'biaozhu'
         "
         :ref="'biaozhu' + index"
         @mousedown.stop="move"
         @click="handelClick(index)"
         v-for="(item, index) in boxArry"
         :key="index"
         :style="{
           width: item.width + 'px',
           height: item.height + 'px',
           position: 'absolute',
           left: item.left + 'px',
           top: item.top + 'px',
           background: 'rgba(43,100,206,0.3)',
           border: 'none',
         }"
       >
         <div class="r_b" @mousedown="mouseMove11" v-if="b_i == index"></div>
       </div>
       <div
         :style="{
           height: biaozhuHeight + 'px',
           width: biaozhuWidth + 'px',
           top: biaozhuTop + 'px',
           left: biaozhuLeft + 'px',
           position: 'absolute',
           background: 'rgba(43,100,206,0.3)',
         }"
       ></div>
       <img
         style="width: 100%; height: 100%; pointer-events: none;"
         src="https://ss0.bdstatic.com/70cFuHSh_Q1YnxGkpoWK1HF6hhy/it/u=3479844176,2436830052&fm=26&gp=0.jpg"
         alt=""
         @mousedown="isTrue ? null : move"
       />
     </div>
   </div>
 </div>
</template>
<script>
export default {
 data() {
   return {
     num: 1,
     boxArry: [],
     isTrue: false,
     width: "",
     height: "",
     left: "",
     top: "",
     b_i: "",
     biaozhuHeight: 0,
     biaozhuWidth: 0,
     biaozhuTop: 0,
     biaozhuLeft: 0,
   };
 },

 methods: {
   getVuex() {
     console.log(this.$store.state.treeData);
   },
   commitVuex() {
     this.$store.commit("changeTreeData", { a: 1, b: 2 });
     
   },
   mouseOver2(e) {
     document.onmousedown = (e) => {
       let odiv = e.target; //获取目标元素

       //算出鼠标相对元素的位置
       let disX = e.clientX - odiv.offsetLeft;
       let disY = e.clientY - odiv.offsetTop;
       let left = e.clientX - disX;
       let top = e.clientY - disY;

       //绑定元素位置到positionX和positionY上面
       this.positionX = top;
       this.positionY = left;
       console.log(this.boxArry, this.dragsIndex);
       //移动当前元素
       this.boxArry[this.b_i].width = left;
       this.boxArry[this.b_i].height = top;
     };
   },
   drags(e) {
     console.log(e);
   },
   mouseMove11(e) {
     // console.log(e,index)
     let odiv = e.target; //获取目标元素

     //算出鼠标相对元素的位置
     let disX = e.clientX - odiv.offsetLeft;
     let disY = e.clientY - odiv.offsetTop;
     // debugger;
     e.target.onmousemove = (e) => {
       //鼠标按下并移动的事件
       //用鼠标的位置减去鼠标相对元素的位置,得到元素的位置
       // console.log('aaaaaaaaaaaaa',e)
       let left = e.clientX - disX;
       let top = e.clientY - disY;

       //绑定元素位置到positionX和positionY上面
       this.positionX = top;
       this.positionY = left;
       // console.log(this.boxArry,this.dragsIndex)
       //移动当前元素
       this.boxArry[this.b_i].width = left;
       this.boxArry[this.b_i].height = top;
       e.target.onmouseup = (e) => {
         e.target.onmousemove = null;

         // document.onmouseup = null;
       };
     };
   },
   gai() {
     this.isTrue = !this.isTrue;
   },
   getOffect(e) {
     console.log(e);
     document.onmouseup = null;
     // this.left=e.offsetX
     //     this.top=e.offsetY
   },
   moveMouse(e) {
     let odiv = e.target; //获取目标元素

     //算出鼠标相对元素的位置
     let disX = e.clientX - odiv.offsetLeft;
     let disY = e.clientY - odiv.offsetTop;
     console.log(disX, disY);
     if (this.isTrue) {
       // 拖动
       document.onmousemove = (e) => {
         //鼠标按下并移动的事件
         //用鼠标的位置减去鼠标相对元素的位置,得到元素的位置
         let left = e.clientX - disX;
         let top = e.clientY - disY;

         //绑定元素位置到positionX和positionY上面
         this.positionX = top;
         this.positionY = left;

         //移动当前元素
         odiv.style.left = left + "px";
         odiv.style.top = top + "px";
       };
       document.onmouseup = (e) => {
         document.onmousemove = null;
         document.onmouseup = null;
       };
     } else {
       // 添加div

       console.log(e);
       document.onmousemove = (e) => {
         //鼠标按下并移动的事件
         //用鼠标的位置减去鼠标相对元素的位置,得到元素的位置

         let left = disX - odiv.getBoundingClientRect().x;
         let top = disY - odiv.getBoundingClientRect().y;

         console.log(e.target.offsetLeft);
         this.width = (e.clientX - disX) / this.num;
         this.height = (e.clientY - disY) / this.num;
         this.biaozhuWidth = this.width;
         this.biaozhuHeight = this.height;
         this.biaozhuLeft = left;
         this.biaozhuTop = top;
         document.onmouseup = (e) => {
           let left = disX - odiv.getBoundingClientRect().x;
           let top = disY - odiv.getBoundingClientRect().y;
           this.width = (e.clientX - disX) / this.num;
           this.height = (e.clientY - disY) / this.num;

           console.log(e.target.getBoundingClientRect(), disX, disY);
           if (this.width > 5 && this.height > 5) {
             this.boxArry.push({
               width: this.width,
               height: this.height,
               left: left,
               top: top,
             });
           }

           this.biaozhuWidth = 0;
           this.biaozhuHeight = 0;
           this.biaozhuLeft = 0;
           this.biaozhuTop = 0;
           document.onmousemove = null;
           document.onmouseup = null;
         };
       };
     }
   },
   move(e) {
     let odiv = e.target; //获取目标元素

     //算出鼠标相对元素的位置
     let disX = e.clientX - odiv.offsetLeft;
     let disY = e.clientY - odiv.offsetTop;
     document.onmousemove = (e) => {
       //鼠标按下并移动的事件
       //用鼠标的位置减去鼠标相对元素的位置,得到元素的位置
       let left = e.clientX - disX;
       let top = e.clientY - disY;

       //绑定元素位置到positionX和positionY上面
       this.positionX = top;
       this.positionY = left;

       //移动当前元素
       odiv.style.left = left + "px";
       odiv.style.top = top + "px";
     };
     document.onmouseup = (e) => {
       document.onmousemove = null;
       document.onmouseup = null;
     };
   },

   fangda() {
     this.num += 0.1;
   },
   suoxiao() {
     this.num -= 0.1;
   },
   tianjia() {
     this.boxArry.push({
       width: 100,
       height: 100,
       left: 20,
       top: 20,
     });
   },
   handelClick(i) {
     this.b_i = i;
     console.log(i);
   },
   dragstart(event, data) {
     // console.log('drag')
     // event.dataTransfer.setData('item', data)
   },
   dragend(event) {
     // event.dataTransfer.clearData()
   },
 },
 directives: {
   drag: function (el) {
     let dragBox = el; //获取当前元素
     dragBox.onmousedown = (e) => {
       //算出鼠标相对元素的位置

       let disX = e.clientX - dragBox.offsetLeft;
       let disY = e.clientY - dragBox.offsetTop;
       console.log(disX, disY);
       document.onmousemove = (e) => {
         //用鼠标的位置减去鼠标相对元素的位置,得到元素的位置
         let left = e.clientX - disX;
         let top = e.clientY - disY;
         //移动当前元素
         dragBox.style.left = left + "px";
         dragBox.style.top = top + "px";
         console.log(left, top, "111111111");
       };
       document.onmouseup = (e) => {
         //鼠标弹起来的时候不再移动
         document.onmousemove = null;
         //预防鼠标弹起来后还会循环(即预防鼠标放上去的时候还会移动)
         document.onmouseup = null;
       };
     };
   },
 },
};
</script>
<style lang="less">
#test {
 /deep/.el-dialog__body {
   padding: 10px 20px !important;
 }
 .content {
   width: 800px;
   height: 500px;
   background: red;
   margin: 0 auto;
   overflow: hidden;
   position: relative;

   .drag_box {
     width: 150px;
     height: 90px;
     border: 1px solid #666;
     background-color: #ccc;
     /* 使用定位,脱离文档流 */
     position: relative;
     top: 100px;
     left: 100px;
     /* 鼠标移入变成拖拽手势 */
     cursor: move;
     z-index: 3000;
   }
   .b_border {
     border: 1px solid red !important;
   }
   .biaozhu {
     z-index: 9999999;
   }
   .r_b {
     position: absolute;
     right: 0;
     bottom: 0;
     width: 20px;
     height: 20px;
     background: red;
   }
   .r_b:hover {
     cursor: se-resize;
   }
 }
}
</style>>

转载请注明出处

GitHub 加速计划 / vu / vue
207.54 K
33.66 K
下载
vuejs/vue: 是一个用于构建用户界面的 JavaScript 框架,具有简洁的语法和丰富的组件库,可以用于开发单页面应用程序和多页面应用程序。
最近提交(Master分支:2 个月前 )
73486cb5 * chore: fix link broken Signed-off-by: snoppy <michaleli@foxmail.com> * Update packages/template-compiler/README.md [skip ci] --------- Signed-off-by: snoppy <michaleli@foxmail.com> Co-authored-by: Eduardo San Martin Morote <posva@users.noreply.github.com> 4 个月前
e428d891 Updated Browser Compatibility reference. The previous currently returns HTTP 404. 5 个月前
Logo

旨在为数千万中国开发者提供一个无缝且高效的云端环境,以支持学习、使用和贡献开源项目。

更多推荐