问题
I'm currently designing Pac Man in java using swing. I have PNG images that are drawn on screen using the following statement.
wall = new ImageIcon(GamePanel.class.getResource("wall.png")).getImage();
g2d.drawImage(wall, x, y, this);
The problem I'm having is that it seems to render a very low colour depth rendition of the actual file. It seems like it does retain transparency (grey background is the Panel bg color), but it loses color depth.
The actual image looks like this:


Does anyone have a solution? Thanks!
回答1:
Something seems definitely wrong in the 2nd image. See it here on a black BG and it looks very different - without the 'halo'.

import java.awt.*;
import java.net.URL;
import javax.swing.*;
public class TestYellowDotImage {
public static JLabel getColoredLabel(Icon icon, Color color) {
JLabel label = new JLabel(icon);
label.setBackground(color);
label.setOpaque(true);
return label;
}
public static void main(String[] args) throws Exception {
URL url = new URL("http://i.stack.imgur.com/1EZVZ.png");
final Icon icon = new ImageIcon(url);
Runnable r = new Runnable() {
@Override
public void run() {
JPanel gui = new JPanel(new GridLayout(0, 4));
gui.add(new JLabel(icon));
gui.add(getColoredLabel(icon, Color.BLACK));
gui.add(getColoredLabel(icon, Color.WHITE));
gui.add(getColoredLabel(icon, Color.RED));
JOptionPane.showMessageDialog(null, gui);
}
};
// Swing GUIs should be created and updated on the EDT
// http://docs.oracle.com/javase/tutorial/uiswing/concurrency/initial.html
SwingUtilities.invokeLater(r);
}
}
回答2:
Try this setting on g2d
:-
Map<RenderingHints.Key, Object> map = new HashMap<RenderingHints.Key, Object>();
map.put(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BICUBIC);
map.put(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
map.put(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
RenderingHints renderHints = new RenderingHints(map);
g2d.setRenderingHints(renderHints);
回答3:
Using Grid, you can mouse over the pixels to see how the alpha component rolls off at the icon's edge.
public Grid(String name) {
this.setBackground(new Color(0xFFFFFFC0));
Icon icon = null;
try {
icon = new ImageIcon(new URL("http://i.stack.imgur.com/1EZVZ.png"));
} catch (MalformedURLException e) {
e.printStackTrace(System.err);
}
...
}

This IconTest
shows how the icon renders with varying alpha and the default AlphaComposite.SRC_OVER
rule.

/*** @see https://stackoverflow.com/a/14432025/230513 */
public class IconTest {
private static final int N = 8;
private static final Random r = new Random();
public static void main(String[] args) throws MalformedURLException {
final URL url = new URL("http://i.stack.imgur.com/1EZVZ.png");
final Icon icon = new ImageIcon(url);
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
JFrame f = new JFrame("IconTest");
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
JPanel p = new JPanel(new GridLayout(N, N));
for (int i = 0; i < N * N; i++) {
final JLabel label = new JLabel(icon);
label.setOpaque(true);
label.setBackground(new Color(0, 0, 255, i));
p.add(label);
}
f.add(p);
f.pack();
f.setLocationRelativeTo(null);
f.setVisible(true);
}
});
}
}
回答4:
Solved. A repaint() was used in the paint() method. Removed it and it works.
Thanks for all the help.
来源:https://stackoverflow.com/questions/14431339/bad-png-rendering-low-color-depth-in-java-swing