import java.awt.*;
import java.awt.event.*;

import javax.swing.*;

import java.util.ArrayList;

@SuppressWarnings("serial")
 public class GUI extends JFrame implements ActionListener, MouseListener {

    private boolean drawLine = false;
    private boolean drawRec = false;
    private boolean drawOval = false;
    private final JButton line;
    private final JButton oval;
    private final JButton rectangle;
    private final JPanel buttonPanel;
    public DrawStuff drawPanel = new DrawStuff();
    public int x1;
    public int x2;
    public int y1;
    public int y2;
    public int click;


     public GUI() {
        super("Graphics IO");
        this.click = 1;
        setSize(600, 600);
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        buttonPanel = new JPanel();
        buttonPanel.setLayout(new GridLayout(1, 3));

        line = new JButton("Line");
        line.addActionListener(this);
        buttonPanel.add(line);

        oval = new JButton("Oval");
        oval.addActionListener(this);
        buttonPanel.add(oval);

        rectangle = new JButton("Rectangle");
        rectangle.addActionListener(this);
        buttonPanel.add(rectangle);

        Container contentPane = this.getContentPane();
        contentPane.add(buttonPanel, BorderLayout.SOUTH);
        //add(drawPanel);
        addMouseListener((MouseListener) this);

        setVisible(true);
    }

    @Override
    public void actionPerformed(ActionEvent event) {
        Object source = event.getSource();

        if (source == line) {
            drawLine = true;
            repaint();
        } else if (source == oval) {

            drawOval = true;
            repaint();
        } else if (source == rectangle) {
            drawRec = true;
            repaint();
        }
    }

    public static void main(String[] args) {
        GUI guiIO = new GUI();

    }

    class DrawStuff extends JPanel {

        @Override
        public void paintComponent(Graphics g) {
            super.paintComponent(g);
            this.setBackground(Color.BLUE);
            ArrayList<Shape> shapes = new ArrayList<>();

            if (drawLine) {
                drawLine = false;
            } else if (drawOval) {
                //no clue how to add an oval
                drawOval = false;
            } else if (drawRec) {
                Rectangle rec = new Rectangle(x1, y1,Math.abs(x2-x1) , Math.abs(y2-y1));
                shapes.add(rec);
                drawRec = false;
            }
            Graphics2D j = (Graphics2D)g;
            shapes.stream().map((s) -> {
                ((Graphics2D) j).draw((Shape) s);
                return s;
            }).forEach((_item) -> {
                repaint();
            });

    }
    }

    @Override
    public void mousePressed(MouseEvent me) {

        if (click == 1){
            x1 = me.getX();
            y1 = me.getY();
            System.out.println(x1);
            System.out.println(y1);
            click = 2;

        }else if (click == 2) {
            x2 = me.getX();
            y2 = me.getY();
            System.out.println(x2);
            System.out.println(y2);
            click = 1;
        }


}
    @Override
    public void mouseReleased(MouseEvent e) {

    }
    @Override
    public void mouseEntered(MouseEvent e) {

    }
    @Override
    public void mouseExited(MouseEvent e) {

    }
    @Override
    public void mouseClicked(MouseEvent e) {

    }


    }


好的,所以我必须制作一个程序来使用两次鼠标单击来创建形状,然后才能导出/导入它们。我正在尝试为此使用arraylist,但是我很难尝试使其工作。 im创建的矩形将不会显示在面板上。我究竟做错了什么?请帮我。

最佳答案

让我们从一个事实开始,即实际上没有将DrawStuff添加到任何能够绘画它的东西中。

DrawStuff#paintComponent应该做出有关更新shapes List状态的决定,相反,您的ActionListenerMouseListener应该做出这些决定(要添加的内容,要修改的内容和内容),而面板应该只绘制DrawStuff列表中的内容

您也不应该在Shape内修改组件的状态,例如paintComponent可能会设置重复的重绘请求,如果不是PC则会破坏应用程序

修改setBackground,使其具有自己的DrawStuff和允许您的MouseListener要求其创建新形状的方法。将GUI shapes设置为实例字段,以便可以更轻松地在List内部进行管理

就像是...

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Container;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.GridLayout;
import java.awt.Point;
import java.awt.Shape;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.geom.Ellipse2D;
import java.awt.geom.Line2D;
import java.awt.geom.Rectangle2D;
import java.util.ArrayList;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;

public class GUI extends JFrame implements ActionListener {

