paper.js 中有没有办法只缩放 canvas 的一部分而不是整个?

is there a way in paper.js to zoom just a part of the canvas instead of the whole?

我正在构建一个包含两个部分的 Webtool canvas:

我对 canvas 中的所有函数使用 paper.js。我为不同的部分制作了两层,并通过跟踪鼠标位置在它们之间切换。

现在我想对第一部分进行缩放。我看到 paper.js 中的视图对象带有缩放功能。经过一些谷歌搜索后,我找到了这个 https://gist.github.com/ryascl/4c1fd9e2d5d0030ba429 解决方案,用于简单的缩放。

现在是我的问题;如果我使用此缩放,整个 canvas 会被缩放 in/out。这不是我需要的。我只需要在第一部分进行缩放。有没有办法只缩放某个区域,或者某个图层?

我看到这个问题有 2 种可能的解决方案:

解决方案 1

您可以使用 item.scale() instead of using view.zoom 直接缩放您的项目。
您可能会遇到的问题是您的图层肯定会重叠,因此您可以将此方法与 group.clipped 结合使用以掩盖您的图层溢出。
这是一个 sketch 演示此解决方案。

// Draw a line materializing layers separation.
new Path.Line({
    from: view.bounds.topCenter,
    to: view.bounds.bottomCenter,
    strokeColor: 'black'
});

// Draw a rectangle that will be used to crop the layer.
var cropRectangle = new Path.Rectangle({
    from: view.bounds.toLeft,
    to: view.bounds.bottomCenter
});

// Draw a circle in the left part of the screen.
var circle = new Path.Circle({
    center: [view.bounds.leftCenter.x + view.center.x / 2, view.center.y],
    radius: 50,
    fillColor: 'orange'
});

// Create a group that will be used to pan/zoom left part.
var group = new Group([circle]);

// Create left part layer and crop it with the rectangle so that overflow is
// hidden.
var layer = new Layer([cropRectangle, group]);
layer.clipped = true;

// Directly manipulate the group when you want to pan/zoom.
group.translate(view.bounds.width / 4, 0);
group.scale(1.5);

// You can use the same architecture for the right part...

解决方案 2

就我个人而言,我会选择另一种解决方案,包括管理 2 个分开的 canvas,在每个 Paper.js 上初始化以生成 2 个不同的 PaperScope 实例。
然后,您将能够控制每个 canvas 的 view.zoom
这是一个 fiddle 演示此解决方案。

// Initialize paper scopes.
var scope1 = new paper.PaperScope();
scope1.setup(document.getElementById('canvas1'));

var scope2 = new paper.PaperScope();
scope2.setup(document.getElementById('canvas2'));

// Draw a circle on left canvas.
new paper.Path.Circle({
    center: scope1.view.center,
    radius: 50,
    fillColor: 'orange',
    parent: scope1.project.activeLayer
});

// Draw a circle on right canvas.
new paper.Path.Circle({
    center: scope2.view.center,
    radius: 50,
    fillColor: 'blue',
    parent: scope2.project.activeLayer
});

// Zoom in left canvas.
scope1.view.zoom = 2;

// Zoom out right canvas.
scope2.view.zoom = 0.5;