Android 不规则封闭区域颜色填充算法实现与示例
一、概述
在移动应用开发中,图像着色(Flood Fill)是常见的交互需求,例如填色游戏或图片编辑工具。图像填充的核心在于如何高效地识别并修改特定区域内的像素颜色。
图像填充主要有两种经典算法:
- 种子填充法(Seed Fill):从点击点开始,递归或迭代地向四周扩散,直到遇到边界。
- 扫描线填充法(Scanline Fill):按行扫描,利用水平连通性减少重复计算。
虽然存在多种变体算法,但在移动端资源受限的环境下,选择效率更高的算法至关重要。本文将详细对比这两种算法的原理,并提供基于 Java 的完整 Android 实现代码。
二、原理分析
1. 种子填充法(四联通/八联通)
算法简介:假设要将某个区域填充成红色。从用户点击点的像素开始,检查上下左右(八联通还包括对角线)四个方向的像素。如果相邻像素的颜色与当前点击点的像素一致,则将其改变为目标色,并继续对该新点进行同样的判断。
这是一个典型的递归过程。一个点扩展到四个点,这四个点再各自扩展,形成树状结构。如果区域较大,递归深度会迅速增加,极易导致栈溢出(StackOverflowException)。
递归实现示例
/**
* @param pixels 像素数组
* @param w 宽度
* @param h 高度
* @param pixel 当前点的颜色
* @param newColor 填充色
* @param i 横坐标
* @param j 纵坐标
*/
private void fillColorRecursive(int[] pixels, int w, int h, int pixel, int newColor, int i, int j) {
int index = j * w + i;
// 边界检查及颜色匹配检查
if (index < 0 || index >= pixels.length ||
i < 0 || i >= w || j < 0 || j >= h ||
pixels[index] != pixel) {
return;
}
pixels[index] = newColor;
// 上
fillColorRecursive(pixels, w, h, pixel, newColor, i, j - 1);
// 右
fillColorRecursive(pixels, w, h, pixel, newColor, i + , j);
fillColorRecursive(pixels, w, h, pixel, newColor, i, j + );
fillColorRecursive(pixels, w, h, pixel, newColor, i - , j);
}


