Commits
use node 22 in dockerfile
expose vitest ports in dev container
by default tests will run headlessly but expose UI page on port 51204
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
Closes https://github.com/excaliburjs/excalibur-tiled/issues/725 (excalibur-tiled)
## Changes:
- Added two methods to Camera: `addStrategies` and `setStrategies`.
- Added getter property, `strategies`, to expose current Camera strategies (so they can be merged via `setStrategies` like `camera.setStrategies([new CustomStrat(), ...camera.strategies])`
- Added additional documentation on custom camera strategies and multiple camera strategies
Bumps [tmp](https://github.com/raszi/node-tmp) from 0.2.3 to 0.2.4.
- [Changelog](https://github.com/raszi/node-tmp/blob/master/CHANGELOG.md)
- [Commits](https://github.com/raszi/node-tmp/compare/v0.2.3...v0.2.4)
---
updated-dependencies:
- dependency-name: tmp
dependency-version: 0.2.4
dependency-type: indirect
...
Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
This splits out our vitest test suite into `unit` and `visual` tests. `unit` will run on chromium, while `visual` will run on chrome. I've removed firefox/webkit browsers as we were not running these in CI, and there's a discussion to be had about whether they even make sense to use in unit tests, or are they actually only valuable for visual tests. If the latter, we need to figure out how to not rely on Chrome for consistent screenshotting.
Tests that are visual simply need to contain `@visual` somewhere in it's test name or `describe` name. Unit tests will run for all tests without `@visual`, while visual tests will run all that contain `@visual`. I had considered splitting them out into different files under different folders, but it's nice to re-use the same setup/teardown logic. Otherwise I had to copy & paste all of that in both places.
I also made some other tweaks to our vitest config:
- I've removed the conditional exemption of `--disable-gpu` flag for Chromium on macOS, which although slower it ensures the visual tests pass. I suppose this is because it uses a software renderer.
- Changed the test pooling from `thread` to the default. I never saw a difference in speed but in theory the default (`fork`) is supposed to be faster
- Enabled fileParallelism for tests. I had run into WebGL context issues before, but now they seem to be gone, so this should lead to faster tests
- I've switched from Chrome to actual Chromium for the visual tests, and then lowered the tolerance on the TextSpec so that it could pass both in Windows/Ubuntu CI as well as macOS locally. I'm fine to undo this, but a lower tolerance on font tests might make sense to do anyway and this frees us from relying on Windows+Chrome to run these tests.
Excalibur makes use of `Map<Entity, TData>` for functionality (event dispatch) and performance, using the entity as a key to event subscriptions or other data. This stores the Entity by reference as a key, making both lookup and storage fairly efficient. Thanks to Excalibur's event system, it's easy for engine developers to maintain these lists in a safe manner (paired entity added and removed event handlers); here we are patching up a few that slipped through.
Fixes open memory leaks I was experiencing in my game (which churns Actors); it now maintains a stable ~80-100mb memory usage, vs climbing to ~2gb before my poor browser gives up. Previously, these maps would grow without bounds as Actors were created and removed.
I did a quick search for more, but wanted to focus on what I could verify.
Tests passed, but I wasn't able to find a place to add new tests to automate verification and left that unchecked for now - if you have a place to start I'd be happy to look!
Thanks for the great engine ⚔️
Closes #3510
## Changes:
- removes entities from internal `Map<Entity>` and `Map<object>` lists when on entity removal
I have noticed this when I have embedded the game inside React with React strict mode on and using the canvasElement option.
Closes #3503
Bug raised in Discord:
https://discord.com/channels/1195771303215513671/1408751467808034936
## Changes
- The ParticleEmitter passes its z value down to particles when configured for Global space
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
Closes #590
Related #1161
## Changes:
- Added a new `ex.Sound({...})` option back constructor to set all the props you could set on sound at constructor time
- Added new `ex.SoundManager({...}` api to manage volume and muting on large groups of sounds at once
```typescript
var soundManager = new ex.SoundManger({
channels: ['fx', 'music', 'background'],
sounds: {
jumpSnd: { sound: jumpSnd, volume: 0.4, channels: ['fx'] },
forestSnd: { sound: forestSnd, volume: 0.2, channels: ['music', 'background'] },
challengeMusic: { sound: challengeMusic, volume: 0.2, channels: ['music'] },
guitarLoop: { sound: guitarLoop, volume: 0.2, channels: ['music'] }
}
});
toggleMusic.on('pointerdown', () => {
soundManager.channel.toggle('music');
});
game.add(toggleMusic);
game.input.keyboard.on('press', (evt) => {
if (evt.key === ex.Keys.J) {
soundManager.play('jumpSnd');
}
if (evt.key === ex.Keys.M) {
soundManager.channel.mute('music');
}
if (evt.key === ex.Keys.A) {
soundManager.mute();
}
if (evt.key === ex.Keys.S) {
soundManager.unmute();
}
if (evt.key === ex.Keys.U) {
soundManager.channel.unmute('music');
}
if (evt.key === ex.Keys.P) {
soundManager.channel.play('music');
}
if (evt.key === ex.Keys.V) {
soundManager.channel.setVolume('music', 0.9);
}
});
```
Added references to my 2 games developed using Excalibur for 2 different game jams:
- SpookyTruth: GBJAM 12 (https://daviderisaliti.itch.io/spookytruth)
- QuadRush: ScoreJam 31 (https://daviderisaliti.itch.io/quadrush)
Feature: Added lerp method to vector class
requested in the discord: https://discord.com/channels/1195771303215513671/1400805035503390721
# Changes
- `ex.Animation.clone()`, `ex.Animation.fromSpriteSheet(...)` and `ex.Animation.fromSpriteSheetCoordinates({...})` now all return the subclass if called from one.
removes unadded entity warning
Feature requested on the discord: https://discord.com/channels/1195771303215513671/1400805035503390721
# Changes
arbitrary meta data can now be added for an `Animation`
```ts
const rect = new ex.Rectangle({
width: 100,
height: 100,
color: ex.Color.Blue
});
const anim = new ex.Animation({
frames: [
{
graphic: rect,
duration: 100
}
],
data: { someKey: 'someValue' }
});
console.log(anim.data.get('someKey')) // someValue
anim.data.set('otherKey', 'otherValue')
console.log(anim.data.get('otherKey')) // otherValue
```
`fromSpriteSheet(...)` now also accepts data as an optional argument.
```ts
const anim = ex.Animation.fromSpriteSheet(someSpriteSheet, [0, 1, 2, 3], 100, ex.AnimationStrategy.Freeze, {
someKey: 'someValue'
});
```
as well as `fromSpriteSheetCoordinates({...})`
```ts
const anim = ex.Animation.fromSpriteSheetCoordinates({
spriteSheet: someSpriteSheet,
frameCoordinates: [{ x: 0, y: 0, duration: 100 }],
data: {
someKey: 'someValue'
}
});
```
Bug found on the discord https://discordapp.com/channels/1195771303215513671/1401189791017467967
## Changes:
- Events can change frames during the frame calculation if reset is called, check for such case
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
Bumps [on-headers](https://github.com/jshttp/on-headers) and [compression](https://github.com/expressjs/compression). These dependencies needed to be updated together.
Updates `on-headers` from 1.0.2 to 1.1.0
- [Release notes](https://github.com/jshttp/on-headers/releases)
- [Changelog](https://github.com/jshttp/on-headers/blob/master/HISTORY.md)
- [Commits](https://github.com/jshttp/on-headers/compare/v1.0.2...v1.1.0)
Updates `compression` from 1.7.4 to 1.8.1
- [Release notes](https://github.com/expressjs/compression/releases)
- [Changelog](https://github.com/expressjs/compression/blob/master/HISTORY.md)
- [Commits](https://github.com/expressjs/compression/compare/1.7.4...v1.8.1)
---
updated-dependencies:
- dependency-name: on-headers
dependency-version: 1.1.0
dependency-type: indirect
- dependency-name: compression
dependency-version: 1.8.1
dependency-type: indirect
...
Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Whene reading Flappy Bird tutorial, on the 12th step, no explanation and no code are added to show the use of animation when bird is going down or up.
## Changes:
- Added new code to put everything together
- Explained and displayed where to use an animation and why resetting some is important
Closes #3469
## Changes:
- Fixed issue where `GpuParticleEmitter` did not rotate with their parents
- Fixed issue where Cpu `ParticleEmitter` did not respect `ParticleTransform.Local`
Related #1294
Related #1510
Same origin iframes were failing to respond to keyboard events
## Changes:
- Adds same origin frame detection
- Updates keyboard and pointer input hosts to handle iframes and grab focus properly
- Adds sandbox integration tests for x-origin and same-origin frames
3 files changed
- Random.ts
- 07-random.mdx
- RandomSpec.ts
# Random.ts
added static intialSeed form Date.now() and an incrementing offset.
also, this ensures that the actual seed used is available property
moved public seed to private _seed
added getter for seed
in constructor(), if no seed provided it pulls from the 'next' seed in the incrementing list
# 07-random.mdx
updated documentation to reflect new functionality
# RandomSpec.ts
-added 2 tests
- will have a seed even if not passed into constructor
- can have sequential random instances with unique seeds
# Checklist for PR
- added tests
- all tests pass locally
- created test project to exercise new logic with favorable results
- updated docs
chore: Update dependency eslint to v9
* Change game.goto to game.goToScene
* Example now compiles and runs correctly
* chore: Update dependency prettier to v3.6.2
* format files to match prettier changes
---------
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
Co-authored-by: Matt Jennings <me@mattjennings.io>
Update 00-z-quick-start.mdx
use node 22 in dockerfile
expose vitest ports in dev container
by default tests will run headlessly but expose UI page on port 51204
Closes https://github.com/excaliburjs/excalibur-tiled/issues/725 (excalibur-tiled)
## Changes:
- Added two methods to Camera: `addStrategies` and `setStrategies`.
- Added getter property, `strategies`, to expose current Camera strategies (so they can be merged via `setStrategies` like `camera.setStrategies([new CustomStrat(), ...camera.strategies])`
- Added additional documentation on custom camera strategies and multiple camera strategies
Bumps [tmp](https://github.com/raszi/node-tmp) from 0.2.3 to 0.2.4.
- [Changelog](https://github.com/raszi/node-tmp/blob/master/CHANGELOG.md)
- [Commits](https://github.com/raszi/node-tmp/compare/v0.2.3...v0.2.4)
---
updated-dependencies:
- dependency-name: tmp
dependency-version: 0.2.4
dependency-type: indirect
...
Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
This splits out our vitest test suite into `unit` and `visual` tests. `unit` will run on chromium, while `visual` will run on chrome. I've removed firefox/webkit browsers as we were not running these in CI, and there's a discussion to be had about whether they even make sense to use in unit tests, or are they actually only valuable for visual tests. If the latter, we need to figure out how to not rely on Chrome for consistent screenshotting.
Tests that are visual simply need to contain `@visual` somewhere in it's test name or `describe` name. Unit tests will run for all tests without `@visual`, while visual tests will run all that contain `@visual`. I had considered splitting them out into different files under different folders, but it's nice to re-use the same setup/teardown logic. Otherwise I had to copy & paste all of that in both places.
I also made some other tweaks to our vitest config:
- I've removed the conditional exemption of `--disable-gpu` flag for Chromium on macOS, which although slower it ensures the visual tests pass. I suppose this is because it uses a software renderer.
- Changed the test pooling from `thread` to the default. I never saw a difference in speed but in theory the default (`fork`) is supposed to be faster
- Enabled fileParallelism for tests. I had run into WebGL context issues before, but now they seem to be gone, so this should lead to faster tests
- I've switched from Chrome to actual Chromium for the visual tests, and then lowered the tolerance on the TextSpec so that it could pass both in Windows/Ubuntu CI as well as macOS locally. I'm fine to undo this, but a lower tolerance on font tests might make sense to do anyway and this frees us from relying on Windows+Chrome to run these tests.
Excalibur makes use of `Map<Entity, TData>` for functionality (event dispatch) and performance, using the entity as a key to event subscriptions or other data. This stores the Entity by reference as a key, making both lookup and storage fairly efficient. Thanks to Excalibur's event system, it's easy for engine developers to maintain these lists in a safe manner (paired entity added and removed event handlers); here we are patching up a few that slipped through.
Fixes open memory leaks I was experiencing in my game (which churns Actors); it now maintains a stable ~80-100mb memory usage, vs climbing to ~2gb before my poor browser gives up. Previously, these maps would grow without bounds as Actors were created and removed.
I did a quick search for more, but wanted to focus on what I could verify.
Tests passed, but I wasn't able to find a place to add new tests to automate verification and left that unchecked for now - if you have a place to start I'd be happy to look!
Thanks for the great engine ⚔️
Closes #3510
## Changes:
- removes entities from internal `Map<Entity>` and `Map<object>` lists when on entity removal
Closes #590
Related #1161
## Changes:
- Added a new `ex.Sound({...})` option back constructor to set all the props you could set on sound at constructor time
- Added new `ex.SoundManager({...}` api to manage volume and muting on large groups of sounds at once
```typescript
var soundManager = new ex.SoundManger({
channels: ['fx', 'music', 'background'],
sounds: {
jumpSnd: { sound: jumpSnd, volume: 0.4, channels: ['fx'] },
forestSnd: { sound: forestSnd, volume: 0.2, channels: ['music', 'background'] },
challengeMusic: { sound: challengeMusic, volume: 0.2, channels: ['music'] },
guitarLoop: { sound: guitarLoop, volume: 0.2, channels: ['music'] }
}
});
toggleMusic.on('pointerdown', () => {
soundManager.channel.toggle('music');
});
game.add(toggleMusic);
game.input.keyboard.on('press', (evt) => {
if (evt.key === ex.Keys.J) {
soundManager.play('jumpSnd');
}
if (evt.key === ex.Keys.M) {
soundManager.channel.mute('music');
}
if (evt.key === ex.Keys.A) {
soundManager.mute();
}
if (evt.key === ex.Keys.S) {
soundManager.unmute();
}
if (evt.key === ex.Keys.U) {
soundManager.channel.unmute('music');
}
if (evt.key === ex.Keys.P) {
soundManager.channel.play('music');
}
if (evt.key === ex.Keys.V) {
soundManager.channel.setVolume('music', 0.9);
}
});
```
Feature requested on the discord: https://discord.com/channels/1195771303215513671/1400805035503390721
# Changes
arbitrary meta data can now be added for an `Animation`
```ts
const rect = new ex.Rectangle({
width: 100,
height: 100,
color: ex.Color.Blue
});
const anim = new ex.Animation({
frames: [
{
graphic: rect,
duration: 100
}
],
data: { someKey: 'someValue' }
});
console.log(anim.data.get('someKey')) // someValue
anim.data.set('otherKey', 'otherValue')
console.log(anim.data.get('otherKey')) // otherValue
```
`fromSpriteSheet(...)` now also accepts data as an optional argument.
```ts
const anim = ex.Animation.fromSpriteSheet(someSpriteSheet, [0, 1, 2, 3], 100, ex.AnimationStrategy.Freeze, {
someKey: 'someValue'
});
```
as well as `fromSpriteSheetCoordinates({...})`
```ts
const anim = ex.Animation.fromSpriteSheetCoordinates({
spriteSheet: someSpriteSheet,
frameCoordinates: [{ x: 0, y: 0, duration: 100 }],
data: {
someKey: 'someValue'
}
});
```
Bumps [on-headers](https://github.com/jshttp/on-headers) and [compression](https://github.com/expressjs/compression). These dependencies needed to be updated together.
Updates `on-headers` from 1.0.2 to 1.1.0
- [Release notes](https://github.com/jshttp/on-headers/releases)
- [Changelog](https://github.com/jshttp/on-headers/blob/master/HISTORY.md)
- [Commits](https://github.com/jshttp/on-headers/compare/v1.0.2...v1.1.0)
Updates `compression` from 1.7.4 to 1.8.1
- [Release notes](https://github.com/expressjs/compression/releases)
- [Changelog](https://github.com/expressjs/compression/blob/master/HISTORY.md)
- [Commits](https://github.com/expressjs/compression/compare/1.7.4...v1.8.1)
---
updated-dependencies:
- dependency-name: on-headers
dependency-version: 1.1.0
dependency-type: indirect
- dependency-name: compression
dependency-version: 1.8.1
dependency-type: indirect
...
Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
3 files changed
- Random.ts
- 07-random.mdx
- RandomSpec.ts
# Random.ts
added static intialSeed form Date.now() and an incrementing offset.
also, this ensures that the actual seed used is available property
moved public seed to private _seed
added getter for seed
in constructor(), if no seed provided it pulls from the 'next' seed in the incrementing list
# 07-random.mdx
updated documentation to reflect new functionality
# RandomSpec.ts
-added 2 tests
- will have a seed even if not passed into constructor
- can have sequential random instances with unique seeds
# Checklist for PR
- added tests
- all tests pass locally
- created test project to exercise new logic with favorable results
- updated docs