RGBImageFilter создает все черные пустые изображения - PullRequest
2 голосов
/ 27 сентября 2011

Я пытаюсь использовать RGBImageFilter для создания простого эффекта прозрачности изображения, однако во время тестирования я обнаружил, что все мои отфильтрованные изображения выглядят пустыми с черным фоном. Я упростил свой фильтр до простого фильтра «Нет операции», который просто возвращает значение RGB, которое было передано. Даже этот упрощенный фильтр NoOp создает пустое изображение. Я пробовал это с импортом и экспортом JPG и PNG с одинаковым эффектом. Я пробовал различные примеры фильтров из интернета, которые вызывают ту же самую проблему черного изображения. Кто-нибудь сталкивался с этим раньше? «Статус загрузки» и «статус записи» ниже возвращают значение «истина», поэтому из MediaTracker я знаю, что исходное изображение загружается полностью и что полученное изображение успешно записывается. Заранее благодарю за любую помощь!

Вот код:

import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.Toolkit;
import java.awt.image.BufferedImage;
import java.awt.image.FilteredImageSource;
import java.awt.image.ImageProducer;
import java.awt.image.RGBImageFilter;
import java.io.File;

import javax.imageio.ImageIO;
import javax.swing.ImageIcon;

class NoOpFilter extends RGBImageFilter {
public NoOpFilter() {
    canFilterIndexColorModel = true;
}

    public int filterRGB(int x, int y, int rgb) {       
    return rgb;
    }




    public static void main(String[] args) throws Exception{
    String originalImageLocation = args[0];
    String baseFileName = args[1];
    String directory = args[2];         
    ImageIcon originalImage = new               ImageIcon(Toolkit.getDefaultToolkit().getImage(originalImageLocation));

    NoOpFilter filter2 = new NoOpFilter();


    ImageProducer ip = new FilteredImageSource(originalImage.getImage().getSource(), filter2);
        Image filteredImage = Toolkit.getDefaultToolkit().createImage(ip);

        System.out.println("Load Status: " + ( originalImage.getImageLoadStatus() == java.awt.MediaTracker.COMPLETE));

        BufferedImage bim = new BufferedImage( originalImage.getIconWidth(),originalImage.getIconHeight(), BufferedImage.TYPE_INT_ARGB);

        Graphics2D g2 = bim.createGraphics();
        g2.drawImage(filteredImage, 0, 0, null);
        g2.dispose();
        File file = new File(directory + File.separator + baseFileName + ".png");
        file.createNewFile();
        boolean status = ImageIO.write(bim, "png", file);
        System.out.print("write() status: " + status);

    }

}

Ответы [ 2 ]

1 голос
/ 27 сентября 2011

Вот исправление, которое сработало для меня. Сразу после создания fileredImage, описанного выше, необходимо было фактически добавить отфильтрованное изображение в JLabel и JLabel в JFrame, чтобы сначала вывести его на экран перед записью в буфер и сохранить на диск:

...
Image filteredImage = Toolkit.getDefaultToolkit().createImage(ip);          
ImageIcon swingImage = new ImageIcon(filteredImage);
JFrame frame = new JFrame();
JLabel label = new JLabel(swingImage);
frame.add(label);
frame.setVisible(true);
frame.dispose();
BufferedImage bim = new BufferedImage( originalImage.getIconWidth(),originalImage.getIconHeight(), BufferedImage.TYPE_INT_ARGB);

Graphics2D g2 = bim.createGraphics();
g2.drawImage(filteredImage, 0, 0, null);
g2.dispose();
File file = new File(directory + File.separator + baseFileName + ".png");
file.createNewFile();
boolean status = ImageIO.write(bim, "png", file);
System.out.print("write() status: " + status);
}

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

Спасибо Hovercraft за указание в правильном направлении.

0 голосов
/ 17 апреля 2014

Вы должны вызвать prepareImage, тогда вам не нужно использовать обходной путь JLabel.

Image filteredImage = Toolkit.getDefaultToolkit().createImage(ip);
Toolkit.getDefaultToolkit().prepareImage(filteredImage, -1, -1, null);
...