@woosh/meep-engine 2.49.6 → 2.49.8

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 (85) hide show
  1. package/editor/enableEditor.js +1 -8
  2. package/package.json +1 -1
  3. package/samples/terrain/editor.js +2 -2
  4. package/src/core/cache/Cache.js +1 -1
  5. package/src/core/cache/LoadingCache.d.ts +2 -0
  6. package/src/core/cache/LoadingCache.js +45 -18
  7. package/src/core/collection/HashSet.js +1 -1
  8. package/src/core/collection/table/RowFirstTableSpec.js +110 -92
  9. package/src/core/collection/table/RowFirstTableSpec.spec.js +49 -0
  10. package/src/core/color/Color.d.ts +4 -2
  11. package/src/core/color/Color.js +7 -8
  12. package/src/core/color/Color.spec.js +93 -0
  13. package/src/core/color/hex2rgb.spec.js +10 -0
  14. package/src/core/color/rgb2hex.js +1 -1
  15. package/src/core/color/rgb2hex.spec.js +13 -0
  16. package/src/core/fsm/simple/SimpleStateMachine.spec.js +75 -0
  17. package/src/core/fsm/simple/SimpleStateMachineDescription.js +1 -1
  18. package/src/core/fsm/simple/SimpleStateMachineDescription.spec.js +32 -0
  19. package/src/core/geom/2d/Rectangle.spec.js +51 -0
  20. package/src/core/geom/3d/aabb/aabb3_intersects_ray.spec.js +90 -0
  21. package/src/core/geom/3d/line/line3_compute_nearest_point_to_point.spec.js +61 -0
  22. package/src/core/geom/3d/morton/mortonEncode_magicbits.js +1 -34
  23. package/src/core/geom/3d/morton/split_by_2.js +17 -0
  24. package/src/core/geom/3d/morton/split_by_3.js +16 -0
  25. package/src/core/geom/3d/plane/computePlaneLineIntersection.js +6 -1
  26. package/src/core/geom/3d/sphere/sphere_intersects_ray.spec.js +11 -0
  27. package/src/core/geom/3d/sphere/sphere_radius_sqr_from_v3_array_transformed.spec.js +8 -0
  28. package/src/core/geom/3d/topology/samples/sampleFloodFill.js +3 -3
  29. package/src/core/geom/3d/topology/struct/binary/io/OrderedEdge.js +1 -1
  30. package/src/core/geom/random/randomPointOnBox.spec.js +57 -0
  31. package/src/core/math/computeGreatestCommonDivisor.spec.js +9 -0
  32. package/src/core/math/statistics/computeStatisticalMean.spec.js +9 -0
  33. package/src/core/math/statistics/halton_sequence.spec.js +6 -1
  34. package/src/core/model/node-graph/node/Port.spec.js +10 -1
  35. package/src/core/model/reactive/evaluation/MultiPredicateEvaluator.js +5 -8
  36. package/src/core/model/reactive/evaluation/MultiPredicateEvaluator.spec.js +41 -0
  37. package/src/core/model/reactive/trigger/BlackboardTrigger.js +5 -0
  38. package/src/core/model/reactive/trigger/BlackboardTrigger.spec.js +24 -0
  39. package/src/core/parser/simple/readBooleanToken.js +38 -0
  40. package/src/core/parser/simple/readHexToken.js +95 -0
  41. package/src/core/parser/simple/readHexToken.spec.js +21 -0
  42. package/src/core/parser/simple/readIdentifierToken.js +43 -0
  43. package/src/core/parser/simple/readIdentifierToken.spec.js +32 -0
  44. package/src/core/parser/simple/readLiteralToken.js +96 -0
  45. package/src/core/parser/simple/readNumberToken.js +73 -0
  46. package/src/core/parser/simple/readNumberToken.spec.js +17 -0
  47. package/src/core/parser/simple/readReferenceToken.js +48 -0
  48. package/src/core/parser/simple/readReferenceToken.spec.js +18 -0
  49. package/src/core/parser/simple/readStringToken.js +94 -0
  50. package/src/core/parser/simple/readStringToken.spec.js +57 -0
  51. package/src/core/parser/simple/{readUnsignedInteger.js → readUnsignedIntegerToken.js} +1 -1
  52. package/src/core/parser/simple/readUnsignedIntegerToken.spec.js +6 -0
  53. package/src/core/process/executor/ConcurrentExecutor.js +147 -234
  54. package/src/engine/Engine.d.ts +4 -2
  55. package/src/engine/Engine.js +62 -41
  56. package/src/engine/Engine.spec.js +11 -0
  57. package/src/engine/InputEngine.js +12 -0
  58. package/src/engine/graphics/GraphicsEngine.js +2 -13
  59. package/src/engine/graphics/ecs/compileAllMaterials.js +1 -1
  60. package/src/engine/graphics/ecs/mesh/createTaskWaitForMeshesToLoad.js +1 -1
  61. package/src/engine/graphics/impostors/octahedral/ImpostorBaker.js +1 -1
  62. package/src/engine/graphics/load_and_set_cubemap_v0.js +21 -0
  63. package/src/engine/graphics/material/optimization/MaterialOptimizationContext.js +1 -1
  64. package/src/engine/graphics/particles/particular/engine/utils/volume/prototypeParticleVolume.js +3 -5
  65. package/src/engine/graphics/render/buffer/buffers/prototypeNormalFrameBuffer.js +2 -4
  66. package/src/engine/graphics/render/forward_plus/plugin/ptototypeFPPlugin.js +1 -1
  67. package/src/engine/graphics/render/forward_plus/prototype/prototypeLightManager.js +1 -1
  68. package/src/engine/graphics/render/visibility/hiz/prototypeHiZ.js +2 -4
  69. package/src/engine/graphics/sh3/prototypeSH3Probe.js +4 -4
  70. package/src/engine/graphics/texture/sampler/copy_Sampler2D_channel_data.js +4 -3
  71. package/src/engine/graphics/texture/virtual/VirtualTexture.js +9 -0
  72. package/src/engine/graphics/texture/virtual/VirtualTexture.spec.js +5 -4
  73. package/src/engine/graphics/texture/virtual/tile/TileLoader.js +5 -0
  74. package/src/engine/input/devices/PointerDevice.spec.js +7 -0
  75. package/src/engine/intelligence/blackboard/Blackboard.d.ts +4 -0
  76. package/src/engine/intelligence/blackboard/Blackboard.js +11 -0
  77. package/src/engine/platform/InMemoryEnginePlatform.js +20 -0
  78. package/src/engine/save/Storage.d.ts +7 -7
  79. package/src/engine/save/storage/InMemoryStorage.js +34 -0
  80. package/src/generation/grid/generation/road/GridTaskGenerateRoads.js +2 -2
  81. package/src/view/tooltip/gml/parser/readReferenceValueToken.js +2 -2
  82. package/src/core/parser/simple/SimpleParser.js +0 -464
  83. package/src/core/parser/simple/SimpleParser.spec.js +0 -105
  84. /package/src/core/collection/{IteratorUtils.js → collectIteratorValueToArray.js} +0 -0
  85. /package/src/core/color/{ColorUtils.js → parseColor.js} +0 -0
