uni-app Vue3/Vite TS版 canvas触摸事件报错
uni-app Vue3/Vite TS版 canvas触摸事件报错
示例代码:
<canvas @touchmove="onTouchmove"></canvas>
<script lang="ts" setup>
function onTouchmove(e){
console.log(e)
}
</script>
操作步骤:
把上方示例放置vue页面编译至h5端触摸移动报错。
预期结果:
正常绘制签名
实际结果:
报错
bug描述:
canvas只要绑定触摸事件,开始点击、滑动就报错 Uncaught TypeError: $event.currentTarget.getBoundingClientRect is not a function at null:7312:45 at null:9693:60 at callWithErrorHandling (null:1336:22) at callWithAsyncErrorHandling (null:1345:21) at HTMLElement.invoker (null:9672:17)
信息 | 值 |
---|---|
产品分类 | uniapp/H5 |
PC开发环境 | Windows |
PC开发环境版本 | Windows11 |
浏览器平台 | Chrome |
浏览器版本 | 119.0.6045.160 |
项目创建方式 | CLI |
CLI版本号 | 3.0.0-alpha-3061020221121002 |
升级依赖报错 npm ERR! code ERESOLVE npm ERR! ERESOLVE could not resolve npm ERR! npm ERR! While resolving: uni-preset-vue@0.0.0 npm ERR! Found: @dcloudio/vite-plugin-uni@3.0.0-alpha-3061020221121002 npm ERR! node_modules/@dcloudio/vite-plugin-uni npm ERR! dev @dcloudio/vite-plugin-uni@“3.0.0-alpha-3090820231120001” from the root project npm ERR! npm ERR! Could not resolve dependency: npm ERR! dev @dcloudio/vite-plugin-uni@“3.0.0-alpha-3090820231120001” from the root project npm ERR! npm ERR! Conflicting peer dependency: vite@4.0.3 npm ERR! node_modules/vite npm ERR! peer vite@"^4.0.0" from @dcloudio/vite-plugin-uni@3.0.0-alpha-3090820231120001 npm ERR! node_modules/@dcloudio/vite-plugin-uni npm ERR! dev @dcloudio/vite-plugin-uni@“3.0.0-alpha-3090820231120001” from the root project
大佬,请问你用bug代码是怎么升级依赖的呢?我选择npm报错依赖冲突,选择pnpm后启动项目报错
回复 YUANRJ: node版本18.19.0 使用yarn和pnpm一样,项目启动报错
测试未复现,请提供下测试工程
代码zip包 已重新提交附件
在使用 uni-app
的 Vue3/Vite TypeScript 版本时,如果你在 canvas
上绑定触摸事件时遇到报错,可能是由于以下几个原因导致的。以下是一些常见的解决方案和排查步骤:
1. 确保 canvas
元素正确绑定
首先,确保你的 canvas
元素在模板中正确绑定,并且 ref
属性被正确使用。
<template>
<canvas ref="myCanvas" [@touchstart](/user/touchstart)="handleTouchStart" [@touchmove](/user/touchmove)="handleTouchMove" [@touchend](/user/touchend)="handleTouchEnd"></canvas>
</template>
<script setup lang="ts">
import { ref, onMounted } from 'vue';
const myCanvas = ref<HTMLCanvasElement | null>(null);
onMounted(() => {
const canvas = myCanvas.value;
if (canvas) {
const ctx = canvas.getContext('2d');
// 初始化 canvas 绘制
}
});
function handleTouchStart(event: TouchEvent) {
console.log('Touch start:', event);
}
function handleTouchMove(event: TouchEvent) {
console.log('Touch move:', event);
}
function handleTouchEnd(event: TouchEvent) {
console.log('Touch end:', event);
}
</script>
2. 确保 canvas
元素已正确挂载
在 onMounted
钩子中确保 canvas
元素已经挂载到 DOM 中,然后再进行事件绑定或绘制操作。
3. 检查事件类型
确保你绑定的事件类型是正确的。canvas
支持的标准触摸事件包括 touchstart
、touchmove
和 touchend
。
4. 检查 TypeScript 类型定义
如果你在 TypeScript 中遇到类型错误,确保你正确导入了 TouchEvent
类型。
import { TouchEvent } from 'react'; // 或者 'vue' 中的 TouchEvent
5. 检查 canvas
的样式和尺寸
确保 canvas
元素的样式和尺寸设置正确,否则可能会导致触摸事件无法正确触发。
<template>
<canvas ref="myCanvas" width="300" height="300" style="border: 1px solid black;"></canvas>
</template>
6. 检查 uni-app
的兼容性
uni-app
在某些平台上可能对 canvas
的支持有所不同,尤其是在小程序或 H5 环境中。确保你使用的 uni-app
版本支持 canvas
的触摸事件。
7. 调试和日志
在事件处理函数中添加 console.log
来调试,确保事件被正确触发。
function handleTouchStart(event: TouchEvent) {
console.log('Touch start:', event.touches);
}
8. 使用 uni-app
的 canvas
API
如果你在 uni-app
中使用 canvas
,可能需要使用 uni-app
提供的 canvas
API 而不是原生的 HTMLCanvasElement
。例如:
const canvas = uni.createCanvasContext('myCanvas');
9. 检查 vite
配置
如果你使用的是 vite
,确保 vite
配置中没有对 canvas
进行特殊处理或限制。
10. 更新依赖
确保你的 uni-app
、vite
和 TypeScript
依赖都是最新版本,以避免已知的 bug 或兼容性问题。
示例代码
以下是一个完整的示例代码,展示了如何在 uni-app
的 Vue3/Vite TypeScript 版本中使用 canvas
并绑定触摸事件:
<template>
<canvas ref="myCanvas" width="300" height="300" style="border: 1px solid black;" [@touchstart](/user/touchstart)="handleTouchStart" [@touchmove](/user/touchmove)="handleTouchMove" [@touchend](/user/touchend)="handleTouchEnd"></canvas>
</template>
<script setup lang="ts">
import { ref, onMounted } from 'vue';
const myCanvas = ref<HTMLCanvasElement | null>(null);
onMounted(() => {
const canvas = myCanvas.value;
if (canvas) {
const ctx = canvas.getContext('2d');
if (ctx) {
ctx.fillStyle = 'green';
ctx.fillRect(10, 10, 100, 100);
}
}
});
function handleTouchStart(event: TouchEvent) {
console.log('Touch start:', event.touches);
}
function handleTouchMove(event: TouchEvent) {
console.log('Touch move:', event.touches);
}
function handleTouchEnd(event: TouchEvent) {
console.log('Touch end:', event.touches);
}
</script>