过去几个月,我一直在做一个免费的开源二维码生成器,在浏览器里就能跑。它能搞自定义渐变、叠加图片、改点的形状——弄出来的效果挺酷的,比如星云图配上紫色渐变。我一直挺满意,直到某天自己真去扫了一下。

问题来了:我在iPhone上试着扫自己最得意的一张设计,扫不出来。完全不行。WhatsApp内置扫码也挂了。换了几台安卓机,有的行,有的不行。我把纠错等级调到H级——就是最高那档,能修复30%损坏的那种——还是没用。

我一开始以为是代码库有bug,花了好几个小时排查,结果不是。真正的锅,是手机的对比度检测算法。

肉眼看见的是颜色,摄像头看见的是噪点

手机相机读二维码跟人眼看图不是一码事。它们跑的是对比度识别,要找深色模块和浅色背景之间的那条界。你看到的是:两种能分清的颜色。算法看到的却是:一团灰乎乎的噪点

纠错在这时候派不上用场。那些数据模块没丢、没缺,它们都在,只是在扫描逻辑眼里,跟隐身了差不多。

这就是为什么很多看着漂亮的艺术二维码,实际扫起来惨不忍睹——设计的越花哨,对比度边界越模糊,算法越容易把它当背景噪声直接忽略。

我搞了个四步验证流程,叫MSQF

搞清楚根因之后,我不打算再玩"生成完祈祷能扫"那套了。现在在做一套新流程,叫多步骤二维码框架(MSQF)。每张码生成后,不是直接输出,而是先过一遍验证管线:

第一步是内部扫描引擎。这个跑在我自己代码里,如果扫不出来,就自动调不透明度和对比度,然后重新扫。第二步用ZXing——Google开源的扫码引擎,安卓机上很常见。第三步切到quirc-wasm,标准更严,专门处理边界情况。

第四步最狠,用ZXing的严格模式跑wasm版本。这是我目前能找到的、最接近iPhone原生相机行为的一套模拟逻辑。

第四步不设为默认,是有原因的

技术上有个取舍:ZXing严格模式太吃资源了,尤其是批量生成的时候,时间成本会明显上去。所以我的设计是让用户自己选——你是要好看,还是必须能扫。这个权衡留给用的人来决定。

说真的,有些设计在自动调参之后,风格直接就变了,原本那种"氛围感"没了。我自己也纠结:这到底还算不算同一张图?

我有两个问题想问各位

这套框架还在搭,过程中遇到两个大疑问,想听听社区的意见。

第一个是引擎选择的问题:用ZXing wasm严格模式去模拟iPhone的视觉框架,到底是不是最好的办法?我目前只能做到近似,没法完全复刻苹果那套方案。

第二个是"好看"和"能用"的边界问题。自动调参为了扫码率,有时候设计效果直接掉档。你们觉得这条线画在哪里合适?到什么程度就该放弃视觉追求,保住功能?

这玩意现在就能用,免费、不需要注册。我很想知道,还有没有人踩过自定义样式二维码扫码率的坑。