Linie mit der Maus auswählen

  • Themenstarter Gelöschtes Mitglied 72742
  • Beginndatum
G

Gelöschtes Mitglied 72742

Gast
Hallo,
um eine gezeichnete Linie (zwei Punkte über new Line2D.Double(punkt1, punkt2) mit der Maus auszuwählen verwende ich "contains". Dazu habe ich ein Beispiel (Polyline) in diesem Forum gefunden und etwas geändert. Theoretisch funktioniert es auch.
Java:
    public boolean isLine(Polyline points, int x, int y) {
        
          return points.contains(x,y);
    };
/**...**/
                Polyline line = new Polyline(2);
                fr.getContentPane().add(line);
                fr.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                fr.setSize(350,350);
                fr.setVisible(true);
                     line.addPoint(100, 120);
                     line.addPoint(200, 80);
                //     line.addPoint(300, 190);
                  System.out.println(line.isLine(line, 100, 20));  //liefert true
                     System.out.println(line.isLine(line, 200, 80));   //liefert true
Allerdings, wenn ich versuche mit Maus over/click die Linie auszuwählen, funktioniert es nicht. Wie macht man sowas am Besten bei Line2D.Double ?
Danke schon mal.
 

Neumi5694

Top Contributor
Wird daran liegen, dass deine Linie keine exakten Integer-Werte hat.
Wenn's "nicht geht", als erstes immer mal ausgeben lassen, was du womit vergleichst, wo du davon ausgehst, dass es klappen sollte und das heißt die Koordinate der Maus und alle Punkte der Polyline, dann mal auf dem Blatt durchrechnen, ob die Annahme auch richtig war.

Du wirst aller Wahrscheinlichkeit nach den Abstand zu den Abschnitten der Polyline berechnen müssen und dann entscheiden, ob die Maus "nahe genug" dran ist oder nicht.

Bau nach Möglichkeit keine Auswertung direkt in den Mouselistener ein, sondern in eine eigene Methode. Der Mouselistener wird zwar aller Wahrscheindlichkeit deine einzige Datenquelle (Mauseingabe) bleiben, aber die Auswertung sollte für Punkte aus egal welcher Quelle klappen.
 
Zuletzt bearbeitet:
G

Gelöschtes Mitglied 72742

Gast
Habe einige Stunden gegoogelt, und einige Möglichkeiten gefunden.
"Die kürzeste Distanz zwischen Line-Segment und Punkt in C++" und "shape.intersects(Rectangle)".

Habe eine Klasse Box erstellt und ein Rechteck um meinen Mauspunkt herum gebaut.
Dann habe ich "shape. intersects(Rectangle) gemacht". Ob es überdimensioniert ist - keine Ahnung. Es funktioniert für eine einfache Linie.
Für die Polylinie weiß ich das noch nicht. Irgendwas muß ich durchlaufen um die Line-Segmente zu bekommen bei "die kürzeste Distanz".
Danke.

Java:
if(s.getShape().contains(a) || s.getShape().intersects(new Box(a)))       //ob der Punkt a drinnen ist
{
    //...
}

Java:
import java.awt.*;

public class Box extends Rectangle {
    Point bpoint = new Point();

    Box (Point bpoint){
        this.bpoint = bpoint;
        this.x=bpoint.x;
        this.y=bpoint.y;
        this.width=4;
        this.height=4;
    }
}
 

Neumi5694

Top Contributor
Heh, auch eine Möglichkeit :)

Meine Methode wäre trigonometrischer Natur gewesen. Der Abstand des Punkts zum Strahl ist z.B. die Höhe des Dreiecks. Dann noch prüfen, ob die durch den Punkt Senkrechte zum Strahl zwischen oder auf einem der beiden Endpunkte liegt (mit Toleranz).
 

Blender3D

