编程语言
首页 > 编程语言> > Java 2D-拖动鼠标以平滑旋转图像

Java 2D-拖动鼠标以平滑旋转图像

作者:互联网

通过鼠标移动旋转图像背后的逻辑是什么?我知道如何使用graphics2d.rotate进行旋转…但是很难用鼠标作为旋转源.这是基本步骤:

>获得距锚点的鼠标x(dx)和鼠标y(dy)的距离(在这种情况下,
我们要旋转的图像的中心).
>在Math.arcTan2(dy,dx)中使用此点来获取角度或旋转.
>将step的值用于Graphics2D.rotate方法.

使用这种策略,每当我旋转图像时,图像都会从-pi开始旋转,旋转90度后,图像会回到-pi.我不明白我在做什么错,这应该是很基本的.

这是代码的一部分:

// mouse dragged events get sent here.
public void mouseDragged( MouseEvent e ) {
    int mx = e.getX( ), my = e.getY( );
    // just checking if it falls within bounds of the image we 
    // want to rotate.
    if( mx > speedKX || mx < speedKX + speedK.getWidth( ) || my > speedKY || my < speedKY + speedK.getHeight( )/2 )
    {
        theta += getTheta( e.getX( ), e.getY( ) ); 
    }
} 

解决方法:

据我了解,您应该寻找初始角度(单击时为锚点和点击之间的线)和当前角度(拖动时为同一行).该角度(与当前距锚点的距离无关)将为您提供旋转角度.

因此,您必须:

rotate(anglenow - angle0)

如何找到它:

在这两种情况下(初始单击和鼠标移动事件),您都必须找到以锚点为原点的锚点和鼠标点之间的角度.

我会使用一种方法(getAngle(x1,y1,x2,y2).该方法(除了类似x或y的竞争条件,易于检测)应该计算arctan(dy / dx).

标志

但是,当您划分dy / dx时,它可以是:

+ / + -> +
+ / - -> -
- / + -> -
- / - -> +

就是说,四个可能性给您两种结果.因此,您必须查看一些条件才能检测到它们.

我应该查看arctan doc或源代码,以查看其给出的值(0和pi之间,或-pi / 2和pi / 2之间),然后检查dx或dy的符号(取决于arctan返回的范围)并使用它将pi添加/减少到最终角度.

然后,您将获得一个getAngle方法,该方法可以正确返回360º空间.

编辑

Javadoc说:

Math.atan调整角度的反正切,范围为-pi / 2到pi / 2.

因此,假设您的值0角是我假设的X轴,则它返回的范围是右半球.因此,您必须区分左半球的右半球.

如果计算dx = xtarget-xorigin(如除法运算),则正确的半球是正确的将为正,否则为负.

因此,如果dy< 0,则必须将pi添加到结果角度.介于-pi / 2和3pi / 2之间.您还可以通过将全部传递到(-pi,pi)范围或(0,2pi)范围来校正结果. 编辑:伪代码,请仔细检查!

onmousedown {
    startpoint = (x,y);
    startangle = getAngle(origin, startpoint);
}

onmousemove {
    currentpoint = (x,y);
    currentangle = getAngle(origin, currentpoint);
    originalimage.rotate(currentangle - startangle);
}

getAngle(origin, other) {
    dy = other.y - origin.y;
    dx = other.x - origin.x;
    if (dx == 0) // special case
        angle = dy >= 0? PI/2: -PI/2;
    else
    {
        angle = Math.atan(dy/dx);
        if (dx < 0) // hemisphere correction
            angle += PI;
    }
    // all between 0 and 2PI
    if (angle < 0) // between -PI/2 and 0
        angle += 2*PI;
    return angle;
}

标签:image,mouseevent,java
来源: https://codeday.me/bug/20191106/2001455.html