float centerX = v.getX() + (float) v.getWidth() / 2;
float centerY = v.getY() + (float) v.getHeight() / 2;
double angle = Math.atan2(touchRawY - centerY, touchRawX - centerX) * 180 / Math.PI;
v.setRotation((float) angle - 45);
// scale
float xx = (touchRawX >= centerX ? deltaRawX : -deltaRawX);
float yy = (touchRawY >= centerY ? deltaRawY : -deltaRawY);
float sf = (v.getScaleX() + xx / v.getWidth() + v.getScaleY() + yy / v.getHeight()) / 2;
v.setScaleX(sf);
v.setScaleY(sf);
结果为正表示从 X 轴逆时针旋转的角度,结果为负表示从 X 轴顺时针旋转的角度。ATAN2(a, b) 与 ATAN(a/b)稍有不同,ATAN2(a,b)的取值范围介于 -pi 到 pi 之间(不包括 -pi),而ATAN(a/b)的取值范围介于-pi/2到pi/2之间(不包括±pi/2)。若要用度表示反正切值,请将结果再乘以 180/3.14159。另外要注意的是,函数atan2(y,x)中参数的顺序是倒置的,atan2(y,x)计算的值相当于点(x,y)的角度值。
/**
* Returns the angle <i>theta</i> from the conversion of rectangular
* coordinates ({@code x}, {@code y}) to polar
* coordinates (r, <i>theta</i>).
* This method computes the phase <i>theta</i> by computing an arc tangent
* of {@code y/x} in the range of -<i>pi</i> to <i>pi</i>. Special
* cases:
* <ul><li>If either argument is NaN, then the result is NaN.
* <li>If the first argument is positive zero and the second argument
* is positive, or the first argument is positive and finite and the
* second argument is positive infinity, then the result is positive
* zero.
* <li>If the first argument is negative zero and the second argument
* is positive, or the first argument is negative and finite and the
* second argument is positive infinity, then the result is negative zero.
* <li>If the first argument is positive zero and the second argument
* is negative, or the first argument is positive and finite and the
* second argument is negative infinity, then the result is the
* {@code double} value closest to <i>pi</i>.
* <li>If the first argument is negative zero and the second argument
* is negative, or the first argument is negative and finite and the
* second argument is negative infinity, then the result is the
* {@code double} value closest to -<i>pi</i>.
* <li>If the first argument is positive and the second argument is
* positive zero or negative zero, or the first argument is positive
* infinity and the second argument is finite, then the result is the
* {@code double} value closest to <i>pi</i>/2.
* <li>If the first argument is negative and the second argument is
* positive zero or negative zero, or the first argument is negative
* infinity and the second argument is finite, then the result is the
* {@code double} value closest to -<i>pi</i>/2.
* <li>If both arguments are positive infinity, then the result is the
* {@code double} value closest to <i>pi</i>/4.
* <li>If the first argument is positive infinity and the second argument
* is negative infinity, then the result is the {@code double}
* value closest to 3*<i>pi</i>/4.
* <li>If the first argument is negative infinity and the second argument
* is positive infinity, then the result is the {@code double} value
* closest to -<i>pi</i>/4.
* <li>If both arguments are negative infinity, then the result is the
* {@code double} value closest to -3*<i>pi</i>/4.</ul>
*
* <p>The computed result must be within 2 ulps of the exact result.
* Results must be semi-monotonic.
*
* @param y the ordinate coordinate
* @param x the abscissa coordinate
* @return the <i>theta</i> component of the point
* (<i>r</i>, <i>theta</i>)
* in polar coordinates that corresponds to the point
* (<i>x</i>, <i>y</i>) in Cartesian coordinates.
*/
@FastNative
public static native double atan2(double y, double x);