交互式 Bayer CFA 解拜耳算法可视化 Interactive Demosaic Algorithm Visualization
从像素级别理解数码相机如何从马赛克传感器数据还原出彩色图像
纯前端 · 零上传 · 隐私安全 · 支持 RAW 文件
| 📷 支持 RAW 格式 | 🔬 像素级演示 | 📐 5 种经典算法 |
|---|---|---|
| NEF / CR2 / ARW / DNG | 100% ~ 1600% 缩放 | 最近邻 → 边缘导向 |
| 自动解析 TIFF 结构 | 看清每个滤色片像素 | 逐步动画对比效果 |
数码相机的图像传感器(CCD/CMOS)本质上是一个光电转换器阵列。每个像素(photosite)只能测量落在其上的光的总强度,无法区分颜色。为了获得彩色图像,1976 年柯达工程师 Bryce Bayer 发明了一种巧妙的方案:在传感器前方放置一层微型彩色滤光片阵列(Color Filter Array, CFA)。
最常见的 CFA 排列是 RGGB(也称 Bayer 模式):
┌───┬───┬───┬───┬───┬───┐
│ R │ G │ R │ G │ R │ G │
├───┼───┼───┼───┼───┼───┤
│ G │ B │ G │ B │ G │ B │
├───┼───┼───┼───┼───┼───┤
│ R │ G │ R │ G │ R │ G │
├───┼───┼───┼───┼───┼───┤
│ G │ B │ G │ B │ G │ B │
└───┴───┴───┴───┴───┴───┘
关键特征:
- 绿色像素占 50%:人眼对绿色(亮度信息)最敏感,因此绿色采样密度是红蓝的两倍
- 红色和蓝色各占 25%
- 每个像素只记录了一个颜色通道的信息,另外两个通道完全缺失
由于每个像素只有一个颜色通道的数据,要得到完整的 RGB 彩色图像,必须通过算法估算(插值)每个像素缺失的两个通道。这个过程称为解拜耳(Demosaicing / Debayering)。
解拜耳算法的质量直接影响最终图像的:
- 锐度:差的算法会模糊边缘
- 伪色(Color Artifacts):在高频纹理区域产生不存在的彩色条纹
- 摩尔纹(Moiré):规则纹理与 Bayer 模式产生干涉
- 拉链效应(Zipper Effect):边缘处出现锯齿状彩色伪影
除了 RGGB,还有三种旋转变体:
- BGGR:蓝色在左上角
- GRBG:绿色在左上角,红色在右上角
- GBRG:绿色在左上角,蓝色在右上角
不同相机厂商使用不同的排列,但算法原理相同。
为了减少摩尔纹和伪色,大部分数码相机在传感器前还放置了一片光学低通滤波器(Anti-Aliasing Filter)。它轻微模糊入射光,使得高频细节不会超过 Bayer 阵列的奈奎斯特频率。代价是牺牲了一些锐度。
近年来一些相机(如 Nikon Z9、Sony A7R V、Fujifilm X-T5)取消了光学低通滤波器,依赖更先进的解拜耳算法和机内处理来抑制伪色问题。
- 上传图片:支持 RAW 格式(NEF/CR2/ARW/DNG 等)和普通图片(JPEG/PNG)
- Bayer 马赛克可视化:
- 灰度模式:模拟传感器原始输出
- 彩色模式:用红/绿/蓝着色显示每个像素的滤色片归属
- 解拜耳算法演示:
- 从图片中选择任意 200×200 区域
- 像素级放大显示
- 逐步动画展示插值过程
- 5 种经典算法对比
- 图片查看器:滚轮缩放、拖拽平移、旋转
- 保存功能:任意视图可导出为 PNG
- RAW 文件支持:自动解析 TIFF 结构,提取内嵌全尺寸 JPEG 预览,正确处理 EXIF Orientation
本项目实现了 5 种经典解拜耳算法,按复杂度递增排列:
最简单的方法。对于每个缺失的颜色通道,直接复制距离最近的同色像素值。
- 优点:计算极快,实现简单
- 缺点:产生严重的块状伪影和锯齿
- 复杂度:O(1) per pixel
对缺失通道取周围同色像素的算术平均值。
- 优点:简单有效,比最近邻平滑很多
- 缺点:在边缘处模糊,会产生拉链效应
- 复杂度:O(1) per pixel(3×3 邻域)
基于 Kimmel (1999) 的思路。核心观察:自然图像中色调(hue)的空间变化比亮度(luminance)更平滑。
算法步骤:
- 先用双线性插值得到完整的 G(亮度)通道
- 计算色调比率 R/G 和 B/G
- 对色调比率进行插值(而非直接对 R、B 插值)
- 用插值后的比率乘以 G 得到 R 和 B
- 优点:显著减少伪色,边缘保持更好
- 缺点:在 G 接近 0 的暗区可能不稳定
- 复杂度:O(1) per pixel,两遍扫描
微软研究院提出的高质量线性插值方法。使用 4 种 5×5 卷积核,关键创新是利用其他颜色通道的高频信息来修正插值结果。
核心思想:在估计某个位置的 G 值时,不仅看周围的 G 像素,还利用当前位置已知的 R 或 B 值(它们包含了局部高频信息)来修正估计。
4 种卷积核(所有系数除以 8):
-
Pattern 1:在 R/B 位置估计 G
-
Pattern 2:在 G 位置估计水平方向的 R 或 B
-
Pattern 3:在 G 位置估计垂直方向的 R 或 B
-
Pattern 4:在 R 位置估计 B(或反之,对角方向)
-
优点:线性算法中质量最高,计算效率好
-
缺点:仍是线性方法,无法完全消除边缘伪色
-
复杂度:O(1) per pixel(5×5 固定核)
基于 Hamilton & Adams (1997) 的思路。核心创新:在插值前先检测局部边缘方向,然后只沿边缘方向插值,避免跨越边缘。
算法步骤:
- 计算水平梯度 dH 和垂直梯度 dV
- 如果 dH < dV:沿水平方向插值(垂直方向有边缘)
- 如果 dV < dH:沿垂直方向插值(水平方向有边缘)
- 如果 dH ≈ dV:取两个方向的平均
- 利用色差(R-G, B-G)的平滑性恢复 R 和 B
- 优点:边缘保持优秀,伪色少
- 缺点:在对角边缘处仍可能产生伪影
- 复杂度:O(1) per pixel,但常数较大
| 技术 | 用途 |
|---|---|
| Vite 6 | 构建工具 |
| React 19 | UI 框架 |
| TypeScript 5.8 | 类型安全 |
| Tailwind CSS 4 | 样式 |
| Canvas API | 图像渲染与像素操作 |
| Web Worker | 后台计算(可选) |
纯前端,零后端依赖,适合部署到任何静态托管平台。
DeDeBayer/
├── src/
│ ├── components/
│ │ ├── CanvasView.tsx # 通用 Canvas 图像显示组件
│ │ ├── DemosaicPlayer.tsx # 解拜耳演示交互组件(局部放大 + 动画)
│ │ ├── ImageUploader.tsx # 图片/RAW 上传组件
│ │ └── ImageViewer.tsx # 全屏图片查看器(缩放/平移/旋转)
│ ├── lib/
│ │ ├── bayer.ts # Bayer CFA 核心:RGB→马赛克、可视化
│ │ ├── demosaic.ts # 5 种解拜耳算法实现
│ │ ├── tiff-parser.ts # TIFF/NEF/CR2 结构解析器
│ │ ├── raw-loader.ts # RAW 文件加载(提取内嵌 JPEG)
│ │ ├── animation.ts # 动画帧生成
│ │ ├── downsample.ts # Bayer 感知下采样
│ │ ├── download.ts # PNG 导出
│ │ └── theme.ts # 明暗主题管理
│ ├── styles/
│ │ └── index.css # Tailwind 入口 + 主题配置
│ ├── App.tsx # 主应用组件
│ └── main.tsx # 入口
├── public/
│ └── vite.svg # Favicon(Bayer 模式图标)
├── .github/workflows/
│ └── deploy.yml # CI/CD:构建 + Cloudflare Pages + Docker
├── Dockerfile # 多阶段构建(Node + Nginx)
├── docker-compose.yml # 一键启动
├── nginx.conf # Nginx 配置(SPA + 缓存)
├── wrangler.toml # Cloudflare Pages 配置
├── vite.config.ts # Vite 配置
├── tsconfig.json # TypeScript 配置
└── package.json
# 克隆
git clone https://github.com/sergioperezcheco/DeDeBayer.git
cd DeDeBayer
# 安装依赖
npm install
# 启动开发服务器
npm run dev
# 构建生产版本
npm run build
# 预览生产构建
npm run preview方式一:GitHub 集成(自动)
- Fork 本仓库
- 在 Cloudflare Dashboard 创建 Pages 项目,连接 GitHub 仓库
- 构建设置:
- 构建命令:
npm run build - 输出目录:
dist
- 构建命令:
- 每次 push 到 main 自动部署
方式二:GitHub Actions(本仓库已配置)
在仓库 Settings → Secrets 中添加:
CLOUDFLARE_API_TOKEN:Cloudflare API Token(需要 Pages 编辑权限)CLOUDFLARE_ACCOUNT_ID:你的 Cloudflare Account ID
Push 到 main 即自动部署。
第一步:获取 Cloudflare 凭证
- 登录 Cloudflare Dashboard
- 获取 Account ID:
- 进入任意域名 → 右侧栏 → Account ID(32 位十六进制字符串)
- 或者:首页 → 左下角 → Account ID
- 创建 API Token:
- 进入 API Tokens 页面
- 点击 Create Token
- 选择模板 Edit Cloudflare Workers 或自定义:
- Permissions:
Account→Cloudflare Pages→Edit
- Permissions:
- 创建后复制 Token(只显示一次)
第二步:在 GitHub 仓库添加 Secrets
- 打开仓库页面 → Settings → 左侧 Secrets and variables → Actions
- 点击 New repository secret,添加:
- Name:
CLOUDFLARE_API_TOKEN,Value: 上面创建的 API Token - Name:
CLOUDFLARE_ACCOUNT_ID,Value: 你的 Account ID
- Name:
第三步:触发部署
- 自动触发:Push 代码到
main分支即自动触发 - 手动触发:进入仓库 → Actions → 选择 workflow → Run workflow
- PR 触发:向
main提交 Pull Request 时会自动构建(但不部署)
第四步:Docker 镜像(自动)
Docker 镜像会自动推送到 GitHub Container Registry (ghcr.io),无需额外配置。GITHUB_TOKEN 是 Actions 自动提供的。
构建完成后可以这样拉取:
docker pull ghcr.io/sergioperezcheco/dedebayer:latest# 使用 docker-compose(推荐)
docker compose up -d
# 或手动构建运行
docker build -t dedebayer .
docker run -p 4321:4321 dedebayer也可以直接拉取 GitHub Container Registry 的镜像:
docker pull ghcr.io/sergioperezcheco/dedebayer:latest
docker run -p 4321:4321 ghcr.io/sergioperezcheco/dedebayer:latest本项目是纯静态站点,npm run build 后将 dist/ 目录部署到任何静态托管即可:
- Vercel:零配置,连接 GitHub 即可
- Netlify:构建命令
npm run build,发布目录dist - GitHub Pages:使用
gh-pages分支或 Actions
-
Bayer, B. E. (1976). Color imaging array. U.S. Patent 3,971,065. Google Patents
-
Hamilton, J. F., & Adams, J. E. (1997). Adaptive color plan interpolation in single sensor color electronic camera. U.S. Patent 5,629,734. Google Patents — 边缘导向插值的奠基性专利。
-
Kimmel, R. (1999). Demosaicing: Image reconstruction from color CCD samples. IEEE Transactions on Image Processing, 8(9), 1221-1228. IEEE Xplore — 提出利用色调平滑性的解拜耳方法。
-
Malvar, H. S., He, L., & Cutler, R. (2004). High-quality linear interpolation for demosaicing of Bayer-patterned color images. IEEE ICASSP, vol. 3, pp. 485-488. Microsoft Research PDF — 微软研究院提出的 5×5 卷积核方法。
-
Gunturk, B. K., Glotzbach, J., Altunbasak, Y., Schafer, R. W., & Mersereau, R. M. (2005). Demosaicking: Color filter array interpolation. IEEE Signal Processing Magazine, 22(1), 44-54. IEEE Xplore — 解拜耳算法的综述论文。
-
Menon, D., Andriani, S., & Calvagno, G. (2007). Demosaicing with directional filtering and a posteriori decision. IEEE Transactions on Image Processing, 16(1), 132-141. IEEE Xplore — 更先进的方向性滤波方法。
-
Li, X., Gunturk, B., & Zhang, L. (2008). Image demosaicing: A systematic survey. Proceedings of SPIE, vol. 6822. SPIE — 全面的解拜耳算法调研。
MIT