@makefully/platypus 4.1.5 → 4.1.6
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.
- package/CHANGELOG.md +10 -0
- package/README.md +3 -3
- package/lib/platypus.js +1 -1
- package/package.json +6 -5
- package/src/AABB.js +685 -0
- package/src/ActionState.js +121 -0
- package/src/AssetManager.js +206 -0
- package/src/CollisionData.js +96 -0
- package/src/CollisionDataContainer.js +127 -0
- package/src/CollisionShape.js +315 -0
- package/src/Component.js +231 -0
- package/src/Data.js +64 -0
- package/src/DataMap.js +204 -0
- package/src/Entity.js +404 -0
- package/src/EntityLinker.js +113 -0
- package/src/EventHandler.js +115 -0
- package/src/EventHandlerList.js +251 -0
- package/src/Game.js +840 -0
- package/src/Gamepad.js +175 -0
- package/src/ID3CaptionPlayer.js +61 -0
- package/src/Messenger.js +365 -0
- package/src/PIXIAnimation.js +622 -0
- package/src/RandomSet.js +140 -0
- package/src/SFXPlayer.js +120 -0
- package/src/StateMap.js +252 -0
- package/src/Storage.js +152 -0
- package/src/TickerClient.js +48 -0
- package/src/TickerServer.js +23 -0
- package/src/TimeEvent.js +50 -0
- package/src/TimeEventList.js +100 -0
- package/src/VOPlayer.js +684 -0
- package/src/Vector.js +702 -0
- package/src/components/AIChaser.js +161 -0
- package/src/components/AIPacer.js +107 -0
- package/src/components/AudioMusic.js +151 -0
- package/src/components/AudioSFX.js +673 -0
- package/src/components/AudioVO.js +301 -0
- package/src/components/CollisionBasic.js +826 -0
- package/src/components/CollisionFilter.js +74 -0
- package/src/components/CollisionGroup.js +448 -0
- package/src/components/CollisionTiles.js +608 -0
- package/src/components/ComponentSwitcher.js +173 -0
- package/src/components/ControllerInput.js +65 -0
- package/src/components/Counter.js +165 -0
- package/src/components/EntityCamera.js +215 -0
- package/src/components/EntityContainer.js +549 -0
- package/src/components/EntityController.js +541 -0
- package/src/components/HandlerCamera.js +1052 -0
- package/src/components/HandlerCollision.js +1318 -0
- package/src/components/HandlerController.js +291 -0
- package/src/components/HandlerLogic.js +394 -0
- package/src/components/HandlerRender.js +217 -0
- package/src/components/Interactive.js +502 -0
- package/src/components/LevelBuilder.js +524 -0
- package/src/components/LogicAngularMovement.js +154 -0
- package/src/components/LogicAttachment.js +265 -0
- package/src/components/LogicButton.js +466 -0
- package/src/components/LogicCarrier.js +39 -0
- package/src/components/LogicDestroyMe.js +58 -0
- package/src/components/LogicDirectionalMovement.js +325 -0
- package/src/components/LogicDragDrop.js +371 -0
- package/src/components/LogicImpactLaunch.js +144 -0
- package/src/components/LogicPacingPlatform.js +64 -0
- package/src/components/LogicPortable.js +112 -0
- package/src/components/LogicPortal.js +115 -0
- package/src/components/LogicPushable.js +98 -0
- package/src/components/LogicRebounder.js +136 -0
- package/src/components/LogicRegionSpawner.js +139 -0
- package/src/components/LogicRotationalMovement.js +205 -0
- package/src/components/LogicSpawner.js +159 -0
- package/src/components/LogicStateMachine.js +382 -0
- package/src/components/LogicSwitch.js +77 -0
- package/src/components/LogicTeleportee.js +68 -0
- package/src/components/LogicTeleporter.js +93 -0
- package/src/components/LogicTimer.js +178 -0
- package/src/components/LogicWindUpRacer.js +179 -0
- package/src/components/Motion.js +371 -0
- package/src/components/Mover.js +566 -0
- package/src/components/Node.js +289 -0
- package/src/components/NodeMap.js +295 -0
- package/src/components/NodeResident.js +636 -0
- package/src/components/Orientation.js +697 -0
- package/src/components/RandomEvents.js +73 -0
- package/src/components/RelativePosition.js +204 -0
- package/src/components/RelayFamily.js +106 -0
- package/src/components/RelayGame.js +53 -0
- package/src/components/RelayLinker.js +94 -0
- package/src/components/RelayParent.js +57 -0
- package/src/components/RelaySelf.js +55 -0
- package/src/components/Render.js +178 -0
- package/src/components/RenderAnimator.js +275 -0
- package/src/components/RenderContainer.js +646 -0
- package/src/components/RenderDebug.js +319 -0
- package/src/components/RenderDestroyMe.js +59 -0
- package/src/components/RenderLottie.js +149 -0
- package/src/components/RenderProgress.js +120 -0
- package/src/components/RenderSpine.js +833 -0
- package/src/components/RenderSprite.js +527 -0
- package/src/components/RenderText.js +147 -0
- package/src/components/RenderTiles.js +1391 -0
- package/src/components/SceneChanger.js +128 -0
- package/src/components/TiledLoader.js +1451 -0
- package/src/components/Timeline.js +314 -0
- package/src/components/Tutorial.js +267 -0
- package/src/components/Tween.js +296 -0
- package/src/components/VoiceOver.js +373 -0
- package/src/components/XHR.js +129 -0
- package/src/components/index.js +79 -0
- package/src/factory.js +305 -0
- package/src/index.js +159 -0
- package/src/mixins/PIXI.Graphics.js +41 -0
- package/src/platypus.css +68 -0
- package/src/sayHello.js +50 -0
- package/src/shapes/Capsule.js +74 -0
- package/src/shapes/Circle.js +43 -0
- package/src/shapes/Ellipse.js +117 -0
- package/src/shapes/Point.js +191 -0
- package/src/shapes/Polygon.js +112 -0
- package/src/shapes/Polyline.js +97 -0
- package/src/shapes/Rectangle.js +78 -0
- package/src/shapes/RoundedRectangle.js +33 -0
- package/src/shapes/Segment.js +346 -0
- package/src/shapes/adjustedXY.js +19 -0
- package/src/shapes/castFromBox2D.js +92 -0
- package/src/shapes/castFromObject.js +53 -0
- package/src/shapes/castFromPixiGraphics.js +6 -0
- package/src/shapes/castFromPixiShape.js +89 -0
- package/src/shapes/castToBox2D.js +190 -0
- package/src/shapes/castToPixiGraphics.js +100 -0
- package/src/shapes/castToPixiShape.js +61 -0
- package/src/shapes/checkPointsMap.js +313 -0
- package/src/shapes/index.js +35 -0
- package/src/utils/array.js +73 -0
- package/src/utils/string.js +39 -0
- package/lib/243.platypus.mjs +0 -1
- package/lib/platypus.mjs +0 -1
|
@@ -0,0 +1,289 @@
|
|
|
1
|
+
/**
|
|
2
|
+
## JSON Definition
|
|
3
|
+
{
|
|
4
|
+
"type": "NodeResident",
|
|
5
|
+
|
|
6
|
+
"nodeId": "city-hall",
|
|
7
|
+
// Optional. The id of the node that this entity should start on. Uses the entity's nodeId property if not set here.
|
|
8
|
+
|
|
9
|
+
"nodes": ['path','sidewalk','road'],
|
|
10
|
+
// Optional. This is a list of node types that this entity can reside on. If not set, entity can reside on any type of node.
|
|
11
|
+
|
|
12
|
+
"shares": ['friends','neighbors','city-council-members'],
|
|
13
|
+
// Optional. This is a list of entities that this entity can reside with on the same node. If not set, this entity cannot reside with any entities on the same node.
|
|
14
|
+
|
|
15
|
+
"speed": 5,
|
|
16
|
+
// Optional. Sets the speed with which the entity moves along an edge to an adjacent node. Default is 0 (instantaneous movement).
|
|
17
|
+
|
|
18
|
+
"updateOrientation": true
|
|
19
|
+
// Optional. Determines whether the entity's orientation is updated by movement across the NodeMap. Default is false.
|
|
20
|
+
}
|
|
21
|
+
*/
|
|
22
|
+
import {arrayCache, greenSplice} from '../utils/array.js';
|
|
23
|
+
import Vector from '../Vector.js';
|
|
24
|
+
import createComponentClass from '../factory.js';
|
|
25
|
+
|
|
26
|
+
export default createComponentClass(/** @lends platypus.components.Node.prototype */{
|
|
27
|
+
|
|
28
|
+
id: 'Node',
|
|
29
|
+
|
|
30
|
+
properties: {
|
|
31
|
+
/**
|
|
32
|
+
* If provided, treats these property names as neighbors, assigning them to the neighbors object. For example, ["east", "west"] creates `entity.east` and `entity.west` entity properties that are pointers to those neighbors.
|
|
33
|
+
*
|
|
34
|
+
* @property neighborProperties
|
|
35
|
+
* @type Array
|
|
36
|
+
* @default null
|
|
37
|
+
*/
|
|
38
|
+
neighborProperties: null
|
|
39
|
+
},
|
|
40
|
+
|
|
41
|
+
publicProperties: {
|
|
42
|
+
neighbors: null,
|
|
43
|
+
nodeId: '',
|
|
44
|
+
x: 0,
|
|
45
|
+
y: 0,
|
|
46
|
+
z: 0
|
|
47
|
+
},
|
|
48
|
+
|
|
49
|
+
/**
|
|
50
|
+
* This component causes an entity to be a position on a [[NodeMap]]. This component should not be confused with `NodeResident` which should be used on entities that move around on a NodeMap: `Node` simply represents a non-moving location on the NodeMap.
|
|
51
|
+
*
|
|
52
|
+
* @memberof platypus.components
|
|
53
|
+
* @uses platypus.Component
|
|
54
|
+
* @constructs
|
|
55
|
+
*/
|
|
56
|
+
initialize: function () {
|
|
57
|
+
const owner = this.owner;
|
|
58
|
+
|
|
59
|
+
this.nodeId = this.nodeId || owner.id || String(Math.random());
|
|
60
|
+
|
|
61
|
+
if ((typeof this.nodeId !== 'string') && (this.nodeId.length)) {
|
|
62
|
+
this.nodeId = this.nodeId.join('|');
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
owner.nodeId = this.nodeId;
|
|
66
|
+
|
|
67
|
+
owner.isNode = true;
|
|
68
|
+
this.map = owner.map = owner.map || owner.parent || null;
|
|
69
|
+
this.contains = owner.contains = arrayCache.setUp();
|
|
70
|
+
this.edgesContain = owner.edgesContain = arrayCache.setUp();
|
|
71
|
+
|
|
72
|
+
Vector.assign(owner, 'position', 'x', 'y', 'z');
|
|
73
|
+
|
|
74
|
+
if (!this.neighbors) {
|
|
75
|
+
this.neighbors = {};
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
if (this.neighborProperties) {
|
|
79
|
+
const properties = this.neighborProperties;
|
|
80
|
+
|
|
81
|
+
for (let i = 0; i < properties.length; i++) {
|
|
82
|
+
const
|
|
83
|
+
propertyName = properties[i],
|
|
84
|
+
value = owner[propertyName];
|
|
85
|
+
|
|
86
|
+
if (value) {
|
|
87
|
+
this.neighbors[propertyName] = value;
|
|
88
|
+
}
|
|
89
|
+
Object.defineProperty(owner, propertyName, {
|
|
90
|
+
get: () => this.neighbors[propertyName],
|
|
91
|
+
set: (value) => {
|
|
92
|
+
if (value !== this.neighbors[propertyName]) {
|
|
93
|
+
this.neighbors[propertyName] = value;
|
|
94
|
+
for (let i = 0; i < this.contains.length; i++) {
|
|
95
|
+
this.contains[i].triggerEvent('set-directions');
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
});
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
},
|
|
103
|
+
|
|
104
|
+
events: {
|
|
105
|
+
"add-neighbors": function (neighbors) {
|
|
106
|
+
const
|
|
107
|
+
directions = Object.keys(neighbors);
|
|
108
|
+
|
|
109
|
+
for (let i = 0; i < directions.length; i++) {
|
|
110
|
+
const
|
|
111
|
+
direction = directions[i];
|
|
112
|
+
|
|
113
|
+
this.neighbors[direction] = neighbors[direction];
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
for (let i = 0; i < this.contains.length; i++) {
|
|
117
|
+
this.contains[i].triggerEvent('set-directions');
|
|
118
|
+
}
|
|
119
|
+
},
|
|
120
|
+
"remove-neighbor": function (nodeOrNodeId) {
|
|
121
|
+
const
|
|
122
|
+
id = nodeOrNodeId.nodeId ?? nodeOrNodeId,
|
|
123
|
+
neighbors = Object.keys(this.neighbors);
|
|
124
|
+
|
|
125
|
+
for (let i = 0; i < neighbors.length; i++) {
|
|
126
|
+
const
|
|
127
|
+
neighbor = neighbors[i];
|
|
128
|
+
|
|
129
|
+
if ((neighbor === id) || (neighbor.nodeId === id)) {
|
|
130
|
+
delete this.neighbors[i];
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
}
|
|
134
|
+
},
|
|
135
|
+
|
|
136
|
+
methods: {
|
|
137
|
+
toJSON (entityProperties) {
|
|
138
|
+
const
|
|
139
|
+
neighborProperties = this.neighborProperties;
|
|
140
|
+
|
|
141
|
+
neighborProperties.forEach((neighbor) => {
|
|
142
|
+
const
|
|
143
|
+
neighborNode = this.neighbors[neighbor];
|
|
144
|
+
|
|
145
|
+
if (neighborNode) {
|
|
146
|
+
entityProperties[neighbor] = neighborNode.id;
|
|
147
|
+
}
|
|
148
|
+
});
|
|
149
|
+
|
|
150
|
+
entityProperties.nodeId = this.nodeId;
|
|
151
|
+
|
|
152
|
+
return {
|
|
153
|
+
type: 'Node',
|
|
154
|
+
neighborProperties
|
|
155
|
+
};
|
|
156
|
+
},
|
|
157
|
+
|
|
158
|
+
destroy () {
|
|
159
|
+
arrayCache.recycle(this.contains);
|
|
160
|
+
this.contains = this.owner.contains = null;
|
|
161
|
+
arrayCache.recycle(this.edgesContain);
|
|
162
|
+
this.edgesContain = this.owner.edgesContain = null;
|
|
163
|
+
}
|
|
164
|
+
},
|
|
165
|
+
|
|
166
|
+
publicMethods: {
|
|
167
|
+
joinNode (node, direction, mutual = false) {
|
|
168
|
+
this.neighbors[direction] = node;
|
|
169
|
+
|
|
170
|
+
for (let i = 0; i < this.contains.length; i++) {
|
|
171
|
+
this.contains[i].triggerEvent('set-directions');
|
|
172
|
+
}
|
|
173
|
+
|
|
174
|
+
if (mutual) {
|
|
175
|
+
node.joinNode(this.owner, (typeof mutual === 'boolean') ? direction : mutual);
|
|
176
|
+
}
|
|
177
|
+
},
|
|
178
|
+
|
|
179
|
+
/**
|
|
180
|
+
* Gets a neighboring node Entity.
|
|
181
|
+
*
|
|
182
|
+
* @memberof Node.prototype
|
|
183
|
+
* @param {String} desc Describes the direction to check.
|
|
184
|
+
* @returns {platypus.Entity}
|
|
185
|
+
*/
|
|
186
|
+
getNode: function (desc) {
|
|
187
|
+
const
|
|
188
|
+
neighbor = this.neighbors[desc];
|
|
189
|
+
|
|
190
|
+
//map check
|
|
191
|
+
if (!this.map && this.owner.map) {
|
|
192
|
+
this.map = this.owner.map;
|
|
193
|
+
}
|
|
194
|
+
|
|
195
|
+
if (neighbor) {
|
|
196
|
+
const
|
|
197
|
+
testNeighbor = neighbor.destroyed ? neighbor.id : neighbor;
|
|
198
|
+
|
|
199
|
+
if (testNeighbor.isNode) {
|
|
200
|
+
return testNeighbor;
|
|
201
|
+
} else if (typeof testNeighbor === 'string') {
|
|
202
|
+
const
|
|
203
|
+
actualNeighbor = this.map.getNode(testNeighbor);
|
|
204
|
+
|
|
205
|
+
if (actualNeighbor) {
|
|
206
|
+
this.neighbors[desc] = actualNeighbor;
|
|
207
|
+
return actualNeighbor;
|
|
208
|
+
}
|
|
209
|
+
} else if (testNeighbor.length) {
|
|
210
|
+
const
|
|
211
|
+
actualNeighbor = this.map.getNode(testNeighbor.join('|'));
|
|
212
|
+
|
|
213
|
+
if (actualNeighbor) {
|
|
214
|
+
this.neighbors[desc] = actualNeighbor;
|
|
215
|
+
return actualNeighbor;
|
|
216
|
+
}
|
|
217
|
+
}
|
|
218
|
+
}
|
|
219
|
+
|
|
220
|
+
return null;
|
|
221
|
+
},
|
|
222
|
+
|
|
223
|
+
/**
|
|
224
|
+
* Puts an entity on this node.
|
|
225
|
+
*
|
|
226
|
+
* @memberof Node.prototype
|
|
227
|
+
* @param {platypus.Entity} entity
|
|
228
|
+
* @returns {platypus.Entity}
|
|
229
|
+
*/
|
|
230
|
+
addToNode: function (entity) {
|
|
231
|
+
for (let i = 0; i < this.contains.length; i++) {
|
|
232
|
+
if (this.contains[i] === entity) {
|
|
233
|
+
return false;
|
|
234
|
+
}
|
|
235
|
+
}
|
|
236
|
+
this.contains.push(entity);
|
|
237
|
+
return entity;
|
|
238
|
+
},
|
|
239
|
+
|
|
240
|
+
/**
|
|
241
|
+
* Removes an entity from this node.
|
|
242
|
+
*
|
|
243
|
+
* @memberof Node.prototype
|
|
244
|
+
* @param {platypus.Entity} entity
|
|
245
|
+
* @returns {platypus.Entity}
|
|
246
|
+
*/
|
|
247
|
+
removeFromNode: function (entity) {
|
|
248
|
+
for (let i = 0; i < this.contains.length; i++) {
|
|
249
|
+
if (this.contains[i] === entity) {
|
|
250
|
+
return greenSplice(this.contains, i);
|
|
251
|
+
}
|
|
252
|
+
}
|
|
253
|
+
return false;
|
|
254
|
+
},
|
|
255
|
+
|
|
256
|
+
/**
|
|
257
|
+
* Adds an entity to this node's edges.
|
|
258
|
+
*
|
|
259
|
+
* @memberof Node.prototype
|
|
260
|
+
* @param {platypus.Entity} entity
|
|
261
|
+
* @returns {platypus.Entity}
|
|
262
|
+
*/
|
|
263
|
+
addToEdge: function (entity) {
|
|
264
|
+
for (let i = 0; i < this.edgesContain.length; i++) {
|
|
265
|
+
if (this.edgesContain[i] === entity) {
|
|
266
|
+
return false;
|
|
267
|
+
}
|
|
268
|
+
}
|
|
269
|
+
this.edgesContain.push(entity);
|
|
270
|
+
return entity;
|
|
271
|
+
},
|
|
272
|
+
|
|
273
|
+
/**
|
|
274
|
+
* Removes an entity from this node's edges.
|
|
275
|
+
*
|
|
276
|
+
* @memberof Node.prototype
|
|
277
|
+
* @param {platypus.Entity} entity
|
|
278
|
+
* @returns {platypus.Entity}
|
|
279
|
+
*/
|
|
280
|
+
removeFromEdge: function (entity) {
|
|
281
|
+
for (let i = 0; i < this.edgesContain.length; i++) {
|
|
282
|
+
if (this.edgesContain[i] === entity) {
|
|
283
|
+
return greenSplice(this.edgesContain, i);
|
|
284
|
+
}
|
|
285
|
+
}
|
|
286
|
+
return false;
|
|
287
|
+
}
|
|
288
|
+
}
|
|
289
|
+
});
|
|
@@ -0,0 +1,295 @@
|
|
|
1
|
+
import {arrayCache, greenSplice} from '../utils/array.js';
|
|
2
|
+
import Entity from '../Entity.js';
|
|
3
|
+
import Vector from '../Vector.js';
|
|
4
|
+
import createComponentClass from '../factory.js';
|
|
5
|
+
import recycle from 'recycle';
|
|
6
|
+
|
|
7
|
+
const
|
|
8
|
+
Node = function (definition, map) { // This is a basic node object, but can be replaced by entities having a `Node` component if more functionality is needed.
|
|
9
|
+
if (definition.id) {
|
|
10
|
+
if (typeof definition.id === 'string') {
|
|
11
|
+
this.id = definition.id;
|
|
12
|
+
} else if (Array.isArray(definition.id)) {
|
|
13
|
+
this.id = definition.id.join('|');
|
|
14
|
+
} else {
|
|
15
|
+
this.id = String(Math.random());
|
|
16
|
+
}
|
|
17
|
+
} else {
|
|
18
|
+
this.id = String(Math.random());
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
this.isNode = true;
|
|
22
|
+
this.map = map;
|
|
23
|
+
this.contains = arrayCache.setUp();
|
|
24
|
+
this.type = definition.type || '';
|
|
25
|
+
|
|
26
|
+
if (!this.position) {
|
|
27
|
+
Vector.assign(this, 'position', 'x', 'y', 'z');
|
|
28
|
+
}
|
|
29
|
+
this.x = definition.x || 0;
|
|
30
|
+
this.y = definition.y || 0;
|
|
31
|
+
this.z = definition.z || 0;
|
|
32
|
+
|
|
33
|
+
this.neighbors = definition.neighbors || {};
|
|
34
|
+
},
|
|
35
|
+
proto = Node.prototype;
|
|
36
|
+
|
|
37
|
+
proto.getNode = function (desc) {
|
|
38
|
+
const
|
|
39
|
+
neighbor = this.neighbors[desc];
|
|
40
|
+
|
|
41
|
+
if (neighbor) {
|
|
42
|
+
if (neighbor.isNode) {
|
|
43
|
+
return neighbor;
|
|
44
|
+
} else if (typeof neighbor === 'string') {
|
|
45
|
+
const
|
|
46
|
+
node = this.map.getNode(neighbor);
|
|
47
|
+
|
|
48
|
+
if (node) {
|
|
49
|
+
this.neighbors[desc] = node;
|
|
50
|
+
return node;
|
|
51
|
+
}
|
|
52
|
+
} else if (Array.isArray(neighbor)) {
|
|
53
|
+
const
|
|
54
|
+
node = this.map.getNode(neighbor.join('|'));
|
|
55
|
+
|
|
56
|
+
if (node) {
|
|
57
|
+
this.neighbors[desc] = node;
|
|
58
|
+
return node;
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
return null;
|
|
62
|
+
} else {
|
|
63
|
+
return null;
|
|
64
|
+
}
|
|
65
|
+
};
|
|
66
|
+
|
|
67
|
+
proto.addToNode = function (entity) {
|
|
68
|
+
for (let i = 0; i < this.contains.length; i++) {
|
|
69
|
+
if (this.contains[i] === entity) {
|
|
70
|
+
return false;
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
this.contains.push(entity);
|
|
74
|
+
return entity;
|
|
75
|
+
};
|
|
76
|
+
|
|
77
|
+
proto.removeFromNode = function (entity) {
|
|
78
|
+
for (let i = 0; i < this.contains.length; i++) {
|
|
79
|
+
if (this.contains[i] === entity) {
|
|
80
|
+
return greenSplice(this.contains, i);
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
return false;
|
|
84
|
+
};
|
|
85
|
+
|
|
86
|
+
recycle.add(Node, 'Node', Node, function () {
|
|
87
|
+
arrayCache.recycle(this.contains);
|
|
88
|
+
}, true);
|
|
89
|
+
|
|
90
|
+
export default createComponentClass(/** @lends platypus.components.NodeMap.prototype */{
|
|
91
|
+
id: 'NodeMap',
|
|
92
|
+
|
|
93
|
+
publicProperties: {
|
|
94
|
+
/**
|
|
95
|
+
* An array of node definitions to create the NodeMap. A node definition can take the following form:
|
|
96
|
+
*
|
|
97
|
+
* {
|
|
98
|
+
* "NodeId": "Node1",
|
|
99
|
+
* // A string or array that becomes the id of the Node. Arrays are joined using "|" to create the id string.
|
|
100
|
+
* "type": "path",
|
|
101
|
+
* // A string that determines the type of the node.
|
|
102
|
+
* "x": 0,
|
|
103
|
+
* // Sets the x axis position of the node.
|
|
104
|
+
* "y": 0,
|
|
105
|
+
* // Sets the y axis position of the node.
|
|
106
|
+
* "z": 0,
|
|
107
|
+
* // Sets the z axis position of the node.
|
|
108
|
+
* "neighbors": {
|
|
109
|
+
* // A list of key/value pairs where the keys are directions from the node and values are node ids.
|
|
110
|
+
* "west": "node0",
|
|
111
|
+
* "east": "node2"
|
|
112
|
+
* }
|
|
113
|
+
* }
|
|
114
|
+
*
|
|
115
|
+
* @property map
|
|
116
|
+
* @type Array
|
|
117
|
+
* @default []
|
|
118
|
+
*/
|
|
119
|
+
map: []
|
|
120
|
+
},
|
|
121
|
+
|
|
122
|
+
/**
|
|
123
|
+
* This component sets up a NodeMap to be used by the [NodeResident](platypus.components.NodeResident.html) component on this entity's child entities.
|
|
124
|
+
*
|
|
125
|
+
* @memberof platypus.components
|
|
126
|
+
* @uses platypus.Component
|
|
127
|
+
* @constructs
|
|
128
|
+
* @listens platypus.Entity#add-node
|
|
129
|
+
* @listens platypus.Entity#child-entity-added
|
|
130
|
+
* @fires platypus.Entity#add-node
|
|
131
|
+
*/
|
|
132
|
+
initialize: function () {
|
|
133
|
+
const
|
|
134
|
+
map = this.map;
|
|
135
|
+
|
|
136
|
+
this.map = arrayCache.setUp(); // Original map is node definitions, so we replace it with actual nodes.
|
|
137
|
+
this.nodes = {};
|
|
138
|
+
this.residentsAwaitingNode = arrayCache.setUp();
|
|
139
|
+
|
|
140
|
+
for (let i = 0; i < map.length; i++) {
|
|
141
|
+
this.addNode(Node.setUp(map[i], this));
|
|
142
|
+
}
|
|
143
|
+
},
|
|
144
|
+
|
|
145
|
+
events: {
|
|
146
|
+
"add-node": function (nodeDefinition) {
|
|
147
|
+
let node = null;
|
|
148
|
+
|
|
149
|
+
if (nodeDefinition.isNode) {// if it's already a node, put it on the map.
|
|
150
|
+
node = nodeDefinition;
|
|
151
|
+
nodeDefinition.map = this;
|
|
152
|
+
} else {
|
|
153
|
+
node = Node.setUp(nodeDefinition, this);
|
|
154
|
+
}
|
|
155
|
+
|
|
156
|
+
this.addNode(node);
|
|
157
|
+
|
|
158
|
+
for (let i = this.residentsAwaitingNode.length - 1; i >= 0; i--) {
|
|
159
|
+
const
|
|
160
|
+
entity = this.residentsAwaitingNode[i];
|
|
161
|
+
|
|
162
|
+
if (node.id === entity.nodeId) {
|
|
163
|
+
greenSplice(this.residentsAwaitingNode, i);
|
|
164
|
+
entity.node = this.getNode(entity.nodeId);
|
|
165
|
+
}
|
|
166
|
+
}
|
|
167
|
+
},
|
|
168
|
+
|
|
169
|
+
"child-entity-added": function (entity) {
|
|
170
|
+
if (entity.isNode) { // a node
|
|
171
|
+
/**
|
|
172
|
+
* Expects a node definition to create a node in the NodeMap.
|
|
173
|
+
*
|
|
174
|
+
* @event platypus.Entity#add-node
|
|
175
|
+
* @param definition {Object} Key/value pairs.
|
|
176
|
+
* @param definition.nodeId {String|Array} This value becomes the id of the Node. Arrays are joined using "|" to create the id string.
|
|
177
|
+
* @param definition.type {String} This determines the type of the node.
|
|
178
|
+
* @param definition.x {String} Sets the x axis position of the node.
|
|
179
|
+
* @param definition.y {String} Sets the y axis position of the node.
|
|
180
|
+
* @param definition.z {String} Sets the z axis position of the node.
|
|
181
|
+
* @param definition.neighbors {Object} A list of key/value pairs where the keys are directions from the node and values are node ids. For example: {"west": "node12"}.
|
|
182
|
+
*/
|
|
183
|
+
this.owner.triggerEvent('add-node', entity);
|
|
184
|
+
} else if (entity.nodeId) { // a NodeResident
|
|
185
|
+
entity.node = this.getNode(entity.nodeId);
|
|
186
|
+
if (!entity.node) {
|
|
187
|
+
this.residentsAwaitingNode.push(entity);
|
|
188
|
+
}
|
|
189
|
+
}
|
|
190
|
+
},
|
|
191
|
+
|
|
192
|
+
"child-entity-removed": function (entity) {
|
|
193
|
+
if (entity.isNode) {
|
|
194
|
+
this.owner.triggerEvent('remove-node', entity);
|
|
195
|
+
}
|
|
196
|
+
},
|
|
197
|
+
|
|
198
|
+
"remove-node": function (node) {
|
|
199
|
+
this.removeNode(node);
|
|
200
|
+
}
|
|
201
|
+
},
|
|
202
|
+
|
|
203
|
+
methods: {
|
|
204
|
+
addNode: function (node) {
|
|
205
|
+
this.map.push(node);
|
|
206
|
+
this.nodes[node.id] = node;
|
|
207
|
+
},
|
|
208
|
+
|
|
209
|
+
removeNode: function (node) {
|
|
210
|
+
const
|
|
211
|
+
index = this.map.indexOf(node);
|
|
212
|
+
|
|
213
|
+
if (index >= 0) {
|
|
214
|
+
this.map.splice(index, 1);
|
|
215
|
+
delete this.nodes[node.id];
|
|
216
|
+
} else {
|
|
217
|
+
platypus.debug.warn(`NodeMap: "${node.id}" is not mapped, so it cannot be removed.`);
|
|
218
|
+
}
|
|
219
|
+
},
|
|
220
|
+
|
|
221
|
+
destroy: function () {
|
|
222
|
+
// Destroy simple node objects.
|
|
223
|
+
for (let i = 0; i < this.map.length; i++) {
|
|
224
|
+
if (!(this.map[i] instanceof Entity)) {
|
|
225
|
+
this.map[i].recycle();
|
|
226
|
+
}
|
|
227
|
+
}
|
|
228
|
+
|
|
229
|
+
arrayCache.recycle(this.map);
|
|
230
|
+
arrayCache.recycle(this.residentsAwaitingNode);
|
|
231
|
+
}
|
|
232
|
+
},
|
|
233
|
+
|
|
234
|
+
publicMethods: {
|
|
235
|
+
/**
|
|
236
|
+
* Gets a node by node id.
|
|
237
|
+
*
|
|
238
|
+
* @method platypus.components.NodeMap#getNode
|
|
239
|
+
* @param id {String|Array|Node} This id of the node to retrieve. If an array or more than one parameter is supplied, values are concatenated with "|" to create a single string id. Supplying a node returns the same node (useful for processing a mixed list of nodes and node ids).
|
|
240
|
+
*/
|
|
241
|
+
getNode: function (...args) {
|
|
242
|
+
let id = args.join('|');
|
|
243
|
+
|
|
244
|
+
if (args.length === 1) {
|
|
245
|
+
if (args[0].isNode) {
|
|
246
|
+
if (args[0].destroyed) {
|
|
247
|
+
return this.nodes[args[0].id];
|
|
248
|
+
} else {
|
|
249
|
+
return args[0];
|
|
250
|
+
}
|
|
251
|
+
} else if (Array.isArray(args[0])) {
|
|
252
|
+
id = args[0].join('|');
|
|
253
|
+
}
|
|
254
|
+
}
|
|
255
|
+
|
|
256
|
+
return this.nodes[id] ?? null;
|
|
257
|
+
},
|
|
258
|
+
|
|
259
|
+
/**
|
|
260
|
+
* Finds the closest node to a given point, with respect to any inclusion or exclusion lists.
|
|
261
|
+
*
|
|
262
|
+
* @method platypus.components.NodeMap#getClosestNode
|
|
263
|
+
* @param point {platypus.Vector} A location for which a closest node is being found.
|
|
264
|
+
* @param [including] {Array} A list of nodes to include in the search. If not set, the entire map is searched.
|
|
265
|
+
* @param [excluding] {Array} A list of nodes to exclude from the search.
|
|
266
|
+
*/
|
|
267
|
+
getClosestNode: function (point, including, excluding) {
|
|
268
|
+
const
|
|
269
|
+
p1 = Vector.setUp(point),
|
|
270
|
+
p2 = Vector.setUp(),
|
|
271
|
+
list = including || this.map;
|
|
272
|
+
let closest = null,
|
|
273
|
+
d = Infinity;
|
|
274
|
+
|
|
275
|
+
for (let i = 0; i < list.length; i++) {
|
|
276
|
+
const
|
|
277
|
+
m = p2.setVector(p1).subtractVector(list[i].position).magnitude();
|
|
278
|
+
|
|
279
|
+
if (m < d) {
|
|
280
|
+
if (excluding?.indexOf(list[i]) >= 0) {
|
|
281
|
+
break;
|
|
282
|
+
}
|
|
283
|
+
|
|
284
|
+
d = m;
|
|
285
|
+
closest = list[i];
|
|
286
|
+
}
|
|
287
|
+
}
|
|
288
|
+
|
|
289
|
+
p1.recycle();
|
|
290
|
+
p2.recycle();
|
|
291
|
+
|
|
292
|
+
return closest;
|
|
293
|
+
}
|
|
294
|
+
}
|
|
295
|
+
});
|