简体   繁体   English

如何使用外部类中的类的Graphics对象

[英]How do i use the Graphics object of a class from an Outer class

I am learning the java awt and swing libs.In this program i am trying to emulate the pencil tool from MSPaint.It works fine when i do the programming in a single class,however,does not work when i use an Outer class to listen to my Mouse motions.My guess is that i am failing to get the Graphics object of application,please enlighten me on where i am going wrong.Thanks! 我正在学习java awt和swing libs。在此程序中,我试图从MSPaint模仿铅笔工具。当我在单个类中进行编程时,它工作正常,但是,当我使用外部类进行侦听时,它不起作用我的鼠标动作。我的猜测是我无法获取应用程序的Graphics对象,请向我介绍我要去哪里的地方。谢谢!
Here's the code 这是代码

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

public class Paint extends Canvas {

    Paint() {
        Outer obj=new Outer(this);
        JFrame frame=new JFrame("Paint");
        frame.setSize(400,400);
        frame.add(this);
        frame.addMouseMotionListener(obj);
        frame.setVisible(true);
    }

    public static void main(String[] args) {
        new Paint();
    }
}

class Outer implements MouseMotionListener {

    static int x,y,x1,y1;

    Paint ob;

    Outer(Paint ob) {
        this.ob=ob;
    }

    public void mouseDragged(MouseEvent me) {
        Graphics g=ob.getGraphics();
        x1=me.getX();
        y1=me.getY();
        _paint_(g,x,y,x1,y1);
        x=x1;
        y=y1;
    }

    public void _paint_(Graphics g,int x,int y,int x1,int y1) {
        g.drawLine(x,y,x1,y1);
    }

    public void mouseMoved(MouseEvent me) {
        y=me.getY();
        x=me.getX();
    }
}

By does not work,i mean that the frame shows up,but the "pencil tool" does not draw lines “通过”不起作用,表示框架出现,但“铅笔工具”未画线

If you want to do this with JavaFX you can read this documentation's tutorial which contains an exact example of what you are looking for. 如果要使用JavaFX进行此操作,可以阅读文档的教程,其中包含您要查找的确切示例。 Simply download the CanvasDoodleTest.zip and run it. 只需下载CanvasDoodleTest.zip并运行它。

If you want to do this with Java Swing you can do it, generally speaking, like so: 如果要使用Java Swing做到这一点,通常可以这样做,例如:

import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.event.MouseMotionListener;
import java.awt.geom.Path2D;
import javax.swing.JFrame;
import javax.swing.JPanel;

public class SwingCanvas extends JPanel implements MouseListener, MouseMotionListener {
    private final Path2D pencilPath; //This will be the Shape we are going to paint in 'myPaint(...)' method.

    public SwingCanvas() {
        pencilPath = new Path2D.Double(); //Create a new path object, i.e. a set of points and lines between them.

        super.addMouseListener(this); //Register this object as its MouseListener (for the mousePressed event).
        super.addMouseMotionListener(this); //Register this object as its MouseMotionListener (for the mouseDragged event).
        super.setPreferredSize(new Dimension(400, 200)); //Set the preferred size of the component (i.e. the size we want the panel to start with).
        super.setBackground(Color.WHITE); //[Optional] Setting the background color of the panel to white.
        super.setOpaque(true); //Opaque components are responsible to paint their full contents. This is the default behaviour of JPanel, so this is an optional call here.
    }

    /**
     * Overriding paintComponent(...) tells Swing how to paint the panel.
     * @param graphics 
     */
    @Override
    public void paintComponent(final Graphics graphics) {
        super.paintComponent(graphics); //Call this in order to clear previous painting state and start over.
        final Graphics2D g2d = (Graphics2D) graphics.create(); //Create a Graphics2D object to paint.
        try {
            myPaint(g2d); //Call our custom paint method.
        }
        catch (final RuntimeException re) { //Catch any exception in our myPaint (eg a NullPointerException) (if any).
            System.err.println(re); //Handle the exception in some way.
        }
        finally {
            g2d.dispose(); //ALWAYS dispose the CREATED Graphics2D object.
        }
    }

