@woosh/meep-engine 2.51.0 → 2.52.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 (98) hide show
  1. package/package.json +1 -1
  2. package/src/core/NumberFormat.js +0 -71
  3. package/src/core/bvh2/bvh3/ExplicitBinaryBoundingVolumeHierarchy.js +1 -0
  4. package/src/core/bvh2/bvh3/query/BVHQueryAny.js +16 -0
  5. package/src/core/bvh2/bvh3/query/bvh_collect_user_data.js +5 -5
  6. package/src/core/bvh2/bvh3/query/bvh_query_leaves_generic.js +2 -3
  7. package/src/core/bvh2/bvh3/query/bvh_query_leaves_generic.spec.js +22 -0
  8. package/src/core/bvh2/bvh3/query/bvh_query_leaves_ray.js +2 -2
  9. package/src/core/bvh2/bvh3/query/bvh_query_leaves_ray.spec.js +64 -0
  10. package/src/core/bvh2/bvh3/query/bvh_query_user_data_generic.js +2 -3
  11. package/src/core/geom/3d/aabb/aabb3_from_threejs_geometry.js +41 -0
  12. package/src/core/geom/3d/topology/struct/TopoMesh.js +3 -2
  13. package/src/core/geom/3d/topology/struct/prototypeBinaryTopology.js +4 -4
  14. package/src/core/geom/Vector2.d.ts +9 -0
  15. package/src/core/geom/Vector2.js +8 -22
  16. package/src/core/geom/Vector2.spec.js +153 -0
  17. package/src/core/model/ModuleRegistry.js +2 -4
  18. package/src/core/model/ModuleRegistry.spec.js +31 -0
  19. package/src/core/model/reactive/js/compileReactiveToJS.spec.js +14 -0
  20. package/src/core/model/reactive/model/logic/ReactiveAnd.spec.js +31 -1
  21. package/src/core/model/reactive/model/logic/ReactiveOr.spec.js +53 -0
  22. package/src/core/model/stat/LinearModifier.js +2 -2
  23. package/src/core/model/stat/LinearModifier.spec.js +62 -0
  24. package/src/core/model/stat/Stat.js +12 -0
  25. package/src/core/model/stat/Stat.spec.js +36 -0
  26. package/src/core/primitives/array/computeStridedIntegerArrayHash.spec.js +28 -0
  27. package/src/core/primitives/numbers/number_format_by_thousands.js +14 -0
  28. package/src/core/primitives/numbers/number_pretty_print.js +49 -0
  29. package/src/core/primitives/strings/computeStringHash.spec.js +12 -5
  30. package/src/core/process/BaseProcess.js +8 -8
  31. package/src/engine/Clock.js +30 -29
  32. package/src/engine/Clock.spec.js +26 -0
  33. package/src/engine/ecs/EntityBuilder.js +3 -1
  34. package/src/engine/ecs/EntityBuilder.spec.js +21 -0
  35. package/src/engine/ecs/gui/GUIElement.js +1 -1
  36. package/src/engine/ecs/gui/position/ViewportPosition.js +3 -3
  37. package/src/engine/ecs/terrain/ecs/TerrainClassifier.js +1 -1
  38. package/src/engine/ecs/terrain/ecs/layers/TerrainLayers.js +1 -1
  39. package/src/engine/ecs/transform/Transform.js +1 -0
  40. package/src/engine/graphics/camera/testClippingPlaneComputation.js +0 -4
  41. package/src/engine/graphics/ecs/animation/animator/graph/AnimationGraph.spec.js +5 -0
  42. package/src/engine/graphics/ecs/animation/animator/graph/definition/AnimationGraphDefinition.js +24 -25
  43. package/src/engine/graphics/ecs/animation/animator/graph/definition/AnimationGraphDefinition.spec.js +5 -0
  44. package/src/engine/graphics/ecs/decal/DecalSystem.js +2 -20
  45. package/src/engine/graphics/ecs/decal/v2/Decal.js +32 -32
  46. package/src/engine/graphics/ecs/decal/v2/Decal.spec.js +5 -0
  47. package/src/engine/graphics/ecs/decal/v2/FPDecalSystem.js +4 -2
  48. package/src/engine/graphics/ecs/mesh-v2/ShadedGeometry.js +4 -33
  49. package/src/engine/graphics/ecs/mesh-v2/ShadedGeometrySystem.js +8 -4
  50. package/src/engine/graphics/ecs/mesh-v2/aggregate/SGMesh.spec.js +5 -0
  51. package/src/engine/graphics/ecs/mesh-v2/sample/prototypeShadedGeometry.js +0 -12
  52. package/src/engine/graphics/ecs/path/testPathDisplaySystem.js +0 -2
  53. package/src/engine/graphics/ecs/path/tube/prototypeAnimatedPathMask.js +0 -4
  54. package/src/engine/graphics/ecs/water2/shader/testWaterShader.js +0 -2
  55. package/src/engine/graphics/geometry/buffered/computeBufferAttributeHash.js +1 -1
  56. package/src/engine/graphics/particles/particular/engine/utils/volume/prototypeParticleVolume.js +0 -2
  57. package/src/engine/graphics/render/buffer/buffers/prototypeNormalFrameBuffer.js +0 -4
  58. package/src/engine/graphics/render/forward_plus/plugin/ptototypeFPPlugin.js +0 -4
  59. package/src/engine/graphics/render/forward_plus/prototype/prototypeLightManager.js +2 -2
  60. package/src/engine/graphics/render/visibility/hiz/prototypeHiZ.js +2 -6
  61. package/src/engine/graphics/sh3/path_tracer/GeometryBVHBatched.js +2 -1
  62. package/src/engine/graphics/sh3/path_tracer/PathTracer.js +6 -1
  63. package/src/engine/graphics/sh3/path_tracer/prototypePathTracer.js +2 -2
  64. package/src/engine/graphics/shadows/testShadowMapRendering.js +0 -2
  65. package/src/engine/graphics/texture/sampler/Sampler2D.js +1 -1
  66. package/src/engine/graphics/three/expand_aabb_by_transformed_three_object.js +3 -23
  67. package/src/engine/grid/components/GridObstacle.js +45 -25
  68. package/src/engine/grid/components/GridObstacle.spec.js +130 -1
  69. package/src/engine/grid/components/GridPosition.js +5 -17
  70. package/src/engine/grid/components/GridPosition2Transform.js +1 -70
  71. package/src/engine/grid/components/GridPosition2TransformSerializationAdapter.js +70 -0
  72. package/src/engine/plugin/EnginePlugin.js +12 -14
  73. package/src/engine/plugin/EnginePlugin.spec.js +5 -0
  74. package/src/engine/plugin/EnginePluginManager.js +18 -22
  75. package/src/engine/scene/transitionToScene.js +12 -1
  76. package/src/engine/simulation/Ticker.js +1 -1
  77. package/src/generation/theme/TerrainLayerDescription.js +1 -1
  78. package/src/view/common/LabelView.js +3 -3
  79. package/src/engine/ecs/components/AimController.js +0 -18
  80. package/src/engine/ecs/components/Attacker.js +0 -13
  81. package/src/engine/ecs/components/MeshCollider.js +0 -15
  82. package/src/engine/ecs/components/RangedAttack.js +0 -12
  83. package/src/engine/ecs/components/TargetAI.js +0 -11
  84. package/src/engine/ecs/components/ViewportMeshProjection.js +0 -18
  85. package/src/engine/ecs/systems/AimControllerSystem.js +0 -63
  86. package/src/engine/ecs/systems/AttackerSystem.js +0 -67
  87. package/src/engine/ecs/systems/MeshColliderSystem.js +0 -47
  88. package/src/engine/ecs/systems/MonsterAISystem.js +0 -163
  89. package/src/engine/ecs/systems/MortalitySystem.js +0 -46
  90. package/src/engine/ecs/systems/RangedAttackSystem.js +0 -132
  91. package/src/engine/ecs/systems/SerializationMetadataSystem.js +0 -10
  92. package/src/engine/ecs/systems/TargetAISystem.js +0 -107
  93. package/src/engine/ecs/systems/ViewportMeshProjectionSystem.js +0 -68
  94. package/src/engine/graphics/particles/ParticleEmitterLibrary.js +0 -87
  95. package/src/engine/grid/components/ViewportGridProjection.js +0 -20
  96. package/src/engine/grid/systems/GridObstacleSystem.js +0 -58
  97. package/src/engine/grid/systems/ViewportGridProjectionSystem.js +0 -105
  98. /package/src/{engine → core/primitives/array}/computeStridedIntegerArrayHash.js +0 -0
