[英]what is Alternative of Paint and repaint function?
在Java中是否有任何可以用paint()
和repaint()
替換的函數。
我有一個場景。
有一個三角形(三角形1) 。 當用戶單擊三角形時,將出現另一個三角形(三角形2),並且第一個(三角形1)將從屏幕上刪除。 (使用JFrame
, paint()
和repaint()
編碼)
到目前為止,我已經做到了。 但是問題是當我使用鼠標最小化或更改窗口的大小作為輸出窗口時,它只是再次繪制了Triangle 1而不是Triangle 2 。 或者如果我調用g2d.clearRect(0, 0, 1000, 1000);
則清除整個屏幕
triangle.reset();g2d.clearRect(0, 0, 1000, 1000);
triangle.reset();g2d.clearRect(0, 0, 1000, 1000);
triangle.reset();
注意:這兩個功能都將刪除先前的三角形(三角形1)。
是否有任何功能不應在最小化或更改窗口大小時更改狀態?
或者我們可以根據情況重寫repaint()
或任何有幫助的內容。
這是工作代碼。 執行它,單擊三角形,然后最小化並再次查看。 您將更清楚地了解問題。
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class Triangle_shape extends JFrame implements ActionListener {
public static JButton btnSubmit = new JButton("Submit");
public Triangle_shape() {
}
public static void main(String[] args) {
JFrame frame = new JFrame();
frame.setExtendedState(JFrame.MAXIMIZED_BOTH);
frame.setLayout(new BorderLayout());
frame.add(new TrianglePanel(), BorderLayout.CENTER);
frame.add(btnSubmit, BorderLayout.PAGE_END);
frame.pack();
frame.repaint();
frame.setTitle("A Test Frame");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setVisible(true);
}
@Override
public void actionPerformed(ActionEvent e) {
throw new UnsupportedOperationException("Not supported yet.");
}
public static class TrianglePanel extends JPanel implements MouseListener {
private Polygon triangle, triangle2;
public TrianglePanel() {
//Create triangle
triangle = new Polygon();
triangle.addPoint(400, 550); //left
triangle.addPoint(600, 550); //right
triangle.addPoint(500, 350); //top
//Add mouse Listener
addMouseListener(this);
//Set size to make sure that the whole triangle is shown
setPreferredSize(new Dimension(300, 300));
}
/**
* Draws the triangle as this frame's painting
*/
@Override
public void paintComponent(Graphics g) {
Graphics2D g2d = (Graphics2D) g;
g2d.draw(triangle);
}
//Required methods for MouseListener, though the only one you care about is click
public void mousePressed(MouseEvent e) {
}
public void mouseReleased(MouseEvent e) {
}
public void mouseEntered(MouseEvent e) {
}
public void mouseExited(MouseEvent e) {
}
/**
* Called whenever the mouse clicks. Could be replaced with setting the
* value of a JLabel, etc.
*/
public void mouseClicked(MouseEvent e) {
Graphics2D g2d = (Graphics2D) this.getGraphics();
Point p = e.getPoint();
if (triangle.contains(p)) {
System.out.println("1");
g2d.clearRect(0, 0, 1000, 1000);
triangle.reset();
g2d.setColor(Color.MAGENTA);
triangle2 = new Polygon();
triangle2.addPoint(600, 550); // left
triangle2.addPoint(700, 350); //top
triangle2.addPoint(800, 550); //right
g2d.draw(triangle2);
} else {
System.out.println("Triangle dont have point");
}
}
}
}
paint()
和repaint()
可以正常工作,但是由於要使用它們,因此您不使用它們。 窗口系統不會保留組件外觀的持久圖像。 它希望您的組件能夠按需重新繪制其整個外觀(例如,當調整窗口大小或最小化窗口時)。
如果使用getGraphics()
捕獲Graphics對象並在組件上繪制某些東西,則當/當需要重新繪制整個組件時,繪制的內容確實會丟失。 因此,您不應這樣做,而應確保您的paintComponent
方法具有完全重新繪制組件所需的所有信息。
如果一次只希望在屏幕上顯示一個三角形,則不要創建單獨的變量triangle2
。 只需按如下所示更改鼠標單擊處理程序來替換一個三角形即可:
public void mouseClicked(MouseEvent e) {
Point p = e.getPoint();
if (triangle.contains(p)) {
triangle = new Polygon();
triangle.addPoint(600, 550); // left
triangle.addPoint(700, 350); //top
triangle.addPoint(800, 550); //right
repaint();
} else {
System.out.println("Point not in triangle");
}
}
您的paintComponent
方法應調用super.paintComponent
以確保繪制背景,但否則無需更改它:
@Override
public void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D)g;
g2d.draw(triangle);
}
或者,如果嘗試在屏幕上保留多個三角形,例如,每次單擊都添加一個新的三角形,則應將它們添加到形狀列表中,以便在需要重新粉刷組件時繪制該形狀:
private final List<Shape> shapes = new ArrayList<>();
@Override
public void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D)g;
for (Shape s : shapes)
g2d.draw(s);
}
然后,要控制屏幕上顯示的一組形狀,操縱列表的內容,並調用repaint();
。
例如,要在屏幕上添加新形狀:
Polygon triangle = new Polygon();
triangle.addPoint(200, 300);
triangle.addPoint(200, 200);
triangle.addPoint(300, 200);
shapes.add(triangle);
repaint();
要從屏幕上刪除所有形狀:
shapes.clear();
repaint();
您還應確保在程序啟動時切換到Swing線程,因為從主線程與Swing組件進行交互並不安全。 在main
:
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
@Override
public void run() {
JFrame frame = new JFrame();
.
.
.
frame.setVisible(true);
}
});
}
您的mouseClicked
方法不應創建新的Triangle對象。 重置triangle
只需向其添加新點即可。 也不要使用此方法繪制,而是調用repaint
:
public void mouseClicked(MouseEvent e) {
Point p = e.getPoint();
if (triangle.contains(p)) {
System.out.println("1");
triangle.reset(); // change the current triangle
triangle.addPoint(600, 550); // new left
triangle.addPoint(700, 350); // new top
triangle.addPoint(800, 550); // new right
repaint(); // force repainting
} else {
System.out.println("Triangle dont have point");
}
}
現在,如果您想要許多三角形,則應該有一個Polygon
的集合。 像這樣 :
public static class TrianglePanel extends JPanel implements MouseListener {
private Vector<Polygon> triangles;
public TrianglePanel() {
n = 0;
// Create an empty collection
triangles = new Vector<Polygon>();
//Create first triangle
Polygon triangle = new Polygon();
triangle.addPoint(400, 550); //left
triangle.addPoint(600, 550); //right
triangle.addPoint(500, 350); //top
// Add the triangle to the collection
triangles.add(triangle);
//Add mouse Listener
addMouseListener(this);
//Set size to make sure that the whole triangle is shown
setPreferredSize(new Dimension(300, 300));
}
/**
* Draws the triangles as this frame's painting
*/
@Override
public void paintComponent(Graphics g) {
Graphics2D g2d = (Graphics2D) g;
for (Polygon p : triangles) // Draw all triangles in the collection
g2d.draw(p);
}
//Required methods for MouseListener, though the only one you care about is click
public void mousePressed(MouseEvent e) {}
public void mouseReleased(MouseEvent e) {}
public void mouseEntered(MouseEvent e) {}
public void mouseExited(MouseEvent e) {}
/**
* Called whenever the mouse clicks. Could be replaced with setting the
* value of a JLabel, etc.
*/
public void mouseClicked(MouseEvent e) {
Graphics2D g2d = (Graphics2D) this.getGraphics();
Point p = e.getPoint();
// Do what you want with p and the collection
// For example : remove all triangles that contain the point p
ListIterator<Polygon> li = triangles.listIterator();
while (li.hasNext()) {
if (li.next().contains℗) li.remove();
}
// Do what you want to update the list
// For example: Add a new triangle...
Polygon triangle = new Polygon();
triangle.addPoint(600+n, 550); // left
triangle.addPoint(700+n, 350); //top
triangle.addPoint(800+n, 550); //right
triangles.add(triangle); // add the new triangle to the list
n += 10; // next new triangle will be "moved" right
repaint();
}
private int n;
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.