uniapp使用canvas+手势缩放

功能介绍,工程类app,需要在手机端查看图纸,canvas绘制点,线。整理随意放大缩小。

  1. canvas绘制方法

//画布image
            drawImage(ctx, path, x, y, dWidth, dHeight) {
                ctx.drawImage(path, x, y, dWidth, dHeight)
            },
            //圆角矩形
            roundNode(ctx, x, y, width, height, radius, color) {
                //圆角矩形部分
                ctx.beginPath()
                if (width < 2 * radius) radius = width / 2;
                if (height < 2 * radius) radius = height / 2;
                ctx.moveTo(x + radius, y);
                ctx.arcTo(x + width, y, x + width, y + height, radius);
                ctx.arcTo(x + width, y + height, x, y + height, radius);
                ctx.arcTo(x, y + height, x, y, radius);
                ctx.arcTo(x, y, x + width, y, radius);
                ctx.setFillStyle(color)
                ctx.fill()
            },
            //绘制三角形  type:箭头朝向:bottom、right、left
            drawTriangle(ctx, x, y, color, type) {
                ctx.beginPath()
                let height = 10 //计算等边三角形的高
                ctx.moveTo(x, y); //x y开始
 
                switch (type) {
                    case 'bottom':
                        ctx.lineTo(x - height / 2, y)
                        ctx.lineTo(x, y + height)
                        ctx.moveTo(x, y)
                        ctx.lineTo(x + height / 2, y)
                        ctx.lineTo(x, y + height)
                        break;
                    case 'left':
                        ctx.lineTo(x, y - height / 2)
                        ctx.lineTo(x - height, y)
                        ctx.moveTo(x, y)
                        ctx.lineTo(x, y + height / 2)
                        ctx.lineTo(x - height, y)
                        break;
                    case 'right':
                        ctx.lineTo(x, y - height / 2)
                        ctx.lineTo(x + height, y)
                        ctx.moveTo(x, y)
                        ctx.lineTo(x, y + height / 2)
                        ctx.lineTo(x + height, y)
                        break;
                    default:
                        break;
                }
 
 
                ctx.setFillStyle(color)
                ctx.fill();
            },
            drawText(ctx, text, x, y, color, size) {
                //文字部分
                ctx.beginPath()
                ctx.setTextAlign('center')
                ctx.setFillStyle(color)
                ctx.setFontSize(size)
                const metrics = ctx.measureText(text)
                //文字统一偏移
                ctx.fillText(text, x + metrics.width / 2, y + 17)
            },
            // 绘制带箭头线 type:箭头朝向:bottom、right、left
            drawLine(ctx, fromX, fromY, toX, toY, color, type, isArrow = true, isDash = false) {
                ctx.beginPath()
                if (isDash) {
                    ctx.setLineDash([10]);
                } else {
                    ctx.setLineDash([]);
                }
                ctx.moveTo(fromX, fromY)
                ctx.lineTo(toX, toY)
                ctx.setLineWidth(1)
                ctx.setStrokeStyle(color)
                ctx.stroke()
                
                //是否绘制箭头
                if (isArrow) {
                    this.drawTriangle(ctx, toX, toY, color, type)
                }
            },
  1. 手势缩放 拖拽功能实现

<movable-area :scale-area="true" :style="{'width':windowWidth+'px','height':windowHeight+'px','backgroundColor':'#ddd','overflow':'hidden'}">
            <movable-view direction="all"  :inertia="true" :scale-min="0.001" :scale-max="4"              :scale="true" :style="{'width':widths+'px','height':heights+'px'}"
                 @scale="scaleChange">
                <canvas id="myCanvas" canvas-id="myCanvas" :style="{'width':widths+'px','height':heights+'px'}"
                    @touchstart="touchstart" />
            </movable-view>
</movable-area>

movable-view + movable-area 实现该功能

windowWidth、windowHeight 是计算屏幕占比 如果需要多设备可以参考

widths、heights 动态movable-view宽高 (我这里图纸太大需要一定缩放,并且movable-view内容最好跟movable-view宽高相同)

//开始绘制
that.context = uni.createCanvasContext('myCanvas')
//画背景
            that.drawImage(that.context,that.infos.pic, 0, 0,that.widths, that.heights)
            //画节点
            //开始节点
           this.roundNode(this.context, 553, 38, 100, 36, 26, '#1EC1C3')
            this.node.push({
                x:553,
                y:38,
                w:100,
                h:36,
                targe:0
            })
                        that.context.draw()
//s缩放比例
scaleChange(e) {
    this.scale = e.detail.scale
}
//点击事件 判断缩放比例 
            touchstart(e) {
                let x = e.touches[0].x
                let y = e.touches[0].y
                this.node.forEach(item => {
                    if (x > item.x * this.scale && x < (item.x + item.w) * this.scale
                        && y > item.y * this.scale && y < (item.y + item.h) * this.scale) {
                        //在范围内,根据标记定义节点类型
                        this.lookDetial(item)
                    }
                }) 
            },

目前就可以 最后需要注意 uniapp 对画布图片的大小,宽高,有很大的限制,如果页面没有显示,或者报错 80%就是这个原因

plus.io.resolveLocalFileSystemURL 安卓可以使用这个来压缩

  • 4
    点赞
  • 17
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
uniapp使用canvas实现手势缩放可以通过以下步骤实现: 1. 在canvas的绘制方法中获取手势事件的信息,包括手势类型、起始点、移动距离等信息。 2. 在手势的处理方法中计算缩放比例,并根据缩放比例对canvas进行缩放。 下面是一个简单的示例代码: ```html <template> <canvas @touchstart="touchStart" @touchmove="touchMove" @touchend="touchEnd" style="width: 100%; height: 100%;" ></canvas> </template> <script> export default { methods: { touchStart(event) { if (event.touches.length === 2) { // 计算两个手指之间的距离 this.distance = Math.sqrt( (event.touches[0].clientX - event.touches[1].clientX) ** 2 + (event.touches[0].clientY - event.touches[1].clientY) ** 2 ); } }, touchMove(event) { if (event.touches.length === 2) { // 计算当前两个手指之间的距离 const currentDistance = Math.sqrt( (event.touches[0].clientX - event.touches[1].clientX) ** 2 + (event.touches[0].clientY - event.touches[1].clientY) ** 2 ); // 计算缩放比例 const scale = currentDistance / this.distance; // 更新缩放比例 this.scale *= scale; // 更新起始点 this.startX = (this.startX + event.touches[0].clientX) / 2; this.startY = (this.startY + event.touches[0].clientY) / 2; // 重新绘制canvas this.draw(); } }, touchEnd() { // 清空手势信息 this.distance = 0; }, draw() { // 获取canvas对象 const ctx = uni.createCanvasContext("myCanvas", this); // 缩放canvas ctx.scale(this.scale, this.scale); // 绘制图形 ctx.fillRect(this.startX, this.startY, 100, 100); // 显示canvas ctx.draw(); }, }, data() { return { startX: 0, // 起始点的x坐标 startY: 0, // 起始点的y坐标 scale: 1, // 缩放比例 distance: 0, // 两个手指之间的距离 }; }, mounted() { // 绘制canvas this.draw(); }, }; </script> ``` 在上面的示例代码中,我们使用uniapp提供的canvas API,通过scale方法实现缩放。在touchMove方法中,根据当前两个手指之间的距离计算缩放比例,并更新缩放比例和起始点的坐标。最后,在draw方法中调用scale方法对canvas进行缩放,然后绘制图形并显示canvas
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值