1
我用Java編寫了一個簡單的繪圖程序,允許用戶在不同的形狀,大小和顏色之間進行選擇(在JMenuBar
中)並用鼠標繪製它們。在克服了許多與該程序有關的問題後(我最初編寫的代碼是AWT
,但確信要切換到Swing,所以請原諒任何可憐的Swing
編碼,因爲這是我第一次使用它),我還有一個問題需要解決。只要用戶在屏幕上繪製某些東西(默認情況下是帶有黑色邊框的紅色矩形),JMenuBar
就會在原來的JMenuBar
下重複。我認爲paintComponent緩衝屏幕的方式有些奇怪,但由於我以前從未使用過,所以我不知道它是如何工作的。繪圖程序重複JMenuBar
任何想法,我可以使它停止重複JMenuBar
?
import java.awt.*;
import java.awt.event.*;
import java.lang.*;
import javax.swing.*;
public class E3G04 extends JFrame implements WindowListener, ActionListener, MouseListener, MouseMotionListener
{
//Variables are declared as volatile to ensure that they're always called from system RAM
static volatile String type = "rectangle";
static volatile Boolean fill = true;
static Color lineColor = Color.BLACK;
static Color fillColor = Color.RED;
static int size = 1;
CanvasEX cx = new CanvasEX();
static boolean running = true;
JMenuBar mb = new JMenuBar();
JMenu fileMenu = new JMenu("File");
JMenuItem newItem = new JMenuItem("New");
JMenuItem quitItem = new JMenuItem ("Quit");
protected E3G04()
{
mb.add(fileMenu);
fileMenu.add(newItem);
fileMenu.add(quitItem);
newItem.setMnemonic('N');
quitItem.setMnemonic('Q');
newItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_N, ActionEvent.CTRL_MASK));
quitItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_Q, ActionEvent.CTRL_MASK));
newItem.addActionListener(this);
quitItem.addActionListener(this);
cx.setSize(800,600);
cx.addMouseListener(this);
cx.addMouseMotionListener(this);
setJMenuBar(mb);
setBounds(100,100,800,600);
setLayout(new BorderLayout());
add("Center",cx);
addWindowListener(this);
setResizable(true);
setVisible(true);
}
public static void main(String [] args)
{
new E3G04();
}
public void stop()
{
newItem.removeActionListener(this);
quitItem.removeActionListener(this);
dispose();
System.exit(0);
}
public void actionPerformed(ActionEvent e)
{
Object o = e.getSource();
if (o == newItem)
{
cx.erase = true;
cx.repaint();
}
if (o == quitItem)
{
running = false;
stop();
}
}
public void mousePressed(MouseEvent m)
{
cx.start = m.getPoint();
cx.end = cx.start;
cx.cur = cx.start;
}
public void mouseDragged(MouseEvent m)
{
cx.cur = m.getPoint();
}
public void mouseReleased(MouseEvent m)
{
cx.end = cx.cur;
cx.repaint();
}
public void itemStateChanged(ItemEvent e)
{
Object o = e.getSource();
}
public void windowClosing(WindowEvent e)
{
running = false;
stop();
}
public void mouseClicked(MouseEvent m){}
public void mouseExited(MouseEvent m){}
public void mouseEntered(MouseEvent m){}
public void mouseMoved(MouseEvent m){}
public void windowClosed(WindowEvent e){}
public void windowOpened(WindowEvent e){}
public void windowActivated(WindowEvent e){}
public void windowDeactivated(WindowEvent e){}
public void windowIconified(WindowEvent e){}
public void windowDeiconified(WindowEvent e){}
}
class CanvasEX extends JPanel
{
Point start = new Point(100,100);
Point cur = new Point(100,100);
Point end = new Point(100,100);
boolean erase = false;
public void paintComponent(Graphics g)
{
Graphics buffer = g;
if (erase)
{
g.dispose();
erase = false;
}
g.setColor(E3G04.lineColor);
if (end.x > start.x && end.y > start.y)
g.fillRect(start.x,start.y, Math.abs(end.x-start.x),Math.abs(end.y-start.y));
if (end.x > start.x && end.y < start.y)
g.fillRect(start.x,end.y, Math.abs(end.x-start.x),Math.abs(end.y-start.y));
if (end.x < start.x && end.y > start.y)
g.fillRect(end.x, start.y, Math.abs(end.x-start.x),Math.abs(end.y-start.y));
if (end.x < start.x && end.y < start.y)
g.fillRect(end.x, end.y, Math.abs(end.x-start.x),Math.abs(end.y-start.y));
g.setColor(E3G04.fillColor);
if (end.x > start.x && end.y > start.y)
g.fillRect(start.x + E3G04.size,start.y + E3G04.size, Math.abs(end.x-start.x) - 2 * E3G04.size,Math.abs(end.y-start.y) - 2 * E3G04.size);
if (end.x > start.x && end.y < start.y)
g.fillRect(start.x + E3G04.size,end.y + E3G04.size, Math.abs(end.x-start.x) - 2 * E3G04.size,Math.abs(end.y-start.y) - 2 * E3G04.size);
if (end.x < start.x && end.y > start.y)
g.fillRect(end.x + E3G04.size, start.y + E3G04.size, Math.abs(end.x-start.x) - 2 * E3G04.size,Math.abs(end.y-start.y) - 2 * E3G04.size);
if (end.x < start.x && end.y < start.y)
g.fillRect(end.x + E3G04.size, end.y + E3G04.size, Math.abs(end.x-start.x) - 2 * E3G04.size,Math.abs(end.y-start.y) - 2 * E3G04.size);
}
}
好吧,那固定的菜單欄在那裏的問題,但現在我的繪畫不是持久的。我如何解決這個問題? –
你需要像'ArrayList'這樣的東西來保存所有的'Rectanlges'來繪製,而在'paintComponent'中,你將遍歷數組列表並重繪每個'Rectangle',因此繪圖將會持久 –
儘管不是所有的矩形, 。沒有一種方法可以創建屏幕圖像(減去JMenubar),然後將該圖像繪製回屏幕上? –