@@ -3,7 +3,6 @@
3
3
  * @copyright Alex Goldring 2016
4
4
  */
5
5
  import View from "../View.js";
6
- import { prettyPrint } from "../../core/NumberFormat.js";
7
6
  import ObservedValue from "../../core/model/ObservedValue.js";
8
7
  import Vector1 from "../../core/geom/Vector1.js";
9
8
  import LinearValue from "../../core/model/LinearValue.js";
@@ -17,6 +16,7 @@ import { assert } from "../../core/assert.js";
17
16
  import ObservedInteger from "../../core/model/ObservedInteger.js";
18
17
  import { noop } from "../../core/function/Functions.js";
19
18
  import { isTypedArray } from "../../core/collection/array/typed/isTypedArray.js";
19
+ import { number_pretty_print } from "../../core/primitives/numbers/number_pretty_print.js";
20
20
 
21
21
 
22
22
  /**
@@ -26,7 +26,7 @@ import { isTypedArray } from "../../core/collection/array/typed/isTypedArray.js"
26
26
  */
27
27
  function format(value) {
28
28
  if (typeof value === 'number') {
29
- return prettyPrint(value);
29
+ return number_pretty_print(value);
30
30
  } else {
31
31
  return value;
32
32
  }
@@ -38,7 +38,7 @@ function format(value) {
38
38
  * @returns {string|number}
39
39
  */
40
40
  function formatNumber(v) {
41
- return prettyPrint(v);
41
+ return number_pretty_print(v);
42
42
  }
43
43
 
44
44
  function formatArray(arr) {
@@ -1,18 +0,0 @@
1
- /**
2
- * User: Alex Goldring
3
- * Date: 13/6/2014
4
- * Time: 22:32
5
- */
6
-
7
-
8
- function AimController(options) {
9
- this.xDelta = 0;
10
- this.yDelta = 0;
11
- //
12
- this.lon = 0;
13
- this.lat = 0;
14
- this.phi = 0;
15
- this.theta = 0;
16
- }
17
-
18
- export default AimController;
@@ -1,13 +0,0 @@
1
- /**
2
- * Created by Alex on 30/06/2014.
3
- */
4
-
5
-
6
- function Attacker(options) {
7
- this.target = null;
8
- this.range = options.range || 0;
9
- this.delay = options.delay || 1;
10
- this.timerValue = 0;
11
- }
12
-
13
- export default Attacker;
@@ -1,15 +0,0 @@
1
- /**
2
- * Created by hdnha on 7/24/2014.
3
- */
4
-
5
-
6
- /**
7
- * @deprecated
8
- * @param options
9
- * @constructor
10
- */
11
- function MeshCollider(options) {
12
- this.tags = options.tags.slice();
13
- }
14
-
15
- export default MeshCollider;
@@ -1,12 +0,0 @@
1
- /**
2
- * Created by Alex on 13/08/2014.
3
- */
4
-
5
-
6
- function RangedAttack(options) {
7
- this.factory = options.factory || null;
8
- this.speed = options.speed || 1;
9
- this.projectileOffset = options.offset || new THREE.Vector3(0, 0, 0);
10
- }
11
-
12
- export default RangedAttack;
@@ -1,11 +0,0 @@
1
- /**
2
- * Created by Alex on 30/06/2014.
3
- */
4
-
5
-
6
- function TargetAI(options) {
7
- this.tags = options.tags || [];
8
- this.range = options.range || 0;
9
- }
10
-
11
- export default TargetAI;
@@ -1,18 +0,0 @@
1
- /**
2
- * Created by Alex on 18/12/2014.
3
- */
4
-
5
- import Vector2 from "../../../core/geom/Vector2.js";
6
-
7
- function ViewportMeshProjection(options) {
8
- if (options === void 0) {
9
- options = {};
10
- }
11
- this.position = options.position !== void 0 ? options.position : new Vector2();
12
- this.entity = options.entity;
13
- }
14
-
15
-
16
- ViewportMeshProjection.typeName = "ViewportMeshProjection";
17
-
18
- export default ViewportMeshProjection;
@@ -1,63 +0,0 @@
1
- /**
2
- * User: Alex Goldring
3
- * Date: 13/6/2014
4
- * Time: 22:33
5
- */
6
- import { System } from '../System.js';
7
- import AimController from '../components/AimController.js';
8
- import CharacterController from '../components/CharacterController.js';
9
- import { Transform } from '../transform/Transform.js';
10
- import { DEG_TO_RAD } from "../../../core/math/DEG_TO_RAD.js";
11
-
12
-
13
- class AimControllerSystem extends System {
14
- constructor() {
15
- super();
16
- this.dependencies = [AimController];
17
-
18
- this.sensitivity = 5 * DEG_TO_RAD;
19
- }
20
-
21
- add(component, entity) {
22
- }
23
-
24
- remove(component) {
25
- }
26
-
27
- update(timeDelta) {
28
- const entityManager = this.entityManager;
29
- const sensitivity = this.sensitivity;
30
- entityManager.traverseEntities([AimController, CharacterController, Transform], function (aimController, character, transform) {
31
- //update controller
32
- updateController(aimController, sensitivity);
33
- //rotate player
34
- const quaternion = new THREE.Quaternion();
35
- quaternion.setFromAxisAngle(new THREE.Vector3(0, 1, 0), -aimController.lon * DEG_TO_RAD);
36
- transform.rotation.copy(quaternion);
37
- //rotate aim transform
38
- const aimTransform = character.aim;
39
- if (aimTransform !== void 0) {
40
- const e = new THREE.Euler();
41
- e.setFromQuaternion(aimTransform.rotation);
42
- e.x = -(aimController.phi - Math.PI / 2);
43
- aimTransform.rotation.setFromEuler(e);
44
- }
45
- });
46
- }
47
- }
48
-
49
-
50
- function updateController(aim, sensitivity) {
51
- aim.lon += sensitivity * aim.xDelta;
52
- aim.lat -= sensitivity * aim.yDelta;
53
- //reset deltas
54
- aim.xDelta = 0;
55
- aim.yDelta = 0;
56
-
57
- aim.lat = Math.max(-85, Math.min(85, aim.lat));
58
- aim.phi = THREE.Math.degToRad(90 - aim.lat);
59
-
60
- aim.theta = THREE.Math.degToRad(aim.lon);
61
- }
62
-
63
- export default AimControllerSystem;
@@ -1,67 +0,0 @@
1
- /**
2
- * Created by Alex on 30/06/2014.
3
- */
4
- import { System } from '../System.js';
5
- import Attacker from '../components/Attacker.js';
6
- import { Transform } from '../transform/Transform.js';
7
-
8
-
9
- class AttackerSystem extends System {
10
- constructor() {
11
- super();
12
-
13
- this.dependencies = [Attacker];
14
- }
15
-
16
- add(component, entity) {
17
- }
18
-
19
- remove(component, entity) {
20
- }
21
-
22
- update(timeDelta) {
23
- /**
24
- *
25
- * @type {EntityManager}
26
- */
27
- const em = this.entityManager;
28
-
29
- /**
30
- *
31
- * @param {Attacker} attacker
32
- * @param {Transform} transform
33
- * @param entity
34
- */
35
- function visitEntity(attacker, transform, entity) {
36
- const target = attacker.target;
37
- if (target === null) {
38
- return; //no target
39
- }
40
- //check distance between attacker and the target
41
- const targetTransform = em.getComponent(target, Transform);
42
- if (targetTransform === null) {
43
- //target doesn't have transform
44
- attacker.target = null; //drop target
45
- return;
46
- }
47
- if (transform.position.distanceTo(targetTransform.position) > attacker.range) {
48
- return; //target is too far
49
- }
50
- const delay = attacker.delay;
51
- let time = attacker.timerValue + timeDelta;
52
- if (time > delay) {
53
- let attacks = Math.floor(time / delay);
54
- time %= delay;
55
- while (attacks-- > 0) {
56
- em.sendEvent(entity, "attack", target);
57
- }
58
- }
59
- attacker.timerValue = time;
60
- }
61
-
62
- em.traverseEntities([Attacker, Transform], visitEntity);
63
- }
64
- }
65
-
66
-
67
- export default AttackerSystem;
@@ -1,47 +0,0 @@
1
- /**
2
- * Created by hdnha on 7/24/2014.
3
- */
4
- import { System } from '../System.js';
5
- import Tag from '../components/Tag.js';
6
- import { Transform } from '../transform/Transform.js';
7
- import Renderable from '../renderable/Renderable.js';
8
- import MeshCollider from '../components/MeshCollider.js';
9
- import { Raycaster } from "three";
10
-
11
-
12
- class MeshColliderSystem extends System {
13
- constructor() {
14
- super();
15
-
16
- this.dependencies = [MeshCollider];
17
- }
18
-
19
- add(component, entity) {
20
- }
21
-
22
- remove(component) {
23
- }
24
-
25
- update(timeDelta) {
26
- const entityManager = this.entityManager;
27
- entityManager.traverseEntities([Transform, MeshCollider], function (transform, meshCollider, entity) {
28
- const delta = transform.position.clone().sub(transform.previousPosition);
29
- const length = delta.length();
30
- let raycaster = new Raycaster(transform.previousPosition, delta.normalize(), 0, length);
31
- if (!raycaster) {
32
- return;
33
- }
34
- entityManager.traverseEntities([Tag, Renderable], function (tag, renderable, otherEntity) {
35
- if (meshCollider.tags.indexOf(tag.name) != -1) {
36
- const objects = raycaster.intersectObject(renderable.mesh);
37
- if (objects.length > 0) {
38
- entityManager.sendEvent(entity, "collision", otherEntity);
39
- return false; //stop traversal
40
- }
41
- }
42
- });
43
- });
44
- }
45
- }
46
-
47
- export default MeshColliderSystem;
@@ -1,163 +0,0 @@
1
- /**
2
- * Created by Alex on 12/08/2014.
3
- */
4
- import { System } from '../System.js';
5
- import { Transform } from '../transform/Transform.js';
6
- import MonsterAI from '../components/MonsterAI.js';
7
- import Tag from '../components/Tag.js';
8
- import PathFollower from '../../navigation/ecs/path_following/PathFollower.js';
9
- import Steering from '../components/Steering.js';
10
- import Attacker from '../components/Attacker.js';
11
-
12
-
13
- class MonsterAISystem extends System {
14
- constructor(pathFinder) {
15
- super();
16
- this.pathFinder = pathFinder;
17
-
18
- this.dependencies = [MonsterAI];
19
- }
20
-
21
- add(component, entity) {
22
- const pathFinder = this.pathFinder;
23
- const em = this.entityManager;
24
- em.addEntityEventListener(entity, "spawned", function () {
25
- //reset current path
26
- const pf = em.getComponent(entity, PathFollower);
27
- pf.path = null;
28
- gotoDefensePoint(em, pathFinder, entity);
29
- });
30
- }
31
-
32
- remove(component) {
33
- }
34
-
35
- update(timeDelta) {
36
- const em = this.entityManager;
37
- const pathFinder = this.pathFinder;
38
- em.traverseEntities([MonsterAI, Attacker, Transform], function (ai, attacker, transform, entity) {
39
- const target = attacker.target;
40
- if (target !== null) {
41
- //there is a target
42
- const targetTransform = em.getComponent(target, Transform);
43
- if (targetTransform === null) {
44
- gotoDefensePoint(em, pathFinder, entity);
45
- return;
46
- }
47
- //check the distance
48
- const distance = transform.position.distanceTo(targetTransform.position);
49
- if (distance <= ai.chaseDistance) {
50
- //check if path exists
51
- pathFinder.findPath(transform.position, targetTransform.position, 2, function (path) {
52
- //find length of the path
53
- if (path !== null && pathLength(path) < ai.chaseDistance) {
54
- const pathFollower = em.getComponent(entity, PathFollower);
55
- if (pathFollower !== null) {
56
- pathFollower.path = path;
57
- pathFollower.lastIndex = 0;
58
- //stop steering
59
- const steering = em.getComponent(entity, Steering);
60
- steering.destination = null;
61
- }
62
- } else {
63
- gotoDefensePoint(em, pathFinder, entity);
64
- }
65
- });
66
- } else {
67
- gotoDefensePoint(em, pathFinder, entity);
68
- }
69
- }
70
- });
71
- }
72
- }
73
-
74
-
75
- function pointsEqual(p1, p2) {
76
- return p1.x === p2.x && p1.y === p2.y && p1.z === p2.z;
77
- }
78
-
79
- function navigateTo(em, entity, target, pathFinder) {
80
- const pathFollower = em.getComponent(entity, PathFollower);
81
- const steering = em.getComponent(entity, Steering);
82
- const source = em.getComponent(entity, Transform);
83
-
84
- //check if already going to the right place
85
- const path = pathFollower.path;
86
- let pathLength;
87
- if (path !== null && path !== void 0 && (pathLength = path.length, pathLength > 0)) {
88
- const lastPointOfPath = path[pathLength - 1];
89
- if (pointsEqual(lastPointOfPath, target.position)) {
90
- return;// already following thr right path
91
- }
92
- }
93
-
94
- //find new path
95
- if (target !== null && !pathFollower.lock) {
96
- pathFollower.lock = true;
97
- pathFinder.findPath(source.position, target.position, 2, function (path) {
98
- //reset path
99
- pathFollower.path = path;
100
- pathFollower.lastIndex = 0;
101
- //stop steering
102
- steering.destination = null;
103
- //release lock
104
- pathFollower.lock = false;
105
- });
106
- }
107
- }
108
-
109
- /**
110
- * finds nearest (straight line distance) entity with matching tag and navigates to it
111
- * @param em
112
- * @param pathFinder
113
- * @param entity
114
- * @param tagName
115
- */
116
- function gotoTag(em, pathFinder, entity, tagName) {
117
- let target = null;
118
- let d = Math.POSITIVE_INFINITY;
119
- const sourceTransform = em.getComponent(entity, Transform);
120
- const sourcePosition = sourceTransform.position;
121
-
122
- /**
123
- *
124
- * @param {Tag} tag
125
- * @param {Transform} transform
126
- */
127
- function visitTag(tag, transform) {
128
- if (tag.contains(tagName)) {
129
- const distanceToSquared = transform.position.distanceToSquared(sourcePosition);
130
- if (target === null || distanceToSquared < d) {
131
- target = transform;
132
- d = distanceToSquared;
133
- }
134
- }
135
- }
136
-
137
- em.traverseEntities([Tag, Transform], visitTag);
138
- navigateTo(em, entity, target, pathFinder);
139
- }
140
-
141
- function pathLength(path) {
142
- let result = 0;
143
- if (path === void 0) {
144
- return 0;
145
- }
146
- const l = path.length - 1;
147
- if (l >= 1) {
148
- let c = path[0], p;
149
- for (let i = 1; i < l; i++) {
150
- p = c;
151
- c = path[i];
152
- result += p.distanceTo(c);
153
- }
154
- }
155
- return result;
156
- }
157
-
158
- function gotoDefensePoint(entityManager, pathFinder, entity) {
159
-
160
- gotoTag(entityManager, pathFinder, entity, "DefensePoint");
161
- }
162
-
163
- export default MonsterAISystem;
@@ -1,46 +0,0 @@
1
- /**
2
- * User: Alex Goldring
3
- * Date: 17/6/2014
4
- * Time: 21:27
5
- */
6
- import { System } from '../System.js';
7
- import Mortality from '../components/Mortality.js';
8
-
9
-
10
- class MortalitySystem extends System {
11
- constructor() {
12
- super();
13
-
14
- this.dependencies = [Mortality];
15
- //
16
- this.__handlers = [];
17
- }
18
-
19
- reset() {
20
- this.__handlers = [];
21
- }
22
-
23
- link(component, entity) {
24
- const entityManager = this.entityManager;
25
- const h = function () {
26
- component.actions.forEach(function (action) {
27
- action(entity, entityManager);
28
- });
29
- };
30
- this.__handlers[entity] = h;
31
- entityManager.addEntityEventListener(entity, "death", h);
32
- }
33
-
34
- unlink(component, entity) {
35
- const handlers = this.__handlers;
36
- const handler = handlers[entity];
37
- this.entityManager.removeEntityEventListener(entity, "death", handler);
38
- delete handlers[entity];
39
- }
40
-
41
- update(timeDelta) {
42
- }
43
- }
44
-
45
-
46
- export default MortalitySystem;
@@ -1,132 +0,0 @@
1
- /**
2
- * Created by Alex on 13/08/2014.
3
- */
4
- import { System } from '../System.js';
5
- import { Transform } from '../transform/Transform.js';
6
- import RangedAttack from '../components/RangedAttack.js';
7
- import PhysicalBody from '../components/PhysicalBody.js';
8
- import Motion from '../components/Motion.js';
9
- import Renderable from '../renderable/Renderable.js';
10
- import { Matrix4 as ThreeMatrix4, Vector3 as ThreeVector3 } from 'three';
11
- import { solveQuadratic } from "../../../core/math/solveQuadratic.js";
12
-
13
- /**
14
- * Return the firing solution for a projectile starting at 'src' with
15
- * velocity 'v', to hit a target, 'dst'.
16
- *
17
- * @param Vector3 source position of shooter
18
- * @param Vector3 target position of target
19
- * @param Vector3 targetVelocity velocity of target object
20
- * @param Vector3 sourceSpeed speed of projectile
21
- * @return Vector3 Coordinate at which to fire (and where intercept occurs)
22
- */
23
- const intercept = (function () {
24
-
25
-
26
- const toTarget = new ThreeVector3();
27
- const v0 = new ThreeVector3();
28
-
29
- function intercept(source, target, targetVelocity, sourceSpeed) {
30
- toTarget.copy(target).sub(source);
31
- // Get quadratic equation components
32
- const a = targetVelocity.dot(targetVelocity) - sourceSpeed * sourceSpeed;
33
- const b = 2 * targetVelocity.dot(toTarget);
34
- const c = toTarget.dot(toTarget);
35
-
36
- // Solve quadratic
37
- const ts = [];
38
- const root_count = solveQuadratic(ts, 0, a, b, c); // See quad(), below
39
-
40
- // Find smallest positive solution
41
- let sol = null;
42
- if (root_count > 0) {
43
- const t0 = ts[0], t1 = ts[1];
44
- let t = Math.min(t0, t1);
45
- if (t < 0) t = Math.max(t0, t1);
46
- if (t > 0) {
47
- v0.copy(targetVelocity).multiplyScalar(t).add(target);
48
- sol = v0;
49
- }
50
- }
51
-
52
- return sol;
53
- }
54
-
55
- return intercept;
56
- })();
57
-
58
-
59
- class RangedAttackSystem extends System {
60
- constructor() {
61
- super();
62
-
63
- this.dependencies = [RangedAttack];
64
- }
65
-
66
- add(component, entity) {
67
- const em = this.entityManager;
68
- em.addEntityEventListener(entity, "attack", function (target) {
69
- //get transform
70
- const targetTransform = em.getComponent(target, Transform);
71
- if (targetTransform === null) {
72
- //target no longer exists
73
- return;
74
- }
75
- const sourceTransform = em.getComponent(entity, Transform);
76
- //get projectile
77
- const projectileBuilder = component.factory();
78
- const projectileTransform = projectileBuilder.getComponent(Transform);
79
- //get delta between source and target
80
- const sourcePosition = sourceTransform.position.clone().add(component.projectileOffset);
81
- let targetPosition = targetTransform.position.clone();
82
-
83
- //check if target has a mesh
84
- const renderable = em.getComponent(target, Renderable);
85
- if (renderable !== null) {
86
- targetPosition.add(renderable.center);
87
- }
88
- //check if target is moving
89
- const motion = em.getComponent(target, Motion);
90
- if (motion !== null) {
91
- //correct targeting, with respect to motion
92
- const interceptPosition = intercept(sourcePosition, targetPosition, motion.velocity, component.speed);
93
- if (interceptPosition !== null) {
94
- //if there is a valid solution, use it
95
- targetPosition = interceptPosition;
96
- }
97
- }
98
- const velocity = targetPosition.clone().sub(sourcePosition).normalize().multiplyScalar(component.speed);
99
- //move projectile to source transform
100
- projectileTransform.position.copy(sourcePosition);
101
- //align rotation
102
- const matrix4 = new ThreeMatrix4();
103
- const up = new ThreeVector3(0, 1, 0);
104
- matrix4.lookAt(sourcePosition, targetPosition, up);
105
- projectileTransform.rotation.setFromRotationMatrix(matrix4);
106
-
107
- //set physical body
108
- const physicalBody = projectileBuilder.getComponent(PhysicalBody);
109
- if (physicalBody !== null && physicalBody !== void 0) {
110
- const body = physicalBody.body;
111
- body.position.copy(sourcePosition);
112
- body.linearVelocity.copy(velocity);
113
- }
114
- //motion of component
115
- const pMotion = projectileBuilder.getComponent(Motion);
116
- if (pMotion !== null) {
117
- pMotion.velocity.copy(velocity);
118
- }
119
- //build
120
- let projectileEntity = projectileBuilder.build(em);
121
- });
122
- }
123
-
124
- remove(component) {
125
- }
126
-
127
- update(timeDelta) {
128
- }
129
- }
130
-
131
-
132
- export default RangedAttackSystem;
@@ -1,10 +0,0 @@
1
- import { System } from "../System.js";
2
- import { SerializationMetadata } from "../components/SerializationMetadata.js";
3
-
4
- export class SerializationMetadataSystem extends System {
5
- constructor() {
6
- super();
7
-
8
- this.dependencies = [SerializationMetadata];
9
- }
10
- }