我正在尝试编写一个使用图层的绘图应用程序。我目前有4层,底层是白色,其他都是透明的。同时我只有第3(顶部)图层绘制到缓冲图像,其他由于某种原因只显示预览但不提交图像。即使我实现了图层的透明度,它也不会产生影响。所有层都是黑色的。好的部分是始终显示最顶层。请帮忙
public class Canvas extends JComponent implements MouseWheelListener {
private static final long serialVersionUID = 1L;
private final List<BufferedImage> images;
private DrawListenerInterface listenerInterface;
private int activeLayer;
private final Color color;
private final Paint frame;
public Canvas(Paint frame) {
this.frame = frame;
this.images = new ArrayList<BufferedImage>();
this.activeLayer = 0;
this.color = Color.red;
for (int i = 0; i < 4; i++) {
images.add(new BufferedImage(800, 600, BufferedImage.TYPE_INT_RGB));
setLayers(i);
}
this.addMouseWheelListener(this);
}
public class Canvas extends JComponent implements MouseWheelListener {
private static final long serialVersionUID = 1L;
private final List<BufferedImage> images;
private DrawListenerInterface listenerInterface;
private int activeLayer;
private final Color color;
private final Paint frame;
public Canvas(Paint frame) {
this.frame = frame;
this.images = new ArrayList<BufferedImage>();
this.activeLayer = 0;
this.color = Color.red;
for (int i = 0; i < 4; i++) {
images.add(new BufferedImage(800, 600, BufferedImage.TYPE_INT_RGB));
setLayers(i);
}
this.addMouseWheelListener(this);
}
public void setListeners(DrawListenerInterface listener) {
if (listenerInterface != null) {
this.removeMouseListener(listenerInterface);
this.removeMouseMotionListener(listenerInterface);
}
this.listenerInterface = listener;
this.addMouseMotionListener(listenerInterface);
this.addMouseListener(listenerInterface);
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
// defaultSettings((Graphics2D) g);
final Iterator<BufferedImage> iter = images.iterator();
while (iter.hasNext()) {
// g2.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER));
g.drawImage(iter.next(), 0, 0, null);
this.repaint();
}
listenerInterface.preview((Graphics2D) g);
this.repaint();
// g2.drawImage(images.get(activeLayer), 0, 0, null);
// }
// g2.setColor(color);
}
public BufferedImage getImage() {
return images.get(activeLayer);
}
public int getActiveLayer() {
return activeLayer;
}
public void setActiveLayer(int activeLayer) {
this.activeLayer = activeLayer;
}
public void setLayers(int layerNumber) {
// System.out.println(layer);
if (layerNumber == 0) {
final Graphics2D g = (Graphics2D) images.get(0).getGraphics();
g.setColor(Color.WHITE);
g.fillRect(0, 0, 800, 600);
} else {
BufferedImage img = images.get(layerNumber);
img = new BufferedImage(800, 600, BufferedImage.TYPE_INT_ARGB);
final Graphics2D graphics = (Graphics2D) img.getGraphics();
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.CLEAR));
graphics.fillRect(0, 0, 800, 600);
// reset composite
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER));
}
repaint();
}
@Override
public void mouseWheelMoved(MouseWheelEvent arg0) {
// TODO Auto-generated method stub
}
public class DrawListener implements DrawListenerInterface {
private final Canvas canvas;
private int x, y;
private int x2;
private int y2;
private final Paint frame;
public DrawListener(Canvas canvas, Paint frame) {
this.canvas = canvas;
this.frame = frame;
}
@Override
public void mouseMoved(MouseEvent e) {
}
@Override
public void mouseDragged(MouseEvent e) {
// TODO Auto-generated method stub
this.x2 = e.getX();
this.y2 = e.getY();
final Graphics2D g2 = (Graphics2D) canvas.getImage().getGraphics();
draw(g2);
canvas.repaint();
x = x2;
y = y2;
}
@Override
public void draw(Graphics2D g2) {
// TODO Auto-generated method stub
g2.drawLine(x, y, x2, y2);
}
@Override
public void mouseClicked(MouseEvent arg0) {
// TODO Auto-generated method stub
}
@Override
public void mouseEntered(MouseEvent arg0) {
// TODO Auto-generated method stub
}
@Override
public void mouseExited(MouseEvent arg0) {
// TODO Auto-generated method stub
}
@Override
public void mousePressed(MouseEvent e) {
// TODO Auto-generated method stub
x = e.getX();
x2 = e.getX();
y = e.getY();
y2 = e.getY();
final Graphics2D g2 = (Graphics2D) canvas.getImage().getGraphics();
draw(g2);
canvas.repaint();
}
@Override
public void mouseReleased(MouseEvent e) {
// TODO Auto-generated method stub
}
@Override
public void preview(Graphics2D g2) {
// TODO Auto-generated method stub
}
public class LayerPanel extends JPanel {
private final JButton layer0, layer1, layer2, layer3;
private final Canvas canvas;
public LayerPanel(Canvas canvas, Paint paint) {
this.canvas = canvas;
this.setSize(new Dimension(200, 400));
this.layer0 = new JButton("Layer 0");
this.layer1 = new JButton("Layer 1");
this.layer2 = new JButton("Layer 2");
this.layer3 = new JButton("Layer 3");
this.layer0.addActionListener(new ButtonListener());
this.layer1.addActionListener(new ButtonListener());
this.layer2.addActionListener(new ButtonListener());
this.layer3.addActionListener(new ButtonListener());
this.setLayout(new GridLayout(4, 1));
this.add(layer3);
this.add(layer2);
this.add(layer1);
this.add(layer0);
}
private class ButtonListener implements ActionListener {
@Override
public void actionPerformed(ActionEvent e) {
// TODO Auto-generated method stub
layer0.setBackground(Color.gray);
layer1.setBackground(Color.gray);
layer2.setBackground(Color.gray);
layer3.setBackground(Color.gray);
if (e.getSource().equals(layer0)) {
canvas.setActiveLayer(0);
final JButton b = (JButton) e.getSource();
b.setBackground(Color.yellow);
} else if (e.getSource().equals(layer1)) {
canvas.setActiveLayer(1);
final JButton b = (JButton) e.getSource();
b.setBackground(Color.yellow);
} else if (e.getSource().equals(layer2)) {
canvas.setActiveLayer(2);
final JButton b = (JButton) e.getSource();
b.setBackground(Color.yellow);
} else if (e.getSource().equals(layer3)) {
canvas.setActiveLayer(3);
final JButton b = (JButton) e.getSource();
b.setBackground(Color.yellow);
}
}
}
public interface DrawListenerInterface extends MouseListener, MouseMotionListener {
public void draw(Graphics2D g2);
public void preview(Graphics2D g2);
答案 0 :(得分:1)
您对super.paintComponent(g)
Canvas
的来电间接致电ComponentUI.update(..)
:
public void update(Graphics g, JComponent c) {
if (c.isOpaque()) {
g.setColor(c.getBackground());
g.fillRect(0, 0, c.getWidth(),c.getHeight());
}
paint(g, c);
}
因此,除非您在某个时刻在组件上调用setOpaque(false)
,否则您始终使用背景颜色填充g
。
我尝试将不透明设置为false
或删除super.paintComponent(g)
来电。
代码似乎还有其他问题。
您在Canvas
构造函数中创建的图片均为TYPE_INT_RGB
,即他们不支持 Alpha通道/透明度。
但是稍后在setLayers()
中对于0以外的图层,您将检索图像img
,然后使用新的,支持透明度的图像覆盖它,您从不存储在任何地方:
BufferedImage img = images.get(layerNumber);
img = new BufferedImage(800, 600, BufferedImage.TYPE_INT_ARGB);
离开相应的区块后, img
就会丢失。
答案 1 :(得分:0)
很难理解你的实际问题,但是:
BufferedImage img = images.get(layerNumber);
img = new BufferedImage(800, 600, BufferedImage.TYPE_INT_ARGB);
final Graphics2D graphics = (Graphics2D) img.getGraphics();
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.CLEAR));
graphics.fillRect(0, 0, 800, 600);
// reset composite
graphics.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_OVER));
即使您为其创建了新实例,也不会将img
存储在任何位置。此外,从images
获取它,然后在将其设置为其他内容之后立即没有任何意义。