ZetCode

JavaScript Canvas 变换教程

最后修改于 2025 年 4 月 3 日

在本文中,我们将探讨 JavaScript 中的 Canvas 变换方法。这些方法允许您为高级图形操纵绘图上下文。变换对于创建复杂的视觉效果和动画至关重要。

基本定义

Canvas 变换会修改绘图上下文的坐标系统。它们允许对绘制的元素进行平移、旋转、缩放和倾斜。可以使用上下文方法保存和恢复变换状态。

主要的变换方法是 `translate`、`rotate`、`scale` 和 `transform`。这些方法会影响所有后续的绘图操作,直到上下文被重置或恢复。

基本平移

此示例演示了如何使用 translate 方法移动原点。

index.html
<!DOCTYPE html>
<html>
<head>
    <title>Basic Translation</title>
</head>
<body>

<canvas id="myCanvas" width="300" height="200"></canvas>

<script>
    const canvas = document.getElementById('myCanvas');
    const ctx = canvas.getContext('2d');
    
    // Draw at original position
    ctx.fillStyle = 'red';
    ctx.fillRect(10, 10, 50, 50);
    
    // Translate and draw again
    ctx.translate(100, 50);
    ctx.fillStyle = 'blue';
    ctx.fillRect(10, 10, 50, 50);
</script>

</body>
</html>

此示例显示了在不同位置绘制的两个正方形。第一个红色正方形绘制在原始原点 (0,0)。调用 `translate` 后,原点向右移动 100 像素,向下移动 50 像素。

蓝色正方形以相同的坐标 (10,10) 绘制,但由于平移,显示在不同的位置。这表明平移如何影响所有后续的绘图操作。

围绕某一点旋转

此示例展示了如何围绕矩形的中心点旋转矩形。

index.html
<!DOCTYPE html>
<html>
<head>
    <title>Rotation Around Point</title>
</head>
<body>

<canvas id="myCanvas" width="300" height="200"></canvas>

<script>
    const canvas = document.getElementById('myCanvas');
    const ctx = canvas.getContext('2d');
    
    const rectWidth = 100;
    const rectHeight = 60;
    const centerX = 150;
    const centerY = 100;
    
    ctx.save();
    ctx.translate(centerX, centerY);
    ctx.rotate(Math.PI / 4); // 45 degrees
    ctx.fillStyle = 'green';
    ctx.fillRect(-rectWidth/2, -rectHeight/2, rectWidth, rectHeight);
    ctx.restore();
</script>

</body>
</html>

要围绕某一点旋转,我们首先平移到该点,然后旋转,然后绘制形状,并根据其尺寸的一半进行偏移。这会将形状的中心置于旋转点。

`save` 和 `restore` 方法会保留原始的变换状态。矩形在其中心 (150,100) 处旋转 45 度(π/4 弧度)。

缩放形状

此示例演示了如何使用 scale 方法缩放形状。

index.html
<!DOCTYPE html>
<html>
<head>
    <title>Scaling Shapes</title>
</head>
<body>

<canvas id="myCanvas" width="300" height="200"></canvas>

<script>
    const canvas = document.getElementById('myCanvas');
    const ctx = canvas.getContext('2d');
    
    // Original shape
    ctx.fillStyle = 'rgba(255, 0, 0, 0.5)';
    ctx.fillRect(50, 50, 50, 50);
    
    // Scaled shape
    ctx.scale(2, 0.5);
    ctx.fillStyle = 'rgba(0, 0, 255, 0.5)';
    ctx.fillRect(50, 50, 50, 50);
</script>

</body>
</html>

这里我们绘制了两个重叠的矩形。第一个正常绘制。第二个在绘制前水平缩放 2 倍,垂直缩放 0.5 倍。

请注意,缩放会影响所有内容,包括描边宽度和文本。透明颜色显示了缩放后的矩形如何变得更宽更短,同时相对于变换后的原点保持其位置。

组合变换

此示例展示了如何组合多个变换以实现复杂的效果。

index.html
<!DOCTYPE html>
<html>
<head>
    <title>Combined Transforms</title>
</head>
<body>

<canvas id="myCanvas" width="400" height="300"></canvas>

<script>
    const canvas = document.getElementById('myCanvas');
    const ctx = canvas.getContext('2d');
    
    function drawHouse() {
        ctx.fillStyle = 'brown';
        ctx.fillRect(-20, -20, 40, 40);
        ctx.beginPath();
        ctx.moveTo(-30, -20);
        ctx.lineTo(0, -40);
        ctx.lineTo(30, -20);
        ctx.fillStyle = 'red';
        ctx.fill();
    }
    
    ctx.save();
    ctx.translate(100, 100);
    drawHouse();
    
    ctx.translate(150, 0);
    ctx.scale(1.5, 1.5);
    drawHouse();
    
    ctx.translate(150, 0);
    ctx.rotate(Math.PI / 4);
    drawHouse();
    ctx.restore();
</script>

</body>
</html>

此示例使用相同的绘图函数绘制三个房屋,但应用了不同的变换。第一个在 (100,100) 正常绘制。

第二个向右平移并放大。第三个向右平移得更远,并旋转 45 度。这表明如何组合变换以从单个绘图函数创建各种外观。

高级矩阵变换

此示例演示了如何使用 transform 方法进行自定义矩阵运算。

index.html
<!DOCTYPE html>
<html>
<head>
    <title>Matrix Transform</title>
</head>
<body>

<canvas id="myCanvas" width="400" height="300"></canvas>

<script>
    const canvas = document.getElementById('myCanvas');
    const ctx = canvas.getContext('2d');
    
    // Original square
    ctx.fillStyle = 'rgba(255, 0, 0, 0.5)';
    ctx.fillRect(50, 50, 100, 100);
    
    // Skewed square
    ctx.transform(1, 0.5, -0.5, 1, 150, 50);
    ctx.fillStyle = 'rgba(0, 0, 255, 0.5)';
    ctx.fillRect(0, 0, 100, 100);
</script>

</body>
</html>

`transform` 方法应用自定义变换矩阵。参数包括:水平缩放、水平倾斜、垂直倾斜、垂直缩放、水平移动和垂直移动。

此示例创建了一个倾斜的平行四边形效果。蓝色正方形通过缩放和倾斜组件进行变换,演示了如何通过直接的矩阵操作实现复杂的变换。

来源

MDN Canvas 变换文档

在本文中,我们探索了用于在 HTML canvas 上操作形状的各种变换技术。掌握这些方法对于在 Web 应用程序中创建高级图形和动画至关重要。

作者

我叫 Jan Bodnar,我是一名热情的程序员,拥有丰富的编程经验。自 2007 年以来,我一直在撰写编程文章。迄今为止,我已撰写了 1,400 多篇文章和 8 本电子书。我在教授编程方面拥有十多年的经验。

列出 所有 JS Canvas 教程