Java 洪水填充算法需要几秒钟的时间
我正在编写一个非常基本的油漆应用程序 我的应用程序有一个图像,当我在任何地方触摸时,这个地方就会充满一种颜色 我使用了洪水填充算法,特别是第二种替代实现方法 我使用像素贴图来更新纹理 这在我的电脑上运行得很好,问题是在我的android motorola moto G上执行应用程序时,分辨率为720p,android 4.4,算法需要几秒钟,我不喜欢这样,我希望这个过程花费更少的时间。因此,问题是,高分辨率或大面积填充算法需要几秒钟的时间 我做的一件事是每5个像素检查一次,而不是每1个像素检查一次,但我想知道是否还有其他优化 我知道有这样的应用程序。有人能告诉我什么建议吗 谢谢 编辑:用一些代码更新问题,我已经从接口中删除了空方法。可能存在未使用的变量。这是检查每个像素的版本 我的洪水填充算法Java 洪水填充算法需要几秒钟的时间,java,android,libgdx,Java,Android,Libgdx,我正在编写一个非常基本的油漆应用程序 我的应用程序有一个图像,当我在任何地方触摸时,这个地方就会充满一种颜色 我使用了洪水填充算法,特别是第二种替代实现方法 我使用像素贴图来更新纹理 这在我的电脑上运行得很好,问题是在我的android motorola moto G上执行应用程序时,分辨率为720p,android 4.4,算法需要几秒钟,我不喜欢这样,我希望这个过程花费更少的时间。因此,问题是,高分辨率或大面积填充算法需要几秒钟的时间 我做的一件事是每5个像素检查一次,而不是每1个像素检查一
import com.badlogic.gdx.*;
import com.badlogic.gdx.assets.AssetManager;
import com.badlogic.gdx.graphics.Color;
import com.badlogic.gdx.graphics.GL20;
import com.badlogic.gdx.graphics.Pixmap;
import com.badlogic.gdx.graphics.Texture;
import com.badlogic.gdx.input.GestureDetector;
import com.badlogic.gdx.math.Vector2;
import com.badlogic.gdx.scenes.scene2d.Stage;
import es.angelluis..Actors.BackgroundActor;
import es.angelluis..Actors.ImageActor;
import es.angelluis..util.Pixel;
import java.util.ArrayList;
public class Images implements Screen, InputProcessor {
private Stage stage;
private ImageActor img = new ImageActor();
private AssetManager manager;
private Texture texture = null;
public Images(){
manager = new AssetManager();
stage = new Stage();
manager.load("dibujo1.png",Texture.class);
stage.addActor(img);
InputMultiplexer im = new InputMultiplexer();
im.addProcessor(this);
im.addProcessor(stage);
Gdx.input.setInputProcessor(im);
}
@Override
public void render(float delta) {
Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);
if (manager.update()){
if (!img.loaded){
texture = manager.get("dibujo1.png", Texture.class);
int x = (Gdx.graphics.getWidth()-texture.getWidth())/2;
int y = (Gdx.graphics.getHeight()-texture.getHeight())/2;
img.load(texture, x,y, texture.getWidth(), texture.getHeight());
texture.getTextureData().prepare();
pix = texture.getTextureData().consumePixmap();
}
stage.draw();
}
}
@Override
public boolean touchDown(int screenX, int screenY, int pointer, int button) {
int colorSelected = Color.rgba8888(Color.RED);
if (screenX < img.getX() || screenX > img.getX() + img.getWidth() || screenY < img.getY() || screenY > img.getY() + img.getHeight()){
return false;
}
//Get Texture to update.
Pixmap source = img.getPixmap();
// Obtenemos las coordenadas locales a la textura.
screenX = screenX - (int)img.getX();
screenY = screenY - (int)img.getY();
// Get Color.
int colorInicial = source.getPixel(screenX, screenY);
// If color is the same we will exit.
if (colorInicial == colorSelected){
return false;
}
ArrayList<Pixel> pixels = new ArrayList<Pixel>();
int colorPixel = source.getPixel(screenX, screenY);
if (colorPixel == colorInicial){
// Store the initial pixel in pixels linked list.
pixels.add(new Pixel(screenX, screenY));
while(!pixels.isEmpty()){
Pixel p = pixels.get(0);
source.setColor(Color.RED);
source.drawPixel(p.getX(), p.getY());
pixels.remove(0);
// Now get all pixel that I should be update in this y coords. So get west and east.
ArrayList<Pixel> line = new ArrayList<Pixel>();
int w = p.getX()-1;
colorPixel = source.getPixel(w, p.getY());
while (colorPixel == colorInicial && w != 0){
line.add(new Pixel(w, p.getY()));
w--;
colorPixel = source.getPixel(w, p.getY());
}
int e = p.getX() + 1;
colorPixel = source.getPixel(e, p.getY());
while (colorPixel == colorInicial && e != img.getWidth()){
line.add(new Pixel(e, p.getY()));
e++;
colorPixel = source.getPixel(e, p.getY());
}
// Draw the line that I store before.
while (!line.isEmpty()){
Pixel linePixel = line.get(0);
line.remove(0);
source.setColor(Color.RED);
source.drawPixel(linePixel.getX(), linePixel.getY());
// I check the north pixel and store it if they should be updated
colorPixel = source.getPixel(linePixel.getX(), linePixel.getY()+1);
if (colorPixel == colorInicial){
pixels.add(new Pixel(linePixel.getX(), linePixel.getY()+1));
}
// I check the south pixel and store it if they should be updated
colorPixel = source.getPixel(linePixel.getX(), linePixel.getY()-1);
if (colorPixel == colorInicial){
//System.out.println("Entramos en sur");
pixels.add(new Pixel(linePixel.getX(), linePixel.getY()-1));
}
}
}
}
img.setTexture(new Texture(source));
return false;
}
}
在执行这些操作时,一个常见的错误是您试图更新屏幕位图,这会大大降低处理速度,因为应用程序同时尝试更新屏幕。 此问题的解决方案是将屏幕复制到位图中,在该位图上执行填充算法,并在完成后将结果复制回屏幕。
如果您提供一些代码,我们可以检查您的方法。发布您的代码。如何设置像素?现代硬件的设计不是一个接一个地设置像素。您需要在位图中构建完整的填充图像,并将其复制到图形设备。我用一些代码更新了我的问题
package es.angelluis..Actors;
import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.graphics.Pixmap;
import com.badlogic.gdx.graphics.Texture;
import com.badlogic.gdx.graphics.g2d.Batch;
import com.badlogic.gdx.scenes.scene2d.Actor;
public class ImageActor extends Actor{
private Texture img;
public boolean loaded = false;
private int x,y,width,height;
public void load(Texture img, int x, int y, int width, int height){
this.img = img;
loaded = true;
this.x = x;
this.y = y;
this.width = width;
this.height = height;
}
public void setTexture(Texture img){
this.img = img;
}
public Pixmap getPixmap(){
if (!img.getTextureData().isPrepared()){
img.getTextureData().prepare();
}
return img.getTextureData().consumePixmap();
}
public float getX() {
return x;
}
public void setX(int x) {
this.x = x;
}
public float getY() {
return y;
}
public void setY(int y) {
this.y = y;
}
public float getWidth() {
return width;
}
public void setWidth(int width) {
this.width = width;
}
public float getHeight() {
return height;
}
public void setHeight(int height) {
this.height = height;
}
@Override
public void draw(Batch batch, float alpha){
batch.draw(img, x, y, width, height);
}
}