Я не очень экспериментировал со слушателями. У меня есть Вектор Line2D (представляющий стены плана этажа). Я рисую их в JFrame.
Я пытаюсь настроить прослушиватель на эти строки, чтобы иметь возможность устанавливать их (менять цвет и т. Д.) При нажатии.
Я потерян, потому что я действительно не знаю, куда поместить слушателя. Я перепробовал много вещей, которые нашел на многих форумах, но на самом деле ничего не работает.
Спасибо.
Edit1:
привет, спасибо за ваш ответ. Это большие проекты со многими классами, поэтому я опубликую код и опишу, как он работает. Первый . Я импортирую изображение с поэтажным планом. У меня есть класс с действиями, который расширяет AbstractAction. Я использую opencv для извлечения строк. Я храню извлеченные строки в векторе стен (созданный мной класс).
Vector<wall> walls
А вот и мой класс стен
//a wall is represented by 2 points (pInitial and pFInal)
private Point pInitial, pFinal;
private double wallAttenuation;
private int wallType;
public wall(Point p1, Point p2) {
// p1 is lower by the height than p2
if (p1.getY() > p2.getY()) {
pInitial = p2;
pFinal = p1;
} else {
pInitial = p1;
pFinal = p2;
}
}
//method to set the attenuation of the wall
public void setWallAttenuation(double a) {
wallAttenuation = a;
}
//methods to set both ends of the wall
public void setPInitial(Point P1) {
pInitial.x=(int)P1.getX();
pInitial.x=(int)P1.getY();
}
public void setPFinal(Point P2) {
pFinal.x=(int)P2.getX();
pFinal.x=(int)P2.getY();
}
//methods to get wall attributes (attenuation , ends and type)
public double getWallAttenuation() {
return wallAttenuation;
}
public Point getPInitial() {
return pInitial;
}
public Point getPFinal() {
return pFinal;
}
public void setWallType(int type) {
wallType = type;
}
public int getWallType() {
return wallType;
}
теперь в моем классе importAction, и после обработки у меня есть этот вектор стен (каждая стена определяется начальной и конечной точкой. После этого я открываю новый фрейм, в котором я рисую линии. Я хочу иметь возможность щелкнуть на каждой стене для дальнейших модификаций.
Сначала я попытался создать класс Frame с обработкой событий мыши следующим образом:
public class CreateJFrameWindowWithMouseEventHandling extends JFrame implements MouseMotionListener,MouseListener {
private static final long serialVersionUID = 1L;
public CreateJFrameWindowWithMouseEventHandling() {
setTitle("Walls calibration");
addMouseListener(this);
}
@Override
public void mouseClicked(MouseEvent e) {
int x = e.getX();
int y = e.getY();
System.out.println("Mouse Clicked at X: " + x + " - Y: " + y);
}
@Override
public void mouseEntered(MouseEvent e) {
int x = e.getX();
int y = e.getY();
System.out.println("Mouse Entered frame at X: " + x + " - Y: " + y);
}
@Override
public void mouseExited(MouseEvent e) {
int x = e.getX();
int y = e.getY();
System.out.println("Mouse Exited frame at X: " + x + " - Y: " + y);
}
@Override
public void mousePressed(MouseEvent e) {
int x = e.getX();
int y = e.getY();
System.out.println("Mouse Pressed at X: " + x + " - Y: " + y);
}
@Override
public void mouseReleased(MouseEvent e) {
int x = e.getX();
int y = e.getY();
System.out.println("Mouse Released at X: " + x + " - Y: " + y);
}
@Override
public void mouseDragged(MouseEvent e) {
}
@Override
public void mouseMoved(MouseEvent e) {
int x = e.getX();
int y = e.getY();
System.out.println("Mouse at X: " + x + " - Y: " + y);
repaint();
}
private static void createAndShowGUI() {
//Create and set up the window.
JFrame frame = new CreateJFrameWindowWithMouseEventHandling();
//Display the window.
frame.setVisible(true);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
но я думаю, что это не было правильным решением. Следующее, что я попробовал, было создать JPanel, просмотреть вектор, нарисовать текущую линию и добавить слушателя. чтобы проверить, работает ли он, я изменяю курсор, если мышь находится над линией:
JFrame wallsEdit = new JFrame("Walls Calibration");
wallsEdit.add(new JPanel() {
@Override
protected void paintComponent(Graphics g) {
Graphics2D g2 = (Graphics2D)g;
for(int i=0;i<walls.size();i++)
{
Point p1 = walls.get(i).getPInitial();
Point p2 = editor.walls.get(i).getPFinal();
g2.setColor(Color.black);
g2.setStroke(new BasicStroke(10));
g2.drawLine((int)p1.getX(),(int)p1.getY(), (int)p2.getX(),(int)p2.getY());
walls.get(i).addMouseListener(new MouseAdapter() {
public void mouseMoved(MouseEvent e) {
Point CursorPoint= MouseInfo.getPointerInfo().getLocation();
double x = CursorPoint.getX();
double y = CursorPoint.getY();
Line2D.Double current = new Line2D.Double(p1.getX(),p1.getY(),p2.getX(),p2.getY()) ;
if(current.intersectsLine(x, y, x, y))
{ setCursor(Cursor.getPredefinedCursor(Cursor.MOVE_CURSOR));
} else { setCursor(Cursor.getPredefinedCursor(Cursor.DEFAULT_CURSOR));
}
repaint();
});
}
}
}, BorderLayout.CENTER);
wallsEdit.setAlwaysOnTop(true);
wallsEdit.setVisible(true);
wallsEdit.setDefaultCloseOperation(JFrame.HIDE_ON_CLOSE);
и, конечно, это не работает. так попробовал другую вещь. я объявил, что мой класс Wall расширяет Component и реализует mouseMotionListener и MouseListener. внутри я написал событие mouseMoved, как для панели.
надеюсь, что я дал все необходимые детали. любая помощь будет оценена большое спасибо