JFrame 或 Jpanel 中的 repaint() 方法?
repaint() method in JFrame or Jpanel?
我是 Java 的新手,刚开始学习 GUI 组件。所以,我正在阅读 Headfirst Java,并且有这段代码解释了 JPanel
的 paintcomponent
方法。每当用户单击 'change colors' 按钮时,它只是改变椭圆的颜色。 -
import javax.swing.*;
import java.awt.*;
import java.awt.event.*;
public class SimpleGui3C implements ActionListener {
JFrame frame;
public static void main(String[] args) {
SimpleGui3C gui = new SimpleGui3C();
gui.go();
}
public void go() {
frame = new JFrame();
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
JButton button = new JButton("Change colors");
button.addActionListener(this);
MyDrawPanel drawPanel = new MyDrawPanel();
frame.getContentPane().add(BorderLayout.SOUTH, button);
frame.getContentPane().add(BorderLayout.CENTER, drawPanel);
frame.setSize(500,500);
frame.setVisible(true);
}
public void actionPerformed(ActionEvent event) {
frame.repaint();
}
}
MyDrawPanel Class -
import javax.swing.*;
import java.awt.*;
class MyDrawPanel extends JPanel {
public void paintComponent(Graphics g) {
Graphics2D g2d = (Graphics2D) g;
// GradientPaint gradient = new GradientPaint(70,70,Color.blue,150,150,Color.orange);
int red = (int) (Math.random() * 255);
int green = (int) (Math.random() * 255);
int blue = (int) (Math.random() * 255);
Color startColor = new Color(red, green, blue);
red = (int) (Math.random() * 255);
green = (int) (Math.random() * 255);
blue = (int) (Math.random() * 255);
Color endColor = new Color(red, green, blue);
GradientPaint gradient = new GradientPaint(70,70,startColor,150,150,endColor);
g2d.setPaint(gradient);
g2d.fillOval(70,70,100,100);
}
}
除了我们调用 repaint()
方法的部分,我从这个例子中得到了所有东西。
书上提到只要重写JPanel
的paintcomponent
方法,当你调用repaint()
时,就会调用paintcomponent
渲染内容(因为我们不直接调用 paintcomponent
)。
现在,我通过扩展 JPanel
并覆盖其 paintComponent
方法创建了 MyDrawPanel
class。现在,当我们将 drawPanel
小部件放在框架上然后单击鼠标时,将调用 repint()
方法。但是这个 repaint()
方法是使用 frame
调用的 - JFrame
的一个对象。根据我的基本 java 理解,如果我使用对象调用方法,则该方法必须在那个 class 或某个 Super class 中。我看不出在 frame
上调用 repaint()
如何触发 MyDrawPanel
的绘制组件。
我做了一些挖掘,看看 JFrame
和 JPanel
是否共享相同的层次结构,这是我发现的:
object
-->
component
(有重绘方法)-->
container
(有paintcomponent方法)-->
`jcomponent` --> `jpanel`
`window` --> `frame` --> `jframe`
所以我想既然 JFrame
和 JPanel
都有 paintComponent
和 repaint
方法,也许我可以扩展 Jframe
来创建 MyDrawPanel
而不是 Jpanel
,它应该可以正常工作。但事实并非如此。它编译正常但抛出运行时异常。
真是令人沮丧。可能是我没有获得 GUI 概念,或者我的基础知识仍然很薄弱。如果我在这里遗漏了一些非常愚蠢的东西,请告诉我。
让我们从 paintComponent
开始,应该在执行任何自定义绘画之前真正调用 super.paintComponent
然后继续阅读 Painting in AWT and Swing and Performing Custom Painting 以更好地理解 Swing 中的绘画工作原理。 repaint
不直接调用 paintComponent
,它要求 RepaintManager
在事件队列中安排一个 paint
事件,该事件在未来的某个时间点由事件调度线程,然后根据容器
的需要处理paint
事件
So I thought that since JFrame and JComponent both get paintComponent
不,他们没有。 JFrame
(及其父级 class)没有 paintComponent
方法
may be I can extend Jframe to create MyDrawPanel instead of Jpanel and it should work fine"
不,你不应该,除了 JFrame
没有 paintComponent
,还有很多事情会干扰你可能尝试在 JFrame
并且您应该继续按原样构建代码
我是 Java 的新手,刚开始学习 GUI 组件。所以,我正在阅读 Headfirst Java,并且有这段代码解释了 JPanel
的 paintcomponent
方法。每当用户单击 'change colors' 按钮时,它只是改变椭圆的颜色。 -
import javax.swing.*;
import java.awt.*;
import java.awt.event.*;
public class SimpleGui3C implements ActionListener {
JFrame frame;
public static void main(String[] args) {
SimpleGui3C gui = new SimpleGui3C();
gui.go();
}
public void go() {
frame = new JFrame();
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
JButton button = new JButton("Change colors");
button.addActionListener(this);
MyDrawPanel drawPanel = new MyDrawPanel();
frame.getContentPane().add(BorderLayout.SOUTH, button);
frame.getContentPane().add(BorderLayout.CENTER, drawPanel);
frame.setSize(500,500);
frame.setVisible(true);
}
public void actionPerformed(ActionEvent event) {
frame.repaint();
}
}
MyDrawPanel Class -
import javax.swing.*;
import java.awt.*;
class MyDrawPanel extends JPanel {
public void paintComponent(Graphics g) {
Graphics2D g2d = (Graphics2D) g;
// GradientPaint gradient = new GradientPaint(70,70,Color.blue,150,150,Color.orange);
int red = (int) (Math.random() * 255);
int green = (int) (Math.random() * 255);
int blue = (int) (Math.random() * 255);
Color startColor = new Color(red, green, blue);
red = (int) (Math.random() * 255);
green = (int) (Math.random() * 255);
blue = (int) (Math.random() * 255);
Color endColor = new Color(red, green, blue);
GradientPaint gradient = new GradientPaint(70,70,startColor,150,150,endColor);
g2d.setPaint(gradient);
g2d.fillOval(70,70,100,100);
}
}
除了我们调用 repaint()
方法的部分,我从这个例子中得到了所有东西。
书上提到只要重写JPanel
的paintcomponent
方法,当你调用repaint()
时,就会调用paintcomponent
渲染内容(因为我们不直接调用 paintcomponent
)。
现在,我通过扩展 JPanel
并覆盖其 paintComponent
方法创建了 MyDrawPanel
class。现在,当我们将 drawPanel
小部件放在框架上然后单击鼠标时,将调用 repint()
方法。但是这个 repaint()
方法是使用 frame
调用的 - JFrame
的一个对象。根据我的基本 java 理解,如果我使用对象调用方法,则该方法必须在那个 class 或某个 Super class 中。我看不出在 frame
上调用 repaint()
如何触发 MyDrawPanel
的绘制组件。
我做了一些挖掘,看看 JFrame
和 JPanel
是否共享相同的层次结构,这是我发现的:
object
-->
component
(有重绘方法)-->
container
(有paintcomponent方法)-->
`jcomponent` --> `jpanel`
`window` --> `frame` --> `jframe`
所以我想既然 JFrame
和 JPanel
都有 paintComponent
和 repaint
方法,也许我可以扩展 Jframe
来创建 MyDrawPanel
而不是 Jpanel
,它应该可以正常工作。但事实并非如此。它编译正常但抛出运行时异常。
真是令人沮丧。可能是我没有获得 GUI 概念,或者我的基础知识仍然很薄弱。如果我在这里遗漏了一些非常愚蠢的东西,请告诉我。
让我们从 paintComponent
开始,应该在执行任何自定义绘画之前真正调用 super.paintComponent
然后继续阅读 Painting in AWT and Swing and Performing Custom Painting 以更好地理解 Swing 中的绘画工作原理。 repaint
不直接调用 paintComponent
,它要求 RepaintManager
在事件队列中安排一个 paint
事件,该事件在未来的某个时间点由事件调度线程,然后根据容器
paint
事件
So I thought that since JFrame and JComponent both get paintComponent
不,他们没有。 JFrame
(及其父级 class)没有 paintComponent
方法
may be I can extend Jframe to create MyDrawPanel instead of Jpanel and it should work fine"
不,你不应该,除了 JFrame
没有 paintComponent
,还有很多事情会干扰你可能尝试在 JFrame
并且您应该继续按原样构建代码