【问题标题】:How to draw shape by right clicking a panel in Swing?如何通过右键单击 Swing 中的面板来绘制形状?
【发布时间】:2012-09-04 08:56:10
【问题描述】:

我正在尝试创建一个摇摆程序。在我的程序中,我想实现这样的事情:右键单击面板并选择菜单“绘制矩形”,程序应该在面板上绘制一个非常简单的矩形。这是我的代码:

import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import javax.swing.border.BevelBorder;

public class MainWindow extends JFrame {

    JFrame frame = null;
    AboutDialog aboutDialog = null;
    JLabel statusLabel = null;    //label on statusPanel

    public MainWindow() {
        frame = new JFrame("Project");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        //MENUS
        JMenuBar menuBar = new JMenuBar();                //menubar
        JMenu menuDosya = new JMenu("Dosya");           //menus on menubar
        JMenu menuYardim = new JMenu("Yardım");               //menus in menus
        menuBar.add(menuDosya);
        menuBar.add(menuYardim);
        JMenuItem menuItemCikis = new JMenuItem("Çıkış", KeyEvent.VK_Q);        //dosya menus
        menuItemCikis.addActionListener(new ActionListener() {

            public void actionPerformed(ActionEvent event) {
                System.exit(0);
            }
        });
        menuDosya.add(menuItemCikis);
        JMenuItem menuItemYardim = new JMenuItem("Hakkında", KeyEvent.VK_H);      //hakkinda menus
        menuItemYardim.addActionListener(new ActionListener() {

            public void actionPerformed(ActionEvent event) {
                JDialog f = new AboutDialog(new JFrame());
                f.show();
            }
        });
        menuYardim.add(menuItemYardim);
        frame.setJMenuBar(menuBar);
        //TOOLBAR
        JToolBar toolbar = new JToolBar();
        JButton exitButton = new JButton("Kapat");
        toolbar.add(exitButton);
        //STATUSBAR
        JPanel statusPanel = new JPanel();
        statusPanel.setBorder(new BevelBorder(BevelBorder.LOWERED));
        frame.add(statusPanel, BorderLayout.SOUTH);
        statusPanel.setPreferredSize(new Dimension(frame.getWidth(), 20));
        statusPanel.setLayout(new BoxLayout(statusPanel, BoxLayout.X_AXIS));
        statusLabel = new JLabel("Ready.");
        statusLabel.setHorizontalAlignment(SwingConstants.LEFT);
        statusPanel.add(statusLabel);
        //MAIN CONTENT OF THE PROGRAM
        final JPanel mainContentPanel = new JPanel();
        //RIGHT CLICK MENU
        final JPopupMenu menuSag = new JPopupMenu("RightClickMenu");
        JMenuItem menuRightClickRectangle = new JMenuItem("draw rectangle");
        menuRightClickRectangle.addActionListener(new ActionListener() {

            public void actionPerformed(ActionEvent event) {
                //CircleShape cs=new CircleShape();
                mainContentPanel.add(new CircleShape()); //trying to draw.

                mainContentPanel.repaint();
                //mainContentPanel.repaint();     boyle olacak.
            }
        });
        JMenuItem menuRightClickCircle = new JMenuItem("Daire çiz");
        menuSag.add(menuRightClickRectangle);
        menuSag.add(menuRightClickCircle);
        mainContentPanel.addMouseListener(new MouseAdapter() {

            public void mouseReleased(MouseEvent e) {
                if (e.getButton() == MouseEvent.BUTTON3) {
                    menuSag.show(e.getComponent(), e.getX(), e.getY());
                    statusLabel.setText("X=" + e.getX() + "  " + "Y=" + e.getY());


                }
            }
        });
        JButton west = new JButton("West");
        JButton center = new JButton("Center");
        JPanel content = new JPanel();   //framein icindeki genel panel. en genel panel bu.
        content.setLayout(new BorderLayout());
        content.add(toolbar, BorderLayout.NORTH);
        content.add(statusPanel, BorderLayout.SOUTH);
        content.add(west, BorderLayout.WEST);
        content.add(mainContentPanel, BorderLayout.CENTER);
        frame.setContentPane(content);
        frame.setPreferredSize(new Dimension(400, 300));
        frame.setLocationRelativeTo(null);
        frame.pack();
        frame.setVisible(true);
    }
}

问题是面板上没有绘制任何内容。我猜程序中有一个事件丢失,但我不知道如何解决这个问题。

【问题讨论】:

标签: java swing user-interface jpanel jcomponent


【解决方案1】:

