Изменение цвета движущегося изображения без снижения частоты кадров

Я только что добавил в свою игру опцию, благодаря которой у всех врагов будет случайный цвет одежды вместо обычного синего. Я использую этот код для рисования прямоугольников поверх рубашки врага.

BufferedImage image = new BufferedImage(z.getWidth(), z.getHeight(), 
    BufferedImage.TYPE_4BYTE_ABGR);
try{
    image = ImageIO.read(new File("C:\\Program Files (x86)\\ZombieGame\\
        Zombie.png"));
}catch (IOException ex) {
}
int j, k, red, green, blue;
    for(j = 0; j < z.getWidth(); j++){
        for(k = 0; k < z.getHeight(); k++){
            Color c = new Color(image.getRGB(j, k));
            red = c.getRed();
            green = c.getGreen();
            blue = c.getBlue();
            if(red == 0 && green == 0 && blue == 178){
                g2d.setColor(Color.red);
                Rectangle r = new Rectangle(j,k, 1, 1);
                Path2D.Double rect = new Path2D.Double(r, at);
                g2d.fill(rect);
            }
        }
    }

Дело в том, что когда я применяю это, игра будет работать в два раза медленнее (до того, как я добавил этот код, я получил твердые 80 кадров в секунду, но так быстро, как я его добавил, я получил около 30 кадров в секунду). Мой вопрос в том, есть ли лучший способ сделать это, в котором я мог бы изменить цвет определенных частей изображения без резкого снижения частоты кадров?


person Community    schedule 21.05.2013    source источник


Ответы (2)


Возможно, вам не следует просто перебирать каждый пиксель. Как я вижу, у этого будет 2 недостатка:

  1. Если у вас есть несколько пикселей, которые вы не хотите менять в пределах одного изображения;
  2. Это очень медленно.

Что касается первого аргумента, давайте предположим, что этого не произойдет, пока ваше изображение (очевидно) содержит один элемент.

А что касается второго вопроса, который на самом деле является основным вашим вопросом - я могу предложить вам посмотреть прикладной ответ в этот вопрос и комментарии к нему. Он содержит описание того, как выполнить вашу задачу быстрее, чем итерация, а в комментарии есть ссылка на пример - вот оно

person Constantine Kozlov    schedule 21.05.2013

Сделайте копию исходного изображения, измените пиксели, которые вы хотите изменить (любым способом, который вам нравится, будь то рисование прямоугольников или замена значений цвета с помощью getRGB/setRRG). Запомните измененное изображение и повторно используйте его для всех последующих визуализаций того же цвета.

Таким образом, вы платите за изменение цвета только один раз, а не каждый раз, когда вам нужно нарисовать изображение. Если у вас не слишком много изображений, вы можете загрузить их все еще до запуска игры. Если изображений слишком много, чтобы загрузить их все, можно использовать какой-то кэш LRU для хранения наиболее часто используемых изображений в памяти.

person Durandal    schedule 21.05.2013