    private boolean drawLine = false;
    private boolean drawRec = false;
    private boolean drawOval = false;
    private final JButton line;
    private final JButton oval;
    private final JButton rectangle;
    private final JPanel buttonPanel;
    public DrawStuff drawPanel = new DrawStuff();
    public int x1;
    public int x2;
    public int y1;
    public int y2;
    public int click;

    public GUI() {
        super("Graphics IO");
        this.click = 1;
        setSize(600, 600);
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        buttonPanel = new JPanel();
        buttonPanel.setLayout(new GridLayout(1, 3));

        line = new JButton("Line");
        line.addActionListener(this);
        buttonPanel.add(line);

        oval = new JButton("Oval");
        oval.addActionListener(this);
        buttonPanel.add(oval);

        rectangle = new JButton("Rectangle");
        rectangle.addActionListener(this);
        buttonPanel.add(rectangle);

        Container contentPane = this.getContentPane();
        contentPane.add(buttonPanel, BorderLayout.SOUTH);
        add(drawPanel);

        setVisible(true);
    }

    @Override
    public void actionPerformed(ActionEvent event) {
        Object source = event.getSource();

        if (source == line) {
            drawPanel.setDrawShape(DrawStuff.DrawShape.LINE);
        } else if (source == oval) {
            drawPanel.setDrawShape(DrawStuff.DrawShape.OVAL);
        } else if (source == rectangle) {
            drawPanel.setDrawShape(DrawStuff.DrawShape.RECTANGLE);
        }
    }

    public static void main(String[] args) {
        EventQueue.invokeLater(new Runnable() {
            @Override
            public void run() {
                try {
                    UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
                    ex.printStackTrace();
                }

                GUI guiIO = new GUI();
            }
        });
    }

    public static class DrawStuff extends JPanel {

        public enum DrawShape {

            LINE, OVAL, RECTANGLE;
        }

        private ArrayList<Shape> shapes = new ArrayList<>();
        private DrawShape drawShape = DrawShape.LINE;
        private Shape currentShape;

        public DrawStuff() {
            setBackground(Color.BLUE);

            MouseAdapter ma = new MouseAdapter() {
                private Point clickPoint;

                @Override
                public void mousePressed(MouseEvent e) {
                    clickPoint = e.getPoint();
                    currentShape = null;
                }

                @Override
                public void mouseReleased(MouseEvent e) {
                    if (currentShape != null) {
                        shapes.add(currentShape);
                        currentShape = null;
                        repaint();
                    }
                }

                @Override
                public void mouseDragged(MouseEvent e) {
                    Point p = e.getPoint();
                    switch (getDrawShape()) {
                        case LINE:
                            currentShape = new Line2D.Double(clickPoint, e.getPoint());
                            break;
                        case OVAL:
                        case RECTANGLE:
                            int x = clickPoint.x;
                            int y = clickPoint.y;
                            int width = p.x - clickPoint.x;
                            int height = p.y - clickPoint.y;

                            if (width < 0) {
                                x = p.x;
                                width *= -1;
                            }
                            if (height < 0) {
                                y = p.y;
                                height *= -1;
                            }
                            switch (getDrawShape()) {
                                case OVAL:
                                    currentShape = new Ellipse2D.Double(x, y, width, height);
                                    break;
                                case RECTANGLE:
                                    currentShape = new Rectangle2D.Double(x, y, width, height);
                                    break;
                            }
                            break;
                    }

                    repaint();
                }

            };

            addMouseListener(ma);
            addMouseMotionListener(ma);
        }

        public DrawShape getDrawShape() {
            return drawShape;
        }

        public void setDrawShape(DrawShape drawShape) {
            this.drawShape = drawShape;
            currentShape = null;
            repaint();
        }

        @Override
        public void paintComponent(Graphics g) {
            super.paintComponent(g);
            Graphics2D g2d = (Graphics2D) g.create();
            g2d.setColor(Color.BLACK);

            for (Shape shape : shapes) {
                g2d.draw(shape);
            }

            if (currentShape != null) {

                g2d.setColor(Color.RED);
                g2d.draw(currentShape);

            }

        }
    }

}


例如。您总是需要问自己“谁负责做什么”。在这种情况下,DrawStuff面板实际上负责确定绘制了“何处”的内容,但是它需要有关“内容”的更多信息,然后可以基于该信息执行实际操作。

08-04 00:39