littlejsengine 1.26.0 → 1.27.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.
- package/CHANGELOG.md +28 -0
- package/FAQ.md +3 -2
- package/README.md +4 -3
- package/REFERENCE.md +47 -3
- package/dist/littlejs.d.ts +204 -19
- package/dist/littlejs.esm.js +855 -113
- package/dist/littlejs.esm.min.js +3 -3
- package/dist/littlejs.js +854 -113
- package/dist/littlejs.min.js +2 -2
- package/dist/littlejs.release.js +834 -107
- package/package.json +1 -1
- package/plugins/lightSystem.js +84 -2
- package/plugins/newgrounds.js +92 -0
- package/plugins/parallax.js +3 -1
- package/plugins/postProcess.js +5 -1
- package/plugins/render3d.js +14 -4
- package/plugins/render3dEditor.js +20 -6
- package/plugins/render3dExtras.js +1 -0
- package/plugins/wavedash.js +235 -4
- package/src/engine.js +39 -7
- package/src/engineDraw.js +3 -0
- package/src/engineExport.js +1 -0
- package/src/engineInput.js +7 -6
- package/src/engineObject.js +244 -65
- package/src/engineParticles.js +8 -3
- package/src/engineTileLayer.js +95 -10
- package/src/engineWebGL.js +4 -4
package/CHANGELOG.md
CHANGED
|
@@ -7,6 +7,34 @@ What changed in each release, newest first. Releases before 1.20.0 are on the
|
|
|
7
7
|
|
|
8
8
|
Nothing yet.
|
|
9
9
|
|
|
10
|
+
## 1.27.0 - 2026-10-08
|
|
11
|
+
|
|
12
|
+
### New Changes
|
|
13
|
+
- 2D lights have cones and gels, as 3D spotlights do: `light.coneAngle` makes a light a cone, like a flashlight or a car's headlights, looking along its up and turned by its `angle`, its edge fading by `coneSoftness`; `light.gel` is a picture the light shines through, a tile or a texture across its square that turns with it, so one light can be a car's headlights and tail lights. Shadows still fall through both, and a light with neither draws as before. The Light System short has a swinging searchlight, and Light Shadows a mouse light shining through colored panes
|
|
14
|
+
- One way collision, platforms jumped up through and landed on: `layer.setOneWay(tile, direction)` makes the cells that draw a tile passable moving that way, up, down, left or right, so they block only what was wholly on their far side before it moved; turned and mirrored as each cell's tile is, so a platform turned a quarter is one way to the side. Objects, particles and raycasts all follow it, `collideWithTile` is not asked about a tile passed through, and returning false from it drops through. A solid object's `oneWay` does the same for objects, and a rising platform keeps its rider. The new Platform Physics short shows it with a lift, a crate, a bouncy ball and an ice floor
|
|
15
|
+
- `obj.isBullet` for small fast objects: it moves through the tiles as a point along a ray, so it never passes through a tile at any speed and is not held to objectMaxSpeed for them; `collideWithTile` sees it where it meets the tile, so sparks start on the surface; it bounces by restitution and goes on with the rest of its move, so it rolls along a floor as a box does. One with a size that collides with solid objects is still held to objectMaxSpeed. The platformer's bullets use it in place of their own raycast
|
|
16
|
+
- Cloud saves on Newgrounds and Wavedash, the same on both: `cloudSave(slot, data)` keeps any value JSON can hold for the player, `cloudLoad(slot)` gives it back, null for an empty slot and undefined for a load that failed, so a game does not save over a save it could not load, with `loadFailure(slot)` saying when the slot holds a file that is not a save, and off the platform or not logged in they do nothing; Wavedash stats, `setStat` and `getStat`, and presence, `setPresence(status, details)`; Newgrounds events, `logEvent(name)`. The Newgrounds calls are built from its API docs and not yet tried on the site
|
|
17
|
+
|
|
18
|
+
### Fixes
|
|
19
|
+
- An object of no size is no longer held to objectMaxSpeed by `collideSolidObjects`, since it never collides with solids; one with `collideLevel` and a mass still is
|
|
20
|
+
- A Shader disposed before its first draw was drawn stayed in the engine's list of shaders, the flush compiling it put it back
|
|
21
|
+
- A ParticleEmitter3D callback that changed a particle's `age` or `lifeTime` had the change thrown away, now it is kept as `pos` and `velocity` are
|
|
22
|
+
- A light pass whose `renderLight` or `renderEmissive` throws hands back the screen, its viewport, texture and blend, where a game that caught the error went on drawing into the lightmap
|
|
23
|
+
- A tile layer redraw whose `onRedraw` or tile draw throws hands back the camera, the canvas and the draw target, where it left the game drawing into the layer
|
|
24
|
+
- 3D level editor: a scale drag keeps a mirrored axis mirrored, where it turned every negative axis to the smallest size; a turned object lands, drops and pastes by the box around it as turned; opening the editor lets go of a mouse the game captured; a frame that throws gives the game its camera back; an orthographic game camera's near is not copied to the editor's view; the box select is drawn over a 3D pass drawn after the 2D
|
|
25
|
+
|
|
26
|
+
## 1.26.1 - 2026-10-08
|
|
27
|
+
|
|
28
|
+
### New Changes
|
|
29
|
+
- A 3D Shader may define `void mainNormal(inout vec3 n)`, given the world normal after the normal map, to bend it per pixel for waves, ripples or a flag; the lighting, shadows, specular, Fresnel, environment reflection and fog all use it
|
|
30
|
+
- `postProcess.enabled`: false skips the post process pass, so an effect turns off and on without taking the plugin apart
|
|
31
|
+
- `averageFPS` is public and kept in release builds, where it read 0 unless debug or the watermark was on; it starts at the first frame's rate rather than climbing from 0
|
|
32
|
+
- `camera.align2DZ`: the z of the plane an align2D camera lines up with the 2D view, 0 as before
|
|
33
|
+
- The right click menu is left on links, as it is on text fields
|
|
34
|
+
|
|
35
|
+
### Fixes
|
|
36
|
+
- A tap starts the audio with touch input off too
|
|
37
|
+
|
|
10
38
|
## 1.26.0 - 2026-10-07
|
|
11
39
|
|
|
12
40
|
### New Changes
|
package/FAQ.md
CHANGED
|
@@ -282,7 +282,8 @@ Plugins are self-contained features that live alongside the engine but aren't pa
|
|
|
282
282
|
| `pathFinder.js` | Grid-based A* pathfinding with optional path smoothing |
|
|
283
283
|
| `tweakables.js` | A debug panel to change values live while the game runs, press 9 with the debug overlay open |
|
|
284
284
|
| `medalSystem.js` | Achievement / medal tracking with popup notifications |
|
|
285
|
-
| `newgrounds.js` | Newgrounds.io integration (medals held on the server, scoreboards) |
|
|
285
|
+
| `newgrounds.js` | Newgrounds.io integration (medals held on the server, scoreboards, cloud saves, events) |
|
|
286
|
+
| `wavedash.js` | Wavedash integration (achievements, leaderboards, cloud saves, stats, presence), the same shape as the Newgrounds one |
|
|
286
287
|
| `audioEffects.js` | Web Audio effects like filter, reverb, delay, distortion and compressor, for a group of sounds or everything |
|
|
287
288
|
| `drawUtilities.js` | Higher-level drawing helpers like nine-slice and three-slice |
|
|
288
289
|
| `render3dVoxels.js` | `VoxelMap`, a 3D grid of blocks that draws itself and that objects collide with |
|
|
@@ -826,7 +827,7 @@ medal_firstWin.unlock();
|
|
|
826
827
|
|
|
827
828
|
You can pass an image URL as the fifth argument to `Medal` instead of an emoji icon. The `saveName` you pass to `medalsInit` is used to track which medals have been unlocked in localStorage, so unlocks persist across visits. Give it a name of its own, not the one you pass to `readSaveData` and `writeSaveData`, or the medals and your save data overwrite each other.
|
|
828
829
|
|
|
829
|
-
The plugin also supports [Newgrounds](https://www.newgrounds.com) scoreboards and medals held on the server through [plugins/newgrounds.js](plugins/newgrounds.js): create each medal as a `NewgroundsMedal` with the id Newgrounds gave it, call `medalsInit` as usual, then `new NewgroundsPlugin(app_id, cipher)`. The "LittleJS Medals & Newgrounds" section of REFERENCE.md has a short example.
|
|
830
|
+
The plugin also supports [Newgrounds](https://www.newgrounds.com) scoreboards and medals held on the server through [plugins/newgrounds.js](plugins/newgrounds.js): create each medal as a `NewgroundsMedal` with the id Newgrounds gave it, call `medalsInit` as usual, then `new NewgroundsPlugin(app_id, cipher)`. The "LittleJS Medals & Newgrounds" section of REFERENCE.md has a short example. [plugins/wavedash.js](plugins/wavedash.js) does the same for [Wavedash](https://wavedash.com/) with `WavedashMedal` and `WavedashPlugin`, and both have `cloudSave(slot, data)` and `cloudLoad(slot)` to keep a player's save on the platform.
|
|
830
831
|
|
|
831
832
|
---
|
|
832
833
|
|
package/README.md
CHANGED
|
@@ -39,7 +39,7 @@ The code is very clean and well documented with many examples to get you started
|
|
|
39
39
|
|
|
40
40
|
- Blazing fast WebGL2 + Canvas2D hybrid rendering system
|
|
41
41
|
- Apply [Shadertoy](https://www.shadertoy.com) style shaders for post-processing effects, or on any object or draw
|
|
42
|
-
- 2D lights with soft shadows, tinted glass and emissive objects
|
|
42
|
+
- 2D lights with soft shadows, tinted glass and emissive objects, a sun with long shadows, and spotlight cones and gels
|
|
43
43
|
- Robust particle effect system with a library of ready made effects and an [effect design tool](https://killedbyapixel.github.io/LittleJS/examples/particles/)
|
|
44
44
|
- Parallax background layers that repeat across a level of any size
|
|
45
45
|
- Load sprites and animations into texture sheets at runtime, or import [TexturePacker](https://www.codeandweb.com/texturepacker) and [Aseprite](https://www.aseprite.org) atlases
|
|
@@ -74,7 +74,8 @@ The code is very clean and well documented with many examples to get you started
|
|
|
74
74
|
### 💥 Physics
|
|
75
75
|
|
|
76
76
|
- Robust arcade physics system with collision handling
|
|
77
|
-
- Fast tilemap collision and raycasting
|
|
77
|
+
- Fast tilemap collision and raycasting, with one-way platforms that turn with their tiles
|
|
78
|
+
- Swept bullet collision, so small fast objects never pass through a wall
|
|
78
79
|
- Object collision that stays fast with thousands of objects
|
|
79
80
|
- Full Box2D integration for realistic physics using [Box2D v2.3.1 wasm](https://github.com/kripken/box2d.js)
|
|
80
81
|
- Grid-based A* pathfinding plugin with optional path smoothing
|
|
@@ -96,7 +97,7 @@ The code is very clean and well documented with many examples to get you started
|
|
|
96
97
|
- UI system with buttons, sliders, text input and nine-slice skins
|
|
97
98
|
- Tween system with easing curves, and a scene system for titles, menus and game states
|
|
98
99
|
- Debug overlay and primitive rendering system
|
|
99
|
-
-
|
|
100
|
+
- Medals, leaderboards and cloud saves on [Newgrounds](https://www.newgrounds.com/) and [Wavedash](https://wavedash.com/)
|
|
100
101
|
- Node.js build system
|
|
101
102
|
|
|
102
103
|
### 🤖 AI Friendly
|
package/REFERENCE.md
CHANGED
|
@@ -25,8 +25,9 @@ engineName // Name of the engine: 'LittleJS'
|
|
|
25
25
|
engineVersion // Version of the engine
|
|
26
26
|
frameRate // Fixed frame rate for updates (60)
|
|
27
27
|
frame // Current update frame
|
|
28
|
-
time // Game time since start in seconds (stops when paused)
|
|
28
|
+
time // Game time since start in seconds (stops when paused, falls behind the clock below 20 FPS)
|
|
29
29
|
timeReal // Real time since start in seconds (keeps running when paused; the debug speed keys scale it)
|
|
30
|
+
averageFPS // Frames drawn per second, smoothed
|
|
30
31
|
timeDelta // Seconds the update covers: 1/60, or the display frame's time with engineVariableStep
|
|
31
32
|
timeScale = 1 // Game speed, more or fewer fixed updates per second; with engineVariableStep it scales timeDelta
|
|
32
33
|
paused // Is the game paused? (set with setPaused)
|
|
@@ -325,7 +326,9 @@ toggleFullscreen()
|
|
|
325
326
|
// Shader Object - a custom fragment shader for objects and draws, 2D or 3D
|
|
326
327
|
new Shader(fragmentCode) // fragmentCode defines void mainImage(out vec4 c, vec2 uv) in the post processing
|
|
327
328
|
// style; it gives the surface color, then the object's color and additive color
|
|
328
|
-
// apply in 2D, and the lighting, shadows and fog in 3D
|
|
329
|
+
// apply in 2D, and the lighting, shadows and fog in 3D; in 3D it may also define
|
|
330
|
+
// void mainNormal(inout vec3 n), the world normal after the normal map, to bend
|
|
331
|
+
// it per pixel (waves, ripples) for the lighting, specular and reflection
|
|
329
332
|
obj.shader = shader // any EngineObject or EngineObject3D; draws that share a Shader share a batch
|
|
330
333
|
shader.dispose() // frees its programs and takes it off the engine's list, which keeps every Shader
|
|
331
334
|
// for a lost context; for one made each time a scene starts; drawn again it
|
|
@@ -686,6 +689,12 @@ EngineObject.clampSpeed // Hold each axis of velocity to objectMaxSpeed while
|
|
|
686
689
|
// while it has a mass, so it can not pass through a thin wall; true by default, false for
|
|
687
690
|
// a fast bullet that collides; what does not collide moves as fast as it is told
|
|
688
691
|
EngineObject.parent / children // Set by addChild, a child is placed by its parent and sits out solid collision
|
|
692
|
+
EngineObject.isBullet // Moves through the tiles as a point along a ray, never passing one at any speed and not held
|
|
693
|
+
// to objectMaxSpeed for them; collideWithTile sees it where it meets the tile; on a hit it
|
|
694
|
+
// bounces by restitution and goes on with the rest of its move, so it rolls along a floor;
|
|
695
|
+
// its collision with solid objects is the usual one, so one with a size is still clamped
|
|
696
|
+
EngineObject.oneWay // Up, down, left or right, like vec2(0, 1): a solid passed through that way, a platform
|
|
697
|
+
// jumped up through; it blocks only what was wholly on its far side or stood on it
|
|
689
698
|
|
|
690
699
|
// Engine Object settings
|
|
691
700
|
enablePhysicsSolver = true // Enable collisions, between objects and with tiles, and in 3D with solids and the level?
|
|
@@ -763,6 +772,12 @@ TileCollisionLayer.collisionTest(pos, size=(0,0), object) // Like tileCollisionT
|
|
|
763
772
|
TileCollisionLayer.collisionRaycast(posStart, posEnd, object, normal) // Like tileCollisionRaycast for this layer only
|
|
764
773
|
TileCollisionLayer.isSolid = true // Solid layers block objects and particles, the solidOnly tests
|
|
765
774
|
// skip the others
|
|
775
|
+
TileCollisionLayer.setOneWay(tile, direction=vec2(0,1)) // The cells drawing that tile index are passed through
|
|
776
|
+
// moving that way and block only what was wholly on the far
|
|
777
|
+
// side, objects, particles and rays; turned and mirrored with
|
|
778
|
+
// each cell's art; vec2(0, 1) is a platform jumped up through
|
|
779
|
+
TileCollisionLayer.oneWayTiles // Map of the one way tiles, tile index to direction; delete one
|
|
780
|
+
// to make it solid again
|
|
766
781
|
tileCollisionGetData(pos, solidOnly=true) // Get tile collision data at pos
|
|
767
782
|
tileCollisionTest(pos, size=(0,0), object) // Check if collision should occur
|
|
768
783
|
tileCollisionRaycast(posStart, posEnd, callbackObject, normal, solidOnly=true) // Where the ray meets the first tile hit,
|
|
@@ -1134,6 +1149,11 @@ new Light(pos, radius, color=WHITE, fadeRange=radius)
|
|
|
1134
1149
|
light.glow = 0 // size across of a soft hazy glow over the light, like a lamp at night, 0 for none; added
|
|
1135
1150
|
// over the lit scene after the lightmap, so it shows in the dark, in front of everything
|
|
1136
1151
|
light.glowFalloff = 1 // how fast the glow fades from its middle, .5 a wide haze, 2 a tight bright core
|
|
1152
|
+
light.coneAngle = 0 // a cone, like a flashlight or headlight: radians from its up to the cone's edge, the beam
|
|
1153
|
+
// twice this across; it looks along getUp(), turned by its angle; 0 shines every way
|
|
1154
|
+
light.coneSoftness = .2 // how much of the cone is its fading edge: 0 a hard edge, 1 fading from the middle
|
|
1155
|
+
light.gel = tileInfo // or a whole TextureInfo: a picture the light shines through, across its square, its top
|
|
1156
|
+
// the way it looks, turned with it, multiplied into its color; shadows still fall
|
|
1137
1157
|
|
|
1138
1158
|
// One directional light, a sun: lights the whole scene from one direction, added with the point lights
|
|
1139
1159
|
new DirectionalLight(sunDirection=vec2(-1,1), color=WHITE) // toward the sun, as render3D.sunDirection; its color
|
|
@@ -1179,6 +1199,7 @@ postProcessBloom(threshold=.6, strength=1, size=6, includeMainCanvas=false) // s
|
|
|
1179
1199
|
// and past a size of 32 it would take hundreds, so that is as wide as it goes
|
|
1180
1200
|
postProcessBloomShader(threshold, strength, size) // its shader code, to pass to PostProcessPlugin or build on
|
|
1181
1201
|
postProcess.setShaderCode(shaderCode) // shade with new code from the next frame, to switch effects while running
|
|
1202
|
+
postProcess.enabled = true // false skips the pass, the frame showing as drawn, to turn an effect off and back on
|
|
1182
1203
|
|
|
1183
1204
|
// Built in effects: each is a piece of shader code with its settings written in, working on c, the pixel's color,
|
|
1184
1205
|
// and uv, where it is on the screen from 0 to 1; postProcessEffects joins pieces in order into one shader, and your
|
|
@@ -1333,6 +1354,7 @@ render3D.camera.follow(target, offset, percent=1) // chase camera: ease toward t
|
|
|
1333
1354
|
// is how far it moves each call, so call it every frame, from
|
|
1334
1355
|
// gameUpdatePost once the target has moved
|
|
1335
1356
|
render3D.camera.align2D = true // lock to the 2D camera so the z=0 plane matches world space, false by default
|
|
1357
|
+
render3D.camera.align2DZ = 0 // the z of the plane align2D lines up, the camera its distance in front
|
|
1336
1358
|
render3D.camera.getForward() .getRight() .getUp() // the camera's axes as it is right now; render3D.cameraRight
|
|
1337
1359
|
// .cameraUp .cameraForward are this frame's, read only
|
|
1338
1360
|
render3D.viewMatrix .projectionMatrix .viewProjection .shadowMatrix // this frame's, rebuilt by updateMatrices()
|
|
@@ -1408,7 +1430,8 @@ render3D.shadowLight = flashlight // a spotlight, a Light3D with a coneAngle
|
|
|
1408
1430
|
render3D.shadowRange = 40 // world size the map covers around shadowCenter, smaller is sharper
|
|
1409
1431
|
// it is a square facing the light, so ~1.5x an area's width covers it
|
|
1410
1432
|
render3D.shadowCenter = undefined // Vector3 center of the shadowed area, read each frame; undefined follows the camera
|
|
1411
|
-
render3D.shadowBias = .003 // raise if lit surfaces get speckled with their own shadow, lower if shadows float away
|
|
1433
|
+
render3D.shadowBias = .003 // raise if lit surfaces get speckled with their own shadow, lower if shadows float away;
|
|
1434
|
+
// a share of the map's depth (2 * shadowRange for the sun), so the gap grows with the range
|
|
1412
1435
|
// from their casters
|
|
1413
1436
|
render3D.shadowSoftness = 1 // how far to blur the shadow edge, in shadow map pixels
|
|
1414
1437
|
|
|
@@ -2264,6 +2287,15 @@ newgrounds.postScore(id, value) // needs a logged in player and a whole num
|
|
|
2264
2287
|
await newgrounds.getScores(id, user, social, skip, limit, period) // the scores are in result.data.scores; period
|
|
2265
2288
|
// 'D' today (the server default), 'W', 'M', 'Y', 'A' all time; a user or social
|
|
2266
2289
|
// narrows it down, and without either it is the whole board even when logged in
|
|
2290
|
+
await newgrounds.cloudSave(slot, data) // any value JSON can hold, to a slot numbered from 1, as many as the app's
|
|
2291
|
+
// settings give; needs a logged in player; true once saved, false with a
|
|
2292
|
+
// warning for a value JSON can not hold
|
|
2293
|
+
await newgrounds.cloudLoad(slot) // the value saved there, null when the slot is empty, undefined when it could
|
|
2294
|
+
// not be loaded or the player is not logged in: never save over one undefined
|
|
2295
|
+
newgrounds.loadFailure(slot) // why that slot's last cloudLoad gave undefined: 'notSave' for a file there that
|
|
2296
|
+
// is not a save, where a game may offer to start over, else 'failed'; a saved
|
|
2297
|
+
// null loads as null, as an empty slot does
|
|
2298
|
+
newgrounds.logEvent(name) // count an event of the game's own, by name, on its stats page
|
|
2267
2299
|
newgrounds.unlockMedal(id) // low level request only, the medal is not changed; games call medal.unlock()
|
|
2268
2300
|
newgrounds.pendingUnlocks // advanced: the unlocks in flight or waiting to be resent, with their promises
|
|
2269
2301
|
newgrounds.resendUnlocks() // advanced: send the ones whose request did not reach the server again now, as
|
|
@@ -2308,6 +2340,18 @@ await wavedash.postScore(name, score) // a whole number, milliseconds for a time
|
|
|
2308
2340
|
await wavedash.getScores(name, offset=0, limit=10, friendsOnly=false) // the entries as Wavedash gives them,
|
|
2309
2341
|
// undefined off Wavedash or when they could not be read
|
|
2310
2342
|
wavedash.leaderboards // each board's id promise by its name
|
|
2343
|
+
await wavedash.cloudSave(slot, data) // any value JSON can hold, kept across devices as saves/slot#.json; at most 30
|
|
2344
|
+
// saves a minute and 300 an hour, so at checkpoints; true once saved, false
|
|
2345
|
+
// with a warning for a value JSON can not hold
|
|
2346
|
+
await wavedash.cloudLoad(slot) // the value saved there, null when the slot is empty, undefined when it could
|
|
2347
|
+
// not be loaded or off Wavedash: never save over one that loaded undefined
|
|
2348
|
+
wavedash.loadFailure(slot) // why that slot's last cloudLoad gave undefined: 'notSave' for a file there that
|
|
2349
|
+
// is not a save, where a game may offer to start over, else 'failed'; a saved
|
|
2350
|
+
// null loads as null, as an empty slot does
|
|
2351
|
+
await wavedash.setStat(name, value, storeNow=false) // a stat made in the developer portal, kept a second later or
|
|
2352
|
+
// at once; the player's stats load the first time one is used
|
|
2353
|
+
await wavedash.getStat(name) // a stat's value, 0 for one never set or off Wavedash
|
|
2354
|
+
await wavedash.setPresence(status, details) // what the player is doing, kept with their presence; none clears it
|
|
2311
2355
|
```
|
|
2312
2356
|
|
|
2313
2357
|
## LittleJS Drawing Utilities
|
package/dist/littlejs.d.ts
CHANGED
|
@@ -606,6 +606,8 @@ declare module "littlejsengine" {
|
|
|
606
606
|
* @memberof Engine */
|
|
607
607
|
export let frame: number;
|
|
608
608
|
/** Current engine time since start in seconds
|
|
609
|
+
* - Below 20 FPS it falls behind the clock, since a frame catches up at most 50 ms of updates, so a timer in
|
|
610
|
+
* real seconds, one that must keep up on a slow device, goes by timeReal
|
|
609
611
|
* @type {number}
|
|
610
612
|
* @memberof Engine */
|
|
611
613
|
export let time: number;
|
|
@@ -613,6 +615,10 @@ declare module "littlejsengine" {
|
|
|
613
615
|
* @type {number}
|
|
614
616
|
* @memberof Engine */
|
|
615
617
|
export let timeReal: number;
|
|
618
|
+
/** Frames drawn per second, smoothed over the last few seconds, in release builds too
|
|
619
|
+
* @type {number}
|
|
620
|
+
* @memberof Engine */
|
|
621
|
+
export let averageFPS: number;
|
|
616
622
|
/** Is the game paused? Causes time and objects to not be updated
|
|
617
623
|
* @type {boolean}
|
|
618
624
|
* @default false
|
|
@@ -647,7 +653,9 @@ declare module "littlejsengine" {
|
|
|
647
653
|
* @param {GameCallback} [gameRender] - Called before objects are rendered, use for drawing backgrounds/world elements
|
|
648
654
|
* @param {GameCallback} [gameRenderPost] - Called after objects are rendered, use for drawing UI/overlays
|
|
649
655
|
* @param {Array<string>|string} [imageSources=[]] - List of image file paths to preload (e.g., ['player.png', 'tiles.png']), or one path
|
|
650
|
-
* @param {HTMLElement} [rootElement] - Root DOM element to attach canvas to, defaults to document.body
|
|
656
|
+
* @param {HTMLElement} [rootElement] - Root DOM element to attach canvas to, defaults to document.body; it is
|
|
657
|
+
* styled for a game (no scroll bars or selection, touch-action none),
|
|
658
|
+
* where its own inline style does not say otherwise
|
|
651
659
|
* It keeps its own inline styles and the canvas centers inside it, but the canvas is still sized from the window,
|
|
652
660
|
* so set canvasFixedSize or canvasMaxSize to fit a smaller element
|
|
653
661
|
* @example
|
|
@@ -2890,6 +2898,9 @@ declare module "littlejsengine" {
|
|
|
2890
2898
|
* across the sprite or the mesh's own uv
|
|
2891
2899
|
* - Names in 3D only: worldPos, worldNormal, cameraPos, sunDirection, sunColor, ambientColor, ambientGroundColor,
|
|
2892
2900
|
* lightCount, lights[i], lightColors[i] and shadow()
|
|
2901
|
+
* - In 3D the snippet may also define void mainNormal(inout vec3 n), given the normal facing the camera after the
|
|
2902
|
+
* normal map, in world space, to bend it per pixel for waves or ripples; the lighting, specular, reflection and
|
|
2903
|
+
* fog then all use it, as they use a normal map
|
|
2893
2904
|
* - In 3D the shadow map is drawn without the Shader, cut only by the texture's alpha, so a snippet that removes
|
|
2894
2905
|
* parts of a surface still shadows with the whole of it
|
|
2895
2906
|
* @example
|
|
@@ -4099,16 +4110,6 @@ declare module "littlejsengine" {
|
|
|
4099
4110
|
* @return {Float32Array} - The audio samples
|
|
4100
4111
|
* @memberof Audio */
|
|
4101
4112
|
export function zzfxG(volume?: number, randomness?: number, frequency?: number, attack?: number, sustain?: number, release?: number, shape?: number, shapeCurve?: number, slide?: number, deltaSlide?: number, pitchJump?: number, pitchJumpTime?: number, repeatTime?: number, noise?: number, modulation?: number, bitCrush?: number, delay?: number, sustainVolume?: number, decay?: number, tremolo?: number, filter?: number): Float32Array;
|
|
4102
|
-
/**
|
|
4103
|
-
* LittleJS Object System
|
|
4104
|
-
* - EngineObject is the base class for all game objects
|
|
4105
|
-
* - Handles automatic updating, rendering, physics, and collision
|
|
4106
|
-
* - Supports parent-child hierarchies with transform inheritance
|
|
4107
|
-
* - 2D physics with velocity, acceleration, damping, and gravity
|
|
4108
|
-
* - Collision system with tiles and other objects
|
|
4109
|
-
* - Renders sprites from tile sheets with color and rotation
|
|
4110
|
-
* - Objects sorted by renderOrder for layered rendering
|
|
4111
|
-
*/
|
|
4112
4113
|
/**
|
|
4113
4114
|
* LittleJS Object Base Object Class
|
|
4114
4115
|
* - Top level object class used by the engine
|
|
@@ -4208,9 +4209,27 @@ declare module "littlejsengine" {
|
|
|
4208
4209
|
children: Array<EngineObject>;
|
|
4209
4210
|
/** @property {boolean} - Limit object speed along x and y axis */
|
|
4210
4211
|
clampSpeed: boolean;
|
|
4212
|
+
/** @property {boolean} - Move through the tiles as a point along a ray, so it can not pass through one at
|
|
4213
|
+
* any speed, for small fast things like bullets: its speed is not held to objectMaxSpeed for the tiles,
|
|
4214
|
+
* collideWithTile is asked with this.pos where the ray goes into the tile, and on a hit it stops at the
|
|
4215
|
+
* surface, bounces off it by restitution and goes on with the rest of its move, so it slides along a floor
|
|
4216
|
+
* - Its collision with solid objects is the usual one, so one with a size that collides with them is still held
|
|
4217
|
+
* to objectMaxSpeed; one of no size is not, it never collides with them
|
|
4218
|
+
* - this.pos is set for each tile asked about and put where the move ends after, so a change collideWithTile
|
|
4219
|
+
* makes to it is not kept; move it after the physics, in update
|
|
4220
|
+
* - Once destroyed, as by its own collideWithTile, it is asked about no more tiles that frame, where an object
|
|
4221
|
+
* that is not a bullet still is */
|
|
4222
|
+
isBullet: boolean;
|
|
4211
4223
|
/** @property {EngineObject|undefined} - Object we are standing on, if any
|
|
4212
4224
|
* @type {EngineObject|undefined} */
|
|
4213
4225
|
groundObject: EngineObject | undefined;
|
|
4226
|
+
/** @property {Vector2|undefined} - Makes a solid object one way, like a platform jumped up through: up, down,
|
|
4227
|
+
* left or right, the way others pass through it; it blocks only what was wholly on its far side before it
|
|
4228
|
+
* moved, or stood on it, and the rest are not stopped or asked through collideWithObject; with no mass it
|
|
4229
|
+
* moves before the other objects each frame, so a lift works the same at any render order; tiles are made one
|
|
4230
|
+
* way by the layer's setOneWay
|
|
4231
|
+
* @type {Vector2|undefined} */
|
|
4232
|
+
oneWay: Vector2 | undefined;
|
|
4214
4233
|
/** @property {EngineObject|undefined} - Parent of object if in local space
|
|
4215
4234
|
* @type {EngineObject|undefined} */
|
|
4216
4235
|
parent: EngineObject | undefined;
|
|
@@ -4239,6 +4258,10 @@ declare module "littlejsengine" {
|
|
|
4239
4258
|
* update: a solid an override moves for another object, a lift carrying a crate, is found there from the next
|
|
4240
4259
|
* update on */
|
|
4241
4260
|
updatePhysics(): void;
|
|
4261
|
+
/** @private */
|
|
4262
|
+
private updatePhysicsBullet;
|
|
4263
|
+
/** @private */
|
|
4264
|
+
private updatePhysicsTiles;
|
|
4242
4265
|
/** Update the object, called automatically by engine once each frame. Does nothing by default */
|
|
4243
4266
|
update(): void;
|
|
4244
4267
|
/** Render the object, draws a tile by default, automatically called each frame, sorted by renderOrder */
|
|
@@ -4276,10 +4299,10 @@ declare module "littlejsengine" {
|
|
|
4276
4299
|
/** Called to check if a tile collision should be resolved. Return true for physics to resolve the collision or false to ignore and resolve it manually
|
|
4277
4300
|
* - Called for each solid tile the physics tests, which can be several times a frame for the same tile, and for
|
|
4278
4301
|
* positions it only tries, so keep it free of side effects or guard them to once a frame
|
|
4279
|
-
* - this.pos has already moved, so a check on where it came from
|
|
4280
|
-
*
|
|
4281
|
-
* - For the point of impact, like sparks where a bullet hit,
|
|
4282
|
-
*
|
|
4302
|
+
* - this.pos has already moved, so a check on where it came from needs the position saved in update; for a one
|
|
4303
|
+
* way platform the layer's setOneWay does that, and this is not asked about a one way tile it passes through
|
|
4304
|
+
* - For the point of impact, like sparks where a bullet hit, set isBullet: this.pos is then where it meets the
|
|
4305
|
+
* tile, as the platformer's Bullet uses it
|
|
4283
4306
|
* @param {number} tileData - the value of the tile at the position
|
|
4284
4307
|
* @param {Vector2} pos - the tile's bottom left corner in world space
|
|
4285
4308
|
* @return {boolean} - true if the collision should be resolved by modifying it's position and velocity */
|
|
@@ -4701,6 +4724,24 @@ declare module "littlejsengine" {
|
|
|
4701
4724
|
/** @property {boolean} - In the light system's shadow pass, cast only from the cells with collision, drawn
|
|
4702
4725
|
* as the layer shows them, so a floor in the same layer stays lit; false casts every tile */
|
|
4703
4726
|
shadowSolidOnly: boolean;
|
|
4727
|
+
/** @property {Map<number, Vector2>} - The tiles set one way, by tile index, and the way each can be passed
|
|
4728
|
+
* through, see setOneWay
|
|
4729
|
+
* @type {Map<number, Vector2>} */
|
|
4730
|
+
oneWayTiles: Map<number, Vector2>;
|
|
4731
|
+
/** Make the cells that draw a tile one way, like a platform jumped up through and landed on: an object, a
|
|
4732
|
+
* particle or a ray passes through moving that way, and the tile blocks only what was wholly on its far side
|
|
4733
|
+
* before it moved, the side it is passed toward; turned and mirrored as each cell's tile is, so a platform turned
|
|
4734
|
+
* a quarter is one way to the side
|
|
4735
|
+
* - A moving object is not stopped or asked through collideWithTile until the tile would block it, so a
|
|
4736
|
+
* collideWithTile that returns false lets it drop through
|
|
4737
|
+
* - tileCollisionTest with an object goes by the object's pos, a raycast by its start, and a test with no object
|
|
4738
|
+
* or with a callback finds every one way tile solid
|
|
4739
|
+
* @param {number} tile - The tile index, as tile() and TileLayerData take it
|
|
4740
|
+
* @param {Vector2} [direction] - Up, down, left or right, the way it can be passed through: vec2(0, 1), the
|
|
4741
|
+
* default, is a platform landed on from above; layer.oneWayTiles.delete(tile) makes the tile solid again
|
|
4742
|
+
* @example
|
|
4743
|
+
* layer.setOneWay(5); // tile 5 is a platform, jumped up through and stood on */
|
|
4744
|
+
setOneWay(tile: number, direction?: Vector2): void;
|
|
4704
4745
|
/** Clear and initialize tile collision, the size is the layer's own, the tile data and canvas keep it
|
|
4705
4746
|
* @param {Vector2} size - width and height of tile collision 2d grid */
|
|
4706
4747
|
initCollision(size: Vector2): void;
|
|
@@ -5122,6 +5163,8 @@ declare module "littlejsengine" {
|
|
|
5122
5163
|
/** @property {Array<Object>} - Scoreboards fetched from Newgrounds, empty until ready
|
|
5123
5164
|
* @type {Array<Object>} */
|
|
5124
5165
|
scoreboards: Array<any>;
|
|
5166
|
+
/** @type {Map<number, 'failed'|'notSave'>} */
|
|
5167
|
+
loadFailures: Map<number, 'failed' | 'notSave'>;
|
|
5125
5168
|
/** @property {{id: number, name: string, url: string, supporter: boolean}|null} - The logged in player once ready, null when not logged in
|
|
5126
5169
|
* @type {{id: number, name: string, url: string, supporter: boolean}|null} */
|
|
5127
5170
|
user: {
|
|
@@ -5171,6 +5214,42 @@ declare module "littlejsengine" {
|
|
|
5171
5214
|
* result.data.scores, each with user.name, value and formatted_value; without a user or social it is the whole board
|
|
5172
5215
|
*/
|
|
5173
5216
|
getScores(id: number, user?: string | number, social?: boolean, skip?: number, limit?: number, period?: string): Promise<any>;
|
|
5217
|
+
/** Save a value to one of the player's cloud save slots, which needs a logged in player
|
|
5218
|
+
* - Any value JSON can hold; the slots are numbered from 1, as many as the app's Newgrounds settings give it
|
|
5219
|
+
* @param {number} slot - The slot number
|
|
5220
|
+
* @param {*} data - The value to save
|
|
5221
|
+
* @return {Promise<boolean>} - Whether it saved, false when not logged in
|
|
5222
|
+
* @example
|
|
5223
|
+
* newgrounds.cloudSave(1, {level, coins}); */
|
|
5224
|
+
cloudSave(slot: number, data: any): Promise<boolean>;
|
|
5225
|
+
/** Load the value a cloud save slot holds: null when Newgrounds says it holds none, undefined when it could not be
|
|
5226
|
+
* loaded or the player is not logged in, said in the console when logged in
|
|
5227
|
+
* - Do not save over a slot that loaded as undefined, it may hold the player's save; loadFailure(slot) says why
|
|
5228
|
+
* it did: 'notSave' for a file there that is not a save, where a game may offer to start over, 'failed' otherwise
|
|
5229
|
+
* - A saved null loads as null, as an empty slot does
|
|
5230
|
+
* @param {number} slot - The slot number
|
|
5231
|
+
* @return {Promise<*>} - The value saved, null for none, undefined for a load that failed
|
|
5232
|
+
* @example
|
|
5233
|
+
* const save = await newgrounds.cloudLoad(1); */
|
|
5234
|
+
cloudLoad(slot: number): Promise<any>;
|
|
5235
|
+
/** Why a slot's last cloudLoad gave undefined: 'notSave' when the slot holds a file that is not a save, where a
|
|
5236
|
+
* game may offer to start over, 'failed' when it could not be loaded, as when not logged in, where a game must
|
|
5237
|
+
* not save over it; undefined when it loaded a save or found the slot empty, or was not loaded
|
|
5238
|
+
* @param {number} slot - The slot number
|
|
5239
|
+
* @return {'failed'|'notSave'|undefined} */
|
|
5240
|
+
loadFailure(slot: number): 'failed' | 'notSave' | undefined;
|
|
5241
|
+
/** A slot's load, its value and why it failed, if it did
|
|
5242
|
+
* @param {number} slot
|
|
5243
|
+
* @return {Promise<{value: *, failure: 'failed'|'notSave'|undefined}>}
|
|
5244
|
+
* @ignore */
|
|
5245
|
+
loadSlot(slot: number): Promise<{
|
|
5246
|
+
value: any;
|
|
5247
|
+
failure: 'failed' | 'notSave' | undefined;
|
|
5248
|
+
}>;
|
|
5249
|
+
/** Count an event of the game's own on its Newgrounds stats page, like a level finished or a button pressed
|
|
5250
|
+
* @param {string} name - The event's name
|
|
5251
|
+
* @return {Promise<Object>} - The response JSON object, undefined when the call failed */
|
|
5252
|
+
logEvent(name: string): Promise<any>;
|
|
5174
5253
|
/** Encrypt text the way the Newgrounds gateway expects, AES-128 CBC with a random iv in front, as Base64
|
|
5175
5254
|
* @param {string} text
|
|
5176
5255
|
* @return {Promise<string>} */
|
|
@@ -5199,7 +5278,8 @@ declare module "littlejsengine" {
|
|
|
5199
5278
|
}
|
|
5200
5279
|
/**
|
|
5201
5280
|
* LittleJS Wavedash Plugin
|
|
5202
|
-
* - The Wavedash twin of the Newgrounds plugin: achievements and
|
|
5281
|
+
* - The Wavedash twin of the Newgrounds plugin: achievements, leaderboards and cloud saves, the same shape so a game
|
|
5282
|
+
* can switch, and stats and presence of Wavedash's own
|
|
5203
5283
|
* - Wavedash serves the game's page and puts its SDK in window.Wavedash before the game runs, so nothing is bundled;
|
|
5204
5284
|
* off Wavedash (local, itch, GitHub Pages) there is none, and every call does nothing
|
|
5205
5285
|
* - Make the plugin when the game can draw, at the end of gameInit: Wavedash.init is called then, and until it is
|
|
@@ -5259,6 +5339,14 @@ declare module "littlejsengine" {
|
|
|
5259
5339
|
};
|
|
5260
5340
|
/** @type {number|undefined} */
|
|
5261
5341
|
achievementRetry: number | undefined;
|
|
5342
|
+
/** @type {Promise<boolean>|undefined} */
|
|
5343
|
+
stats: Promise<boolean> | undefined;
|
|
5344
|
+
/** @type {Map<string, Promise<*>>} */
|
|
5345
|
+
slotQueues: Map<string, Promise<any>>;
|
|
5346
|
+
/** @type {Map<string, Set<Promise<*>>>} */
|
|
5347
|
+
slotCalls: Map<string, Set<Promise<any>>>;
|
|
5348
|
+
/** @type {Map<string, 'failed'|'notSave'>} */
|
|
5349
|
+
loadFailures: Map<string, 'failed' | 'notSave'>;
|
|
5262
5350
|
/** Whether the game is on Wavedash, its SDK on the page
|
|
5263
5351
|
* @return {boolean} */
|
|
5264
5352
|
isActive(): boolean;
|
|
@@ -5287,6 +5375,74 @@ declare module "littlejsengine" {
|
|
|
5287
5375
|
* @param {boolean} [friendsOnly] - Only the player and their friends
|
|
5288
5376
|
* @return {Promise<Array<Object>|undefined>} - The entries, as Wavedash gives them */
|
|
5289
5377
|
getScores(name: string, offset?: number, limit?: number, friendsOnly?: boolean): Promise<Array<any> | undefined>;
|
|
5378
|
+
/** Save a value to one of the player's cloud save slots, kept by Wavedash across devices; off Wavedash it does
|
|
5379
|
+
* nothing
|
|
5380
|
+
* - Any value JSON can hold, stored as the file saves/slot#.json
|
|
5381
|
+
* - Wavedash takes at most 30 saves a minute and 300 an hour from a player, so save at checkpoints, the end of a
|
|
5382
|
+
* level or when asked, not every frame; one over the limit is refused, said in the console
|
|
5383
|
+
* @param {number} slot - The slot number, any whole number the game picks
|
|
5384
|
+
* @param {*} data - The value to save
|
|
5385
|
+
* @return {Promise<boolean>} - Whether it saved
|
|
5386
|
+
* @example
|
|
5387
|
+
* wavedash.cloudSave(1, {level, coins}); */
|
|
5388
|
+
cloudSave(slot: number, data: any): Promise<boolean>;
|
|
5389
|
+
/** Load the value a cloud save slot holds: null when Wavedash says it holds none, undefined when it could not be
|
|
5390
|
+
* loaded or off Wavedash, said in the console on Wavedash
|
|
5391
|
+
* - Do not save over a slot that loaded as undefined, it may hold the player's save; loadFailure(slot) says why
|
|
5392
|
+
* it did: 'notSave' for a file there that is not a save, where a game may offer to start over, 'failed' otherwise
|
|
5393
|
+
* - A saved null loads as null, as an empty slot does
|
|
5394
|
+
* @param {number} slot - The slot number
|
|
5395
|
+
* @return {Promise<*>} - The value saved, null for none, undefined for a load that failed
|
|
5396
|
+
* @example
|
|
5397
|
+
* const save = await wavedash.cloudLoad(1); */
|
|
5398
|
+
cloudLoad(slot: number): Promise<any>;
|
|
5399
|
+
/** Why a slot's last cloudLoad gave undefined: 'notSave' when the slot holds a file that is not a save, where a
|
|
5400
|
+
* game may offer to start over, 'failed' when it could not be loaded, as off Wavedash or on a timeout, where a
|
|
5401
|
+
* game must not save over it; undefined when it loaded a save or found the slot empty, or was not loaded
|
|
5402
|
+
* @param {number} slot - The slot number
|
|
5403
|
+
* @return {'failed'|'notSave'|undefined} */
|
|
5404
|
+
loadFailure(slot: number): 'failed' | 'notSave' | undefined;
|
|
5405
|
+
/** A slot's load, its value and why it failed, if it did
|
|
5406
|
+
* @param {number} slot
|
|
5407
|
+
* @param {function(*): *} track
|
|
5408
|
+
* @return {Promise<{value: *, failure: 'failed'|'notSave'|undefined}>}
|
|
5409
|
+
* @ignore */
|
|
5410
|
+
loadSlot(slot: number, track: (arg0: any) => any): Promise<{
|
|
5411
|
+
value: any;
|
|
5412
|
+
failure: 'failed' | 'notSave' | undefined;
|
|
5413
|
+
}>;
|
|
5414
|
+
/** Run a slot's save or load after the one before it, as they share the slot's local file; other slots go on
|
|
5415
|
+
* at once, and one that fails does not hold up the next
|
|
5416
|
+
* - A call that timed out may still change the file when Wavedash gets to it, so the next waits for it to be
|
|
5417
|
+
* answered too, and gives up with failed when it is not, leaving the file alone
|
|
5418
|
+
* @param {number} slot
|
|
5419
|
+
* @param {*} failed - What the task gives when it can not run
|
|
5420
|
+
* @param {function(function(*): *): Promise<*>} task - Given track, which keeps a call's answer until it is in
|
|
5421
|
+
* @return {Promise<*>}
|
|
5422
|
+
* @ignore */
|
|
5423
|
+
slotQueue(slot: number, failed: any, task: (arg0: (arg0: any) => any) => Promise<any>): Promise<any>;
|
|
5424
|
+
/** Set one of the player's stats, as made for the game in the Wavedash developer portal, which can unlock an
|
|
5425
|
+
* achievement set to follow it; Wavedash keeps it about a second later, or at once with storeNow; off Wavedash it
|
|
5426
|
+
* does nothing
|
|
5427
|
+
* @param {string} name - The stat's identifier
|
|
5428
|
+
* @param {number} value
|
|
5429
|
+
* @param {boolean} [storeNow] - Keep it now, as at the end of a game, not a second later
|
|
5430
|
+
* @return {Promise<boolean>} - Whether Wavedash took it */
|
|
5431
|
+
setStat(name: string, value: number, storeNow?: boolean): Promise<boolean>;
|
|
5432
|
+
/** Read one of the player's stats, 0 for one never set or off Wavedash
|
|
5433
|
+
* @param {string} name - The stat's identifier
|
|
5434
|
+
* @return {Promise<number>} */
|
|
5435
|
+
getStat(name: string): Promise<number>;
|
|
5436
|
+
/** The player's stats loaded from Wavedash, which they must be before they are read or set, asked for the first
|
|
5437
|
+
* time a stat is
|
|
5438
|
+
* @return {Promise<boolean>} - Whether they loaded
|
|
5439
|
+
* @ignore */
|
|
5440
|
+
statsLoaded(): Promise<boolean>;
|
|
5441
|
+
/** Set what the player is doing, kept with their presence on Wavedash; off Wavedash it does nothing
|
|
5442
|
+
* @param {string} [status] - One line of what they are doing, like 'In a race'
|
|
5443
|
+
* @param {string} [details] - More about it, like 'Lap 2 of 3'; both left out clears it
|
|
5444
|
+
* @return {Promise<boolean>} - Whether it was set */
|
|
5445
|
+
setPresence(status?: string, details?: string): Promise<boolean>;
|
|
5290
5446
|
/** Send every unlocked WavedashMedal's achievement Wavedash has not taken yet, again every two seconds while it
|
|
5291
5447
|
* refuses some, as it does until it has loaded the player's achievements; one refused for about a minute is
|
|
5292
5448
|
* taken as an identifier Wavedash does not have, said once in the console, and not sent again this visit
|
|
@@ -5350,6 +5506,9 @@ declare module "littlejsengine" {
|
|
|
5350
5506
|
constructor(shaderCode?: string, includeMainCanvas?: boolean, feedbackTexture?: boolean);
|
|
5351
5507
|
/** @property {string} - The shadertoy style mainImage code it shades with, see setShaderCode */
|
|
5352
5508
|
shaderCode: string;
|
|
5509
|
+
/** @property {boolean} - Is the pass on? Off, the frame shows as the engine drew it, the shader is kept,
|
|
5510
|
+
* and the feedback texture holds the last frame drawn with it on */
|
|
5511
|
+
enabled: boolean;
|
|
5353
5512
|
/** @property {Object<string, number|Array<number>>} - The game's own values for the shader, a uniform each
|
|
5354
5513
|
* by its name, a number a float and a list of 2 to 4 numbers a vector, set every frame as they are; an
|
|
5355
5514
|
* effect setting can be one of these names, so it changes every frame without making the shader again, all
|
|
@@ -5699,11 +5858,16 @@ declare module "littlejsengine" {
|
|
|
5699
5858
|
* - A light inside a caster is blocked entirely, so the object that holds it, its lamp, a torch, the player
|
|
5700
5859
|
* carrying it, needs a shadowCore that reaches past it, castShadow = false, or a renderShadow that leaves
|
|
5701
5860
|
* the light's spot out
|
|
5861
|
+
* - A coneAngle makes it a cone along its up, turned by its angle, and a gel is a picture it shines through; both
|
|
5862
|
+
* are applied over the round light with its shadows, so they cost next to nothing
|
|
5702
5863
|
* @extends EngineObject
|
|
5703
5864
|
* @memberof LightSystem
|
|
5704
5865
|
* @example
|
|
5705
5866
|
* new Light(vec2(5, 5), 4, rgb(1, 0.5, 0)); // orange light, full soft blob
|
|
5706
5867
|
* new Light(vec2(0, 0), 8, rgb(1, 1, 1), 2); // white core with 2-unit soft halo
|
|
5868
|
+
* const flashlight = new Light(vec2(), 10); // a flashlight looking right, its beam 60 degrees across
|
|
5869
|
+
* flashlight.coneAngle = PI/6;
|
|
5870
|
+
* flashlight.angle = PI/2;
|
|
5707
5871
|
*/
|
|
5708
5872
|
export class Light extends EngineObject {
|
|
5709
5873
|
/** Create a light object and add it to the engine object list
|
|
@@ -5728,6 +5892,19 @@ declare module "littlejsengine" {
|
|
|
5728
5892
|
glowFalloff: number;
|
|
5729
5893
|
/** @type {TileInfo|undefined} */
|
|
5730
5894
|
glowTileInfo: TileInfo | undefined;
|
|
5895
|
+
/** @property {number} - Makes it a cone, like a flashlight or headlight: the angle in radians from its up out
|
|
5896
|
+
* to the edge of the cone, so the beam is twice this across; it looks along getUp(), turned by its angle and
|
|
5897
|
+
* by what it is attached to; 0 for a light that shines every way */
|
|
5898
|
+
coneAngle: number;
|
|
5899
|
+
/** @property {number} - How much of the cone is its fading edge: 0 a hard edge, .2 by default, the outer
|
|
5900
|
+
* fifth, 1 fading all the way from the middle of the beam */
|
|
5901
|
+
coneSoftness: number;
|
|
5902
|
+
/** @property {TileInfo|TextureInfo|undefined} - A gel, a picture the light shines through, called a cookie in
|
|
5903
|
+
* some engines: stretched across the light's square, twice its radius, its top the way the light looks,
|
|
5904
|
+
* turned with it, and multiplied into its color, so one light can be a car's headlights and tail lights;
|
|
5905
|
+
* a TileInfo's own tile, or a whole TextureInfo; shadows still fall through it
|
|
5906
|
+
* @type {TileInfo|TextureInfo|undefined} */
|
|
5907
|
+
gel: TileInfo | TextureInfo | undefined;
|
|
5731
5908
|
/** Draw this light's glow, soft and round, its glow size across and in its color, added over the lit scene;
|
|
5732
5909
|
* called by LightSystemPlugin after the lightmap is applied */
|
|
5733
5910
|
renderGlow(): void;
|
|
@@ -8054,7 +8231,9 @@ declare module "littlejsengine" {
|
|
|
8054
8231
|
* and 1 with the screen, a Vector2 to follow x and y by different amounts
|
|
8055
8232
|
* @param {number} [renderOrder] - Low to draw behind the game, far layers lowest
|
|
8056
8233
|
* @param {function(OffscreenCanvasRenderingContext2D, Vector2, ParallaxLayer): void} [drawFunction] - Draws
|
|
8057
|
-
* the image, given the canvas context, its size in pixels and the layer; mountains when not given
|
|
8234
|
+
* the image, given the canvas context, its size in pixels and the layer; mountains when not given; called
|
|
8235
|
+
* once when the layer is made and on redraw(), not each frame, so it draws with the canvas 2D context, not
|
|
8236
|
+
* the engine's draws like drawTile
|
|
8058
8237
|
* @param {Vector2} [canvasSize] - Size of the image in pixels */
|
|
8059
8238
|
constructor(pos?: Vector2, size?: Vector2, parallax?: number | Vector2, renderOrder?: number, drawFunction?: (arg0: OffscreenCanvasRenderingContext2D, arg1: Vector2, arg2: ParallaxLayer) => void, canvasSize?: Vector2);
|
|
8060
8239
|
/** @property {Vector2} - How much of the camera's movement it follows on each axis, 0 stays with the world
|
|
@@ -8788,7 +8967,8 @@ declare module "littlejsengine" {
|
|
|
8788
8967
|
* - EngineObject3D is an EngineObject with a 3D position, rotation and mesh
|
|
8789
8968
|
* - The 3D scene draws under the 2D sprites, so HUD and text land on top
|
|
8790
8969
|
* - Lighting is the sun plus ambient, with optional extra lights, fog and shadows
|
|
8791
|
-
* - Any object or draw can bring its own Shader, a mainImage snippet the lighting then applies to
|
|
8970
|
+
* - Any object or draw can bring its own Shader, a mainImage snippet the lighting then applies to, and a
|
|
8971
|
+
* mainNormal in it bends the normal the lighting uses
|
|
8792
8972
|
* - Meshes and the basic builders are in render3dMesh.js, EngineObject3D, instancing and lights in
|
|
8793
8973
|
* render3dObject.js, both right after this one; the other builders, terrain, particles, camera controls and the
|
|
8794
8974
|
* OBJ loader are in the Render3D Extras plugin, which goes after those
|
|
@@ -8873,7 +9053,9 @@ declare module "littlejsengine" {
|
|
|
8873
9053
|
/** @property {Vector3|undefined} - Center of the shadowed area, read each frame, undefined follows the camera
|
|
8874
9054
|
* @type {Vector3|undefined} */
|
|
8875
9055
|
shadowCenter: Vector3 | undefined;
|
|
8876
|
-
/** @property {number} - Stops surfaces shadowing themselves, raise for speckles, lower if shadows drift off
|
|
9056
|
+
/** @property {number} - Stops surfaces shadowing themselves, raise for speckles, lower if shadows drift off;
|
|
9057
|
+
* a share of the shadow map's depth, twice shadowRange for the sun and a spotlight's radius, so the gap behind
|
|
9058
|
+
* a caster grows with the range as the map's texels do, and the speckles they make stay away */
|
|
8877
9059
|
shadowBias: number;
|
|
8878
9060
|
/** @property {number} - How much to blur the shadow edges */
|
|
8879
9061
|
shadowSoftness: number;
|
|
@@ -9417,6 +9599,9 @@ declare module "littlejsengine" {
|
|
|
9417
9599
|
/** @property {boolean} - Line the 3D camera up with the 2D camera, so 3D things at z=0 sit on the 2D sprites;
|
|
9418
9600
|
* it lines up with the 2D view of the main canvas, whatever canvas size a screenToRay is given */
|
|
9419
9601
|
align2D: boolean;
|
|
9602
|
+
/** @property {number} - The z of the plane align2D lines up with the 2D view, the camera sitting its
|
|
9603
|
+
* distance in front of it */
|
|
9604
|
+
align2DZ: number;
|
|
9420
9605
|
/** Returns the camera's world transform
|
|
9421
9606
|
* @return {Matrix4} */
|
|
9422
9607
|
getMatrix(): Matrix4;
|