ICode9

精准搜索请尝试: 精确搜索
首页 > 编程语言> 文章详细

Java绘画问题

2019-05-29 21:49:59  阅读:239  来源: 互联网

标签:java user-interface swing graphics paint


好吧,我一直在搜索和谷歌搜索多年,它正在推动我MAD. (请记住,这是从大学开始的代码).

任何帮助都将受到大力赞赏!因为我在java图形方面似乎有一个心理障碍:(.

问题是标记图像,但是由于各种原因我有一半图像丢失的问题,除非我在框架周围移动然后它回来.同样,如果我尝试删除BufferedImage上绘制的’标签’,我必须在Jframe周围移动才能看到结果.

最后,当JOptionPane弹出以询问标签名称时,它会在关闭时执行此操作:

获取图片发布
https://docs.google.com/document/d/1I5rFH23a75IHB6twTu1dPRwmRt-By1sIUvDvI6FE_OY/edit

    package hci;

import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

/**
 * Deals with the label tools
 */
public class LabelToolGUI extends JPanel implements ActionListener {

        JButton newButton = new JButton("New");
        JButton deleteButton = new JButton("Delete");
        JButton editButton = new JButton("Edit");
        JButton undoButton = new JButton("Undo");
        JComboBox labelsBox = new JComboBox();

    String saveIcon = "./images/icons/save.jpg";
    String deleteIcon = "./images/icons/delete.jpg";
    String openIcon = "./images/icons/open.jpg";
    String newIcon = "./images/icons/new.jpg";
    String helpIcon = "./images/icons/help.jpg";
    String labelsIcon = "./images/icons/help.jpg";
    String fname = "";
    String fnameURL = "";

    public LabelToolGUI() {
        super();
        newButton.addActionListener(this);
        deleteButton.addActionListener(this);
        editButton.addActionListener(this);
        undoButton.addActionListener(this);

        setLayout(new BorderLayout());
        setBorder(BorderFactory.createTitledBorder("Label tools"));

        add(newButton, BorderLayout.WEST);
        add(deleteButton, BorderLayout.EAST);
        add(editButton, BorderLayout.CENTER);
        add(labelsBox, BorderLayout.NORTH);
        add(undoButton, BorderLayout.SOUTH);
    }

    @Override
    public void actionPerformed(ActionEvent e) {
        Object src = e.getSource();
        if(src == newButton) {
            String labelName = JOptionPane.showInputDialog("Please input a value");
            ImageLabeller.addNewPolygon(labelName);
            labelsBox.addItem(labelName);
        } else if(src == deleteButton) {
            String toDelete = labelsBox.getSelectedItem().toString();
            System.out.println("Deleting " + toDelete);
            labelsBox.removeItem(labelsBox.getSelectedItem());
            ImageLabeller.removeLabel(toDelete);
        } else if(src == undoButton) {
            ImageLabeller.undo();
            ImageLabeller.imagePanel.repaint();
        }
    }
}
package hci;

import javax.swing.*;

import java.awt.Graphics;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;

/**
 * Main class of the program - handles display of the main window
 * @author Michal
 *
 */
public class ImageLabeller extends JFrame implements ActionListener {
    /**
     * some java stuff to get rid of warnings
     */
    private static final long serialVersionUID = 1L;

    /**
     * main window panel
     */
    JPanel appPanel = null;

    /**
     * toolbox - put all buttons and stuff here!
     */
    JPanel toolboxPanel = null;


    /**
     * image panel - displays image and editing area
     */
    static ImagePanel imagePanel = null;

    /**
     * handles New Object button action
     */
    public static void addNewPolygon(String labelName) {
        imagePanel.addNewPolygon(labelName);
    }

    public static void removeLabel(String labelName) {
        LabelHandler.deleteLabel(labelName);
    }

    /**
     * Removes last point added to the label.
     */
    public static void undo() {
        imagePanel.currentLabel.removeLast();
    }

    /*@Override
    public void paint(Graphics g) {
        super.paint(g);
        imagePanel.paint(g); //update image panel
    }  */

    /**
     * sets up application window
     * @param imageFilename image to be loaded for editing
     * @throws Exception
     */
    public void setupGUI(String imageFilename) throws Exception {
        this.addWindowListener(new WindowAdapter() {
            public void windowClosing(WindowEvent event) {
                //here we exit the program (maybe we should ask if the user really wants to do it?)
                //maybe we also want to store the polygons somewhere? and read them next time
                System.out.println("Bye bye!");
                System.exit(0);
            }
        });

        //setup main window panel
        appPanel = new JPanel();
        this.setLayout(new BoxLayout(appPanel, BoxLayout.X_AXIS));
        this.setContentPane(appPanel);

        //Create and set up the image panel.
        imagePanel = new ImagePanel(imageFilename);
        imagePanel.setOpaque(true); //content panes must be opaque

            appPanel.add(imagePanel);

        //add toolbox to window
        appPanel.add(new LabelToolGUI());

        //display all the stuff
        this.pack();
            this.setVisible(true);
    }


    /**
     * Runs the program
     * @param argv path to an image
     */
    public static void main(String argv[]) {
        try {
            //create a window and display the image
            ImageLabeller window = new ImageLabeller();
            window.setupGUI(argv[0]);
        } catch (Exception e) {
            System.err.println("Image: " + argv[0]);
            e.printStackTrace();
        }
    }

    @Override
    public void actionPerformed(ActionEvent e) {
        System.out.println("Action clicked");
        imagePanel.paint(imagePanel.getGraphics());
    }
}
package hci;

import javax.imageio.ImageIO;
import javax.swing.JPanel;

import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.image.BufferedImage;
import java.io.File;
import java.util.ArrayList;

import hci.utils.*;

/**
 * Handles image editing panel
 * @author Michal
 *
 */
public class ImagePanel extends JPanel implements MouseListener {
    /**
     * some java stuff to get rid of warnings
     */
    private static final long serialVersionUID = 1L;

    /**
     * image to be tagged
     */
    BufferedImage image = null;

    /**
     * list of current polygon's vertices 
     */
    Label currentLabel = null;

    /**
     * default constructor, sets up the window properties
     */
    public ImagePanel() {
        currentLabel = new Label();

        this.setVisible(true);

        Dimension panelSize = new Dimension(800, 600);
        this.setSize(panelSize);
        this.setMinimumSize(panelSize);
        this.setPreferredSize(panelSize);
        this.setMaximumSize(panelSize);

        addMouseListener(this);
    }

    /**
     * extended constructor - loads image to be labelled
     * @param imageName - path to image
     * @throws Exception if error loading the image
     */
    public ImagePanel(String imageName) throws Exception{
        this();
        image = ImageIO.read(new File(imageName));
        if (image.getWidth() > 800 || image.getHeight() > 600) {
            int newWidth = image.getWidth() > 800 ? 800 : (image.getWidth() * 600)/image.getHeight();
            int newHeight = image.getHeight() > 600 ? 600 : (image.getHeight() * 800)/image.getWidth();
            System.out.println("SCALING TO " + newWidth + "x" + newHeight );
            Image scaledImage = image.getScaledInstance(newWidth, newHeight, Image.SCALE_FAST);
            image = new BufferedImage(newWidth, newHeight, BufferedImage.TYPE_INT_RGB);
            image.getGraphics().drawImage(scaledImage, 0, 0, this);
        }
    }

    /**
     * Displays the image
     */
    public void ShowImage() {
        Graphics g = this.getGraphics();

        if (image != null) {
            g.drawImage(image, 0, 0, null);
        }
    }

    public void paintComponent(Graphics g) {
        super.paintComponent(g);

        //display iamge
        ShowImage();

        //display all the completed polygons
        for(Label l : LabelHandler.labels) {
            drawLabel(l);
            finishPolygon(l);
        }

        //display current polygon
        drawLabel(currentLabel);
    }

    /**
     * displays a polygon without last stroke
     * @param l label to be displayed
     */
    public void drawLabel(Label l) {
        Graphics2D g = (Graphics2D)this.getGraphics();
        g.setColor(Color.GREEN);
        for(int i = 0; i < l.size(); i++) {
            Point currentVertex = l.getPoint(i);
            if (i != 0) {
                Point prevVertex = l.getPoint(i - 1);
                g.drawLine(prevVertex.getX(), prevVertex.getY(), currentVertex.getX(), currentVertex.getY());
            }
            g.fillOval(currentVertex.getX() - 5, currentVertex.getY() - 5, 10, 10);
        }
    }

    /**
     * displays last stroke of the polygon (arch between the last and first vertices)
     * @param l label to be finished
     */
    public void finishPolygon(Label l) {
        //if there are less than 3 vertices than nothing to be completed
        if (l.size() >= 3) {
            Point firstVertex = l.getPoint(0);
            Point lastVertex = l.getPoint(l.size() - 1);

            Graphics2D g = (Graphics2D)this.getGraphics();
            g.setColor(Color.GREEN);
            g.drawLine(firstVertex.getX(), firstVertex.getY(), lastVertex.getX(), lastVertex.getY());
        }
    }

    /**
     * moves current polygon to the list of polygons and makes pace for a new one
     */
    public void addNewPolygon(String labelName) {
        //finish the current polygon if any
        if (currentLabel != null ) {
            finishPolygon(currentLabel);
            LabelHandler.addLabel(currentLabel);
        }

        currentLabel = new Label(labelName);
    }

    @Override
    public void mouseClicked(MouseEvent e) {
        int x = e.getX();
        int y = e.getY();

        //check if the cursos withing image area
        if (x > image.getWidth() || y > image.getHeight()) {
            //if not do nothing
            return;
        }

        Graphics2D g = (Graphics2D)this.getGraphics();

        //if the left button than we will add a vertex to poly
        if (e.getButton() == MouseEvent.BUTTON1) {
            g.setColor(Color.GREEN);
            if (currentLabel.size() != 0) {
                Point lastVertex = currentLabel.getPoint(currentLabel.size() - 1);
                g.drawLine(lastVertex.getX(), lastVertex.getY(), x, y);
            }
            g.fillOval(x-5,y-5,10,10);

            currentLabel.addPoint(new Point(x,y));
            System.out.println(x + " " + y);
        } 
    }

    @Override
    public void mouseEntered(MouseEvent arg0) {
    }

    @Override
    public void mouseExited(MouseEvent arg0) {
    }

    @Override
    public void mousePressed(MouseEvent arg0) {
    }

    @Override
    public void mouseReleased(MouseEvent arg0) {
    }

}

解决方法:

不要为绘画使用getGraphics(),因为它是临时缓冲区,在下次重绘时会被回收.你是否在paintComponent()中绘画并在需要时调用repaint().

也不要手动调用paint()(即:imagePanel.paint(imagePanel.getGraphics());)

有关更多信息,请参见Performing Custom Painting.另见Painting in AWT and Swing.

标签:java,user-interface,swing,graphics,paint
来源: https://codeday.me/bug/20190529/1181072.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有