@woosh/meep-engine 2.67.0 → 2.68.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (50) hide show
  1. package/build/meep.cjs +0 -1
  2. package/build/meep.module.js +0 -1
  3. package/package.json +1 -1
  4. package/src/engine/graphics/ecs/mesh/Mesh.d.ts +0 -1
  5. package/src/engine/graphics/ecs/mesh-v2/ShadedGeometry.d.ts +0 -5
  6. package/src/engine/graphics/ecs/mesh-v2/ShadedGeometry.js +0 -1
  7. package/src/engine/graphics/material/optimization/prototypeMaterialOptimizer.js +16 -19
  8. package/src/engine/graphics/render/forward_plus/prototype/prototypeLightManager.js +46 -47
  9. package/src/core/bvh2/BVHTasks.js +0 -65
  10. package/src/core/bvh2/BinaryNode.d.ts +0 -13
  11. package/src/core/bvh2/BinaryNode.js +0 -1188
  12. package/src/core/bvh2/BinaryNode.spec.js +0 -309
  13. package/src/core/bvh2/LeafNode.d.ts +0 -7
  14. package/src/core/bvh2/LeafNode.js +0 -147
  15. package/src/core/bvh2/Node.d.ts +0 -9
  16. package/src/core/bvh2/Node.js +0 -196
  17. package/src/core/bvh2/NodeValidator.js +0 -197
  18. package/src/core/bvh2/StacklessTraverser.js +0 -154
  19. package/src/core/bvh2/StacklessTraverser.spec.js +0 -109
  20. package/src/core/bvh2/serialization/deserializeBinaryNode.js +0 -40
  21. package/src/core/bvh2/serialization/deserializeBinaryNodeFromBinaryBuffer.js +0 -90
  22. package/src/core/bvh2/serialization/serializeBinaryNode.js +0 -31
  23. package/src/core/bvh2/serialization/serializeBinaryNodeToBinaryBuffer.js +0 -86
  24. package/src/core/bvh2/transform/BottomUpOptimizingRebuilder.js +0 -144
  25. package/src/core/bvh2/transform/RotationOptimizer.js +0 -123
  26. package/src/core/bvh2/transform/RotationOptimizer.spec.js +0 -303
  27. package/src/core/bvh2/transform/tryRotateSingleNode.js +0 -260
  28. package/src/core/bvh2/traversal/BVHVisitor.js +0 -30
  29. package/src/core/bvh2/traversal/RaycastBVHVisitor.js +0 -66
  30. package/src/core/bvh2/traversal/ThreeClippingPlaneComputingBVHVisitor.js +0 -384
  31. package/src/core/bvh2/traversal/ThreeFrustumsIntersectionBVHVisitor.js +0 -52
  32. package/src/core/bvh2/traversal/bvh_traverse_pre_order_using_stack.js +0 -43
  33. package/src/core/bvh2/traversal/queryBinaryNode_ClippingPlanes.d.ts +0 -5
  34. package/src/core/bvh2/traversal/queryBinaryNode_ClippingPlanes.js +0 -66
  35. package/src/core/bvh2/traversal/queryBinaryNode_CollectData.js +0 -49
  36. package/src/core/bvh2/traversal/queryBinaryNode_CollectLeaves.js +0 -51
  37. package/src/core/bvh2/traversal/queryBinaryNode_FrustumIntersections.js +0 -77
  38. package/src/core/bvh2/traversal/queryBinaryNode_SphereIntersections.js +0 -63
  39. package/src/core/bvh2/traversal/traverseBinaryNodeUsingVisitor.js +0 -50
  40. package/src/core/bvh2/traversal/traverseBinaryNodeUsingVisitor_DepthFirst_PreOrder.js +0 -34
  41. package/src/core/bvh2/util/find_least_common_ancestor.js +0 -34
  42. package/src/core/bvh2/visual/convert_bvh_to_dot_format_string.js +0 -50
  43. package/src/core/geom/2d/bvh/BinaryNode2.js +0 -152
  44. package/src/core/geom/2d/bvh/LeafNode2.js +0 -11
  45. package/src/core/geom/2d/bvh/Node2.js +0 -51
  46. package/src/engine/ecs/terrain/tiles/FirstRayIntersectionTerrainBVHVisitor.js +0 -74
  47. package/src/engine/graphics/geometry/bvh/BVHFromGeometry.js +0 -72
  48. package/src/engine/graphics/geometry/bvh/buffered/BVHGeometryRaycaster.js +0 -240
  49. package/src/engine/graphics/geometry/bvh/buffered/IndexedTraingleBoundsComputer.js +0 -43
  50. package/src/engine/graphics/render/forward_plus/query/query_bvh_frustum_from_objects.js +0 -133
