一、游戏开发的技术演进
在聊 Canvas 之前,先看看网页游戏是怎么一路发展过来的:
| 阶段 | 代表 | 技术特点 |
|---|---|---|
| 页游时代 | 早期网页游戏 | 简单图文 + 表单交互 |
| Flash 时代 | 4399 小游戏 | Flash 插件,已淘汰 |
| HTML5 时代 | 现代 2D/3D 游戏 | Canvas + WebGL,浏览器原生支持 |
Flash 已经退出历史舞台,HTML5 Canvas 成了网页游戏与可视化的事实标准。AI 时代的爆发(three.js 3D 场景、物理大模型可视化)更是把 Canvas 推到了前台。
二、Canvas 是什么?
一句话:HTML5 提供的一块"画布",搭配 JS 绘图 API,想怎么画就怎么画。
与传统 HTML 的区别
- 普通 HTML 标签(
div/p/img):浏览器帮你排版,像"摆积木" - Canvas:给你一张白纸 + 一支笔,所有像素由你控制
类似 Photoshop 画布 vs Word 文档的关系。
兼容性
老旧浏览器(IE8 及以下)不支持,但现代浏览器全部原生支持,无需任何插件。
三、Canvas 三步上手
第 1 步:放一块画布
html
<canvas id="myCanvas" width="600" height="400" style="border:1px solid #333;">
<!-- 旧浏览器会显示这段降级文字 -->
你的浏览器不支持 canvas
</canvas>
⚠️
width/height是画布的实际像素尺寸,必须写在标签属性里,不要用 CSS 设置(CSS 设置会拉伸画布导致模糊)。
第 2 步:拿画笔(上下文)
js
const canvas = document.querySelector('#myCanvas');
const ctx = canvas.getContext('2d'); // 2D 绘图上下文
// const gl = canvas.getContext('webgl'); // 3D 绘图上下文
上下文(Context)是 Canvas 的核心概念:
'2d':平面绘图,做 2D 游戏、图表'webgl':3D 绘图,激发 GPU 显存能力,配合 three.js 做 3D 场景
选哪种 context,决定了你能用哪套 API。
第 3 步:用 API 画图
js
ctx.fillStyle = '#4299e1'; // 设置填充颜色
ctx.fillRect(20, 20, 100, 80); // 画填充矩形:x, y, 宽, 高
ctx.strokeStyle = '#f56565'; // 设置边框颜色
ctx.lineWidth = 4; // 线宽
ctx.strokeRect(150, 20, 100, 80); // 画边框矩形
ctx.clearRect(50, 50, 40, 30); // 擦除矩形区域
四、绘图 API 速查
| API | 作用 | 参数 |
|---|---|---|
fillRect(x, y, w, h) |
填充矩形 | 左上角坐标 + 宽高 |
strokeRect(x, y, w, h) |
边框矩形 | 同上 |
clearRect(x, y, w, h) |
擦除区域 | 同上 |
fillStyle |
填充颜色 | 颜色值 |
strokeStyle |
边框颜色 | 颜色值 |
lineWidth |
线宽 | 数字 |
除了矩形,还能画:
- 圆 :
arc(x, y, r, 起始角, 结束角) - 线 :
moveTo()+lineTo()+stroke() - 图片 :
drawImage(img, x, y, w, h) - 文字 :
fillText()/strokeText()
五、动画原理:帧动画
核心思想:每秒把画面重画很多次,每次位置稍微变一点,人就看到连续动画了。
浏览器显卡刷新率一般是 60fps(1 秒 60 帧),所以每帧大约 16ms 画一次。
三步循环
擦掉上一帧 → 计算新位置 → 画上新内容 → 重复
(一个矩形从左飞到右):
js
let x = 20;
const y = 20;
const width = 100;
const height = 80;
const speed = 3;
function animate() {
// 1. 擦掉整个画布
ctx.clearRect(0, 0, canvas.width, canvas.height);
// 2. 画新位置的矩形
ctx.fillStyle = '#4299e1';
ctx.fillRect(x, y, width, height);
// 3. 更新位置
x += speed;
// 飞出右边就从左边重新进来
if (x > canvas.width) {
x = -width;
}
// 4. 请求下一帧
requestAnimationFrame(animate);
}
animate(); // 启动循环
关键点:不擦除的话,每一帧的矩形会叠在一起,变成一条"拖尾",而不是移动的方块。
六、requestAnimationFrame 详解
为什么不用 setInterval?
| 方式 | 问题 |
|---|---|
setInterval(fn, 16) |
定时器是死的,跟屏幕刷新不同步,导致画面撕裂、卡顿、掉帧 |
requestAnimationFrame(fn) |
浏览器智能调度,自动匹配屏幕刷新率(60Hz/120Hz 都行) |
额外优势
- 自动匹配刷新率:60Hz 屏幕跑 60 次,120Hz 跑 120 次,体验更协调
- 后台自动暂停:页面切到后台时停止渲染,省电省性能
- 递归调用:参数是一个绘制函数,函数内部再次调用自己
使用范式
js
function draw() {
// 擦 → 算 → 画
ctx.clearRect(...);
// 更新状态...
// 绘制...
requestAnimationFrame(draw); // 递归
}
draw();
帧动画不停的画,就有了动画;加上交互,就有了游戏。
七、飞机游戏开发流程
整个流程是:
1. 工程初始化
bash
npm create vite@latest airplane -- --template vanilla
cd airplane
npm install
git init
- Vite:现代前端构建工具,热更新快
- Git:版本管理
.env:存放 API key 等环境变量
2. 与 Claude Code 头脑风暴
这一步是 AI 时代的开发新姿势:
- 产品功能列表:让 AI 帮你列出游戏可能的功能
- MVP(最小可行性方案):选其中几个核心功能做第一阶段
- 技术路线:用什么库?架构怎么设计?
- 技术方案:最终落地的实现细节
3. LLM 生成代码
把方案确定后,让 LLM 生成具体代码,再人工调整。
💡 这套流程的核心思想:AI 不只是写代码工具,更是产品经理 + 架构师。
八、数据可视化:ECharts
Canvas 除了做游戏,另一个超级应用是数据可视化。ECharts 就是底层基于 Canvas 的图表库。
js
import * as echarts from 'echarts'
const chartDom = document.getElementById('chart')
const chart = echarts.init(chartDom) // 初始化图表实例
const option = {
title: { text: '运动鞋月度销售额', left: 'center' },
tooltip: { trigger: 'axis' }, // 鼠标悬浮提示
xAxis: { type: 'category', data: months }, // X 轴
yAxis: { type: 'value' }, // Y 轴
series: [{
name: '销售额',
type: 'bar', // 柱状图
data: salesValues,
itemStyle: { borderRadius: [6, 6, 0, 0] }
}]
}
chart.setOption(option) // 应用配置
window.addEventListener('resize', () => chart.resize()) // 响应式
ECharts 的优势:
- 不用手写 Canvas 绘图 API,配置式开发
- 内置几十种图表:柱状图、折线图、饼图、地图、3D 图
- 底层自动用 Canvas/WebGL 渲染,性能好
九、知识图谱总结
arduino
HTML5 Canvas
├── 基础
│ ├── <canvas> 标签(width/height 像素尺寸)
│ ├── getContext('2d' | 'webgl') 上下文
│ └── 绘图 API(fillRect / strokeRect / clearRect / arc / drawImage...)
│
├── 动画
│ ├── 帧动画三步:擦 → 算 → 画
│ ├── requestAnimationFrame(不用 setInterval)
│ └── 60fps 屏幕刷新率
│
├── 应用场景
│ ├── 2D 游戏(飞机大战)
│ ├── 3D 场景(three.js + WebGL)
│ ├── 数据可视化(ECharts)
│ └── 图片处理 / 签名板 / 特效
│
└── 开发流程(AI 时代)
├── Vite 工程化
├── 与 CC 头脑风暴 → MVP
└── LLM 生成代码