请按以下方式修改代码。像这样添加一个新类:

  class MainPanel extends JPanel {

    private List<Rectangle> rectangles = new ArrayList<Rectangle>();

    private void addRectangle(Rectangle rectangle) {
      rectangles.add(rectangle);
    }

    public void paintComponent(Graphics g) {
      super.paintComponent(g);
      Graphics2D g2 = (Graphics2D) g;
      for (Rectangle rectangle : rectangles) {
        g2.drawRect(rectangle.x, rectangle.y, rectangle.width, rectangle.height);
      }
    }

  }

然后,而不是

final JPanel mainContentPanel = new JPanel();

你应该这样做:

final MainPanel mainContentPanel = new MainPanel();

菜单项的动作监听器变成这样:

menuRightClickRectangle.addActionListener(new ActionListener() {
  public void actionPerformed(ActionEvent event) {
    // TODO: add your own logic here, currently a hardcoded rectangle
    mainContentPanel.addRectangle(new Rectangle(10, 10, 100, 50));
    mainContentPanel.repaint();
  }
});

【讨论】:

    【解决方案2】:

    您不能通过调用add 方法来做到这一点。要绘制形状,您必须覆盖paintComponent 方法:

    绘制矩形示例:

    public void paintComponent(Graphics g){
        g.setColor(Color.RED);
        g.fillRect(50,50,50,50);
    }
    

    【讨论】:

    • 在小程序上更容易,但它们很慢不是吗? Ant awt 项目与摆动元素重叠
    • @tuğrulbüyükışık 你这是什么意思?
    • 我的意思是你只是声明一个图像变量(缓冲)然后重载paint()或者不重载paint而只使用repaint()。但它很慢
    • @tuğrulbüyükışık 它是一个基本形状,没有任何图像。
    【解决方案3】:

    嗯,为你做了一个简短的例子:

    Test.java:

    import java.awt.Dimension;
    import java.awt.Graphics;
    import java.awt.Graphics2D;
    import java.awt.Rectangle;
    import java.awt.event.ActionEvent;
    import java.awt.event.ActionListener;
    import java.awt.event.MouseEvent;
    import java.awt.event.MouseListener;
    import java.util.ArrayList;
    import java.util.List;
    import javax.swing.*;
    
    public class Test {
    
        private final JFrame frame = new JFrame();
        private final MyPanel panel = new MyPanel();
    
        private void createAndShowUI() {
            frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            frame.setResizable(false);
            frame.add(panel);
            frame.pack();
            frame.setVisible(true);
        }
    
        public static void main(String[] args) {
            SwingUtilities.invokeLater(new Runnable() {
    
                @Override
                public void run() {
                    new Test().createAndShowUI();
                }
            });
        }
    }
    

    MyPanel.java:

    class MyPanel extends JPanel {
    
        private final JPopupMenu popupMenu = new JPopupMenu();
        private final JMenuItem drawRectJMenu = new JMenuItem("Draw Rectangle here");
        private int x = 0, y = 0;
        private List<Rectangle> recs = new ArrayList<>();
    
        public MyPanel() {
            initComponents();
        }
    
        private void initComponents() {
            setBounds(0, 0, 600, 600);
            setPreferredSize(new Dimension(600, 600));
            popupMenu.add(drawRectJMenu);
            add(popupMenu);
            addMouseListener(new MouseListener() {
    
                @Override
                public void mouseClicked(MouseEvent e) {
                    checkForTriggerEvent(e);
                }
    
                @Override
                public void mouseEntered(MouseEvent e) {
                }
    
                @Override
                public void mouseExited(MouseEvent e) {
                }
    
                @Override
                public void mousePressed(MouseEvent e) {
                }
    
                @Override
                public void mouseReleased(MouseEvent e) {
                }
    
                private void checkForTriggerEvent(MouseEvent e) {
                    if (e.getButton() == MouseEvent.BUTTON3) {
                        x = e.getX();
                        y = e.getY();
                        popupMenu.show(e.getComponent(), x,y);
                    }
                }
            });
            drawRectJMenu.addActionListener(new ActionListener() {
    
                @Override
                public void actionPerformed(ActionEvent e) {
                    addRec(new Rectangle(x, y, 100, 100));
                    repaint();
                }
            });
        }
    
        public void addRec(Rectangle rec) {
            recs.add(rec);
        }
    
        @Override
        public void paintComponent(Graphics g) {
            super.paintComponent(g);
    
            Graphics2D g2d = (Graphics2D) g;
    
            for (Rectangle rec : recs) {
                g2d.drawRect(rec.x, rec.y, rec.width, rec.height);
            }
        }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2021-07-23
      • 1970-01-01
      • 1970-01-01
      • 2014-04-02
      • 1970-01-01
      • 1970-01-01
      • 2021-08-10
      相关资源
      最近更新 更多