Results 1 to 15 of 15
  1. #1
    hornet7288 is offline Member
    Join Date
    Sep 2016
    Posts
    32
    Rep Power
    0

    Default Adding dots to a pane for each mouse click

    I am working on a convex hull project that is due in a couple of weeks for class. I am trying to work on putting it all together one step at a time. This project has to use a GUI to detect mouse click events. A left click adds a point to the window and a right click removes that point. Those points are then used to calculate and draw the convex hull. I have already been given the algorithm to calculate the points for the convex hull so that is not an issue. All I have gotten so far is that I am able to detect mouse click events. I am not sure how to add a dot to the window each time the mouse is pressed. Could anybody tell me where to go next?

    Java Code:
    import javafx.application.Application;
    import javafx.scene.Scene;
    import javafx.scene.input.MouseButton;
    import javafx.scene.layout.Pane;
    import javafx.stage.Stage;
    
    public class Test extends Application {
    
        Pane pane = new Pane();
    
        @Override
        public void start(Stage primaryStage) {
    
            Scene scene = new Scene(pane, 350, 200);
    
            primaryStage.setTitle("Test");
            primaryStage.setScene(scene);
            primaryStage.show();
    
            pane.setOnMouseClicked(e -> {
                if (e.getButton() == MouseButton.PRIMARY) {
                    System.out.println("Left-Click");
                    drawPoint(e.getX(), e.getY());
                } else if (e.getButton() == MouseButton.SECONDARY) {
                    System.out.println("Right-Click");
                }
    
            });
    
        }
    
        void drawPoint(double x, double y) {
            System.out.println("In draw");
    
            Circle circle = new Circle(5);
        }
    
        public static void main(String[] args) {
            launch(args);
        }
    }
    Last edited by hornet7288; 09-17-2016 at 07:44 PM.

  2. #2
    hornet7288 is offline Member
    Join Date
    Sep 2016
    Posts
    32
    Rep Power
    0

    Default Re: Adding dots to a pane for each mouse click

    So I ended up being able to get the program to draw a dot each time a mouse click in the scene happens. Now I am trying to get it to delete the dots with a right click. Also, I need to store the X, Y pair of the dots so that they can be used later to be sent to the method which calculates the convex hull. Not too sure if I am going about drawing new dots the right way given that I need to be able to remove the dot with a right click.

    Java Code:
    import javafx.application.Application;
    import javafx.scene.Scene;
    import javafx.scene.input.MouseButton;
    import javafx.scene.layout.Pane;
    import javafx.stage.Stage;
    import javafx.scene.shape.Circle;
    
    public class Test extends Application {
    
        public Pane pane = new Pane();
    
        @Override
        public void start(Stage primaryStage) {
    
            Scene scene = new Scene(pane, 350, 200);
    
            primaryStage.setTitle("Test");
            primaryStage.setScene(scene);
            primaryStage.show();
    
            scene.setOnMouseClicked(e -> {
                if (e.getButton() == MouseButton.PRIMARY) {
                    Circle circle = new Circle(4);
    
                    circle.setTranslateX(e.getX());
                    circle.setTranslateY(e.getY());
                    pane.getChildren().addAll(circle);
                } else if (e.getButton() == MouseButton.SECONDARY) {
    
                    System.out.println("Right-Click");
                }
    
            });
    
        }
    
        public static void main(String[] args) {
            launch(args);
        }
    }

  3. #3
    Norm's Avatar
    Norm is offline Moderator
    Join Date
    Jun 2008
    Location
    Eastern Florida
    Posts
    20,003
    Rep Power
    33

    Default Re: Adding dots to a pane for each mouse click

    need to be able to remove the dot with a right click
    The x,y coords of the click point could be saved in a class object and that object would be saved in a list. The right click can then get the last click point from the end of the list.
    If you don't understand my response, don't ignore it, ask a question.

  4. #4
    hornet7288 is offline Member
    Join Date
    Sep 2016
    Posts
    32
    Rep Power
    0

    Default Re: Adding dots to a pane for each mouse click

    Ok that makes sense. So instead of drawing a new circle each time I should add the two new coordinates to a list. That way points can easily be removed. And then after the fact I can draw the points based on the coordinates in the list.

  5. #5
    hornet7288 is offline Member
    Join Date
    Sep 2016
    Posts
    32
    Rep Power
    0

    Default Re: Adding dots to a pane for each mouse click

    Here is where I am so far. I don't know why but this exercise is really giving me a hard time. I probably need to use a list which I believe can grow automatically.

    Java Code:
    import javafx.application.Application;
    import javafx.scene.Scene;
    import javafx.scene.input.MouseButton;
    import javafx.scene.layout.Pane;
    import javafx.stage.Stage;
    import javafx.scene.shape.Circle;
    
    public class Test extends Application {
    
        public Pane pane = new Pane();
        int numberOfPoints = 0;
        double[][] p = new double[numberOfPoints][2];
    
        @Override
        public void start(Stage primaryStage) {
    
            Scene scene = new Scene(pane, 350, 200);
    
            primaryStage.setTitle("Test");
            primaryStage.setScene(scene);
            primaryStage.show();
    
            scene.setOnMouseClicked(e -> {
                if (e.getButton() == MouseButton.PRIMARY) {
    
                    addPoints(e.getX(), e.getY());
    
                    numberOfPoints++;
                    //addToArray(numberOfPoints, e.getX(), e.getY());
    
    //                Circle circle = new Circle(4);
    //                circle.setTranslateX(e.getX());
    //                circle.setTranslateY(e.getY());
    //                pane.getChildren().addAll(circle);
                } else if (e.getButton() == MouseButton.SECONDARY) {
                    numberOfPoints--;
                    System.out.println(numberOfPoints);
    
                }
    
            });
    
        }
    
        void addPoints(double x, double y) {
            System.out.println(x);
            System.out.println(y);
    
            Double[] nums = new Double[2];
            nums[0] = x;
            nums[1] = y;
    
            for (int j = 0; j < 2; j++) {
                p[numberOfPoints][j] = nums[j];
            }
        }
    
        public static void main(String[] args) {
            launch(args);
        }
    }
    Last edited by hornet7288; 09-17-2016 at 10:53 PM.

  6. #6
    Norm's Avatar
    Norm is offline Moderator
    Join Date
    Jun 2008
    Location
    Eastern Florida
    Posts
    20,003
    Rep Power
    33

    Default Re: Adding dots to a pane for each mouse click

    Instead of an array of primitives, use an ArrayList of class objects that hold the data needed to process any click points. The beauty of a class is that all the data for a point is in one place and if more data is needed to be saved for a point, it is easy to add it to the point saving class's definition.
    Also with an ArrayList it is easy to add and remove items that have been saved in the list.

    Showing the dots visually would make it easier to draw shapes.
    Last edited by Norm; 09-17-2016 at 11:16 PM.
    If you don't understand my response, don't ignore it, ask a question.

  7. #7
    hornet7288 is offline Member
    Join Date
    Sep 2016
    Posts
    32
    Rep Power
    0

    Default Re: Adding dots to a pane for each mouse click

    Looks like this seems to be adding the points to the list:

    Java Code:
    import java.util.ArrayList;
    import javafx.application.Application;
    import javafx.scene.Scene;
    import javafx.scene.input.MouseButton;
    import javafx.scene.layout.Pane;
    import javafx.stage.Stage;
    import javafx.scene.shape.Circle;
    
    public class Test extends Application {
    
        public Pane pane = new Pane();
        int numberOfPoints = 0;
        double[][] p = new double[numberOfPoints][2];
        
        ArrayList<Double> list = new ArrayList<>();
    
        @Override
        public void start(Stage primaryStage) {
    
            Scene scene = new Scene(pane, 350, 200);
    
            primaryStage.setTitle("Test");
            primaryStage.setScene(scene);
            primaryStage.show();
    
            scene.setOnMouseClicked(e -> {
                if (e.getButton() == MouseButton.PRIMARY) {
                    
                    numberOfPoints++;
                    list.add(e.getX());
                    list.add(e.getY());
    
                } else if (e.getButton() == MouseButton.SECONDARY) {
                    numberOfPoints--;
    
                    System.out.println(numberOfPoints);
                    double[][] p = new double[numberOfPoints][2];
                }
    
            });
    
        }
        public static void main(String[] args) {
            launch(args);
        }
    }
    Last edited by hornet7288; 09-17-2016 at 11:54 PM.

  8. #8
    Norm's Avatar
    Norm is offline Moderator
    Join Date
    Jun 2008
    Location
    Eastern Florida
    Posts
    20,003
    Rep Power
    33

    Default Re: Adding dots to a pane for each mouse click

    1) define a class to hold the data for the click points - what data needs to be saved?
    2) define an ArrayList to hold instances of the class
    3) When there is a click, create an instance of the class with the data to be saved for the click
    4) add that instance of the class to the ArrayList
    If you don't understand my response, don't ignore it, ask a question.

  9. #9
    jim829 is offline Senior Member
    Join Date
    Jan 2013
    Location
    Northern Virginia, United States
    Posts
    6,226
    Rep Power
    14

    Default Re: Adding dots to a pane for each mouse click

    Actually, you don't need to save anything. Just get the children from the pane and filter based on whether the appropriate bounds
    contains the current mouse location once translated. If so, remove it from the children list. If returned list from filter is empty, then add
    to the children list.

    Regards,
    Jim
    The JavaTM Tutorials | SSCCE | Java Naming Conventions
    Poor planning on your part does not constitute an emergency on my part

  10. #10
    hornet7288 is offline Member
    Join Date
    Sep 2016
    Posts
    32
    Rep Power
    0

    Default Re: Adding dots to a pane for each mouse click

    I have made it fairly far now. The program properly displays the output in the console window as far as the coordinates to the convex hull. It is not drawing the lines properly and I am not too sure quite why. I am not sure if I need to sort the points or what.

    Also, if someone could tell me if there is a polygon object I should be using to draw this instead of drawing single lines at a time.

    Java Code:
    import java.util.ArrayList;
    import javafx.application.Application;
    import javafx.scene.Scene;
    import javafx.scene.input.MouseButton;
    import javafx.scene.layout.Pane;
    import javafx.scene.shape.Circle;
    import javafx.stage.Stage;
    import javafx.scene.shape.Line;
    import javafx.geometry.Point2D;
    import javafx.geometry.Pos;
    
    public class extends Application {
    
        public Pane pane = new Pane();
        int numberOfPoints = 0;
    
        ArrayList<Double> list = new ArrayList<>();
    
        @Override
        public void start(Stage primaryStage) {
            Scene scene = new Scene(pane, 350, 200);
    
            primaryStage.setTitle("Test");
            primaryStage.setScene(scene);
            primaryStage.show();
    
            scene.setOnMouseClicked(e -> {
                if (e.getButton() == MouseButton.PRIMARY) {
    
                    numberOfPoints++;
                    list.add(e.getX());
                    list.add(e.getY());
    
                    double[][] p = new double[numberOfPoints][2];
    
                    for (int i = 0; i < p.length; i++) {
                        for (int j = 0; j < p[i].length; j++) {
                            if (j == 0) {
                                p[i][j] = list.get(i * 2);
                            } else {
                                p[i][j] = list.get((i * 2) + 1);
                            }
                        }
                    }
    
                    ArrayList<MyPoint> listC = getConvexHull(p);
                    drawCircles(p);
                    //Remove later
                    System.out.print("The convex hull is ");
                    for (int i = 0; i < listC.size(); i++) {
                        System.out.print("(" + listC.get(i).x + ", " + listC.get(i).y + ") ");
                    }
                    System.out.println();
                } else if (e.getButton() == MouseButton.SECONDARY) {
    
                    double x = e.getX();
                    double y = e.getY();
                    //Add in the remove function 
                }
    
            });
        }
    
        //Method is called everytime a circle is added or removed so that a new dot is added. 
        void drawCircles(double p[][]) {
    
            Circle circle = new Circle(4);
            Line line = new Line();
    
            for (int i = 0; i < p.length; i++) {
                for (int j = 0; j < p[i].length; j++) {
                    if (j == 0) {
                        circle.setTranslateX(p[i][j]);
                    } else {
                        circle.setTranslateY(p[i][j]);
                    }
                }
            }
    
            ArrayList<MyPoint> listC = getConvexHull(p);
            int size = listC.size();
      
            
    
            double[] pairsX = new double[size];
            double[] pairsY = new double[size];
    
            if (size >= 2) {
                for (int i = 0; i < size; i++) {
                    pairsX[i] = listC.get(i).x;
                    pairsY[i] = listC.get(i).y;
                }
                
                System.out.println("Size: " + size);
    
                for (int i = 0; i < size; i++) {
    
                    if (i != size - 1) {
                        line.setStartX(pairsX[i]);
                        line.setStartY(pairsY[i]);
                        line.setEndX(pairsX[i + 1]);
                        line.setEndY(pairsY[i + 1]);
    
                    } else {
    
                        line.setStartX(pairsX[i]);
                        line.setStartY(pairsY[i]);
                        line.setEndX(pairsX[0]);
                        line.setEndY(pairsY[0]);
                    }
                }
            }
            pane.getChildren().addAll(circle, line);
        }
    
        static class MyPoint {
    
            double x, y;
    
            MyPoint(double x, double y) {
                this.x = x;
                this.y = y;
            }
        }
    
        /**
         * Return the points that form a convex hull
         */
        public static ArrayList<MyPoint> getConvexHull(double[][] s) {
            // For efficiency, create an array of objects 
            MyPoint[] myPoints = new MyPoint[s.length];
            for (int i = 0; i < myPoints.length; i++) {
                myPoints[i] = new MyPoint(s[i][0], s[i][1]);
            }
    
            // Step 1
            MyPoint h0 = getRightmostLowestPoint(myPoints);
            ArrayList<MyPoint> H = new ArrayList<MyPoint>();
            H.add(h0);
    
            MyPoint t0 = h0;
    
            // Step 2 and Step 3
            while (true) {
                MyPoint t1 = myPoints[0];
                for (int i = 1; i < myPoints.length; i++) {
                    double status = whichSide(t0.x, t0.y, t1.x, t1.y, myPoints[i].x, myPoints[i].y);
    
                    if (status > 0) // Right side of the line. Please note we are using the Java coordinate system. y increases downward
                    {
                        t1 = myPoints[i];
                    } else if (status == 0) {
                        if (distance(s[i][0], s[i][1], t0.x, t0.y) > distance(t1.x, t1.y, t0.x, t0.y)) {
                            t1 = myPoints[i];
                        }
                    }
                }
    
                if (t1.x == h0.x && t1.y == h0.y) {
                    break; // A convex hull is found
                } else {
                    H.add(t1);
                    t0 = t1;
                }
            }
    
            return H;
        }
    
        /**
         * Return the rightmost lowest point in S
         */
        private static MyPoint getRightmostLowestPoint(MyPoint[] p) {
            int rightMostIndex = 0;
            double rightMostX = p[0].x;
            double rightMostY = p[0].y;
    
            for (int i = 1; i < p.length; i++) {
                if (rightMostY < p[i].y) {
                    rightMostY = p[i].y;
                    rightMostX = p[i].x;
                    rightMostIndex = i;
                } else if (rightMostY == p[i].y && rightMostX < p[i].x) {
                    rightMostX = p[i].x;
                    rightMostIndex = i;
                }
            }
    
            return p[rightMostIndex];
        }
    
        public static double distance(double x1, double y1, double x2, double y2) {
            return Math.sqrt((x1 - x2) * (x1 - x2) + (y1 - y2) * (y1 - y2));
        }
    
        static double whichSide(double x0, double y0, double x1, double y1, double x2, double y2) {
            return (x1 - x0) * (y2 - y0) - (x2 - x0) * (y1 - y0);
        }
    
        public static void main(String[] args) {
            launch(args);
    
        }
    }
    Last edited by hornet7288; 09-18-2016 at 04:57 AM.

  11. #11
    Norm's Avatar
    Norm is offline Moderator
    Join Date
    Jun 2008
    Location
    Eastern Florida
    Posts
    20,003
    Rep Power
    33

    Default Re: Adding dots to a pane for each mouse click

    A left click adds a point to the window and a right click removes that point.
    Is there a new design for the program? For example: The right click doesn't remove the last point now.

    It is not drawing the lines properly
    Please explain? Give a verbal explanation of what you want the program to do.
    For example:
    the user clicks at a point
    the program does ...
    the user clicks at another point
    the program does ...
    the user clicks at another point
    the program does ...
    etc
    If you don't understand my response, don't ignore it, ask a question.

  12. #12
    jim829 is offline Senior Member
    Join Date
    Jan 2013
    Location
    Northern Virginia, United States
    Posts
    6,226
    Rep Power
    14

    Default Re: Adding dots to a pane for each mouse click

    In line with what Norm said, it is difficult to offer suggestions without knowing the ultimate, final goal of the program. That's because
    any suggestions we make may be incompatible with future enhancements.

    Regards,
    Jim
    The JavaTM Tutorials | SSCCE | Java Naming Conventions
    Poor planning on your part does not constitute an emergency on my part

  13. #13
    hornet7288 is offline Member
    Join Date
    Sep 2016
    Posts
    32
    Rep Power
    0

    Default Re: Adding dots to a pane for each mouse click

    My apologies. The goal of the program is to draw a polygon which is created using the outermost points which are placed on the pane by clicks of the mouse.

    So I ended up messing around with it last night and figured out how to properly do it. Instead of drawing lines one at a time, I used a polygon shape and fed it the arrays of X and Y points.

    Now I just need to get the remove function working which removed a dot on a right click. I have it working, but it is extremely sensitive and has to be in the exact spot to remove a dot from the list (I don't have it removing the dot graphically yet). Trying to figure out a way to make it less sensitive.

    Thanks for all the help! This forum is a great tool with some extremely knowledgeable people!

  14. #14
    Norm's Avatar
    Norm is offline Moderator
    Join Date
    Jun 2008
    Location
    Eastern Florida
    Posts
    20,003
    Rep Power
    33

    Default Re: Adding dots to a pane for each mouse click

    The posted code uses too many arrays. The MyPoint class is not used enough.
    For example the MyPoint class could use some methods to compare the positions of two points.
    For example a boolean method named: isBelow(MyPoint mp) returns true if the current point is below (greater y) than the mp object's y value.
    If you don't understand my response, don't ignore it, ask a question.

  15. #15
    hornet7288 is offline Member
    Join Date
    Sep 2016
    Posts
    32
    Rep Power
    0

    Default Re: Adding dots to a pane for each mouse click

    That portion of the code was given to me by the instructor. However, I may change it around to make it a little more efficient. You are right, it is using many arrays. Even in the code I wrote I could probably slim down my array usage some.

Similar Threads

  1. Replies: 6
    Last Post: 11-05-2014, 02:34 AM
  2. I need help adding a mouse click event to my code
    By Djblacklantern in forum New To Java
    Replies: 1
    Last Post: 11-09-2012, 06:41 PM
  3. add tabbed pane to the frame on a button click
    By Mahaveer in forum New To Java
    Replies: 0
    Last Post: 11-20-2009, 09:19 AM
  4. [SOLVED] Mouse event in JTabbed Pane
    By javanewbie in forum AWT / Swing
    Replies: 6
    Last Post: 06-10-2009, 08:50 AM
  5. mouse click alert
    By amir in forum AWT / Swing
    Replies: 1
    Last Post: 08-05-2008, 10:42 PM

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •