「这是我参与2022首次更文挑战的第7天,活动详情查看:2022首次更文挑战」
一、问题描述
在一个三维坐标系中,已知三个点,比如A点坐标:(0, 0, 0),B点坐标:(20, 0, 0), c点坐标:(0, 40, 0),求解这三个点所构成的三角形的面积是多少?
二、解题思路
当拿到这个问题的时候,我第一反应有点懵,不知怎么下手,后来冷静下来仔细想想我发现解题可以分为下面几部:
二维坐标系中的三角形面积求解
在一个二维坐标系中,已知三个点,比如A点坐标:(0, 0),B点坐标:(20, 0), c点坐标:(0, 40),求解这三个点所构成的三角形的面积是多少?
答:如果我们知道三角形底a,高h,则我可以用公式: S=ah/2
,或者我们知道两条边a,b和夹角C,着我们就可以用公式:S=1/2absinC
,这是小学数学问题了,但是如果我们知道向量a,和向量b,我们就可以用叉乘,我们就可以用公式:S=1/2|a||b|sin<|a||b|>
,因为在坐标系中,所以我们可以用这个公式解题:
向量a = (20, 0);向量b = (0, 40);面积就等于:1/2 * (20, 0) * (0, 40) = 400;
三维坐标系中的三角形面积求解
有了上面的解题思路我们发现,我们可以用向量的叉乘求夹角和面积,当我发现threejs里面有向量后,我决定用threejs 解决这个问题。
答: 向量a = (20, 0, 0);向量b = (0, 40, 0);面积就等于:1/2 * (20, 0, 0) * (0, 40, 0) = 400;
三、编码实现
- 先设置三角形的三个点坐标p1,p2,p3
// 三角形的三个点坐标p1,p2,p3
const p1 = new THREE.Vector3(0, 0, 0); // 点1坐标
const p2 = new THREE.Vector3(20, 0, 0); // 点2坐标
const p3 = new THREE.Vector3(0, 40, 0); // 点3坐标
- p1,p2两个点确定一个向量v1
// p1,p2两个点确定一个向量
const v1 = p1.clone().sub(p2);
- p1,p3两个点确定一个向量v2
// p1,p3两个点确定一个向量
const v2 = p1.clone().sub(p3);
- 返回三角形顶点p1对应夹角余弦值
const CosineValue = v1.dot(v2) / (v1.length() * v2.length());
- 返回三角形顶点p1对应夹角角度
Math.acos(CosineValue) * 180) / Math.PI
- 三角形面积计算
areaOfTriangle(
p1: THREE.Vector3,
p2: THREE.Vector3,
p3: THREE.Vector3
): number {
let v1 = new THREE.Vector3();
let v2 = new THREE.Vector3();
// 通过两个顶点坐标计算其中两条边构成的向量
v1 = p1.clone().sub(p2);
v2 = p1.clone().sub(p3);
const v3 = new THREE.Vector3();
// 三角形面积计算
v3.crossVectors(v1, v2);
const s = v3.length() / 2;
return s;
}
6.看结果
我们得出:三角形两条边夹角余弦值为 0
, 三角形两条边夹角为90
, 三角形的面积为400
。
四、思考
任意三角形的面积
有了上面三角形的公式,我们可以得出任意三角形的面积和夹角了,比如
const p1 = new THREE.Vector3(0, 0, 20); // 点1坐标
const p2 = new THREE.Vector3(20, 0, 0); // 点2坐标
const p3 = new THREE.Vector3(0, 40, 0); // 点3坐标
p1,p2,p3构成的三角形的面积是多少?
答: 三角形两条边夹角余弦值 0.3162277660168379
,三角形两条边夹角 71.56505117707799
,三角形的面积为600
。
任意长方形的面积
如果知道长方体p1,p2,p3,p4坐标求面积?
const p1 = new THREE.Vector3(0, 0, 20); // 点1坐标
const p2 = new THREE.Vector3(20, 0, 0); // 点2坐标
const p3 = new THREE.Vector3(0, 40, 0); // 点3坐标
const p4 = new THREE.Vector3(20, 40, 0); // 点4坐标
答:长方体就是两个三角形,所以我们的公式如下:
// 长方形
areaOfCuboid(
p1: THREE.Vector3,
p2: THREE.Vector3,
p3: THREE.Vector3,
p4: THREE.Vector3
): number {
let v1 = new THREE.Vector3();
let v2 = new THREE.Vector3();
let v3 = new THREE.Vector3();
let v4 = new THREE.Vector3();
// 通过两个顶点坐标计算其中两条边构成的向量
v1 = p1.clone().sub(p2);
v2 = p1.clone().sub(p3);
v3 = p4.clone().sub(p2);
v4 = p4.clone().sub(p3);
const v5 = new THREE.Vector3();
const v6 = new THREE.Vector3();
// 三角形面积计算
v5.crossVectors(v1, v2);
v6.crossVectors(v3, v4);
console.log(v5, v6);
const s1 = v5.length() / 2;
const s2 = v6.length() / 2;
return s1 + s2;
}
结果: 长方体的面积为1000