emeraldengine 3.0.0 → 3.1.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 (103) hide show
  1. package/README.md +1498 -1659
  2. package/dist/types/index.d.ts +4 -1
  3. package/dist/types/src/Animator.d.ts +1 -1
  4. package/dist/types/src/CollisionLayers.d.ts +2 -2
  5. package/dist/types/src/Color.d.ts +1 -0
  6. package/dist/types/src/Drawable.d.ts +1 -1
  7. package/dist/types/src/EmeraldDB.d.ts +2 -2
  8. package/dist/types/src/InstancedTexture.d.ts +17 -2
  9. package/dist/types/src/Material.d.ts +2 -2
  10. package/dist/types/src/MathUtils.d.ts +2 -1
  11. package/dist/types/src/ParticleEmitter.d.ts +1 -1
  12. package/dist/types/src/Physics.d.ts +148 -18
  13. package/dist/types/src/Scene.d.ts +1 -1
  14. package/dist/types/src/Shaders.d.ts +2 -2
  15. package/dist/types/src/Tilemap.d.ts +1 -1
  16. package/dist/types/src/UI.d.ts +1 -1
  17. package/dist/types/src/components/Behaviour.d.ts +2 -2
  18. package/dist/types/src/components/Collider.d.ts +7 -1
  19. package/dist/types/src/components/GameObject.d.ts +2 -2
  20. package/dist/types/src/components/PolygonCollider.d.ts +33 -0
  21. package/dist/types/src/components/RigidBody.d.ts +281 -8
  22. package/dist/types/src/importers/Aseprite.d.ts +2 -2
  23. package/dist/types/src/importers/ForgeLevel.d.ts +97 -0
  24. package/dist/types/src/importers/TiledMap.d.ts +1 -1
  25. package/dist/types/src/managers/EventManager.d.ts +1 -1
  26. package/dist/types/src/managers/Gamepad.d.ts +102 -0
  27. package/dist/types/src/managers/InputManager.d.ts +93 -2
  28. package/dist/types/src/managers/NetworkManager.d.ts +2 -2
  29. package/dist/types/src/managers/RenderStats.d.ts +1 -1
  30. package/dist/types/src/managers/TextureManager.d.ts +1 -1
  31. package/dist/types/src/physics/AABB.d.ts +92 -0
  32. package/dist/types/src/physics/Body.d.ts +435 -0
  33. package/dist/types/src/physics/BodyType.d.ts +6 -0
  34. package/dist/types/src/physics/BroadPhase.d.ts +210 -0
  35. package/dist/types/src/physics/Collision.d.ts +102 -0
  36. package/dist/types/src/physics/Contact.d.ts +206 -0
  37. package/dist/types/src/physics/ContactSolver.d.ts +108 -0
  38. package/dist/types/src/physics/Distance.d.ts +54 -0
  39. package/dist/types/src/physics/DistanceJoint.d.ts +90 -0
  40. package/dist/types/src/physics/Fixture.d.ts +221 -0
  41. package/dist/types/src/physics/Island.d.ts +52 -0
  42. package/dist/types/src/physics/Joint.d.ts +59 -0
  43. package/dist/types/src/physics/Math2D.d.ts +371 -0
  44. package/dist/types/src/physics/RevoluteJoint.d.ts +119 -0
  45. package/dist/types/src/physics/Settings.d.ts +22 -0
  46. package/dist/types/src/physics/Shapes.d.ts +207 -0
  47. package/dist/types/src/physics/TimeOfImpact.d.ts +22 -0
  48. package/dist/types/src/physics/World.d.ts +274 -0
  49. package/dist/types/src/physics/index.d.ts +34 -0
  50. package/index.js +6 -0
  51. package/package.json +2 -3
  52. package/src/Animator.js +1 -1
  53. package/src/CollisionLayers.js +3 -3
  54. package/src/Color.js +8 -0
  55. package/src/Drawable.js +1 -1
  56. package/src/Emerald.js +1 -1
  57. package/src/EmeraldDB.js +2 -2
  58. package/src/InstancedTexture.js +57 -9
  59. package/src/Material.js +2 -2
  60. package/src/MathUtils.js +2 -1
  61. package/src/ParticleEmitter.js +1 -1
  62. package/src/Physics.js +270 -60
  63. package/src/Scene.js +1 -1
  64. package/src/Shaders.js +20 -20
  65. package/src/Tilemap.js +1 -1
  66. package/src/UI.js +1 -1
  67. package/src/components/Behaviour.js +2 -2
  68. package/src/components/BoxCollider.js +7 -9
  69. package/src/components/BoxColliderDebug.js +3 -4
  70. package/src/components/CircleCollider.js +7 -9
  71. package/src/components/CircleColliderDebug.js +3 -2
  72. package/src/components/Collider.js +13 -3
  73. package/src/components/GameObject.js +2 -2
  74. package/src/components/PolygonCollider.js +55 -0
  75. package/src/components/RigidBody.js +441 -14
  76. package/src/importers/Aseprite.js +2 -2
  77. package/src/importers/ForgeLevel.js +581 -0
  78. package/src/importers/TiledMap.js +1 -1
  79. package/src/managers/EventManager.js +1 -1
  80. package/src/managers/Gamepad.js +126 -0
  81. package/src/managers/InputManager.js +129 -3
  82. package/src/managers/NetworkManager.js +2 -2
  83. package/src/managers/RenderStats.js +1 -1
  84. package/src/managers/TextureManager.js +1 -1
  85. package/src/physics/AABB.js +207 -0
  86. package/src/physics/Body.js +862 -0
  87. package/src/physics/BodyType.js +16 -0
  88. package/src/physics/BroadPhase.js +641 -0
  89. package/src/physics/Collision.js +534 -0
  90. package/src/physics/Contact.js +500 -0
  91. package/src/physics/ContactSolver.js +526 -0
  92. package/src/physics/Distance.js +403 -0
  93. package/src/physics/DistanceJoint.js +227 -0
  94. package/src/physics/Fixture.js +346 -0
  95. package/src/physics/Island.js +203 -0
  96. package/src/physics/Joint.js +78 -0
  97. package/src/physics/Math2D.js +573 -0
  98. package/src/physics/RevoluteJoint.js +278 -0
  99. package/src/physics/Settings.js +78 -0
  100. package/src/physics/Shapes.js +549 -0
  101. package/src/physics/TimeOfImpact.js +87 -0
  102. package/src/physics/World.js +731 -0
  103. package/src/physics/index.js +79 -0