@@ -0,0 +1,75 @@
1
+ import { SimpleStateMachine } from "./SimpleStateMachine.js";
2
+ import { SimpleStateMachineDescription } from "./SimpleStateMachineDescription.js";
3
+
4
+ test("constructor does not throw", () => {
5
+ const description = new SimpleStateMachineDescription();
6
+
7
+ expect(() => new SimpleStateMachine(description)).not.toThrow();
8
+ });
9
+
10
+
11
+ test("state entry event handler is fired as expected", () => {
12
+
13
+ const description = new SimpleStateMachineDescription();
14
+
15
+ const a = description.createState();
16
+ const b = description.createState();
17
+
18
+ description.createEdge(a, b);
19
+
20
+ const fsm = new SimpleStateMachine(description);
21
+
22
+ fsm.setState(a);
23
+
24
+ const entry_callback = jest.fn();
25
+
26
+ fsm.addEventHandlerStateEntry(b, entry_callback);
27
+
28
+ fsm.setState(b);
29
+
30
+ expect(entry_callback).toHaveBeenCalledTimes(1);
31
+ expect(entry_callback).toHaveBeenCalledWith(b, a);
32
+ });
33
+
34
+ test("state exit event handler is fired as expected", () => {
35
+
36
+ const description = new SimpleStateMachineDescription();
37
+
38
+ const a = description.createState();
39
+ const b = description.createState();
40
+
41
+ description.createEdge(a, b);
42
+
43
+ const fsm = new SimpleStateMachine(description);
44
+
45
+ fsm.setState(a);
46
+
47
+ const entry_callback = jest.fn();
48
+
49
+ fsm.addEventHandlerStateExit(a, entry_callback);
50
+
51
+ fsm.setState(b);
52
+
53
+ expect(entry_callback).toHaveBeenCalledTimes(1);
54
+ expect(entry_callback).toHaveBeenCalledWith(a, b);
55
+ });
56
+
57
+ test("'advance' moves us to the next state in the chain", () => {
58
+
59
+
60
+ const description = new SimpleStateMachineDescription();
61
+
62
+ const a = description.createState();
63
+ const b = description.createState();
64
+
65
+ description.createEdge(a, b);
66
+
67
+ const fsm = new SimpleStateMachine(description);
68
+
69
+ fsm.setState(a);
70
+
71
+ fsm.advance(0);
72
+
73
+ expect(fsm.getState()).toBe(b);
74
+
75
+ });
@@ -141,7 +141,7 @@ export class SimpleStateMachineDescription {
141
141
  *
142
142
  * @param {number} start
143
143
  * @param {number} goal
144
- * @returns {number[]}
144
+ * @returns {number[]|null}
145
145
  */
146
146
  findPath(start, goal) {
147
147
  assert.ok(this.stateExists(start), `start state ${start} doesn't exist`);
@@ -69,3 +69,35 @@ test('getIncomingStates', () => {
69
69
  expect(smd.getIncomingStates(b)).toEqual([a]);
70
70
  expect(smd.getIncomingStates(c)).toEqual([a]);
71
71
  });
72
+
73
+ test('edgeExists', () => {
74
+
75
+ const smd = new SimpleStateMachineDescription();
76
+
77
+ const a = smd.createState();
78
+ const b = smd.createState();
79
+
80
+ expect(smd.edgeExists(a, b)).toBe(false);
81
+ expect(smd.edgeExists(b, a)).toBe(false);
82
+
83
+ smd.createEdge(a, b);
84
+
85
+ expect(smd.edgeExists(a, b)).toEqual(true);
86
+ expect(smd.edgeExists(b, a)).toEqual(false);
87
+ });
88
+
89
+ test("findPath sanity check", () => {
90
+
91
+ const smd = new SimpleStateMachineDescription();
92
+
93
+ const a = smd.createState();
94
+ const b = smd.createState();
95
+
96
+ expect(smd.findPath(a, a)).toEqual([a]);
97
+
98
+ expect(smd.findPath(a, b)).toEqual(null);
99
+
100
+ smd.createEdge(a, b);
101
+
102
+ expect(smd.findPath(a, b)).toEqual([a, b]);
103
+ });
@@ -1,4 +1,19 @@
1
1
  import Rectangle from "./Rectangle.js";
2
+ import Vector2 from "../Vector2.js";
3
+
4
+ test("constructor", () => {
5
+ expect(() => new Rectangle()).not.toThrow();
6
+ });
7
+
8
+ test("default constructor produces 0 size rectangle with valid position", () => {
9
+ const r = new Rectangle();
10
+
11
+ expect(r.size.x).toBe(0);
12
+ expect(r.size.y).toBe(0);
13
+
14
+ expect(r.position.x).not.toBeNaN();
15
+ expect(r.position.y).not.toBeNaN();
16
+ });
2
17
 
3
18
  test("toArray works correctly", () => {
4
19
  const v = new Rectangle(1, 2, 3, 4);
@@ -9,3 +24,39 @@ test("toArray works correctly", () => {
9
24
 
10
25
  expect(actual).toEqual([1, 2, 3, 4]);
11
26
  });
27
+
28
+ test("toJSON", () => {
29
+ const r = new Rectangle(1, 3, 7, 11);
30
+
31
+ expect(r.toJSON()).toEqual({
32
+ position: { x: 1, y: 3 },
33
+ size: { x: 7, y: 11 }
34
+ });
35
+ });
36
+
37
+ test("fromJSON", () => {
38
+
39
+ const r = new Rectangle();
40
+
41
+ r.fromJSON({
42
+ position: { x: 1, y: 3 },
43
+ size: { x: 7, y: 11 }
44
+ });
45
+
46
+ expect(r.position.x).toBe(1);
47
+ expect(r.position.y).toBe(3);
48
+
49
+ expect(r.size.x).toBe(7);
50
+ expect(r.size.y).toBe(11);
51
+ });
52
+
53
+ test("computeCenter", () => {
54
+ const r = new Rectangle(1, 3, 7, 11);
55
+
56
+ const center = new Vector2();
57
+
58
+ r.computeCenter(center);
59
+
60
+ expect(center.x).toBe(4.5);
61
+ expect(center.y).toBe(8.5);
62
+ });
@@ -1,6 +1,96 @@
1
1
  import { seededRandom } from "../../../math/random/seededRandom.js";
2
2
  import { aabb3_intersects_ray } from "./aabb3_intersects_ray.js";
3
3
 
4
+ test("axis aligned ray on X", () => {
5
+ expect(aabb3_intersects_ray(
6
+ -0.5, -0.5, -0.5,
7
+ +0.5, +0.5, +0.5,
8
+ -1, 0, 0,
9
+ 1, 0, 0
10
+ )).toBe(true);
11
+
12
+ expect(aabb3_intersects_ray(
13
+ -0.5, -0.5, -0.5,
14
+ +0.5, +0.5, +0.5,
15
+ -1, 0, 0,
16
+ -1, 0, 0
17
+ )).toBe(false);
18
+
19
+ expect(aabb3_intersects_ray(
20
+ -0.5, -0.5, -0.5,
21
+ +0.5, +0.5, +0.5,
22
+ 1, 0, 0,
23
+ -1, 0, 0
24
+ )).toBe(true);
25
+
26
+ expect(aabb3_intersects_ray(
27
+ -0.5, -0.5, -0.5,
28
+ +0.5, +0.5, +0.5,
29
+ 1, 0, 0,
30
+ 1, 0, 0
31
+ )).toBe(false);
32
+ });
33
+
34
+ test("axis aligned ray on Y", () => {
35
+ expect(aabb3_intersects_ray(
36
+ -0.5, -0.5, -0.5,
37
+ +0.5, +0.5, +0.5,
38
+ 0, -1, 0,
39
+ 0, 1, 0
40
+ )).toBe(true);
41
+
42
+ expect(aabb3_intersects_ray(
43
+ -0.5, -0.5, -0.5,
44
+ +0.5, +0.5, +0.5,
45
+ 0, -1, 0,
46
+ 0, -1, 0
47
+ )).toBe(false);
48
+
49
+ expect(aabb3_intersects_ray(
50
+ -0.5, -0.5, -0.5,
51
+ +0.5, +0.5, +0.5,
52
+ 0, 1, 0,
53
+ 0, -1, 0
54
+ )).toBe(true);
55
+
56
+ expect(aabb3_intersects_ray(
57
+ -0.5, -0.5, -0.5,
58
+ +0.5, +0.5, +0.5,
59
+ 0, 1, 0,
60
+ 0, 1, 0
61
+ )).toBe(false);
62
+ });
63
+
64
+ test("axis aligned ray on Z", () => {
65
+ expect(aabb3_intersects_ray(
66
+ -0.5, -0.5, -0.5,
67
+ +0.5, +0.5, +0.5,
68
+ 0, 0, -1,
69
+ 0, 0, 1
70
+ )).toBe(true);
71
+
72
+ expect(aabb3_intersects_ray(
73
+ -0.5, -0.5, -0.5,
74
+ +0.5, +0.5, +0.5,
75
+ 0, 0, -1,
76
+ 0, 0, -1
77
+ )).toBe(false);
78
+
79
+ expect(aabb3_intersects_ray(
80
+ -0.5, -0.5, -0.5,
81
+ +0.5, +0.5, +0.5,
82
+ 0, 0, 1,
83
+ 0, 0, -1
84
+ )).toBe(true);
85
+
86
+ expect(aabb3_intersects_ray(
87
+ -0.5, -0.5, -0.5,
88
+ +0.5, +0.5, +0.5,
89
+ 0, 0, 1,
90
+ 0, 0, 1
91
+ )).toBe(false);
92
+ });
93
+
4
94
  test.skip("performance raycast", () => {
5
95
  const rng = seededRandom(42);
6
96
 
@@ -0,0 +1,61 @@
1
+ import { line3_compute_nearest_point_to_point } from "./line3_compute_nearest_point_to_point.js";
2
+
3
+ test("aligned with the start of the line", () => {
4
+ const result = [];
5
+
6
+ line3_compute_nearest_point_to_point(result, 0,
7
+ 1, 3, 7, 11, 13, 17,
8
+ 1, 3, 7
9
+ );
10
+
11
+ expect(result).toEqual([1, 3, 7])
12
+ });
13
+
14
+ test("aligned with the end of the line", () => {
15
+ const result = [];
16
+
17
+ line3_compute_nearest_point_to_point(result, 0,
18
+ 1, 3, 7, 11, 13, 17,
19
+ 11, 13, 17
20
+ );
21
+
22
+ expect(result).toEqual([11, 13, 17])
23
+ });
24
+
25
+ test("ref point is on line past line ends", () => {
26
+
27
+ const result = [];
28
+
29
+ line3_compute_nearest_point_to_point(result, 0,
30
+ -1, 0, 0, 3, 0, 0,
31
+ -2, 0, 0
32
+ );
33
+
34
+ expect(result).toEqual([-1, 0, 0])
35
+
36
+ line3_compute_nearest_point_to_point(result, 0,
37
+ -1, 0, 0, 3, 0, 0,
38
+ 7, 0, 0
39
+ );
40
+
41
+ expect(result).toEqual([3, 0, 0])
42
+ });
43
+
44
+ test("ref point is on the line", () => {
45
+
46
+ const result = [];
47
+
48
+ line3_compute_nearest_point_to_point(result, 0,
49
+ -1, 0, 0, 3, 0, 0,
50
+ 1, 0, 0
51
+ );
52
+
53
+ expect(result).toEqual([1, 0, 0])
54
+
55
+ line3_compute_nearest_point_to_point(result, 0,
56
+ -1, 0, 0, 3, 0, 0,
57
+ 2, 0, 0
58
+ );
59
+
60
+ expect(result).toEqual([2, 0, 0])
61
+ });
@@ -1,37 +1,4 @@
1
- /**
2
- * method to separate bits from a given integer 3 positions apart
3
- * we only look at the first 10 bits
4
- *
5
- * @example when input is ABC, output bits are A00B00C
6
- * @param {number} a
7
- * @returns {number}
8
- */
9
- function split_by_3(a) {
10
- let x = a;
11
- x = (x | x << 16) & 0x30000ff;
12
- x = (x | x << 8) & 0x0300f00f;
13
- x = (x | x << 4) & 0x30c30c3;
14
- x = (x | x << 2) & 0x9249249;
15
- return x;
16
- }
17
-
18
- /**
19
- * method to separate bits from a given integer 2 positions apart
20
- *
21
- * @example when input is ABC, output bits are A00B00C
22
- * @see https://github.com/Forceflow/libmorton/blob/234a443ca8e2c64f6385f1a9d6ee10a70d08a3fa/include/libmorton/morton2D.h#L99
23
- * @param {number} a
24
- * @returns {number}
25
- */
26
- export function split_by_2(a) {
27
- let x = a;
28
- x = (x | x << 16) & 0x0000FFFF;
29
- x = (x | x << 8) & 0x00FF00FF;
30
- x = (x | x << 4) & 0x0F0F0F0F;
31
- x = (x | x << 2) & 0x33333333;
32
- x = (x | x << 1) & 0x55555555;
33
- return x;
34
- }
1
+ import { split_by_3 } from "./split_by_3.js";
35
2
 
36
3
  /**
37
4
  * Based on article and C++ source code:
@@ -0,0 +1,17 @@
1
+ /**
2
+ * method to separate bits from a given integer 2 positions apart
3
+ *
4
+ * @example when input is ABC, output bits are A00B00C
5
+ * @see https://github.com/Forceflow/libmorton/blob/234a443ca8e2c64f6385f1a9d6ee10a70d08a3fa/include/libmorton/morton2D.h#L99
6
+ * @param {number} a
7
+ * @returns {number}
8
+ */
9
+ export function split_by_2(a) {
10
+ let x = a;
11
+ x = (x | x << 16) & 0x0000FFFF;
12
+ x = (x | x << 8) & 0x00FF00FF;
13
+ x = (x | x << 4) & 0x0F0F0F0F;
14
+ x = (x | x << 2) & 0x33333333;
15
+ x = (x | x << 1) & 0x55555555;
16
+ return x;
17
+ }
@@ -0,0 +1,16 @@
1
+ /**
2
+ * method to separate bits from a given integer 3 positions apart
3
+ * we only look at the first 10 bits
4
+ *
5
+ * @example when input is ABC, output bits are A00B00C
6
+ * @param {number} a
7
+ * @returns {number}
8
+ */
9
+ export function split_by_3(a) {
10
+ let x = a;
11
+ x = (x | x << 16) & 0x30000ff;
12
+ x = (x | x << 8) & 0x0300f00f;
13
+ x = (x | x << 4) & 0x30c30c3;
14
+ x = (x | x << 2) & 0x9249249;
15
+ return x;
16
+ }
@@ -15,7 +15,12 @@ import { v3_dot } from "../../v3_dot.js";
15
15
  * @param {number} dist Plane distance
16
16
  * @returns {boolean} true if intersection is found, false otherwise
17
17
  */
18
- export function computePlaneLineIntersection(out, originX, originY, originZ, directionX, directionY, directionZ, normalX, normalY, normalZ, dist) {
18
+ export function computePlaneLineIntersection(
19
+ out,
20
+ originX, originY, originZ,
21
+ directionX, directionY, directionZ,
22
+ normalX, normalY, normalZ, dist
23
+ ) {
19
24
  const denom = v3_dot(directionX, directionY, directionZ, normalX, normalY, normalZ);
20
25
 
21
26
  const p = v3_dot(normalX, normalY, normalZ, originX, originY, originZ) + dist;
@@ -47,3 +47,14 @@ test("ray from +Z to -Z intersects sphere", () => {
47
47
  0, 0, -1
48
48
  )).toBe(true);
49
49
  });
50
+
51
+
52
+ // negative cases
53
+
54
+ test("ray from -X to -X", () => {
55
+ expect(sphere_intersects_ray(
56
+ 0, 0, 0, 1,
57
+ -2, 0, 0,
58
+ -1, 0, 0
59
+ )).toBe(false);
60
+ });
@@ -0,0 +1,8 @@
1
+ import { sphere_radius_sqr_from_v3_array_transformed } from "./sphere_radius_sqr_from_v3_array_transformed.js";
2
+ import { MATRIX_4_IDENTITY } from "../matrix/MATRIX_4_IDENTITY.js";
3
+
4
+ test("base case", () => {
5
+ expect(sphere_radius_sqr_from_v3_array_transformed([0, 0, 0], 3, MATRIX_4_IDENTITY)).toBe(0);
6
+ expect(sphere_radius_sqr_from_v3_array_transformed([1, 0, 0], 3, MATRIX_4_IDENTITY)).toBe(1);
7
+ expect(sphere_radius_sqr_from_v3_array_transformed([-1, 0, 0], 3, MATRIX_4_IDENTITY)).toBe(1);
8
+ });
@@ -9,7 +9,7 @@ import { topo_mesh_to_three_buffer_geometry } from "../topo_mesh_to_three_buffer
9
9
  import { three_buffer_geometry_to_topo_mesh } from "../three_buffer_geometry_to_topo_mesh.js";
10
10
  import { mesh_flood_fill } from "../util/mesh_flood_fill.js";
11
11
  import { compute_aabb_from_points } from "../../aabb/compute_aabb_from_points.js";
12
- import { AABB3 } from "../../../../bvh2/aabb3/AABB3.js";
12
+ import { AABB3 } from "../../../../geom/3d/aabb/AABB3.js";
13
13
  import { mergeVertices } from "three/examples/jsm/utils/BufferGeometryUtils.js";
14
14
  import { makeGeometryIndexed } from "../../../../../engine/graphics/geometry/buffered/makeGeometryIndexed.js";
15
15
  import { v3_dot } from "../../../v3_dot.js";
@@ -23,10 +23,10 @@ import { SGMeshEvents } from "../../../../../engine/graphics/ecs/mesh-v2/aggrega
23
23
  import { Color } from "../../../../color/Color.js";
24
24
  import { seededRandom } from "../../../../math/random/seededRandom.js";
25
25
  import { expandConnectivityByLocality } from "../expandConnectivityByLocality.js";
26
- import { buildCubeURLs } from "../../../../../engine/graphics/texture/cubemap/buildCubeURLs.js";
27
26
  import { EntityNode } from "../../../../../engine/ecs/parent/EntityNode.js";
28
27
  import { TransformAttachmentSystem } from "../../../../../engine/ecs/transform-attachment/TransformAttachmentSystem.js";
29
28
  import { make_ray_from_viewport_position } from "../../../../../engine/graphics/make_ray_from_viewport_position.js";
29
+ import { load_and_set_cubemap_v0 } from "../../../../../engine/graphics/load_and_set_cubemap_v0.js";
30
30
 
31
31
  const harness = new EngineHarness();
32
32
 
@@ -98,7 +98,7 @@ async function main(engine) {
98
98
  enableTerrain: false
99
99
  });
100
100
 
101
- engine.graphics.loadEnvironmentMap(buildCubeURLs('data/textures/cubemaps/hip_miramar/32/', '.png'));
101
+ load_and_set_cubemap_v0(engine.graphics,'data/textures/cubemaps/hip_miramar/32/', '.png')
102
102
 
103
103
  const path = 'data/models/sponza-pbr/gltf/sponza.glb';
104
104
 
@@ -1,4 +1,4 @@
1
- import { split_by_2 } from "../../../../morton/mortonEncode_magicbits.js";
1
+ import { split_by_2 } from "../../../../morton/split_by_2.js";
2
2
 
3
3
  export class OrderedEdge {
4
4
  /**
@@ -0,0 +1,57 @@
1
+ import { randomPointOnBox } from "./randomPointOnBox.js";
2
+
3
+ function assert_point_on_box(sample) {
4
+
5
+ const x = sample[0];
6
+ const y = sample[1];
7
+ const z = sample[2];
8
+
9
+ function assert_range(v) {
10
+ expect(v).toBeGreaterThanOrEqual(-0.5);
11
+ expect(v).toBeLessThanOrEqual(0.5);
12
+ }
13
+
14
+ if (Math.abs(x) === 0.5 && Math.abs(y) === 0.5) {
15
+ assert_range(z);
16
+ } else if (Math.abs(x) === 0.5 && Math.abs(z) === 0.5) {
17
+ assert_range(y);
18
+ } else if (Math.abs(y) === 0.5 && Math.abs(z) === 0.5) {
19
+ assert_range(x);
20
+ } else if (Math.abs(x) === 0.5) {
21
+ assert_range(y);
22
+ assert_range(z);
23
+ } else if (Math.abs(y) === 0.5) {
24
+ assert_range(x);
25
+ assert_range(z);
26
+ } else if (Math.abs(z) === 0.5) {
27
+ assert_range(y);
28
+ assert_range(x);
29
+ } else {
30
+ throw new Error(`Unexpected ${sample}`);
31
+ }
32
+
33
+ }
34
+
35
+ test("samples are on box shell", () => {
36
+ function validate(sample_value) {
37
+
38
+ const sample = [];
39
+
40
+ randomPointOnBox(() => sample_value, sample, 0);
41
+
42
+ assert_point_on_box(sample);
43
+ }
44
+
45
+ validate(0);
46
+ validate(1);
47
+
48
+ validate(0.1);
49
+ validate(0.2);
50
+ validate(0.3);
51
+ validate(0.4);
52
+ validate(0.5);
53
+ validate(0.6);
54
+ validate(0.7);
55
+ validate(0.8);
56
+ validate(0.9);
57
+ });
@@ -0,0 +1,9 @@
1
+ import { computeGreatestCommonDivisor } from "./computeGreatestCommonDivisor.js";
2
+
3
+ test("1 and 1", () => {
4
+ expect(computeGreatestCommonDivisor(1, 1)).toBe(1);
5
+ });
6
+
7
+ test("6 and 9", () => {
8
+ expect(computeGreatestCommonDivisor(6, 9)).toBe(3);
9
+ });
@@ -0,0 +1,9 @@
1
+ import { computeStatisticalMean } from "./computeStatisticalMean.js";
2
+
3
+ test("from just 1 item", () => {
4
+ expect(computeStatisticalMean([-7])).toEqual(-7)
5
+ });
6
+
7
+ test("from 2 items", () => {
8
+ expect(computeStatisticalMean([-7, 17])).toEqual(5)
9
+ });
@@ -5,7 +5,12 @@ test("unique values in base 10", () => {
5
5
  const values = [];
6
6
 
7
7
  for (let i = 0; i < 10; i++) {
8
- values.push(halton_sequence(10, i));
8
+ const v = halton_sequence(10, i);
9
+
10
+ expect(v).toBeGreaterThanOrEqual(0);
11
+ expect(v).toBeLessThanOrEqual(1);
12
+
13
+ values.push(v);
9
14
  }
10
15
 
11
16
  values.sort();
@@ -40,5 +40,14 @@ test("equality works as intended", () => {
40
40
  b.id = a.id;
41
41
 
42
42
  expect(b.equals(a)).toEqual(true);
43
-
43
+
44
+ });
45
+
46
+ test("toString on newly crated instance produces a valid string", () => {
47
+ const port = new Port();
48
+
49
+ const s = port.toString();
50
+
51
+ expect(typeof s).toBe('string');
52
+ expect(s.trim().length).toBeGreaterThan(0); // non-empty
44
53
  });
@@ -1,7 +1,6 @@
1
1
  import { assert } from "../../../assert.js";
2
2
  import { BitSet } from "../../../binary/BitSet.js";
3
3
  import { HashMap } from "../../../collection/HashMap.js";
4
- import { returnZero } from "../../../function/Functions.js";
5
4
  import { max2 } from "../../../math/max2.js";
6
5
  import DataType from "../../../parser/simple/DataType.js";
7
6
 
@@ -95,15 +94,13 @@ class ExpressionNode {
95
94
 
96
95
  /**
97
96
  *
98
- * @param {ExpressionNode} n
99
- * @return {number}
97
+ * @param {ReactiveExpression} exp
98
+ * @returns {number}
100
99
  */
101
- function scoreNode(n) {
102
- return n.getScore();
100
+ function scoreByTreeSize(exp){
101
+ return exp.computeTreeSize();
103
102
  }
104
103
 
105
- const temp_array = [];
106
-
107
104
  /**
108
105
  * Evaluate given state against multiple predicates, order of evaluation is controlled by scoring function, highest score nodes are evaluated first
109
106
  */
@@ -112,7 +109,7 @@ export class MultiPredicateEvaluator {
112
109
  *
113
110
  * @param {function(ReactiveExpression):number} scoringFunction
114
111
  */
115
- constructor(scoringFunction = returnZero) {
112
+ constructor(scoringFunction = scoreByTreeSize) {
116
113
  /**
117
114
  *
118
115
  * @type {function(ReactiveExpression): number}
@@ -9,6 +9,47 @@ import { MultiPredicateEvaluator } from "./MultiPredicateEvaluator.js";
9
9
  import { randomFromArray } from "../../../math/random/randomFromArray.js";
10
10
  import { randomFloatBetween } from "../../../math/random/randomFloatBetween.js";
11
11
  import { randomIntegerBetween } from "../../../math/random/randomIntegerBetween.js";
12
+ import { ReactiveEquals } from "../model/comparative/ReactiveEquals.js";
13
+
14
+ test('constructor does not throw', () => {
15
+ expect(() => new MultiPredicateEvaluator()).not.toThrow();
16
+ });
17
+
18
+ test('build empty', () => {
19
+ const processor = new MultiPredicateEvaluator();
20
+
21
+ expect(() => processor.build([])).not.toThrow();
22
+ });
23
+
24
+ test('match against empty list of predicates', () => {
25
+
26
+ const processor = new MultiPredicateEvaluator();
27
+ processor.build([]);
28
+
29
+ processor.initialize({});
30
+
31
+ expect(processor.next()).toBeUndefined();
32
+ });
33
+
34
+ test('match against one predicate', () => {
35
+
36
+ const processor = new MultiPredicateEvaluator();
37
+
38
+ const predicate = ReactiveEquals.from(new ReactiveReference('a'), ReactiveLiteralNumber.from(7));
39
+
40
+ processor.build([predicate]);
41
+
42
+ processor.initialize({ a: 1 });
43
+
44
+ expect(processor.next()).toBeUndefined();
45
+
46
+ processor.finalize();
47
+ processor.initialize({ a: 7 });
48
+
49
+ expect(processor.next()).toBe(predicate);
50
+ expect(processor.next()).toBeUndefined();
51
+
52
+ });
12
53
 
13
54
  test.skip('performance', () => {
14
55
  const random = seededRandom(12319);