@g20/euclid
Version:
Euclidean Geometry Utilities
65 lines (61 loc) • 2.07 kB
JavaScript
/**
* @g20/euclid 1.0.0-alpha.46
* (c) David Geo Holmes david.geo.holmes@gmail.com
* Released under the MIT License.
*/
'use strict';
var core = require('@g20/core');
/**
* The vector from the center of circleA to the center of circleB.
*/
const D = core.G20.vector(0, 0);
function circle_circle_intersection(circleA, circleB) {
const point1 = core.G20.zero.clone();
const point2 = core.G20.zero.clone();
const disposables = [];
let enabled = false;
const calculate = () => {
if (enabled) {
update_circle_crcle_intersection_points(point1, point2, circleA.X, circleB.X, circleA.radius.a, circleB.radius.a);
}
};
disposables.push(circleA.X.change$.subscribe(calculate));
disposables.push(circleB.X.change$.subscribe(calculate));
disposables.push(circleA.radius.change$.subscribe(calculate));
disposables.push(circleB.radius.change$.subscribe(calculate));
enabled = true;
calculate();
const disposable = {
dispose() {
core.dispose(disposables);
}
};
return [point1, point2, disposable];
}
function update_circle_crcle_intersection_points(point1, point2, ca, cb, R, r) {
if (R !== -1 && r !== -1) {
D.copyVector(cb).sub(ca);
const dd = D.quaditude();
const rr = r * r;
const RR = R * R;
const d = Math.sqrt(dd);
const λ = (dd - rr + RR) / (2 * d);
const aa = RR - λ * λ;
if (aa >= 0) {
const a = Math.sqrt(aa);
const dhat = D.clone().scale(1 / d);
const ahat = dhat.clone().mul(core.G20.I);
const λdhat = dhat.clone().scale(λ);
const avec = ahat.clone().scale(a);
point1.copyVector(ca).add(λdhat).add(avec);
point2.copyVector(ca).add(λdhat).sub(avec);
}
else {
// No intersection.
point1.set(NaN, NaN);
point2.set(NaN, NaN);
}
}
}
exports.circle_circle_intersection = circle_circle_intersection;
//# sourceMappingURL=index.js.map