无法根据光标调整 Rectangle2D 的大小

Unable to resize a Rectangle2D following the cursor

我正在尝试使用鼠标拖动方法调整 一个Rectangle2D。 另外我想重新居中它在JPanel的中间。 我认为代码和公式是正确的,但它不能正常工作,因为它过度调整了矩形的大小并且它不适合跟随光标。

这里我会post相关代码

构造函数:

public Canvas(double width, double height) {
    this.width = width;
    this.height = height;

    rect = new Rectangle2D.Double(this.x, this.y, this.width, this.height);
    vertex = new Rectangle2D[4];

    this.addMouseMotionListener(this);
    this.addMouseListener(this);
}

vertexRectangle2D 的数组,仅当鼠标在

内时才绘制到矩形的顶点

paintComponent:

@Override
protected void paintComponent(Graphics g) {
    super.paintComponent(g);

    //RETTANGOLO
    Graphics2D g2 = (Graphics2D)g;
    Stroke oldStroke = g2.getStroke();
    g2.setStroke(new BasicStroke(SPESSORE));
    g2.draw(rect);
    g2.setStroke(oldStroke);
    g2.setColor(Color.BLACK);

    setAtCenter();

    //VERTICI
    vertex[0] = new Rectangle2D.Double(this.x, this.y, SIZEV, SIZEV);
    vertex[1] = new Rectangle2D.Double(this.x + this.width - SIZEV, 
                                        this.y, SIZEV, SIZEV);
    vertex[2] = new Rectangle2D.Double(this.x, this.y + this.height - SIZEV, 
                                        SIZEV, SIZEV);
    vertex[3] = new Rectangle2D.Double(this.x + this.width - SIZEV, 
                                        this.y + this.height - SIZEV, 
                                        SIZEV, SIZEV);
    if (dentro) {
        for (int i = 0; i < 4; i++) {
            g2.draw(vertex[i]);
        }
    } 
}

private void setAtCenter() {
    this.x = ((this.getWidth()/2) - (this.width/2));
    this.y = ((this.getHeight()/2) - (this.height/2));
    rect.setRect(x, y, this.width, this.height);
}

mouseMoved:

@Override
public void mouseMoved(MouseEvent e) {
    dentro = false;
    inVertex = -1;
    if (rect.contains(e.getPoint())) {
        dentro = true;
    }
    for (int i = 0; i < 4; i++) {
        if (vertex[i].contains(e.getPoint())) {
            inVertex = i;
            break;
        }
    }
}

鼠标按下:

@Override
public void mousePressed(MouseEvent e) {
    if (inVertex >= 0) {
        this.startX = e.getX();
        this.startY = e.getY();
    }
}

鼠标拖动:

@Override
public void mouseDragged(MouseEvent e) {
    double dX;
    double dY;
    if (inVertex >= 0) {
        this.endX = e.getX();
        this.endY = e.getY();
        dX = startX - endX;
        dY = startY - endY;
        this.width += dX;
        this.height += dY;
        this.repaint();
    }
}

我希望我已经 post 提供了所有必要的信息,并且终于有人帮助我解决了这个困扰我太久的问题。

编辑: 我通过相应地设置宽度和高度来跟踪顶点的位置解决了这个问题。我简化了代码,只允许从原点调整大小。感谢支持。

谢谢大家!

mouseDragged()会被重复调用。在您当前的实现中,每次调用 mouseDragged() 时,您都会一次又一次地添加整个距离,而不是仅仅添加自上次 mouseDragged() 调用以来发生的变化。

    this.width += dX;
    this.height += dY;

一个快速修复方法是在每次调用 mouseDragged() 时将当前位置存储在 startXstartY 中。

@Override
public void mouseDragged(MouseEvent e) {
    double dX;
    double dY;
    if (inVertex >= 0) {
        this.endX = e.getX();
        this.endY = e.getY();
        dX = startX - endX;
        dY = startY - endY;
        this.width += dX;
        this.height += dY;

        this.startX = this.endX;
        this.startY = this.endY;

        this.repaint();
    }
}

但是这种将大小的增量变化相加是一种奇怪的方法。你可能最好只跟踪哪个顶点被抓取,然后更新它的位置。然后根据顶点的位置绘制形状,而不跟踪大小变化——也就是说,矩形的大小是基于顶点的位置隐含的。