    /**
     * Do whatever painting you need here.
     * In our case, we draw the full path the pencil has followed.
     * @param g2d The {@link Graphics2D} object to paint on.
     */
    protected void myPaint(final Graphics2D g2d) {
        g2d.draw(pencilPath);
    }

    @Override
    public void mousePressed(final MouseEvent e) {
        pencilPath.moveTo(e.getX(), e.getY()); //Move the drawing pencil (without drawing anything new) to the new position.
    }

    @Override
    public void mouseClicked(final MouseEvent e) {
        //Do nothing.
    }

    @Override
    public void mouseReleased(final MouseEvent e) {
        //Do nothing.
    }

    @Override
    public void mouseEntered(final MouseEvent e) {
        //Do nothing.
    }

    @Override
    public void mouseExited(final MouseEvent e) {
        //Do nothing.
    }

    @Override
    public void mouseMoved(final MouseEvent e) {
        //Do nothing.
    }

    @Override
    public void mouseDragged(final MouseEvent e) {
        if (pencilPath.getCurrentPoint() == null) //If the initial point of the path is not set (via a call to "moveTo(...)") then:
            pencilPath.moveTo(e.getX(), e.getY()); //Register the new point from which the new lines will be drawn.
        else
            pencilPath.lineTo(e.getX(), e.getY()); //Register a new line in the path to be drawn.
        repaint(); //Notify Swing to repaint the component (which will call paintComponent(...) which will call myPaint(...) which will paint the pencilPath...
    }

    public static void main(final String[] args)  {
        final JFrame frame = new JFrame("SwingPaint pencil"); //Creates a new application's window.
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); //Tells the new window to close the application if the user closes the window.
        frame.getContentPane().add(new SwingCanvas()); //Add our custom painting panel to the window's content pane.
        frame.pack(); //Automatic sizing of the window, based on preferred sizes of contained components.
        frame.setLocationRelativeTo(null); //Put the window in the center of the screen.
        frame.setVisible(true); //Pop the window.
    }
}

If you want, you can also combine the two methods, because Canvas is a Component (so it can be added to the main frame's content pane in the Swing example). 如果需要,还可以将这两种方法结合使用,因为Canvas是一个Component (因此可以在Swing示例中将其添加到主框架的内容窗格中)。

If you want to access MouseEvent s of SwingCanvas from another class, then you can extend a MouseAdapter and add it to the panel. 如果要从另一个类访问SwingCanvas MouseEvent ,则可以扩展MouseAdapter并将其添加到面板中。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 如何通过另一个类的图形对象调用函数? - How do I call a function with a graphics object from another class? 我有一个外部类的对象。 如何从中获取内部类的对象? - I have an object of an outer class. How do I get the object of the inner class from it? 如何在内部类中引用“ display”变量,以在JLabel的外部类中使用 - How do I reference the “display” variable from my inner class, to use in the outer class in my JLabel 我如何从内部类对象访问外部类的方法和全局变量,以及如果我不能拥有内部类的目的 - How do I access the methods and Global variables of outer class from an inner class object, and if I cannot what is purpose of having an Inner class 从外部 class 方法清除图形 - Clearing Graphics from an outer class method 我如何使用 Graphics - 一个抽象类 - How can I use Graphics - an abstract class 如何使用在不同类中实例化的对象的方法? - How do I use methods from an object instantiated in a different class? 如何在外部类构造函数中创建内部类的实例 - How do I create an instance of a inner class in the outer class constructor 如何从封闭的外部 class 调用同名方法作为在匿名 class 中实现的方法? - How do I call a method of same name from an enclosing outer class as the one being implemented in an anonymous class? 我如何获取已从jdialog类创建的对象以在另一个jdialog类中使用 - how do i get a object that has been created from a jdialog class to be use in another jdialog class
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM