Hri*_*tov 2 java graphics swing awt
所以,我正在JPanel使用一个对象绘制图形Grahics2D.当我的图形大于窗口时,
将JPanel其放置在a JScrollPane中.
但在我绘制图形之后,其JPanel尺寸不会改变,我无法滚动查看图形的其余部分,因此我找到了最低点和最左点,并在绘制图形的方法中手动设置尺寸(方法称为drawTrack()).
当我切换窗口或做其他事,使的JPanel可以重画,我的图形消失,所以我重写paint(),repaint(),validate(),invalidate()方法和在那里我调用drawTrack()汲取重绘JPanel的每一种可能的情况下,我的图形方法.
问题是当JPanel调用其中一个方法进行重绘我调用drawTrack()它们时,重绘我的图形后手动设置大小,以便我可以滚动JScrollPane并查看我的整个图形.但是当我setSize()在JPanel上调用方法使其再次重绘时,这意味着要调用drawTrack()等等.
出现滚动条是因为大小正确但它会创建一个无限循环,一遍又一遍地重绘我的图形.如果我没有调用setSize()方法,我JPanel会获得默认大小,因此它可以放在JScrollPane视口中,因此我无法滚动它来查看我的图形.
有什么建议?
当您调整JPanel的大小时,您会激活重绘,因此如果您在paint或paintComponent方法中更改大小或在这些方法中调用的方法中更改大小,那么我有可能导致无限循环.
解决方案:不要在paint或paintComponent方法中调整任何大小.那种方法只适用于绘画而不是其他任何东西.相反,如果要设置JPanel的大小,请覆盖其getPreferredSize()方法.
这是一个"丰富多彩"的例子:
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
@SuppressWarnings("serial")
public class ImageReSize extends JPanel {
private static final int INIT_WIDTH = 400;
private static final int MAX_WIDTH = 1200;
private static final int TIMER_DELAY = 20;
protected static final int WIDTH_STEP = 5;
private int width = INIT_WIDTH;
private int height = INIT_WIDTH;
private boolean growing = true;
public ImageReSize() {
new Timer(TIMER_DELAY, new ActionListener() {
public void actionPerformed(ActionEvent e) {
if (growing && width < MAX_WIDTH) {
width += WIDTH_STEP;
height += WIDTH_STEP;
} else {
growing = false;
}
if (!growing && width > INIT_WIDTH) {
width -= WIDTH_STEP;
height -= WIDTH_STEP;
} else {
growing = true;
}
// get the parent container which is the scrollpane's viewport
JComponent parent = (JComponent)getParent();
parent.revalidate(); // let it relayout the changed size JPanel
parent.repaint(); // and repaint all
}
}).start();
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2 = (Graphics2D)g;
float x = (float)width / 10;
float y = (float)height / 10;
g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
g2.setPaint(new GradientPaint(x, 0, Color.green, 0, y, Color.black, true));
g2.fillRect(0, 0, getWidth(), getHeight());
g2.setPaint(new GradientPaint(0, 0, Color.blue, x, y, Color.red, true));
g2.fillOval(0, 0, width, height);
}
@Override
public Dimension getPreferredSize() {
return new Dimension(width, height);
}
private static void createAndShowUI() {
ImageReSize imageReSize = new ImageReSize();
JFrame frame = new JFrame("ImageReSize");
frame.getContentPane().add(new JScrollPane(imageReSize));
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
public static void main(String[] args) {
java.awt.EventQueue.invokeLater(new Runnable() {
public void run() {
createAndShowUI();
}
});
}
}
Run Code Online (Sandbox Code Playgroud)