将画布缩放到鼠标光标


77

我正在编写一个HTML5 <canvas>项目,该项目涉及使用滚轮放大和缩小图像。我想像Google Maps一样向光标方向缩放,但是我完全不知道如何计算运动。

我所拥有的:图像x和y(左上角);图像的宽度和高度;光标x和y相对于画布中心的位置。


15
您应该接受此答案或修改您的问题
ghayes

Answers:


234

简而言之,您希望translate()通过偏移量到达画布上下文,将scale()其放大或缩小,然后translate()通过鼠标偏移量的相反方向返回。请注意,您需要将光标位置从屏幕空间转换为转换后的画布上下文。

ctx.translate(pt.x,pt.y);
ctx.scale(factor,factor);
ctx.translate(-pt.x,-pt.y);

演示:http//phrogz.net/tmp/canvas_zoom_to_cursor.html

我已经在我的网站上提供了一个完整的工作示例,供您检查,支持拖动,单击以放大,按住Shift并单击以移出或上/下滚轮。

唯一(当前)的问题是,与Chrome或Firefox相比,Safari缩放速度过快


2
这个例子不错。谢谢!
Mikael Eliasson

4
哇,@ phrogz,您超越了一切!
snapfractalpop 2012年

1
嘿@Phrogz,太棒了!我只是想知道我们是否可以限制拖动,以便不能将图像拖动到边界之外。如果没有更多图像要拖动,则拖动应仅在此处停止,而不是无限期拖动。我对它进行了刺刺,但似乎数学不正确:-(
Christoph

2
@Christoph很简单。获得比例-您可以从以下比例获取比例:var scale = ctx.getTransform()。a; 然后采用图片的当前左上角位置:var curX = ctx.getTransform()。e; var curY = ctx.getTransform()。f; 估计位置变化:var deltaX = pt.x-dragStart.x; var deltaY = pt.y-dragStart.y; 然后有原始图像尺寸,以宽度为例(当scale = 1时):imageW,并且画布宽度为canvasW,则条件应为false以允许拖动:curX + deltaX + imageW * scale <canvasW和另外一个( curX + DELTAX> 0 || CURY +移动deltaY> 0)

1
用手势在手机上很难实现吗?例如,让两根手指只放大图像,而不放大整个网站?
托马斯·


10

我最近需要存档与Phrogz相同的结果,但是context.scale()我没有使用,而是根据比率计算了每个对象的大小。

这就是我想出的。其背后的逻辑非常简单。在缩放之前,我以百分比计算到边缘的点距离,然后将视口调整到正确的位置。

我花了相当长的时间才想出它,希望它可以节省一些人的时间。


6

我以@Phrogz的答案为基础,并制作了一个小型库,该库可通过拖动,缩放和旋转来启用画布。这是例子。

var canvas = document.getElementById('canvas')
//assuming that @param draw is a function where you do your main drawing.
var control = new CanvasManipulation(canvas, draw)
control.init()
control.layout()
//now you can drag, zoom and rotate in canvas

您可以在项目页面上找到更多详细的示例和文档

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.