https://article.itxueyuan.com/vOkjra https://blog.csdn.net/kongjiea/article/details/43016085
下面这个官网功能可以查看源码 http://hammerjs.github.io/
下面(用于通过tap代替click,click需延时300ms才会被触发) https://github.com/hammerjs/hammer-time
<template>
<div class="page">
<div style="background-color:yellow;position: relative;width: 500px;height: 300px;overflow: hidden;">
<div id="demoImg">
<img src="https://zhyframe.fzh.fun/attachment/images/1023/2022/09/02d9610f22ac4c15877a043a3d481d83.png" class="demo-img" />
<div style="background-color: red;width: 20px;height: 20px;font-size: 10px;" class="new_label" @click="click_label" data-id="A1">
A1
</div>
<div style="background-color: red;width: 20px;height: 20px;font-size: 10px;" class="new_label2" @click="click_label" data-id="B2">
B2
</div>
</div>
</div>
</div>
</template>
<script>
import Hammer from 'hammerjs'
// import { setTimeout } from 'timers'
export default {
data () {
return {
config: {},
id: null,
mc: null,
timer: false,
translateX: 0,
translateY: 0,
scale: 1,
firstTouch: true,
relateX: 0,
relateY: 0,
oldX: 0,
oldY: 0,
oldScale: 1
}
},
mounted () {
this.$nextTick(() => {
this.picInit()
})
},
methods: {
click_label(e){
let id = e.currentTarget.dataset.id;
alert("click id:" + id);
},
picInit () {
this.id = document.getElementById('demoImg')
this.mc = new Hammer(this.id)
this.relateX = 0;//(document.body.clientWidth - this.id.offsetWidth) / 2
this.relateY = 0;//(document.body.clientHeight - this.id.offsetHeight) / 2
this.mc.add(new Hammer.Pan({
direction: Hammer.DIRECTION_ALL,
threshold: 0,
pointers: 0
}))
this.mc.add(new Hammer.Pinch({
threshold: 0
})).recognizeWith(this.mc.get('pan'))
this.mc.on('hammer.input', this.isFinal)
this.mc.on('panstart panmove', this.onPan)
this.mc.on('pinchstart pinchmove', this.onPinch)
this.setPosition()
},
isFinal (ev) {
if (ev.isFinal) {
this.oldX = this.translateX
this.oldY = this.translateY
this.oldScale = this.scale
}
},
// 初始化图片位置及缩放
setPosition () {
this.selfPosition({
translateX: this.relateX,
translateY: this.relateY,
scale: this.scale
})
},
// 单点触发 - 拖拉
onPan (ev) {
// console.log(this.firstTouch)
if (this.firstTouch) {
this.oldX = this.relateX
this.oldY = this.relateY
}
// console.log(this.oldX)
// console.log(this.oldY)
this.translateX = this.oldX + ev.deltaX
this.translateY = this.oldY + ev.deltaY
const position = {
translateX: this.translateX,
translateY: this.translateY,
scale: this.scale
}
this.selfPosition(position)
this.firstTouch = false
},
// 多点触发 - 缩放
onPinch (ev) {
this.scale = this.oldScale * ev.scale
this.selfPosition({
translateX: this.translateX,
translateY: this.translateY,
scale: this.scale
})
// this.selfPosition(this.position)
},
selfPosition (pos) {
return this.picAnimate()(() => this.tempPos(pos))
},
tempPos (pos) {
let style = [
`translate3d(${pos.translateX}px, ${pos.translateY}px, 0)`,
`scale(${pos.scale}, ${pos.scale})`
// `scale(${pos.scale > 1.2 ? 1.2 : pos.scale}, ${pos.scale > 1.2 ? 1.2 : pos.scale})`
]
style = style.join(' ')
this.id.style.transform = style
},
picAnimate () {
return window[Hammer.prefixed(window, 'requestAnimationFrame')] || function (callback) {
setTimeout(callback, 1000 / 60)
}
}
}
}
</script>
<style >
.page {
width: 600px;
height: 100vh;
background-color: red;
}
.demo-img {
position: absolute;
left: 0;
top: 0;
width: 260px;
height: 260px;
}
.new_label{
position: absolute;
top: 100px;
left: 100px;
}
.new_label2{
position: absolute;
top: 200px;
left: 200px;
}
</style>