Seth Larson 做了一个很小的纸笔实验:在一张带 10×10 网格和 2×10 辅助网格的便签纸上,手绘出一个能被手机识别的二维码。
这个二维码不是 Micro QR,而是普通 QR Code 的 Version 1。它的尺寸是 21×21 个模块,也就是最小规格里的常见起点。
我更在意的不是“人手也能画二维码”这件事,而是它暴露了二维码真正依赖什么:不是黑白块像不像,而是每个模块在不在该在的位置上。
21×21 模块先卡住了纸和内容
Version 1 的 21×21 模块,听起来很小。落到便签纸上,就不轻松。
Larson 手里的网格只有 10×10。要画 21×21,他必须把格子拆半,还要利用边距。纸张、留白、模块大小,马上从“美观问题”变成“能不能识别”的问题。
内容也有边界。
他最初发现,小写完整 URL https://sethmlarson.dev 放不进这个 Version 1 码,于是改用 sethmlarson.dev。后来有读者指出,如果把 URL 改成全大写,QR Code 可以走 alphanumeric 字符集,HTTPS://SETHMLARSON.DEV 也能放进去。
这里的重点是:二维码容量不是一句“能放多少字节”就能讲完。它取决于版本、纠错等级和编码模式。
| 变量 | Larson 的处理 | 影响 |
|---|---|---|
| QR 规格 | 普通 QR Code Version 1 | 固定为 21×21 模块 |
| 纸面网格 | 10×10 网格拆半,并借用边距 | 决定模块是否能画准 |
| 内容选择 | 先用域名,后确认全大写 HTTPS URL 可行 | 编码模式会改变容量上限 |
| 参考生成 | 用 Python 的 qrcode 包 | 避免人工重新排布数据 |
| 命令细节 | 用 echo -n | 避免尾随换行被编码进去 |
这对技术读者很有用。以后看二维码容量,不要只问“这个 URL 多长”。要看它被当作 byte mode 还是 alphanumeric mode,也要看纠错等级。
对做手工名片、贴纸、网格画的人,也有一个直接动作:先用工具生成参考码,再照着模块画。不要凭视觉补块。二维码不是马赛克画。
手绘能成,靠定位图案和纠错
Larson 的绘制顺序很关键。
他先画三个角上的定位图案,再补时序线,最后填数据模块。定位图案告诉扫描器“这里有二维码”。时序线帮助扫描器确认网格节奏。数据区才是具体内容。
这也是很多人误解二维码的地方。
它不是把黑白块随便凑到一起。结构区错了,扫描器可能连入口都找不到。数据区错一点,反而还有机会被纠错拉回来。
Larson 在绘制过程中逐步测试。画到一定阶段后,手机已经开始把这块图案当作二维码处理。最终即使有一处数据错误,在最低纠错等级 L 下仍然可以识别。
这里能看出二维码和一维条码的差别。一维条码主要沿一个方向读取宽窄线条。二维码把定位、格式、数据和纠错都塞进二维网格。Denso Wave 1994 年推出 QR Code 时,服务的是制造和物流里的快速识别;今天它能被手绘复现,靠的仍是这套工程取舍。
规矩越清楚,容错才有意义。
真正的限制在纸面误差
实验后半段最有意思的限制,不在算法,而在纸。
纸张卷曲会影响近距离扫描。Larson 把纸压平后更容易识别;把二维码挂在显示器上,效果反而更好。原因并不神秘:扫描器需要看到稳定的边界、足够的对比,以及相对平整的模块排列。
这对两类人影响不同。
对研究二维码原理的技术读者,这个实验适合当一张“最小可观察样本”。你可以从 Version 1、纠错等级、编码模式、格式信息、静区这些变量入手,看哪些是硬条件,哪些是可容忍误差。
对喜欢纸笔实验和网格艺术的创作者,动作更具体:
- 保留二维码四周静区,不要让装饰贴太近;
- 用深色笔和浅色纸,别让对比度变低;
- 控制墨迹扩散,模块边界要清楚;
- 画完先压平再扫,不要拿卷曲纸面硬试;
- 如果要放进完整 URL,优先检查编码模式,而不是直接换更大的码。
接下来最该看的,也不是“能不能画更复杂”。更现实的变量是误差边界:粗笔会不会糊住模块,彩色墨水会不会降低对比,纸面弯折到什么程度会失败,提高纠错等级会不会换来更大图案。
目前能确认的是,手绘二维码可行。但它不是玄学,也不是运气。它只是把标准留出的余量,用一支笔和一张纸显了形。