Top Contributor
Habe eine Klasse Box erstellt und ein Rechteck um meinen Mauspunkt herum gebaut.
Dann habe ich "shape. intersects(Rectangle) gemacht". Ob es überdimensioniert ist - keine Ahnung. Es funktioniert für eine einfache Linie.
Für die Polylinie weiß ich das noch nicht. Irgendwas muß ich durchlaufen um die Line-Segmente zu bekommen bei "die kürzeste Distanz".
Danke.
1674605213828.png
Ein Beispiel wie man so etwas umsetzen könnte.
Mit der Maus lassen sich Linien zeichnen. Bewegt man die Maus über eine Linie wird diese rot, sobald der Punkt auf der Linie liegt.
Da die Bildpunkte ganzzahligen Koordinaten sind benötigt man eine Epsilon Umgebung, um sich anzunähern.
Zum Testen einfach lines.jar downloaden.
Hier der Code dazu.
Java:
import javax.swing.JFrame;

public class StartLineTool {

    public static void main(String[] args) {
        JFrame frame = new JFrame("Click for lines");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.add(new LinePanel(400, 400));
        frame.pack();
        frame.setVisible(true);
    }
}
Java:
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Point;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.util.Vector;
import javax.swing.JPanel;

@SuppressWarnings("serial")
public class LinePanel extends JPanel {
    private Point2D start;
    private Segment line;
    private Vector<Segment> lines = new Vector<>();   

    public LinePanel(int width, int height) {
        setPreferredSize(new Dimension(width, height));
        addMouseListener(new MouseAdapter() {
            @Override
            public void mouseReleased(MouseEvent e) {
                Point p = e.getPoint();
                if (start == null)
                    start = new Point2D(p);
                else {
                    lines.add(line);
                    start = null;
                    line = null;
                    repaint();
                }
            }
        });
        addMouseMotionListener(new MouseAdapter() {
            @Override
            public void mouseMoved(MouseEvent e) {
                Point p = e.getPoint();
                updateLineColor(p);
                if (start != null)
                    line = new Segment(start, new Point2D(p));
                repaint();
            }
        });
        setBackground(Color.LIGHT_GRAY);
    }

    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);
        for (Segment l : lines)
            l.draw(g);
        if (line != null)
            line.draw(g);
    }

    private void updateLineColor(Point p) {
        if (lines.size() == 0)
            return;
        for (Segment l : lines)
            l.setColor(l.contains(p, 2.5) ? Color.RED : Color.BLACK);
    }
}
Java:
public class Segment {
    public final Point2D a;
    public final Point2D b;
    private Color color = Color.BLACK;

    public Segment(Point2D a, Point2D b) {
        this.a = a;
        this.b = b;
    }

    public boolean contains(Point p, double eps) {
        return contains(p.x, p.y, eps);
    }

    public boolean contains(double x, double y, double eps) {
        if (!getBoundingBox().contains(x, y))
            return false;
        Point2D p = new Point2D(x, y);
        Point2D dir = p.sub(a).normalize();
        Point2D test = a.add(dir.mul(lenght()));
        double xx = Math.abs(b.x - test.x);
        double yy = Math.abs(b.y - test.y);
        return xx <= eps && yy <= eps;
    }

    public void draw(Graphics g) {
        if (a == null || b == null)
            return;
        Point start = a.toPoint();
        Point end = b.toPoint();
        g.setColor(color);
        g.drawLine(start.x, start.y, end.x, end.y);
    }

    public Rectangle2D.Double getBoundingBox() {
        Point2D min = getMinPoint();
        Point2D max = getMaxPoint();
        return new Rectangle2D.Double(min.x, min.y, max.x - min.x, max.y - min.y);
    }

    private Point2D getMaxPoint() {
        return new Point2D(a.x > b.x ? a.x : b.x, a.y > b.y ? a.y : b.y);
    }

    private Point2D getMinPoint() {
        return new Point2D(a.x < b.x ? a.x : b.x, a.y < b.y ? a.y : b.y);
    }

    public double lenght() {
        return a.getDistanceTo(b);
    }

    public void setColor(Color color) {
        this.color = color;
    }

    @Override
    public String toString() {
        return "<" + a + " - " + b + ">";
    }

}
Java:
import java.awt.Point;

public class Point2D {
    public final double x;
    public final double y;

    public Point2D(double x, double y) {
        this.x = x;
        this.y = y;
    }

    public Point2D(Point p) {
        this.x = p.x;
        this.y = p.y;
    }