@@ -0,0 +1,6 @@
1
+ export type BodyType = BodyType;
2
+ export namespace BodyType {
3
+ let STATIC: string;
4
+ let KINEMATIC: string;
5
+ let DYNAMIC: string;
6
+ }
@@ -0,0 +1,210 @@
1
+ /**
2
+ * @class BroadPhase
3
+ * @description Keeps the AABB tree and the list of proxies that moved since the
4
+ * last step, and turns those into the candidate pairs the narrowphase looks at.
5
+ */
6
+ export class BroadPhase {
7
+ /** @private */
8
+ private tree;
9
+ /** @private */
10
+ private moveBuffer;
11
+ /** @private */
12
+ private proxyCount;
13
+ /**
14
+ * @method createProxy
15
+ * @description Adds a fixture proxy and queues it for pairing.
16
+ * @param {AABB} aabb
17
+ * @param {Object} userData
18
+ * @returns {number} - Proxy id
19
+ */
20
+ createProxy(aabb: AABB, userData: any): number;
21
+ /**
22
+ * @method destroyProxy
23
+ * @description Removes a fixture proxy.
24
+ * @param {number} id
25
+ */
26
+ destroyProxy(id: number): void;
27
+ /**
28
+ * @method moveProxy
29
+ * @description Updates a proxy's box, queueing it for re-pairing if the tree
30
+ * actually had to move it.
31
+ * @param {number} id
32
+ * @param {AABB} aabb
33
+ * @param {Object} displacement
34
+ */
35
+ moveProxy(id: number, aabb: AABB, displacement: any): void;
36
+ /**
37
+ * @method touchProxy
38
+ * @description Forces a proxy to be re-paired next update even though it
39
+ * didn't move (used when a fixture's filter changes).
40
+ * @param {number} id
41
+ */
42
+ touchProxy(id: number): void;
43
+ /** @private */
44
+ private bufferMove;
45
+ /** @private */
46
+ private unbufferMove;
47
+ /**
48
+ * @method getFatAABB
49
+ * @description Returns a proxy's fattened AABB.
50
+ * @param {number} id
51
+ * @returns {AABB}
52
+ */
53
+ getFatAABB(id: number): AABB;
54
+ /**
55
+ * @method getUserData
56
+ * @description Returns a proxy's payload.
57
+ * @param {number} id
58
+ * @returns {Object}
59
+ */
60
+ getUserData(id: number): any;
61
+ /**
62
+ * @method testOverlap
63
+ * @description True when two proxies' fat AABBs overlap.
64
+ * @param {number} idA
65
+ * @param {number} idB
66
+ * @returns {boolean}
67
+ */
68
+ testOverlap(idA: number, idB: number): boolean;
69
+ /**
70
+ * @method query
71
+ * @description Forwards an AABB query to the tree.
72
+ * @param {AABB} aabb
73
+ * @param {Function} callback
74
+ */
75
+ query(aabb: AABB, callback: Function): void;
76
+ /**
77
+ * @method rayCast
78
+ * @description Forwards a ray cast to the tree.
79
+ * @param {Object} input
80
+ * @param {Function} callback
81
+ */
82
+ rayCast(input: any, callback: Function): void;
83
+ /**
84
+ * @method updatePairs
85
+ * @description Emits `callback(userDataA, userDataB)` once for every new
86
+ * overlapping pair among the proxies that moved. Pairs are de-duplicated, so
87
+ * two proxies moving towards each other still report once.
88
+ * @param {Function} callback
89
+ */
90
+ updatePairs(callback: Function): void;
91
+ }
92
+ /**
93
+ * @class DynamicTree
94
+ * @description A balanced tree of axis-aligned boxes over every fixture in the
95
+ * world. Leaves are stored with a "fat" AABB so a body can jiggle a little
96
+ * without forcing a re-insert, and the tree is rebalanced with rotations on the
97
+ * way back up after each change. Every broadphase query, world raycast and
98
+ * continuous-collision sweep goes through it.
99
+ */
100
+ export class DynamicTree {
101
+ /** @private */
102
+ private root;
103
+ /** @private */
104
+ private nodes;
105
+ /** @private */
106
+ private freeList;
107
+ /** @private */
108
+ private nodeCount;
109
+ /**
110
+ * @method allocateNode
111
+ * @description Takes a node from the free list, growing the pool if needed.
112
+ * @returns {number} - The node id
113
+ * @private
114
+ */
115
+ private allocateNode;
116
+ /**
117
+ * @method freeNode
118
+ * @description Returns a node to the free list.
119
+ * @param {number} id
120
+ * @private
121
+ */
122
+ private freeNode;
123
+ /**
124
+ * @method createProxy
125
+ * @description Adds a fixture proxy to the tree.
126
+ * @param {AABB} aabb - The tight world AABB
127
+ * @param {Object} userData - The FixtureProxy this leaf stands for
128
+ * @returns {number} - The proxy id
129
+ */
130
+ createProxy(aabb: AABB, userData: any): number;
131
+ /**
132
+ * @method destroyProxy
133
+ * @description Removes a proxy from the tree.
134
+ * @param {number} id
135
+ */
136
+ destroyProxy(id: number): void;
137
+ /**
138
+ * @method moveProxy
139
+ * @description Re-fits a proxy whose fixture moved. Returns false (and does
140
+ * nothing) while the new box still fits inside the fat one.
141
+ * @param {number} id
142
+ * @param {AABB} aabb - The new tight AABB
143
+ * @param {Object} displacement - How far the body moved this step
144
+ * @returns {boolean} - Whether the proxy was actually re-inserted
145
+ */
146
+ moveProxy(id: number, aabb: AABB, displacement: any): boolean;
147
+ /**
148
+ * @method getFatAABB
149
+ * @description Returns the stored (fattened) AABB of a proxy.
150
+ * @param {number} id
151
+ * @returns {AABB}
152
+ */
153
+ getFatAABB(id: number): AABB;
154
+ /**
155
+ * @method getUserData
156
+ * @description Returns the proxy payload of a leaf.
157
+ * @param {number} id
158
+ * @returns {Object}
159
+ */
160
+ getUserData(id: number): any;
161
+ /**
162
+ * @method insertLeaf
163
+ * @description Inserts a leaf, choosing the sibling that grows the tree's
164
+ * total surface area least, then rebalancing on the way back to the root.
165
+ * @param {number} leaf
166
+ * @private
167
+ */
168
+ private insertLeaf;
169
+ /**
170
+ * @method removeLeaf
171
+ * @description Unlinks a leaf and collapses its now-single-child parent.
172
+ * @param {number} leaf
173
+ * @private
174
+ */
175
+ private removeLeaf;
176
+ /**
177
+ * @method balance
178
+ * @description One AVL-style rotation at `iA` if its subtrees differ in
179
+ * height by more than one. Keeps queries logarithmic.
180
+ * @param {number} iA
181
+ * @returns {number} - The new root of that subtree
182
+ * @private
183
+ */
184
+ private balance;
185
+ /**
186
+ * @method query
187
+ * @description Calls `callback(proxyId)` for every leaf whose fat AABB
188
+ * overlaps `aabb`. Returning false from the callback stops the query.
189
+ * @param {AABB} aabb
190
+ * @param {Function} callback
191
+ */
192
+ query(aabb: AABB, callback: Function): void;
193
+ /**
194
+ * @method rayCast
195
+ * @description Walks the tree along a ray, calling
196
+ * `callback(subInput, proxyId)`. The callback returns the new max fraction
197
+ * (0 terminates the cast), which lets the traversal shrink as it finds hits.
198
+ * @param {Object} input - `{ p1, p2, maxFraction }`
199
+ * @param {Function} callback
200
+ */
201
+ rayCast(input: any, callback: Function): void;
202
+ /**
203
+ * @method getHeight
204
+ * @description Height of the tree (0 when empty), useful when profiling.
205
+ * @returns {number}
206
+ */
207
+ getHeight(): number;
208
+ }
209
+ export const NULL_NODE: -1;
210
+ import AABB from "./AABB.js";
@@ -0,0 +1,102 @@
1
+ /**
2
+ * @class Manifold
3
+ * @description Up to two contact points plus the frame they are expressed in.
4
+ * Two points is all a 2D convex-convex overlap can produce, and it is exactly
5
+ * what a stable resting contact (a box on the ground) needs.
6
+ */
7
+ export class Manifold {
8
+ type: number;
9
+ localNormal: Vec2;
10
+ localPoint: Vec2;
11
+ points: ManifoldPoint[];
12
+ pointCount: number;
13
+ /**
14
+ * @method reset
15
+ * @description Empties the manifold.
16
+ */
17
+ reset(): void;
18
+ }
19
+ /**
20
+ * @class ManifoldPoint
21
+ * @description A single contact point, stored in the reference body's local
22
+ * frame so it stays valid as the bodies move within a step.
23
+ */
24
+ export class ManifoldPoint {
25
+ localPoint: Vec2;
26
+ normalImpulse: number;
27
+ tangentImpulse: number;
28
+ id: number;
29
+ }
30
+ export type ManifoldType = ManifoldType;
31
+ export namespace ManifoldType {
32
+ let CIRCLES: number;
33
+ let FACE_A: number;
34
+ let FACE_B: number;
35
+ }
36
+ /**
37
+ * @class WorldManifold
38
+ * @description A manifold converted into world space: the collision normal
39
+ * (always pointing from body A to body B), the contact points, and how deeply
40
+ * each one is penetrating (negative means overlapping).
41
+ */
42
+ export class WorldManifold {
43
+ normal: Vec2;
44
+ points: Vec2[];
45
+ separations: number[];
46
+ pointCount: number;
47
+ /**
48
+ * @method initialize
49
+ * @description Fills this world manifold from a local manifold.
50
+ * @param {Manifold} manifold
51
+ * @param {Transform2} xfA
52
+ * @param {number} radiusA
53
+ * @param {Transform2} xfB
54
+ * @param {number} radiusB
55
+ * @returns {WorldManifold} - this
56
+ */
57
+ initialize(manifold: Manifold, xfA: Transform2, radiusA: number, xfB: Transform2, radiusB: number): WorldManifold;
58
+ }
59
+ /**
60
+ * @function collideCircles
61
+ * @description Builds the manifold for two circles.
62
+ * @param {Manifold} manifold - Output manifold
63
+ * @param {CircleShape} circleA
64
+ * @param {Transform2} xfA
65
+ * @param {CircleShape} circleB
66
+ * @param {Transform2} xfB
67
+ */
68
+ export function collideCircles(manifold: Manifold, circleA: CircleShape, xfA: Transform2, circleB: CircleShape, xfB: Transform2): void;
69
+ /**
70
+ * @function collidePolygonAndCircle
71
+ * @description Builds the manifold for a polygon against a circle. The circle
72
+ * is pushed into the polygon's frame, then tested against the closest face,
73
+ * falling back to the nearest corner when it sits past the face's edge.
74
+ * @param {Manifold} manifold - Output manifold
75
+ * @param {PolygonShape} polygonA
76
+ * @param {Transform2} xfA
77
+ * @param {CircleShape} circleB
78
+ * @param {Transform2} xfB
79
+ */
80
+ export function collidePolygonAndCircle(manifold: Manifold, polygonA: PolygonShape, xfA: Transform2, circleB: CircleShape, xfB: Transform2): void;
81
+ /**
82
+ * @function collidePolygons
83
+ * @description Builds the manifold for two convex polygons using the
84
+ * separating-axis test to pick a reference face, then clipping the opposing
85
+ * (incident) edge against it. The result is the one- or two-point contact patch
86
+ * that makes boxes rest flat instead of rocking.
87
+ * @param {Manifold} manifold - Output manifold
88
+ * @param {PolygonShape} polyA
89
+ * @param {Transform2} xfA
90
+ * @param {PolygonShape} polyB
91
+ * @param {Transform2} xfB
92
+ */
93
+ export function collidePolygons(manifold: Manifold, polyA: PolygonShape, xfA: Transform2, polyB: PolygonShape, xfB: Transform2): void;
94
+ /**
95
+ * @function mulTXf
96
+ * @description Composes transforms: returns the transform of `B` expressed in
97
+ * `A`'s frame.
98
+ * @private
99
+ */
100
+ export function mulTXf(A: any, B: any): Transform2;
101
+ import { Vec2 } from "./Math2D.js";
102
+ import { Transform2 } from "./Math2D.js";
@@ -0,0 +1,206 @@
1
+ /**
2
+ * @class Contact
3
+ * @description A potential or actual touch between two fixtures. The broadphase
4
+ * creates one as soon as two AABBs overlap; `touching` only becomes true once
5
+ * the narrowphase finds real contact points. Contacts persist across steps,
6
+ * which is what lets the solver warm-start from last frame's impulses.
7
+ */
8
+ export class Contact {
9
+ /**
10
+ * @method create
11
+ * @description Builds a contact for a fixture pair, normalizing the order so
12
+ * mixed polygon/circle pairs always arrive as (polygon, circle): the one
13
+ * ordering the narrowphase implements.
14
+ * @param {Fixture} fixtureA
15
+ * @param {Fixture} fixtureB
16
+ * @returns {Contact}
17
+ */
18
+ static create(fixtureA: Fixture, fixtureB: Fixture): Contact;
19
+ constructor(fixtureA: any, fixtureB: any);
20
+ fixtureA: any;
21
+ fixtureB: any;
22
+ manifold: Manifold;
23
+ friction: number;
24
+ restitution: any;
25
+ tangentSpeed: number;
26
+ /** @private */
27
+ private touching;
28
+ /** @private */
29
+ private enabled;
30
+ /** @private */
31
+ private filterFlag;
32
+ /** @private */
33
+ private islandFlag;
34
+ /** @private */
35
+ private toiFlag;
36
+ /** @private */
37
+ private toi;
38
+ /** @private */
39
+ private _index;
40
+ /**
41
+ * @method getManifold
42
+ * @description Returns the local-space manifold.
43
+ * @returns {Manifold}
44
+ */
45
+ getManifold(): Manifold;
46
+ /**
47
+ * @method getWorldManifold
48
+ * @description Returns the contact in world space: the normal (pointing from
49
+ * fixture A's body towards fixture B's), the contact points, and the
50
+ * separation at each point.
51
+ * @param {WorldManifold} [worldManifold] - Optional object to fill
52
+ * @returns {WorldManifold}
53
+ */
54
+ getWorldManifold(worldManifold?: WorldManifold): WorldManifold;
55
+ /**
56
+ * @method isTouching
57
+ * @description Whether the fixtures are actually in contact this step.
58
+ * @returns {boolean}
59
+ */
60
+ isTouching(): boolean;
61
+ /**
62
+ * @method setEnabled
63
+ * @description Enables or disables the collision response for this contact.
64
+ * Disabling only lasts for the current step (useful from a pre-solve
65
+ * callback to build one-way platforms).
66
+ * @param {boolean} value
67
+ */
68
+ setEnabled(value: boolean): void;
69
+ /**
70
+ * @method isEnabled
71
+ * @description Whether the collision response is enabled.
72
+ * @returns {boolean}
73
+ */
74
+ isEnabled(): boolean;
75
+ /**
76
+ * @method getFixtureA
77
+ * @description Returns the first fixture.
78
+ * @returns {Fixture}
79
+ */
80
+ getFixtureA(): Fixture;
81
+ /**
82
+ * @method getFixtureB
83
+ * @description Returns the second fixture.
84
+ * @returns {Fixture}
85
+ */
86
+ getFixtureB(): Fixture;
87
+ /**
88
+ * @method getFriction
89
+ * @description Returns the mixed friction used by the solver.
90
+ * @returns {number}
91
+ */
92
+ getFriction(): number;
93
+ /**
94
+ * @method setFriction
95
+ * @description Overrides the mixed friction for this contact.
96
+ * @param {number} friction
97
+ */
98
+ setFriction(friction: number): void;
99
+ /**
100
+ * @method resetFriction
101
+ * @description Restores the friction mixed from the two fixtures.
102
+ */
103
+ resetFriction(): void;
104
+ /**
105
+ * @method getRestitution
106
+ * @description Returns the mixed restitution used by the solver.
107
+ * @returns {number}
108
+ */
109
+ getRestitution(): number;
110
+ /**
111
+ * @method setRestitution
112
+ * @description Overrides the mixed restitution for this contact.
113
+ * @param {number} restitution
114
+ */
115
+ setRestitution(restitution: number): void;
116
+ /**
117
+ * @method resetRestitution
118
+ * @description Restores the restitution mixed from the two fixtures.
119
+ */
120
+ resetRestitution(): void;
121
+ /**
122
+ * @method flagForFiltering
123
+ * @description Marks the contact so the next step re-checks whether these two
124
+ * fixtures are still allowed to collide.
125
+ */
126
+ flagForFiltering(): void;
127
+ /**
128
+ * @method evaluate
129
+ * @description Runs the narrowphase for this fixture pair into `manifold`.
130
+ * @param {Manifold} manifold
131
+ * @param {Transform2} xfA
132
+ * @param {Transform2} xfB
133
+ * @private
134
+ */
135
+ private evaluate;
136
+ /**
137
+ * @method update
138
+ * @description Re-runs the narrowphase, carries last step's impulses over to
139
+ * matching contact points (warm starting), and fires begin/end contact
140
+ * events on the world when the touching state flips.
141
+ * @param {World} world - The owning world, used to dispatch events
142
+ */
143
+ update(world: World): void;
144
+ }
145
+ /**
146
+ * @class ContactManager
147
+ * @description Owns the world's contact list: creates contacts from broadphase
148
+ * pairs, drops them once the AABBs stop overlapping, and refreshes the ones
149
+ * that remain each step.
150
+ */
151
+ export class ContactManager {
152
+ constructor(world: any);
153
+ world: any;
154
+ contacts: any[];
155
+ /**
156
+ * @method addPair
157
+ * @description Creates a contact for a new broadphase pair, unless the two
158
+ * fixtures share a body, already have a contact, or the filter rejects them.
159
+ * @param {FixtureProxy} proxyA
160
+ * @param {FixtureProxy} proxyB
161
+ */
162
+ addPair(proxyA: FixtureProxy, proxyB: FixtureProxy): void;
163
+ /**
164
+ * @method findNewContacts
165
+ * @description Turns this step's broadphase movement into new contacts.
166
+ */
167
+ findNewContacts(): void;
168
+ /**
169
+ * @method destroy
170
+ * @description Removes a contact, firing end-contact if it was touching.
171
+ * @param {Contact} contact
172
+ */
173
+ destroy(contact: Contact): void;
174
+ /**
175
+ * @method collide
176
+ * @description Refreshes every contact: drops the ones whose AABBs no longer
177
+ * overlap or whose filters changed, and re-runs the narrowphase on the rest.
178
+ */
179
+ collide(): void;
180
+ }
181
+ /**
182
+ * @function shouldCollide
183
+ * @description Applies the collision filter to a fixture pair. A positive
184
+ * shared group index always collides, a negative one never does; otherwise each
185
+ * fixture's category must appear in the other's mask.
186
+ * @param {Fixture} fixtureA
187
+ * @param {Fixture} fixtureB
188
+ * @returns {boolean}
189
+ */
190
+ export function shouldCollide(fixtureA: Fixture, fixtureB: Fixture): boolean;
191
+ /**
192
+ * @function mixFriction
193
+ * @description Combines two friction coefficients (geometric mean), so a slick
194
+ * body sliding on a rough one lands somewhere in between.
195
+ * @private
196
+ */
197
+ export function mixFriction(a: any, b: any): number;
198
+ /**
199
+ * @function mixRestitution
200
+ * @description Combines two restitutions: the bouncier surface wins, which is
201
+ * what players expect from a trampoline on concrete.
202
+ * @private
203
+ */
204
+ export function mixRestitution(a: any, b: any): any;
205
+ import { Manifold } from "./Collision.js";
206
+ import { WorldManifold } from "./Collision.js";
@@ -0,0 +1,108 @@
1
+ export default ContactSolver;
2
+ /**
3
+ * @class ContactSolver
4
+ * @description Resolves every contact in an island with sequential impulses:
5
+ * for each contact point it works out the impulse that removes the approaching
6
+ * velocity (plus any bounce), applies it, and repeats over all points for a
7
+ * fixed number of iterations. Impulses are accumulated and clamped so they can
8
+ * only ever push, never pull, and they carry over between steps (warm starting)
9
+ * so stacks settle instead of sinking.
10
+ *
11
+ * Position error left over after the velocity pass is fixed separately, by
12
+ * nudging the bodies apart without injecting energy.
13
+ *
14
+ * @param {Object} def - `{ contacts, positions, velocities, dt, velocityThreshold }`
15
+ */
16
+ declare class ContactSolver {
17
+ constructor(def: any);
18
+ positions: any;
19
+ velocities: any;
20
+ contacts: any;
21
+ dt: any;
22
+ velocityThreshold: any;
23
+ velocityConstraints: {
24
+ friction: any;
25
+ restitution: any;
26
+ tangentSpeed: any;
27
+ indexA: any;
28
+ indexB: any;
29
+ invMassA: any;
30
+ invMassB: any;
31
+ invIA: any;
32
+ invIB: any;
33
+ contactIndex: number;
34
+ pointCount: any;
35
+ normal: Vec2;
36
+ tangent: Vec2;
37
+ K: {
38
+ k11: number;
39
+ k12: number;
40
+ k22: number;
41
+ };
42
+ normalMass: {
43
+ k11: number;
44
+ k12: number;
45
+ k22: number;
46
+ };
47
+ points: any[];
48
+ }[];
49
+ positionConstraints: {
50
+ indexA: any;
51
+ indexB: any;
52
+ invMassA: any;
53
+ invMassB: any;
54
+ invIA: any;
55
+ invIB: any;
56
+ localCenterA: any;
57
+ localCenterB: any;
58
+ radiusA: any;
59
+ radiusB: any;
60
+ type: any;
61
+ localNormal: any;
62
+ localPoint: any;
63
+ localPoints: any[];
64
+ pointCount: any;
65
+ }[];
66
+ /**
67
+ * @method initializeVelocityConstraints
68
+ * @description Computes the effective mass at every contact point and the
69
+ * bounce target, from the state at the start of the step.
70
+ */
71
+ initializeVelocityConstraints(): void;
72
+ /**
73
+ * @method warmStart
74
+ * @description Re-applies last step's impulses before solving, which gets the
75
+ * solver most of the way to the answer immediately.
76
+ */
77
+ warmStart(): void;
78
+ /**
79
+ * @method solveVelocityConstraints
80
+ * @description One relaxation pass over every contact point: friction first,
81
+ * then the normal impulses that stop the bodies interpenetrating.
82
+ */
83
+ solveVelocityConstraints(): void;
84
+ /**
85
+ * @method _solveBlock
86
+ * @description Two-point block solve. Solving both points of a manifold
87
+ * together (rather than one after the other) is what keeps a box resting on
88
+ * the ground from rocking between its corners. Four candidate solutions are
89
+ * tried in turn: both points pushing, either one alone, or neither.
90
+ * @private
91
+ */
92
+ private _solveBlock;
93
+ /**
94
+ * @method storeImpulses
95
+ * @description Writes the accumulated impulses back onto the manifold so the
96
+ * next step can warm-start from them.
97
+ */
98
+ storeImpulses(): void;
99
+ /**
100
+ * @method solvePositionConstraints
101
+ * @description Pushes overlapping bodies apart geometrically. This runs on
102
+ * positions only, no velocity is added, so separating a deep overlap can't
103
+ * fling bodies across the level.
104
+ * @returns {boolean} - True once every overlap is within tolerance
105
+ */
106
+ solvePositionConstraints(): boolean;
107
+ }
108
+ import { Vec2 } from "./Math2D.js";
@@ -0,0 +1,54 @@
1
+ /**
2
+ * @class DistanceProxy
3
+ * @description A convex shape reduced to what GJK needs: a point cloud plus a
4
+ * skin radius. Circles collapse to a single point with a large radius; polygons
5
+ * keep their corners and carry the small polygon skin.
6
+ */
7
+ export class DistanceProxy {
8
+ vertices: any[];
9
+ radius: number;
10
+ /**
11
+ * @method set
12
+ * @description Fills this proxy from a shape.
13
+ * @param {Shape} shape - A CircleShape or PolygonShape
14
+ * @returns {DistanceProxy} - this
15
+ */
16
+ set(shape: Shape): DistanceProxy;
17
+ /**
18
+ * @method getSupport
19
+ * @description Index of the vertex furthest along a direction.
20
+ * @param {Object} d - Direction in the proxy's local frame
21
+ * @returns {number}
22
+ */
23
+ getSupport(d: any): number;
24
+ /**
25
+ * @method getMaxExtent
26
+ * @description Distance from the local origin to the furthest vertex, plus
27
+ * the skin. Continuous collision uses it to bound how fast a rotating body's
28
+ * surface can approach another.
29
+ * @returns {number}
30
+ */
31
+ getMaxExtent(): number;
32
+ }
33
+ /**
34
+ * @function distance
35
+ * @description GJK: computes the distance and the closest points between two
36
+ * convex proxies. This is the primitive continuous collision and overlap tests
37
+ * are built on.
38
+ * @param {Object} output - Written as `{ distance, pointA, pointB, iterations }`
39
+ * @param {Object} input - `{ proxyA, proxyB, transformA, transformB, useRadii }`
40
+ * @returns {Object} - The same output object
41
+ */
42
+ export function distance(output: any, input: any): any;
43
+ /**
44
+ * @function testOverlap
45
+ * @description True when two shapes overlap under their transforms. Sensors use
46
+ * this instead of building a manifold, since they never need contact points.
47
+ * @param {Shape} shapeA
48
+ * @param {Transform2} xfA
49
+ * @param {Shape} shapeB
50
+ * @param {Transform2} xfB
51
+ * @returns {boolean}
52
+ */
53
+ export function testOverlap(shapeA: Shape, xfA: Transform2, shapeB: Shape, xfB: Transform2): boolean;
54
+ import { Transform2 } from "./Math2D.js";