1. 簡介
向量是指在數學中用于表示大小和方向的量。在計算機科學中,向量通常用于表示物體的位置、速度和加速度等。在Java中,可以使用坐標系中兩點之間的差異來計算向量之間的距離。
在二維空間中,向量通常表示為一個有序的數對(x, y),其中x和y分別表示向量在x軸和y軸上的分量。例如,向量(3, 4)表示一個向右3個單位和向上4個單位的向量。在三維空間中,向量通常表示為一個有序的三元組(x, y, z),其中x、y和z分別表示向量在x、y和z軸上的分量。
我們可以通過計算線段的向量,來判斷手指(鼠標)在屏幕中的移動方向。速度等信息。可以通過向量計算兩條線段的夾角度數等。
2. 獲取線段的向量
向量可以進行加法和減法運算。向量的加法運算是將兩個向量的分量相加,得到一個新的向量。向量的減法運算是將一個向量的分量減去另一個向量的分量,得到一個新的向量。
而我們如何通過坐標獲取線段的向量呢?很簡單x1-x2 就是向量x,y1-y2就是向量y。合起來就是向量在二維平面(直角坐標系)中的向量值:
public static void getVectors(Point p1,Point p2,Point p3,Point p4){
double ABx = p1.x - p2.x;
double ABy = p1.y - p2.y;
double CDx = p3.x - p4.x;
double CDy = p3.y - p4.y;
System.out.println("線段1的向量是: (" + ABx + ", " + ABy + ").");
System.out.println("線段2的向量是: (" + CDx + ", " + CDy + ").");
//向量的加法:
double[] sum = new double[2];
sum[0] = ABx + CDx;
sum[1] = ABy + CDy;
//得到的和sum就是一個新的向量了。是線段1和線段2的向量和。而減法也就是將+號跟換為-號而已。
}
我們得到的向量有什么用處呢?下面就是向量的一些簡單使用場景了。
3. 計算線段和X軸的角度
假如,我們有兩個任意的坐標點,需要計算這兩個坐標點連接的線段與X軸的夾角。
我們可以使用向量的知識,很簡單的得到這個角度:
public double getDegrees(Point p1, Point p2) {
//得到兩個坐標點的差值, 其實得到的dx 和dy 就是我們線條的向量了
double dx = p2.x - p1.x;
double dy = p2.y - p1.y;
double angleRadians = Math.atan2(dy, dx); // 根據該方法,可以直接獲取坐標點和x軸的夾角,返回的是一個-π到π之間的弧度值
double degrees = Math.toDegrees(angleRadians); //調用Math的API 將弧度轉為角度,角度值范圍為±180°。
return degrees;
}
在這個方法中,我們傳入的坐標點的Y值的大小,決定了角度的正負數。
如果p1的Y值大于p2,返回的就是:-179°~0 中間的值。
如果p1的Y值小于p2,返回的就是:0~180°中間的值。
我們如果結合手機或者電腦屏幕的坐標來計算。
簡單理解就是,點p1在p2的上方,那么計算的就是從x軸出發順時針的角度,也就是0~180°
而點p1在點p2的下方,那么計算的就是從x軸出發,逆時針的角度。也就是-179°~0。(因為180°的時候,p1和p2平行,無所謂順時針逆時針)。
4. 根據用戶移動軌跡,判斷用戶的移動方向
在上面計算了線段和X軸的夾角。我們其實可以根據這個角度,判斷計算用戶的移動軌跡。也就能得到用戶手指或者鼠標的移動軌跡了。
示例如下:
public static String getDegrees(Point p1, Point p2) {
//得到線段的向量
double dx = p2.x - p1.x;
double dy = p2.y - p1.y;
//得到線段和x軸的夾角弧度
double angleRadians = Math.atan2(dy, dx);
//zinyan.com 將弧度值轉為角度值
double degrees = Math.toDegrees(angleRadians);
//根據角度確定方向
if (degrees >= -45 && degrees < 45) {
return "right";//從右往左,也就是所謂的右邊進入
} else if (degrees >= 45 && degrees < 135) {
return "up"; //從下往上 ,也就是所謂的上部進入
} else if (degrees >= -135 && degrees < -45) {
return "down";//從上往下 ,也就是所謂的底部進入
} else {
return "left"; //其他的就是左邊進入的了, 從左往右移動的軌跡
}
}
上面的角度比較值,其實45度比較好理解。我們平面畫一條直線當做X軸。線條上面的就是0~-180°,線條下面的就是0~180°
然后畫一個米字格,每個線段的夾角就是45°。那么右邊就是±45°。上面就是45°~135°了(PS:135=45+45+45)。
5. 通過向量和角度,計算兩個線條的夾角
在前面,我們計算了如何獲取線條和X軸的夾角。我們如果有兩條線段,那么如何獲取這兩條線段的夾角呢?
處理邏輯很簡單,例如線段1和x軸的夾角是90°,線段2和x軸的夾角是130°。那么線段1和線段2的夾角應該是:130°-90°=40°
使用x軸當做基準點,進行處理,你會發現運算邏輯很簡單,具體示例代碼如下:
//p1和p2 組合成線段1,p3和p4組合成線段2
public static double getDegress(Point p1,Point p2,Point p3,Point p4){
//這里是p2-p1也可以是p1-p2 位置是無所謂的,只是要統一。如果x軸是p2-p1,那么y軸也得是p2-p1
double d1x = p2.x - p1.x;
double d1y = p2.y - p1.y;
//這個的邏輯和上面一樣,p3-p4或者p4-p3都可以
double d2x = p4.x - p3.x;
double d2y = p4.y - p3.y;
//然后通過atan2 得到弧度,要注意了這個方法中必須是y軸值在前面,x軸值在后面
//兩個弧度相減,就是兩個線段的夾角弧度
double angle = Math.atan2(d1y, d1x) - Math.atan2(d2y, d2x);
//將弧度,轉為角度。并通過絕對值去除正負符號
angle = Math.abs(Math.toDegrees(angle));
if (angle > 180) {
//因為線段夾角內角+外角=360°,
// 如果超過180°了說明我們得到的是最大的外角了,而夾角應該是最小的角度,所以進行了360-angile
angle = 360 - angle;
}
return angle;
}
當我們使用向量和Math的API。你會發現計算角度等會很方便
Math.atan2() 方法返回從 X 軸到指定坐標點 (x,y) 之間的角度(以弧度為單位)。它是 Math.atan(y/x)的安全版,可以避免除數為 0 的情況。
6. 小結
關于向量也就是這些了。還有更多復雜的使用場景。這里就不擴展了,太復雜了。