    public Point2D add(Point2D p) {
        return new Point2D(x + p.x, y + p.y);
    }

    public double getDistanceTo(Point2D p) {
        double xx = p.x - x;
        double yy = p.y - y;
        return Math.sqrt(xx * xx + yy * yy);
    }

    public double lenght() {
        return Math.sqrt(x * x + y * y);
    }

    public Point2D normalize() {
        return this.mul(1d / lenght());
    }

    public Point2D mul(double value) {
        return new Point2D(x * value, y * value);
    }

    public Point2D sub(Point2D b) {
        return new Point2D(x - b.x, y - b.y);
    }

    public Point toPoint() {
        return new Point((int) x, (int) y);
    }

    @Override
    public String toString() {
        return String.format("[%.2f|%.2f]", x, y);
    }
}
 

Anhänge

  • lines.jar
    6,3 KB · Aufrufe: 2
G

Gelöschtes Mitglied 72742

Gast
Anhang anzeigen 20377
Ein Beispiel wie man so etwas umsetzen könnte.
Mit der Maus lassen sich Linien zeichnen. Bewegt man die Maus über eine Linie wird diese rot, sobald der Punkt auf der Linie liegt.
Da die Bildpunkte ganzzahligen Koordinaten sind benötigt man eine Epsilon Umgebung, um sich anzunähern.
Zum Testen einfach lines.jar downloaden.
Hier der Code dazu.
Java:
import javax.swing.JFrame;

public class StartLineTool {

    public static void main(String[] args) {
        JFrame frame = new JFrame("Click for lines");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.add(new LinePanel(400, 400));
        frame.pack();
        frame.setVisible(true);
    }
}
Java:
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Point;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.util.Vector;
import javax.swing.JPanel;

@SuppressWarnings("serial")
public class LinePanel extends JPanel {
    private Point2D start;
    private Segment line;
    private Vector<Segment> lines = new Vector<>();  

    public LinePanel(int width, int height) {
        setPreferredSize(new Dimension(width, height));
        addMouseListener(new MouseAdapter() {
            @Override
            public void mouseReleased(MouseEvent e) {
                Point p = e.getPoint();
                if (start == null)
                    start = new Point2D(p);
                else {
                    lines.add(line);
                    start = null;
                    line = null;
                    repaint();
                }
            }
        });
        addMouseMotionListener(new MouseAdapter() {
            @Override
            public void mouseMoved(MouseEvent e) {
                Point p = e.getPoint();
                updateLineColor(p);
                if (start != null)
                    line = new Segment(start, new Point2D(p));
                repaint();
            }
        });
        setBackground(Color.LIGHT_GRAY);
    }

    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);
        for (Segment l : lines)
            l.draw(g);
        if (line != null)
            line.draw(g);
    }

    private void updateLineColor(Point p) {
        if (lines.size() == 0)
            return;
        for (Segment l : lines)
            l.setColor(l.contains(p, 2.5) ? Color.RED : Color.BLACK);
    }
}
Java:
public class Segment {
    public final Point2D a;
    public final Point2D b;
    private Color color = Color.BLACK;

    public Segment(Point2D a, Point2D b) {
        this.a = a;
        this.b = b;
    }

    public boolean contains(Point p, double eps) {
        return contains(p.x, p.y, eps);
    }

    public boolean contains(double x, double y, double eps) {
        if (!getBoundingBox().contains(x, y))
            return false;
        Point2D p = new Point2D(x, y);
        Point2D dir = p.sub(a).normalize();
        Point2D test = a.add(dir.mul(lenght()));
        double xx = Math.abs(b.x - test.x);
        double yy = Math.abs(b.y - test.y);
        return xx <= eps && yy <= eps;
    }

    public void draw(Graphics g) {
        if (a == null || b == null)
            return;
        Point start = a.toPoint();
        Point end = b.toPoint();
        g.setColor(color);
        g.drawLine(start.x, start.y, end.x, end.y);
    }

    public Rectangle2D.Double getBoundingBox() {
        Point2D min = getMinPoint();
        Point2D max = getMaxPoint();
        return new Rectangle2D.Double(min.x, min.y, max.x - min.x, max.y - min.y);
    }

