我有两个类似的类,在MyPanel类中,我重写了paintComponent
方法,将自己的“图形”添加到JPanel
。我之所以调用super.paintComponent(g),是因为据我了解,当我使用自己的继承方法实现时,我也重写了此方法的标准“隐藏”功能。我了解,如果我想在myPanel上使用诸如setBackground / setBorder之类的方法,则必须从扩展类中调用paintComponent方法,以使其以自己的标准方式工作
(油漆背景,寄宿生等)。
因此,我认为每当我按下鼠标按钮时,我都会调用moveSquare方法,它将调用repaint方法。调用repaint方法时,程序将转到重写的paintComponent方法。我知道当我使用
repaint(squareX, squareY, squareW, squareH);
在moveSquare方法中,它将仅重新绘制红色方块(不会重新绘制背景),这就是为什么我将在面板上看到每个红色方块的原因。我知道如果我会在第一次调用中使用repaint()然后使用这样的参数进行重画:
repaint();
squareX=x;
squareY=y;
repaint(squareX, squareY, squareW, squareH);
它会重新绘制背景,然后绘制一个正方形,所以我将只能在面板上看到最后一个红色绘制的正方形。我不明白的是为什么为什么要对带有参数的repaint方法进行两次调用:
repaint(squareX, squareY, squareW, squareH);
squareX=x;
squareY=y;
repaint(squareX, squareY, squareW, squareH);
将首先绘制一个带有背景颜色的正方形,然后绘制一个红色(它的行为就像我会在不带参数的情况下调用repaint,然后使用参数进行重画)。
很抱歉提供这么长的解释,但是我认为,如果
我将解释我认为它应该如何工作。
SwingMoveSquareDemo类
public class SwingMoveSquareDemo {
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable(){
public void run(){
System.out.println("GUI started");
createGUI();
}
});
}
public static void createGUI(){
JFrame f = new JFrame("Move square demo");
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.add(new MyPanel());
f.pack();
f.setVisible(true);
}
}
MyPanel类
public class MyPanel extends JPanel {
private int squareX=1;
private int squareY=1;
private int squareW=20;
private int squareH=20;
public MyPanel(){
setBackground(Color.GRAY);
setBorder(BorderFactory.createLineBorder(Color.WHITE));
setPreferredSize(new Dimension(400,250));
addMouseListener(new MouseAdapter() {
public void mousePressed(MouseEvent e) {
System.out.println("mouspressed");
moveSquare(e.getX(),e.getY());
}
});
}
private void moveSquare (int x, int y){
repaint(squareX, squareY, squareW, squareH);
squareX=x;
squareY=y;
repaint(squareX, squareY, squareW, squareH);
}
public void paintComponent(Graphics g){
super.paintComponent(g);
System.out.println("paint component");
g.setColor(Color.RED);
g.fillRect(squareX, squareY, squareW, squareH);
}
}
最佳答案
paintComponent
委托给ComponentUI#update
,后者将Graphics
上下文的颜色设置为组件的背景色并填充0, 0, c.getWidth(), c.getHeight()
(其中c
是对绘制组件的引用)。
基本上,这意味着,即使您使用repaint
或repaint(x, y, width, height)
,背景也会开始完全更新。
不同之处在于Graphics
剪辑会更改。调用repaint
时,剪辑将是组件的大小,使用repaint(x, y, width, height)
时,剪辑的形状将与您传递的值相同。
您可能需要查看Painting in AWT and Swing以获得更多详细信息。
记住,Swing中的绘画受RepaintManager
的控制,它将决定应绘画什么以及何时绘画。当它决定需要进行更新时,它将在事件队列中放置一个“绘制”事件,该事件将在将来的某个时间由事件调度线程进行处理。这意味着,在大多数情况下,绘画不是即时的。
关于java - Java Swing-super.paintcomponent(g)-repaint(),我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/20083404/