I basically wanna make a single window application where the user will be able to draw segment lines. The application flow should be:
I already have the following piece of code:
public class LineEditor extends JComponent{
private class Point{
int x, y;
public Point(int x, int y){
this.x = x;
this.y = y;
}
}
private class Line{
Point a, b;
public Line(Point a, Point b){
this.a = a;
this.b = b;
}
}
private ArrayList<Line> lines = new ArrayList<Line>();
public void setLine(Point a, Point b){
lines.add(new Line(a, b));
repaint();
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
for (Line line : lines) {
g.setColor(line.color);
g.drawLine(line.a.x, line.a.y, line.b.x, line.b.y);
}
}
public static void main(String[] args){
int height = 500, width = 500;
JFrame frame = new JFrame();
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
// Properties of the main window
frame.setAlwaysOnTop(true);
final LineEditor lineEditor = new LineEditor();
lineEditor.setPreferredSize(new Dimension(width, height));
JPanel panelCanvas = new JPanel();
panelCanvas.setPreferredSize(new Dimension(width, height));
JPanel secondaryPanel = new JPanel();
JButton addLineButton = new JButton("Add new line");
secondaryPanel.add(addLineButton);
frame.getContentPane().add(lineEditor, BorderLayout.CENTER);
frame.getContentPane().add(panelCanvas, BorderLayout.CENTER);
frame.getContentPane().add(secondaryPanel, BorderLayout.NORTH);
panelCanvas.addMouseListener(new MouseAdapter() {
@Override
public void mousePressed(MouseEvent e) {
int x = e.getX();
int y = e.getY();
}
});
addLineButton.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
// x
}
});
frame.pack();
frame.setVisible(true);
}
}
I don't get how to:
I wanna achieve something like:
addLineButton.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
// Wait for the first user click
int x1 = mouseListener.getX();
int y1 = mouseListener.getY();
Point a = new Point(x1, y1);
// Wait for the second user click
int x2 = mouseListener.getX();
int y2 = mouseListener.getY();
Point b = new Point(x2, y2);
lineEditor.setLine(a, b);
}
});
I finally solved the problem by forcing the user to follow the next flow when drawing a new line:
Note that this's just an approach to what I was looking for (first click&release=first point, second click&release=second point), but still I think it could be a nice sample for swing beginners.
public class LineEditor extends JComponent{
private static class Point{
final int x, y;
public Point(int x, int y){
this.x = x;
this.y = y;
}
}
private static class Line{
final Point a, b;
final Color color;
public Line(Point a, Point b, Color color) {
this.a = a;
this.b = b;
this.color = color;
}
}
private final LinkedList<Line> lines = new LinkedList<Line>();
public void addLine(int xa, int ya, int xb, int yb, Color color) {
lines.add(new Line(new Point(xa, ya), new Point(xb, yb), color));
repaint();
}
public void clearScreen() {
if(lines.size() > 0){
lines.remove(lines.getLast());
repaint();
}
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
for (Line line : lines) {
g.setColor(line.color);
g.drawLine(line.a.x, line.a.y, line.b.x, line.b.y);
}
}
public static void main(String[] args) {
int width, height;
width = 500;
height = 500;
JFrame backgroundFrame = new JFrame();
backgroundFrame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
final LineEditor lineEditor = new LineEditor();
lineEditor.setPreferredSize(new Dimension(width, height));
backgroundFrame.getContentPane().add(lineEditor, BorderLayout.CENTER);
JPanel buttonsPanel = new JPanel();
JButton clearScreen = new JButton("Remove last line");
buttonsPanel.add(clearScreen);
backgroundFrame.getContentPane().add(buttonsPanel, BorderLayout.SOUTH);
backgroundFrame.addMouseListener(new MouseAdapter() {
int ax, ay, bx, by;
Color color;
Boolean colorSetted = false;
@Override
public void mouseEntered(MouseEvent e) {
if(!colorSetted){
JColorChooser colorChooser =new JColorChooser();
this.color = colorChooser.showDialog(null, "Select a color", Color.BLACK);
colorSetted = true;
}
}
@Override
public void mousePressed(MouseEvent e) {
ax = e.getX();
ay = e.getY();
System.out.println("Mouse pressed: " + ax + ", " + ay);
}
@Override
public void mouseReleased(MouseEvent e) {
bx = e.getX();
by = e.getY();
System.out.println("Mouse released: " + bx + ", " + by);
lineEditor.addLine(ax, ay, bx, by, color);
colorSetted = false;
}
});
clearScreen.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
lineEditor.clearScreen();
}
});
backgroundFrame.pack();
backgroundFrame.setVisible(true);
}
}