    private Point2D getMaxPoint() {
        return new Point2D(a.x > b.x ? a.x : b.x, a.y > b.y ? a.y : b.y);
    }

    private Point2D getMinPoint() {
        return new Point2D(a.x < b.x ? a.x : b.x, a.y < b.y ? a.y : b.y);
    }

    public double lenght() {
        return a.getDistanceTo(b);
    }

    public void setColor(Color color) {
        this.color = color;
    }

    @Override
    public String toString() {
        return "<" + a + " - " + b + ">";
    }

}
Java:
import java.awt.Point;

public class Point2D {
    public final double x;
    public final double y;

    public Point2D(double x, double y) {
        this.x = x;
        this.y = y;
    }

    public Point2D(Point p) {
        this.x = p.x;
        this.y = p.y;
    }

    public Point2D add(Point2D p) {
        return new Point2D(x + p.x, y + p.y);
    }

    public double getDistanceTo(Point2D p) {
        double xx = p.x - x;
        double yy = p.y - y;
        return Math.sqrt(xx * xx + yy * yy);
    }

    public double lenght() {
        return Math.sqrt(x * x + y * y);
    }

    public Point2D normalize() {
        return this.mul(1d / lenght());
    }

    public Point2D mul(double value) {
        return new Point2D(x * value, y * value);
    }

    public Point2D sub(Point2D b) {
        return new Point2D(x - b.x, y - b.y);
    }

    public Point toPoint() {
        return new Point((int) x, (int) y);
    }

    @Override
    public String toString() {
        return String.format("[%.2f|%.2f]", x, y);
    }
}
Das ist sehr gut. Danke.
 
Ähnliche Java Themen
  Titel Forum Antworten Datum
