uniapp中同时触发@markertap和@tap事件如何解决?
在uniapp中,当我点击地图上的marker时,同时触发了@markertap和@tap事件,导致重复执行逻辑。如何让这两个事件互不干扰,或者只触发其中一个事件?目前尝试用stopPropagation()无效,有没有其他解决方案?
2 回复
在uniapp中,同时触发@markertap和@tap事件时,可以通过阻止事件冒泡来解决。在@markertap事件处理函数中使用e.stopPropagation(),或者在@tap事件中判断事件源,避免重复处理。
在uniapp中,当点击地图上的标记(marker)时,会同时触发@markertap和@tap事件。这是因为@tap是地图的点击事件,而@markertap是标记的点击事件,两者属于不同层级。
解决方案
方案1:使用事件对象判断
在@tap事件中通过事件对象判断是否点击了标记:
<map
@markertap="onMarkerTap"
@tap="onMapTap"
style="width: 100%; height: 300px;"
:markers="markers">
</map>
methods: {
onMarkerTap(e) {
console.log('点击了标记:', e.markerId)
// 处理标记点击逻辑
},
onMapTap(e) {
// 如果没有markerId,说明点击的是地图空白区域
if (!e.markerId) {
console.log('点击了地图空白区域')
// 处理地图点击逻辑
}
}
}
方案2:使用定时器延迟处理
通过setTimeout让@tap事件延迟执行,在@markertap中取消@tap的执行:
data() {
return {
tapTimer: null
}
},
methods: {
onMarkerTap(e) {
// 清除tap定时器
clearTimeout(this.tapTimer)
console.log('点击了标记:', e.markerId)
// 处理标记点击逻辑
},
onMapTap(e) {
// 设置定时器,延迟执行
this.tapTimer = setTimeout(() => {
if (!e.markerId) {
console.log('点击了地图空白区域')
// 处理地图点击逻辑
}
}, 100)
}
}
方案3:使用标志变量
通过标志变量控制事件执行:
data() {
return {
isMarkerTapped: false
}
},
methods: {
onMarkerTap(e) {
this.isMarkerTapped = true
console.log('点击了标记:', e.markerId)
// 处理标记点击逻辑
// 重置标志
setTimeout(() => {
this.isMarkerTapped = false
}, 50)
},
onMapTap(e) {
if (!this.isMarkerTapped) {
console.log('点击了地图空白区域')
// 处理地图点击逻辑
}
}
}
推荐方案
方案1是最推荐的,因为它:
- 代码简洁明了
- 性能最佳
- 无需额外的状态管理
- 符合uniapp的事件机制
在实际开发中,根据具体需求选择合适的解决方案即可。

