quadtree-ts
Version:
A simple quad tree implementation in TypeScript
149 lines • 7.72 kB
JavaScript
"use strict";
var __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (receiver, state, value, kind, f) {
if (kind === "m") throw new TypeError("Private method is not writable");
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a setter");
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot write private member to an object whose class did not declare it");
return (kind === "a" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;
};
var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
};
var _QuadTree_instances, _QuadTree_container, _QuadTree_children, _QuadTree_insert, _QuadTree_getAllItems, _QuadTree_addToChild, _QuadTree_getChildNodes, _QuadTree_getItems, _QuadTree_splitAndAddNextItem;
Object.defineProperty(exports, "__esModule", { value: true });
exports.QuadTree = void 0;
const utils_1 = require("./utils");
class QuadTree {
constructor(container) {
_QuadTree_instances.add(this);
_QuadTree_container.set(this, void 0);
_QuadTree_children.set(this, {
type: 'leaves',
items: [],
});
__classPrivateFieldSet(this, _QuadTree_container, container, "f");
}
get values() {
return __classPrivateFieldGet(this, _QuadTree_children, "f").type === 'leaves' ? __classPrivateFieldGet(this, _QuadTree_children, "f").items : [];
}
get children() {
return __classPrivateFieldGet(this, _QuadTree_children, "f").type === 'nodes' ? __classPrivateFieldGet(this, _QuadTree_children, "f").nodes : [];
}
get boundary() {
return __classPrivateFieldGet(this, _QuadTree_container, "f");
}
contains(point) {
return (0, utils_1.contains)(__classPrivateFieldGet(this, _QuadTree_container, "f"), point);
}
add(...items) {
for (const item of items) {
__classPrivateFieldGet(this, _QuadTree_instances, "m", _QuadTree_insert).call(this, item);
}
}
query(shape) {
if (shape == null) {
return __classPrivateFieldGet(this, _QuadTree_instances, "m", _QuadTree_getAllItems).call(this);
}
const result = [];
console.log({ shape, container: __classPrivateFieldGet(this, _QuadTree_container, "f") });
console.log((0, utils_1.intersects)(shape, __classPrivateFieldGet(this, _QuadTree_container, "f")));
if ((0, utils_1.doesFullyContain)(shape, __classPrivateFieldGet(this, _QuadTree_container, "f"))) {
result.push(...__classPrivateFieldGet(this, _QuadTree_instances, "m", _QuadTree_getAllItems).call(this));
}
else if ((0, utils_1.intersects)(shape, __classPrivateFieldGet(this, _QuadTree_container, "f"))) {
console.log(__classPrivateFieldGet(this, _QuadTree_instances, "m", _QuadTree_getItems).call(this));
for (const item of __classPrivateFieldGet(this, _QuadTree_instances, "m", _QuadTree_getItems).call(this)) {
console.log({ shape, item });
if ((0, utils_1.contains)(shape, item)) {
result.push(item);
}
}
for (const child of __classPrivateFieldGet(this, _QuadTree_instances, "m", _QuadTree_getChildNodes).call(this)) {
result.push(...child.query(shape));
}
}
return result;
}
}
exports.QuadTree = QuadTree;
_QuadTree_container = new WeakMap(), _QuadTree_children = new WeakMap(), _QuadTree_instances = new WeakSet(), _QuadTree_insert = function _QuadTree_insert(item) {
if (this.contains(item)) {
if (__classPrivateFieldGet(this, _QuadTree_children, "f").type === 'leaves' &&
__classPrivateFieldGet(this, _QuadTree_children, "f").items.length < QuadTree.MAX_ITEMS) {
__classPrivateFieldGet(this, _QuadTree_children, "f").items.push(item);
}
else if (__classPrivateFieldGet(this, _QuadTree_children, "f").type === 'leaves') {
__classPrivateFieldGet(this, _QuadTree_instances, "m", _QuadTree_splitAndAddNextItem).call(this, item);
}
else {
__classPrivateFieldGet(this, _QuadTree_instances, "m", _QuadTree_addToChild).call(this, item);
}
}
}, _QuadTree_getAllItems = function _QuadTree_getAllItems() {
const result = [];
result.push(...__classPrivateFieldGet(this, _QuadTree_instances, "m", _QuadTree_getItems).call(this));
for (const child of __classPrivateFieldGet(this, _QuadTree_instances, "m", _QuadTree_getChildNodes).call(this)) {
result.push(...child.query());
}
return result;
}, _QuadTree_addToChild = function _QuadTree_addToChild(unit) {
for (const child of __classPrivateFieldGet(this, _QuadTree_instances, "m", _QuadTree_getChildNodes).call(this)) {
if (child.contains(unit)) {
child.add(unit);
return;
}
}
}, _QuadTree_getChildNodes = function _QuadTree_getChildNodes() {
if (__classPrivateFieldGet(this, _QuadTree_children, "f").type === 'nodes') {
return __classPrivateFieldGet(this, _QuadTree_children, "f").nodes;
}
return [];
}, _QuadTree_getItems = function _QuadTree_getItems() {
if (__classPrivateFieldGet(this, _QuadTree_children, "f").type === 'leaves') {
return __classPrivateFieldGet(this, _QuadTree_children, "f").items;
}
return [];
}, _QuadTree_splitAndAddNextItem = function _QuadTree_splitAndAddNextItem(item) {
const items = [...__classPrivateFieldGet(this, _QuadTree_instances, "m", _QuadTree_getItems).call(this), item];
const splitWidth = __classPrivateFieldGet(this, _QuadTree_container, "f").size.width / 2;
const splitHeight = __classPrivateFieldGet(this, _QuadTree_container, "f").size.height / 2;
const splitSize = {
width: splitWidth,
height: splitHeight,
};
const topLeft = new QuadTree({
location: __classPrivateFieldGet(this, _QuadTree_container, "f").location,
size: splitSize,
});
const topRight = new QuadTree({
location: {
x: __classPrivateFieldGet(this, _QuadTree_container, "f").location.x + splitWidth,
y: __classPrivateFieldGet(this, _QuadTree_container, "f").location.y,
},
size: splitSize,
});
const bottomRight = new QuadTree({
location: {
x: __classPrivateFieldGet(this, _QuadTree_container, "f").location.x + splitWidth,
y: __classPrivateFieldGet(this, _QuadTree_container, "f").location.y + splitHeight,
},
size: splitSize,
});
const bottomLeft = new QuadTree({
location: {
x: __classPrivateFieldGet(this, _QuadTree_container, "f").location.x,
y: __classPrivateFieldGet(this, _QuadTree_container, "f").location.y + splitHeight,
},
size: splitSize,
});
__classPrivateFieldSet(this, _QuadTree_children, {
type: 'nodes',
nodes: [topLeft, topRight, bottomRight, bottomLeft],
}, "f");
for (const item of items) {
__classPrivateFieldGet(this, _QuadTree_instances, "m", _QuadTree_addToChild).call(this, item);
}
};
QuadTree.MAX_ITEMS = 4;
//# sourceMappingURL=QuadTree.js.map