M JavaFX Diagonale Linie nicht ausgegeben/angezeigt AWT, Swing, JavaFX & SWT 1
G JavaFX Line Chart mit Farbverlauf/Gradient in Linie AWT, Swing, JavaFX & SWT 1
L 2D-Grafik Linie von Kreis zu Kreis AWT, Swing, JavaFX & SWT 3
J 2D-Grafik Linie wird nach Mausklick nicht am richtigen Ort gezeichnet AWT, Swing, JavaFX & SWT 11
K JavaFX Linie immer in der Mitte der Szene halten AWT, Swing, JavaFX & SWT 12
L JavaFX Horizontale Linie zur Scene binding AWT, Swing, JavaFX & SWT 3
3 2D-Grafik BasicStroke dash pattern - Linie zu lang!? AWT, Swing, JavaFX & SWT 1
I Text zur Linie zeichnen AWT, Swing, JavaFX & SWT 1
I Pfeil zeichnen am Ende einer Linie AWT, Swing, JavaFX & SWT 1
javampir Kubische Interpolation einer Linie AWT, Swing, JavaFX & SWT 5
C AWT Horizontale Linie in einem Panel AWT, Swing, JavaFX & SWT 12
B Linie zwischen 2 Elementen AWT, Swing, JavaFX & SWT 5
propra Auf einem JPanel gezeichnete Linie auswählen AWT, Swing, JavaFX & SWT 3
Gossi 2D-Grafik Linie erweitern? AWT, Swing, JavaFX & SWT 10
V Linie mit Länge und Bogenmaß AWT, Swing, JavaFX & SWT 3
J 2D-Grafik Linie hat Löcher AWT, Swing, JavaFX & SWT 10
P 2D-Grafik Neue Farbe für einen Teilbereich einer Linie? AWT, Swing, JavaFX & SWT 8
K 2D-Grafik Linie verschwindet beim Zeichnen AWT, Swing, JavaFX & SWT 10
I Schrift und Farbe formatieren, und zwar pro Linie... AWT, Swing, JavaFX & SWT 4
C Swing JTable: Horizontale Linie bei einzelnen Zellen ausblenden AWT, Swing, JavaFX & SWT 5
G SWT Linie unter transparentes Canvas zeichnen AWT, Swing, JavaFX & SWT 4
B SWT Linie soll in Abhängigkeit der aktuellen Uhrzeit gezeichnet werden AWT, Swing, JavaFX & SWT 16
M Labels in ScrollPane mit Linie verbinden AWT, Swing, JavaFX & SWT 2
R JPanel - zeichnen in skalierten Bereich - Linie (X-Achse) nicht sichtbar AWT, Swing, JavaFX & SWT 11
J Swing - ich sehe keine Linie, andere schon AWT, Swing, JavaFX & SWT 6
S JXTaskPane und gepunktete Linie AWT, Swing, JavaFX & SWT 2
G SWT Linie AWT, Swing, JavaFX & SWT 13
F Rahmen mit gestrichelter Linie zeichnen AWT, Swing, JavaFX & SWT 4
G Linie nach Höhe einer Zahl zeichnen? AWT, Swing, JavaFX & SWT 3
M Linie zwischen JComponents AWT, Swing, JavaFX & SWT 5
T Linie langsam zeichnen AWT, Swing, JavaFX & SWT 3
L Linie mit drawLine auf JPanel AWT, Swing, JavaFX & SWT 7
A gezeichnete Linie verschwindet, wenn ich JMenuBar öffne AWT, Swing, JavaFX & SWT 2
S Problem mit dem Zeichnen einer Linie auf einem JPanel AWT, Swing, JavaFX & SWT 30
TheJavaKid Kreis, Rechteck, Linie. verschieben AWT, Swing, JavaFX & SWT 5
Student "Dicke" einer Linie - Line2D.Double AWT, Swing, JavaFX & SWT 12
R drawLine gibt hässliche linie AWT, Swing, JavaFX & SWT 4
T Vertikale Linie abgeschnitten AWT, Swing, JavaFX & SWT 2
C Linie in einem JLabel AWT, Swing, JavaFX & SWT 14
G linie / vektor zeichnen AWT, Swing, JavaFX & SWT 2
K Linie wird falsch auf Panel gezeichnet AWT, Swing, JavaFX & SWT 11
M JButtons mit Linie verbinden AWT, Swing, JavaFX & SWT 4
B mit maus Objekt bewegen AWT, Swing, JavaFX & SWT 3
R Swing Panel nur bei Maus sichtbar AWT, Swing, JavaFX & SWT 2
B mit Maus verschiebbares Panel AWT, Swing, JavaFX & SWT 2
C JTextField Inhalt mit Maus selektieren wenn disabled AWT, Swing, JavaFX & SWT 2
S JavaFX Fenster aufkommen lassen, wenn mit der Maus über bestimmten Bereich fahren AWT, Swing, JavaFX & SWT 1
F Event wenn Maus eine JList verlässt AWT, Swing, JavaFX & SWT 13
T Timer und GIF Animationen pausieren während Maus sich bewegt AWT, Swing, JavaFX & SWT 4
M Bild in JPanel mit Maus einfügen AWT, Swing, JavaFX & SWT 0
B Swing Form undecorated: Beim Bewegen geht die Maus immer automatisch zur linken Seite. AWT, Swing, JavaFX & SWT 7
L 2D-Grafik Bild in Richtung Maus drehen AWT, Swing, JavaFX & SWT 18
K Swing Maus in Panel einsperren AWT, Swing, JavaFX & SWT 8
D Swing JList keine Selektionsänderung bei "dragged-Maus" AWT, Swing, JavaFX & SWT 4
A JFrame Größenänderung mit Maus und GridLayout AWT, Swing, JavaFX & SWT 10
J Maus "locken" für Menü AWT, Swing, JavaFX & SWT 8
D Grafiken an Maus anhängen AWT, Swing, JavaFX & SWT 2
P Pfeilpolygon per Maus rotierbar machen - Kleine Schwierigkeiten AWT, Swing, JavaFX & SWT 29
P Event Handling Gedrückte Maus Blockiert MausEvents AWT, Swing, JavaFX & SWT 2
R Swing Per Maus JLabel resizen AWT, Swing, JavaFX & SWT 6
F Maus von alleine bewegen! AWT, Swing, JavaFX & SWT 8
G Swing JPanel per Maus verschieben AWT, Swing, JavaFX & SWT 5
A SWT Tooltip soll nicht verschwinden, solange User mit Maus auf Control ist AWT, Swing, JavaFX & SWT 5
C AWT Mausbarriere Maus fangen AWT, Swing, JavaFX & SWT 10
J "Auswahlfenster" mit Maus auf JLabel zeichnen AWT, Swing, JavaFX & SWT 4
W Swing Bild zeichnen wenn Maus an bestimmter Position ist AWT, Swing, JavaFX & SWT 4
J Inaktivität von Maus und Tastatur AWT, Swing, JavaFX & SWT 4
G AWT Images aus Imagearray an die Maus pappen und bewegen AWT, Swing, JavaFX & SWT 4
F Element anzeigen / erstellen. Maus vs Controller AWT, Swing, JavaFX & SWT 7
M 3D-Grafik Bewegung mit der Maus ohne Klicken AWT, Swing, JavaFX & SWT 10
F Swing Objekte mit Maus verschieben AWT, Swing, JavaFX & SWT 8
O Swing JButton werden richtig gewechselt aber die Maus macht die alten wieder Sichtbar?? AWT, Swing, JavaFX & SWT 5
Y AWT Maus Koordinaten abspeichern in eine Textfile AWT, Swing, JavaFX & SWT 3
Weltall 7 AWT Maus-Events werden doppelt ausgeführt AWT, Swing, JavaFX & SWT 12
C permanente aktualisierung der Koordinaten der Maus auf einem Panel AWT, Swing, JavaFX & SWT 8
J maus festlegen AWT, Swing, JavaFX & SWT 6
C paintComponent mit Maus verschieben - wie? AWT, Swing, JavaFX & SWT 2
T Swing JComboBox: Listeneinträge mit der Maus verschieben AWT, Swing, JavaFX & SWT 5
O JSlider - wie unterscheide ich mit Maus verändert und durch setValue verändert. AWT, Swing, JavaFX & SWT 16
W Swing Maus Rastersprung AWT, Swing, JavaFX & SWT 3
S Swing JTable Auswahl mehrerer Zellen mit STRG+Maus AWT, Swing, JavaFX & SWT 3
E Hilfetext anzeigen beim Überfahren mit der Maus AWT, Swing, JavaFX & SWT 3
G Maus über Button AWT, Swing, JavaFX & SWT 3
S Funktion nur ausführen, wenn Maus über Componente ist AWT, Swing, JavaFX & SWT 2
G Listenelemente mit der Maus verschieben AWT, Swing, JavaFX & SWT 4
B kein MouseEvent bei zu schneller Bewegung der Maus AWT, Swing, JavaFX & SWT 7
B JTable - Wechsel der Spalte bei TAB, RETURN oder Maus AWT, Swing, JavaFX & SWT 5
D Mit der Maus in verschiedene Modi wechseln AWT, Swing, JavaFX & SWT 15
Z Buttons erscheinen erst wenn man mit der Maus drüber geht AWT, Swing, JavaFX & SWT 7
G Elemente erst da wenn mit Maus drüber gefahren bin AWT, Swing, JavaFX & SWT 2
M Kreis mit gedrückter Maus bewegen AWT, Swing, JavaFX & SWT 20
F Größenänderung mittels Maus - selbst implementieren? AWT, Swing, JavaFX & SWT 3
R Einstellen der Maus Rad Geschwindigkeit beim Scrollen AWT, Swing, JavaFX & SWT 3
G Kreis zeichnen und mit Maus ziehen AWT, Swing, JavaFX & SWT 3
W Maus Rahmen zeichnen AWT, Swing, JavaFX & SWT 10
A JFileChooser - Mehrere Dateien per Maus markieren (nokeys) AWT, Swing, JavaFX & SWT 7
V JTable Handling Fokus on Keystroke und Maus Doubleclick AWT, Swing, JavaFX & SWT 9
R JTable: Maus-Click ohne Datensätze AWT, Swing, JavaFX & SWT 9
L Größe von Komponenten im Nulllayout mit der Maus verändern. AWT, Swing, JavaFX & SWT 2
J Context Menü Maus AWT, Swing, JavaFX & SWT 3

Ähnliche Java Themen

Neue Themen


Oben