填入 Java

FloodFill in Java

我正在尝试实现一个 FloodFill 版本,该版本在 up/down 方向进行递归调用,但在 left/right 方向使用迭代。但是,由于我缺乏图形编程经验,实施起来很痛苦。让我先写下我一直在做的事情,以便您了解发生了什么:

首先,我加载了一个 BufferedImage 和我想要应用 FloodFill 的测试图像:

m_objShape = ImageIO.read(FloodFillTest.class.getResourceAsStream("Untitled.png"));

canvas.drawImage(m_objShape, 100, 100, null);

图像,看起来像这样:

在此之后,我 select 使用我创建的调色板中的填充颜色,并使用 MouseEvent 检测图像被点击的位置。

现在,一切正常,直到我调用 FloodFill,

我的 first 问题是没有应用颜色,除非我最小化并恢复 Java Applet

second问题是x方向循环没有到达图像的末端。即使我的循环被设置为在找到不同的像素时停止。递归调用也是一场灾难,它不尊重图像的边界。这是我的代码:

private void DoFloodFill(int x, int y) {
    int startColor = GetPixel(x, y);

    int fillColor = m_objSelectedColor.getRGB();

    if(startColor == fillColor) return;

    FloodFill(x, y, m_objShape.getWidth(), m_objShape.getHeight(), fillColor, startColor);
}

private void FloodFill(int x, int y, int w, int h, int fillColor, int startColor) {

    if(x < 0 || y < 0 || x >= w || y >= h) return;

    if(GetPixel(x, y) != startColor) return;

    int xx = x;

    while(xx < w && GetPixel(xx, y) == startColor){
        SetPixel(xx - 100, y - 100 , fillColor);
        xx++;
    }

    int p = x - 1;

    while(p >= 0 && GetPixel(p, y) == startColor){
        SetPixel(p - 100  , y - 100, fillColor);
        p--;
    }

    FloodFill(x, y + 1, w, h, fillColor, startColor);
    FloodFill(x, y - 1, w, h, fillColor, startColor);
}

public void SetPixel(int x, int y, int nColor){
    m_objShape.setRGB(x, y, nColor);
}

public int GetPixel(int x, int y){
    return(m_objShape.getRGB(x, y));
}

图像应该是 627Wx454H,当我在中间单击时,第一个循环甚至在到达第 600 个像素之前就停止了。 StartColor 有时等于 -1 或 -16777216。但是,这些值与我单击的值不匹配。有人可以向我解释发生了什么吗?

谢谢

Edit 例如,我在第一个 while 循环后注释掉了代码。现在,这些是以下变量的值:

x: 482

y: 289

w: 627

小时:454

xx: 532

而且,图像看起来像这样。但是,该行应该到达图像的末尾。

最后,我错了很多。但是,可以这样解决。但是,正如@The111所说,它不是很安全,因为我很容易得到。

private void DoFloodFill(int x, int y) {
    // TODO Auto-generated method stub

    int x_offset = x - 100;
    int y_offset = y - 100;

    int startColor = GetPixel(x, y);

    int fillColor = m_objSelectedColor.getRGB();

    if(startColor == fillColor) return;

    FloodFill(x_offset, y_offset, m_objShape.getWidth(), m_objShape.getHeight(), fillColor, startColor);
}

private void FloodFill(int x, int y, int w, int h, int fillColor, int startColor) {

    if(x < 0 || y < 0 || x >= w || y >= h) return;

    if(GetPixel(x, y) != startColor) return;

    int xx = x, left = 0, right = 0;

    while(xx < w && GetPixel(xx, y) == startColor){
        SetPixel(xx, y , fillColor);
        right = xx;
        xx++;
    }

    xx = x - 1;

    while(xx >= 0 && GetPixel(xx, y) == startColor){
        SetPixel(xx, y, fillColor);
        left = xx;
        xx--;
    }

    while(xx < right){
        FloodFill(xx, y - 1, w, h, fillColor, startColor);
        FloodFill(xx, y + 1, w, h, fillColor, startColor);
        xx++;
    }

}