@@ -1,197 +0,0 @@
1
- import { BinaryNode } from "./BinaryNode.js";
2
- import { isLeaf } from "./LeafNode.js";
3
- import { buildShortStringPath } from "./Node.js";
4
-
5
- /**
6
- *
7
- * @param {Node} node
8
- * @param {ViolationType} type
9
- * @param {String} message
10
- * @constructor
11
- */
12
- function Violation(node, type, message) {
13
- this.node = node;
14
- this.type = type;
15
- this.message = message;
16
- }
17
-
18
-
19
- Violation.prototype.toString = function () {
20
- return `Path: ${buildShortStringPath(this.node, 5)}, Type: ${this.type}, Message: ${this.message}`;
21
- };
22
-
23
- /**
24
- *
25
- * @enum {string}
26
- */
27
- const ViolationType = {
28
- IllegalChildValue: "illegal child value",
29
- IllegalParentValue: "illegal parent value",
30
- Containment: "containment",
31
- Bounds: "bounds"
32
- };
33
-
34
-
35
- /**
36
- *
37
- * @param {BinaryNode} node
38
- * @param {function(Violation)} violationCallback
39
- * @returns {boolean}
40
- */
41
- function validateTree(node, violationCallback) {
42
- const visited = new Set();
43
- let violatingNodes = 0;
44
- node.traversePreOrder(function (n) {
45
- if (visited.has(n)) {
46
- violatingNodes++;
47
- addReason(node, ViolationType.Containment, `node is found in multiple locations in the tree`, violationCallback);
48
- } else {
49
- visited.add(n);
50
- }
51
-
52
- let isValid = validateNode(n, violationCallback);
53
-
54
- if (!isValid) {
55
- violatingNodes++;
56
- }
57
- });
58
- return violatingNodes === 0;
59
- }
60
-
61
- function addReason(node, type, message, reasonCallback, reasonCallbackThisArg) {
62
- if (typeof reasonCallback === "function") {
63
- const violation = new Violation(node, type, message);
64
- reasonCallback.call(reasonCallbackThisArg, violation);
65
- }
66
- }
67
-
68
- /**
69
- *
70
- * @param {NodeDescription} node
71
- * @param {function(Violation)} violationCallback
72
- * @param reasonCallbackThisArg
73
- * @returns {boolean}
74
- */
75
- function validateNode(node, violationCallback, reasonCallbackThisArg) {
76
- let result = true;
77
-
78
- /**
79
- *
80
- * @param {*} value
81
- * @param {string} name
82
- * @returns {boolean}
83
- */
84
- function validateCoordinate(value, name) {
85
- let result = true;
86
- if (typeof value !== "number") {
87
- addReason(node, ViolationType.Bounds, `${name} must be a number, but instead was ${typeof value}`, violationCallback, reasonCallbackThisArg);
88
- result = false;
89
- } else if (Number.isNaN(value)) {
90
- addReason(node, ViolationType.Bounds, `${name} is NaN`, violationCallback, reasonCallbackThisArg);
91
- result = false;
92
- }
93
- return result;
94
- }
95
-
96
- function validateAxis(name) {
97
- const v0Name = name + "0";
98
- const v1Name = name + "1";
99
-
100
- const v0 = node[v0Name];
101
- const v1 = node[v1Name];
102
-
103
- const valid0 = validateCoordinate(v0, v0Name);
104
- const valid1 = validateCoordinate(v1, v1Name);
105
-
106
- if (!valid0 || !valid1) {
107
- result = false;
108
- } else if (v0 > v1) {
109
- addReason(node, ViolationType.Bounds, `${v0Name}(=${v0}) > ${v1Name}(=${v1}), negative size`, violationCallback, reasonCallbackThisArg);
110
- result = false;
111
- }
112
- }
113
-
114
- //check bounds
115
- validateAxis("x");
116
- validateAxis("y");
117
- validateAxis("z");
118
-
119
- if (!isLeaf(node)) {
120
- const binaryNodeConstraintsValid = validateBinaryNode(node, violationCallback, reasonCallbackThisArg);
121
- if (!binaryNodeConstraintsValid) {
122
- result = false;
123
- }
124
- }
125
-
126
- return result;
127
- }
128
-
129
- /**
130
- *
131
- * @param {BinaryNode} node
132
- * @param {function(Violation)} [reasonCallback]
133
- * @param {*} [reasonCallbackThisArg]
134
- * @returns {boolean}
135
- */
136
- function validateBinaryNode(node, reasonCallback, reasonCallbackThisArg) {
137
-
138
- function validateChild(child, name) {
139
- if (child === null) {
140
- return true;
141
- }
142
-
143
- if (child === undefined) {
144
- addReason(node, ViolationType.IllegalChildValue, name + " child is 'undefined', this is an illegal value.", reasonCallback, reasonCallbackThisArg);
145
- return false;
146
- }
147
-
148
- if (child.parentNode !== node) {
149
- addReason(node, ViolationType.IllegalParentValue, name + " child is parented to different node than this one.", reasonCallback, reasonCallbackThisArg);
150
- return false;
151
- }
152
-
153
- if (!node.containsBox(child)) {
154
- addReason(node, ViolationType.Containment, name + " child violates parent's bounds", reasonCallback, reasonCallbackThisArg);
155
- return false;
156
- }
157
-
158
- return true;
159
- }
160
-
161
- let result = true;
162
-
163
- result = result && validateChild(node.left, "left");
164
- result = result && validateChild(node.right, "right");
165
-
166
- //left and right node must be different nodes
167
- if (node.left !== null && node.left === node.right) {
168
- addReason(node, ViolationType.IllegalChildValue, "left and right child are the same non-null node", reasonCallback, reasonCallbackThisArg);
169
- result = false;
170
- }
171
-
172
- return result;
173
- }
174
-
175
- function validateContainment(node, violation) {
176
- if (node.left !== null) {
177
- if (!node.containsBox(node.left)) {
178
- violation(node.left)
179
- } else if (node.left instanceof BinaryNode) {
180
- validateContainment(node.left, violation);
181
- }
182
-
183
- }
184
- if (node.right !== null) {
185
- if (!node.containsBox(node.right)) {
186
- violation(node.right)
187
- } else if (node.right instanceof BinaryNode) {
188
- validateContainment(node.right, violation);
189
- }
190
- }
191
- }
192
-
193
- export {
194
- ViolationType,
195
- validateNode,
196
- validateTree
197
- };
@@ -1,154 +0,0 @@
1
- import { isLeaf } from "./LeafNode.js";
2
-
3
- const StateFromParent = 0;
4
- const StateFromSibling = 1;
5
- const StateFromChild = 2;
6
-
7
- function getLeft(node) {
8
- return node.left;
9
- }
10
-
11
- function parent(node) {
12
- return node.parentNode;
13
- }
14
-
15
- function sibling(node) {
16
- const parentNode = node.parentNode;
17
- return parentNode.right;
18
- }
19
-
20
-
21
- /**
22
- * Implementation based on code listing from paper:
23
- * "Efficient Stack-less BVH Traversal for Ray Tracing" 2011 Michal Hapala et.al
24
- * http://www.sci.utah.edu/~wald/Publications/2011/StackFree/sccg2011.pdf
25
- *
26
- * NOTE: Based on a few quick benchmarks this algorithm is slower than using stack
27
- * NOTE: this algorithm could be useful for incremental traversal as it retains state
28
- */
29
- function StacklessTraverser() {
30
- this.state = 0;
31
- /**
32
- *
33
- * @type {BinaryNode|null}
34
- */
35
- this.current = null;
36
- }
37
-
38
- /**
39
- *
40
- * @param {BinaryNode} node
41
- */
42
- StacklessTraverser.prototype.init = function (node) {
43
- this.root = node;
44
- this.state = StateFromParent;
45
- this.current = node;
46
- };
47
-
48
- /**
49
- *
50
- * Advanced traverser. Visitor will be invoked only on those advancements that produce a unique visit
51
- * @param {function(node:NodeDescription):boolean} visitor terminate branch and do no traverse descendants when visitor returns false
52
- * @param {*} [thisArg]
53
- * @returns {boolean}
54
- */
55
- StacklessTraverser.prototype.advance = function (visitor, thisArg) {
56
- let n;
57
-
58
- let state = this.state, current = this.current;
59
-
60
- switch (state) {
61
- case StateFromChild:
62
- //traversal up
63
- if (current === this.root) {
64
- //finished
65
- return false;
66
- }
67
- n = sibling(current);
68
- if (current === n || n == null) {
69
- //ascend
70
- current = parent(current);
71
- state = StateFromChild;
72
- } else {
73
- //move right
74
- current = n;
75
- state = StateFromSibling;
76
- }
77
- break;
78
- case StateFromSibling:
79
- if (visitor.call(thisArg, current) === false || isLeaf(current)) {
80
- current = parent(current);
81
- state = StateFromChild;
82
- } else {
83
- n = getLeft(current);
84
- if (n === null) {
85
- //ascent
86
- current = parent(current);
87
- state = StateFromChild;
88
- } else {
89
- //descend
90
- current = n;
91
- state = StateFromParent;
92
- }
93
- }
94
- break;
95
- case StateFromParent:
96
- if (visitor.call(thisArg, current) === false || isLeaf(current)) {
97
- n = sibling(current);
98
- if (n == null) {
99
- //ascend
100
- current = parent(current);
101
- state = StateFromChild;
102
- } else {
103
- //more right
104
- current = n;
105
- state = StateFromSibling;
106
- }
107
- } else {
108
- n = getLeft(current);
109
- if (n === null) {
110
- if (current.parentNode === null) {
111
- //already at root
112
- n = current.right;
113
- if (n === null) {
114
- //put traverser into terminal state
115
- current = this.root;
116
- state = StateFromChild;
117
- } else {
118
- current = n;
119
- state = StateFromSibling;
120
- }
121
- } else {
122
-
123
- n = sibling(current);
124
- if (n === null) {
125
- //ascent
126
- current = parent(current);
127
- state = StateFromChild;
128
-
129
- } else {
130
- current = n;
131
- state = StateFromSibling;
132
- }
133
- }
134
- } else {
135
- //descend
136
- current = n;
137
- state = StateFromParent;
138
- }
139
- }
140
- break;
141
- }
142
-
143
- this.current = current;
144
- this.state = state;
145
-
146
- return true;
147
- };
148
-
149
- export {
150
- StacklessTraverser,
151
- StateFromParent,
152
- StateFromSibling,
153
- StateFromChild
154
- };
@@ -1,109 +0,0 @@
1
- import { jest } from "@jest/globals";
2
- import { BinaryNode } from "./BinaryNode.js";
3
- import { StacklessTraverser } from "./StacklessTraverser.js";
4
-
5
- test("empty node traversal", () => {
6
- const node = new BinaryNode();
7
-
8
- const traverser = new StacklessTraverser();
9
-
10
- traverser.init(node);
11
-
12
- const visitor = jest.fn();
13
-
14
- expect(traverser.advance(visitor)).toBe(true);
15
-
16
- expect(visitor).toHaveBeenCalledTimes(1);
17
- expect(visitor).toHaveBeenCalledWith(node);
18
-
19
- expect(traverser.advance(visitor)).toBe(false);
20
-
21
- expect(visitor).toHaveBeenCalledTimes(1);
22
- });
23
-
24
- test("only left child", () => {
25
- const node = new BinaryNode();
26
- node.left = new BinaryNode();
27
- node.left.parentNode = node;
28
-
29
- const traverser = new StacklessTraverser();
30
-
31
- traverser.init(node);
32
-
33
- const visitor = jest.fn();
34
-
35
- expect(traverser.advance(visitor)).toBe(true);
36
-
37
- expect(visitor).toHaveBeenCalledTimes(1);
38
- expect(visitor).toHaveBeenCalledWith(node);
39
-
40
- expect(traverser.advance(visitor)).toBe(true);
41
-
42
- expect(visitor).toHaveBeenCalledTimes(2);
43
- expect(visitor).toHaveBeenLastCalledWith(node.left);
44
-
45
- expect(traverser.advance(visitor)).toBe(false);
46
-
47
- expect(visitor).toHaveBeenCalledTimes(2);
48
- });
49
-
50
- test("only right child", () => {
51
- const node = new BinaryNode();
52
- node.right = new BinaryNode();
53
- node.right.parentNode = node;
54
-
55
- const traverser = new StacklessTraverser();
56
-
57
- traverser.init(node);
58
-
59
- const visitor = jest.fn();
60
-
61
- expect(traverser.advance(visitor)).toBe(true);
62
-
63
- expect(visitor).toHaveBeenCalledTimes(1);
64
- expect(visitor).toHaveBeenCalledWith(node);
65
-
66
- expect(traverser.advance(visitor)).toBe(true);
67
-
68
- expect(visitor).toHaveBeenCalledTimes(2);
69
- expect(visitor).toHaveBeenLastCalledWith(node.right);
70
-
71
- expect(traverser.advance(visitor)).toBe(false);
72
-
73
- expect(visitor).toHaveBeenCalledTimes(2);
74
- });
75
-
76
- test("node with left and right child", () => {
77
- const node = new BinaryNode();
78
-
79
- node.right = new BinaryNode();
80
- node.right.parentNode = node;
81
-
82
- node.left = new BinaryNode();
83
- node.left.parentNode = node;
84
-
85
- const traverser = new StacklessTraverser();
86
-
87
- traverser.init(node);
88
-
89
- const visitor = jest.fn();
90
-
91
- expect(traverser.advance(visitor)).toBe(true);
92
-
93
- expect(visitor).toHaveBeenCalledTimes(1);
94
- expect(visitor).toHaveBeenCalledWith(node);
95
-
96
- expect(traverser.advance(visitor)).toBe(true);
97
-
98
- expect(visitor).toHaveBeenCalledTimes(2);
99
- expect(visitor).toHaveBeenLastCalledWith(node.left);
100
-
101
- expect(traverser.advance(visitor)).toBe(true);
102
-
103
- expect(visitor).toHaveBeenCalledTimes(3);
104
- expect(visitor).toHaveBeenLastCalledWith(node.right);
105
-
106
- expect(traverser.advance(visitor)).toBe(false);
107
-
108
- expect(visitor).toHaveBeenCalledTimes(3);
109
- });
@@ -1,40 +0,0 @@
1
- import { BinaryNode } from "../BinaryNode.js";
2
- import { deserializeLeafNode, LeafNode } from "../LeafNode.js";
3
- import { deserializeAABB3 } from "../../geom/3d/aabb/deserializeAABB3.js";
4
-
5
- /**
6
- *
7
- * @param {BinaryBuffer} buffer
8
- * @param {BinaryNode} node
9
- * @param {function(buffer:BinaryBuffer):void} leafValueDeserializer
10
- */
11
- function deserializeBinaryNode(buffer, node, leafValueDeserializer) {
12
- deserializeAABB3(buffer, node);
13
-
14
- function deserializeChild() {
15
- const nodeType = buffer.readUint8();
16
- if (nodeType === 0) {
17
- return null;
18
- } else if (nodeType === 1) {
19
- const leafNode = new LeafNode();
20
- deserializeLeafNode(buffer, leafNode, leafValueDeserializer);
21
- leafNode.parentNode = node;
22
- return leafNode;
23
- } else if (nodeType === 2) {
24
- const binaryNode = new BinaryNode();
25
- deserializeBinaryNode(buffer, binaryNode, leafValueDeserializer);
26
- binaryNode.parentNode = node;
27
- return binaryNode;
28
- }
29
- }
30
-
31
- const leftNode = deserializeChild();
32
- const rightNode = deserializeChild();
33
-
34
- node.left = leftNode;
35
- node.right = rightNode;
36
-
37
- node.updateLeafNodeCount();
38
- }
39
-
40
- export { deserializeBinaryNode };
@@ -1,90 +0,0 @@
1
- import { BinaryNode } from "../BinaryNode.js";
2
- import { LeafNode } from "../LeafNode.js";
3
- import { deserializeAABB3Encoded_v0 } from "../../geom/3d/aabb/deserializeAABB3Encoded_v0.js";
4
- import { deserializeAABB3 } from "../../geom/3d/aabb/deserializeAABB3.js";
5
-
6
- /**
7
- *
8
- * @param {BinaryNode} root
9
- * @param {BinaryBuffer} buffer
10
- * @param {function(buffer:BinaryBuffer):*} leafValueDeserializer
11
- */
12
- export function deserializeBinaryNodeFromBinaryBuffer(root, buffer, leafValueDeserializer) {
13
- //read bounds
14
- deserializeAABB3(buffer, root);
15
-
16
- /**
17
- *
18
- * @param {BinaryNode} parent
19
- * @returns {BinaryNode}
20
- */
21
- function readBinaryNode(parent) {
22
-
23
- const node = new BinaryNode();
24
-
25
- node.parentNode = parent;
26
-
27
- //read bounds
28
- deserializeAABB3Encoded_v0(buffer, node, parent.x0, parent.y0, parent.z0, parent.x1, parent.y1, parent.z1);
29
-
30
- //read marker
31
- const marker = buffer.readUint8();
32
-
33
- if ((marker & 3) === 3) {
34
- node.left = readBinaryNode(node);
35
- } else if ((marker & 2) === 2) {
36
- node.left = readLeafNode(node);
37
- } else {
38
- node.left = null;
39
- }
40
-
41
- if ((marker & 12) === 12) {
42
- node.right = readBinaryNode(node);
43
- } else if ((marker & 8) === 8) {
44
- node.right = readLeafNode(node);
45
- } else {
46
- node.right = null;
47
- }
48
-
49
- node.updateLeafNodeCount();
50
-
51
- return node;
52
- }
53
-
54
- /**
55
- *
56
- * @param {BinaryNode} parent
57
- * @returns {LeafNode}
58
- */
59
- function readLeafNode(parent) {
60
- const node = new LeafNode();
61
-
62
- node.parentNode = parent;
63
-
64
- //read bounds
65
- deserializeAABB3Encoded_v0(buffer, node, parent.x0, parent.y0, parent.z0, parent.x1, parent.y1, parent.z1);
66
-
67
- node.object = leafValueDeserializer(buffer);
68
-
69
- return node;
70
- }
71
-
72
- //read marker
73
- const marker = buffer.readUint8();
74
-
75
- if ((marker & 3) === 3) {
76
- root.left = readBinaryNode(root);
77
- } else if ((marker & 2) === 2) {
78
- root.left = readLeafNode(root);
79
- } else {
80
- root.left = null;
81
- }
82
-
83
- if ((marker & 12) === 12) {
84
- root.right = readBinaryNode(root);
85
- } else if ((marker & 8) === 8) {
86
- root.right = readLeafNode(root);
87
- } else {
88
- root.right = null;
89
- }
90
- }
@@ -1,31 +0,0 @@
1
- import {serializeAABB3} from "../../geom/3d/aabb/serializeAABB3.js";
2
- import {isLeaf, serializeLeafNode} from "../LeafNode.js";
3
-
4
- /**
5
- *
6
- * @param {BinaryBuffer} buffer
7
- * @param {BinaryNode} node
8
- * @param {function(buffer:BinaryBuffer,value:any):void} leafValueSerializer
9
- */
10
- function serializeBinaryNode(buffer, node, leafValueSerializer) {
11
- serializeAABB3(buffer, node);
12
-
13
- function serializeChild(child) {
14
- if (child === null) {
15
- buffer.writeUint8(0);
16
- } else {
17
- if (isLeaf(child)) {
18
- buffer.writeUint8(1);
19
- serializeLeafNode(buffer, child, leafValueSerializer);
20
- } else {
21
- buffer.writeUint8(2);
22
- serializeBinaryNode(buffer, child, leafValueSerializer);
23
- }
24
- }
25
- }
26
-
27
- serializeChild(node.left);
28
- serializeChild(node.right);
29
- }
30
-
31
- export {serializeBinaryNode};
@@ -1,86 +0,0 @@
1
- import { serializeAABB3 } from "../../geom/3d/aabb/serializeAABB3.js";
2
- import { serializeAABB3Encoded_v0 } from "../../geom/3d/aabb/serializeAABB3Encoded_v0.js";
3
-
4
- /**
5
- *
6
- * @param {BinaryBuffer} buffer
7
- * @param {BinaryNode} node
8
- * @param {BinaryNode} parent
9
- * @param {function(buffer:BinaryBuffer, value:*):void} leafValueSerializer
10
- */
11
- function writeBinaryNode(buffer, node, parent, leafValueSerializer) {
12
- serializeAABB3Encoded_v0(buffer, node, parent.x0, parent.y0, parent.z0, parent.x1, parent.y1, parent.z1);
13
-
14
- writeBinaryNodeContents(buffer, node, leafValueSerializer);
15
- }
16
-
17
- /**
18
- *
19
- * @param {BinaryBuffer} buffer
20
- * @param {BinaryNode} node
21
- * @param {function(buffer:BinaryBuffer, value:*):void} leafValueSerializer
22
- */
23
- function writeBinaryNodeContents(buffer, node, leafValueSerializer) {
24
-
25
- //build header marker for the node
26
- let marker = 0;
27
-
28
- const right = node.right;
29
-
30
- if (right !== null) {
31
- if (right.isLeafNode) {
32
- marker |= 8;
33
- } else {
34
- marker |= 12;
35
- }
36
- }
37
-
38
- const left = node.left;
39
-
40
- if (left !== null) {
41
- if (left.isLeafNode) {
42
- marker |= 2;
43
- } else {
44
- marker |= 3;
45
- }
46
- }
47
-
48
- buffer.writeUint8(marker);
49
-
50
- if ((marker & 3) === 3) {
51
- writeBinaryNode(buffer, left, node, leafValueSerializer);
52
- } else if ((marker & 2) === 2) {
53
- writeLeafNode(buffer, left, node, leafValueSerializer);
54
- }
55
-
56
- if ((marker & 12) === 12) {
57
- writeBinaryNode(buffer, right, node, leafValueSerializer);
58
- } else if ((marker & 8) === 8) {
59
- writeLeafNode(buffer, right, node, leafValueSerializer);
60
- }
61
- }
62
-
63
- /**
64
- *
65
- * @param {BinaryBuffer} buffer
66
- * @param {LeafNode} node
67
- * @param {BinaryNode} parent
68
- * @param {function(buffer:BinaryBuffer, value:*):void} leafValueSerializer
69
- */
70
- function writeLeafNode(buffer, node, parent, leafValueSerializer) {
71
- serializeAABB3Encoded_v0(buffer, node, parent.x0, parent.y0, parent.z0, parent.x1, parent.y1, parent.z1);
72
- leafValueSerializer(buffer, node.object);
73
- }
74
-
75
- /**
76
- * Writing is lossy, all descendants have their bounds quantized to uin16
77
- * @param {BinaryNode} root
78
- * @param {BinaryBuffer} buffer
79
- * @param {function(buffer:BinaryBuffer, value:*):void} leafValueSerializer
80
- */
81
- export function serializeBinaryNodeToBinaryBuffer(root, buffer, leafValueSerializer) {
82
- //write initial size
83
- serializeAABB3(buffer, root);
84
-
85
- writeBinaryNodeContents(buffer, root, leafValueSerializer);
86
- }