0

一連のマウスクリックから線を引こうとしています。

たとえば、画面上のある点から次の点をクリックすると、線がつながり、次の点までクリックし続けて、連続した描画線を描き続けることができます。

例は次のとおりです: http://oneslime.net/java/Tutorial_2の演習 2の下

私のロジックには何らかのエラーがあると思います (線を描画せず、点だけを描画します) が、それを見つけることができないようです!

誰でも私を助けることができますか?

これが私のコードです:

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

public class RoadCreator extends JPanel {

    private MouseHandler mouseHandler = new MouseHandler();

    private Point previousPoint = new Point();
    private Point nextPoint = new Point();
    private boolean drawing;

    public RoadCreator() {
        this.setPreferredSize(new Dimension(640, 480));
        this.addMouseListener(mouseHandler);
       this.addMouseMotionListener(mouseHandler);
    }

    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);
        Graphics2D g2d = (Graphics2D) g;
        g2d.setColor(Color.blue);
        g2d.setRenderingHint(
            RenderingHints.KEY_ANTIALIASING,
            RenderingHints.VALUE_ANTIALIAS_ON);
        g2d.setStroke(new BasicStroke(8,
            BasicStroke.CAP_ROUND, BasicStroke.JOIN_BEVEL));
        g.drawLine(previousPoint.x, previousPoint.y, nextPoint.x, nextPoint.y);
    }

    private class MouseHandler extends MouseAdapter {

        @Override
        public void mousePressed(MouseEvent e) {
            drawing = true;
            nextPoint = e.getPoint();
            repaint();
            previousPoint = e.getPoint();

        }
    }

    public void display() {
        JFrame f = new JFrame("Road Creator");
        f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        f.add(this);
        f.pack();
        f.setVisible(true);
    }

    }

どんな助けでも大歓迎です、ありがとう!

4

3 に答える 3

6

代わりにGeneralPathまたはを使用します。Path2D

このGeneralPathクラスは、直線、2 次および 3 次 (ベジエ) 曲線から構築された幾何学的パスを表します。複数のサブパスを含めることができます。

ここに画像の説明を入力

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

public class RoadCreator extends JPanel {

    private MouseHandler mouseHandler = new MouseHandler();

    GeneralPath path = null;
    private boolean drawing = false;

    public RoadCreator() {
        this.setPreferredSize(new Dimension(320, 200));
        this.addMouseListener(mouseHandler);
        this.addMouseMotionListener(mouseHandler);
    }

    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);
        Graphics2D g2d = (Graphics2D) g;
        g2d.setColor(Color.blue);
        g2d.setRenderingHint(
                RenderingHints.KEY_ANTIALIASING,
                RenderingHints.VALUE_ANTIALIAS_ON);
        g2d.setStroke(new BasicStroke(8,
                BasicStroke.CAP_ROUND, BasicStroke.JOIN_BEVEL));
        if (path!=null) {
            g2d.draw(path);
        }
    }

    private class MouseHandler extends MouseAdapter {

        @Override
        public void mousePressed(MouseEvent e) {
            Point p = e.getPoint(); 
            if (!drawing) {
                path = new GeneralPath();
                path.moveTo(p.x, p.y);
                drawing = true;
            } else {
                path.lineTo(p.x, p.y);
            }

            repaint();
        }
    }

    public void display() {
        JFrame f = new JFrame("Road Creator");
        f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        f.add(this);
        f.pack();
        f.setVisible(true);
    }

    public static void main(String[] args) {
        RoadCreator rc = new RoadCreator();
        rc.display();
    }
}
于 2012-09-04T07:00:51.937 に答える
1

これはうまくいきません。

public void mousePressed(MouseEvent e) {
    drawing = true;
    nextPoint = e.getPoint();
    repaint();
    previousPoint = e.getPoint();
}

これはインライン呼び出しであると想定していrepaintます (つまり、戻る前にペイントします)。そうではなく、repaint将来のある時点で更新される再描画マネージャーへの要求をキューに入れます。

public void mousePressed(MouseEvent e) {
    drawing = true;
    previousPoint = nextPoint
    nextPoint = e.getPoint();
    repaint();
}

ユーザーがもう一度クリックするまで、previousPoint は null になることに注意してください。

于 2012-09-04T06:45:11.983 に答える
0

私は、可能な限り少ない労力でこのタスクを達成する方法を見つけました。ただし、これはアプリケーションを作成する「良い」方法とは異なります。他のオブジェクトを描画する機能など、将来のスケーラビリティを考慮する必要があります。それでは、それを機能させる方法に取り掛かりましょう。

1)paintComponentメソッドを省略しましょう...これはpaint()である必要があると思います。

    //@Override
    /*protected void paintComponent(Graphics g) {
         //Do Something...
      }*/

2)このメソッドを追加しましょう:

    public void drawLineHelper(Point prev, Point next){
        Graphics g = getGraphics();
        g.setColor(Color.blue);
        g.drawLine(previousPoint.x, previousPoint.y, nextPoint.x, nextPoint.y);
    }

3)最後に、mouseHandlerクラスにいくつかの変更を加える必要があります。

   private class MouseHandler extends MouseAdapter {
        //twoPoints make sure we have two points.
        boolean twoPoints=false;

        @Override
        public void mousePressed(MouseEvent e) {
            if(twoPoints==false){
                nextPoint = e.getPoint();
                twoPoints = true;
            }
            else{
                //Set previous to next from now on.
                previousPoint = nextPoint;

                //Get a new next point.
                nextPoint = e.getPoint();

                //Helper method will draw the line each time.
                drawLineHelper(previousPoint,nextPoint);
                //repaint() no longer necessary.

            }
        }
    }

これは、同じ問題を抱えている別の例へのクイックリファレンスです。このページの最後の投稿では、これと同じ方法について説明しています。http ://www.ozzu.com/programming-forum/java-repainting-problem-t49362.html

于 2012-09-04T16:28:20.083 に答える