Canvas坐标系原点在左上角(0, 0),x向右、y向下递增,是W3C标准;需区分canvas.width/height(绘图分辨率)与CSS尺寸(显示大小),并通过translate、scale等变换适配数学坐标系或高清屏。

Canvas 绘图坐标系的原点在画布左上角(0, 0),x 向右递增,y 向下递增——这不是设计缺陷,而是 W3C 标准,与 CSS、Android Canvas、WebGL 保持一致。
原点位置与方向规则
默认坐标系中,(0, 0)就是 canvas 元素左上角的第一个像素点。这意味着:
-
fillRect(0, 0, 50, 50)会紧贴左上角绘制一个方块 -
strokeText("Hi", 10, 20)的文字基线落在 y=20 处,实际字体会向下延伸(可能被裁掉顶部) - 圆心设为
(x, y)时,y 值越大,圆越靠下——和数学直角坐标系相反
canvas.width/height 与 CSS 尺寸的区别
Canvas 有两个独立尺寸控制项,混淆会导致坐标漂移或图形模糊:
- canvas.width / canvas.height 属性:决定内部位图的像素数量(即 getImageData 操作的真实分辨率)
- CSS width / height 样式:只控制元素在页面上的显示大小(等比缩放渲染)
例如:<canvas width="600" height="400" style="width:300px; height:200px"></canvas>,绘图仍按 600×400 像素坐标计算,但被压缩显示。鼠标事件坐标需用 getBoundingClientRect() 校准后映射回真实绘图空间。
实现数学坐标系的常用变换
若需 y 向上为正、原点居中(如画函数图像),不能靠手动加减,应使用坐标系变换:
-
ctx.translate(canvas.width/2, canvas.height/2):把原点移到画布中心 -
ctx.scale(1, -1):翻转 y 轴方向(此时lineTo(0, 100)真正向上画) - 注意:变换后所有绘图命令都基于新坐标系,建议用
ctx.save()/ctx.restore()隔离作用域
高清屏下的像素对齐要点
在 retina 屏等高 DPI 设备上,逻辑像素 ≠ 物理像素。为避免模糊,需按 devicePixelRatio 调整:
- 获取设备像素比:
const dpr = window.devicePixelRatio || 1 - 设 canvas 属性:
canvas.width = Math.floor(400 * dpr),canvas.height = Math.floor(300 * dpr) - 再用 CSS 缩放到目标显示尺寸:
canvas.style.width = "400px",canvas.style.height = "300px" - 最后设置绘图上下文缩放:
ctx.scale(dpr, dpr),使 1 单位坐标对应 1 物理像素


















