Merge remote-tracking branch 'upstream/master'

This commit is contained in:
Jason Nicholls 2019-03-10 13:47:29 +02:00
commit b3f847d09b
1543 changed files with 142348 additions and 96060 deletions

View file

@ -8,8 +8,6 @@ src/geom/polygon/Earcut.js
src/utils/array/StableSort.js src/utils/array/StableSort.js
src/utils/object/Extend.js src/utils/object/Extend.js
src/structs/RTree.js src/structs/RTree.js
src/dom/_ScaleManager.js
src/dom/VisualBounds.js
plugins/spine/src/spine-canvas.js plugins/spine/src/spine-canvas.js
plugins/spine/src/spine-webgl.js plugins/spine/src/spine-webgl.js
webpack.* webpack.*

View file

@ -85,7 +85,7 @@
"no-trailing-spaces": [ "error", { "skipBlankLines": true, "ignoreComments": true } ], "no-trailing-spaces": [ "error", { "skipBlankLines": true, "ignoreComments": true } ],
"no-underscore-dangle": "off", "no-underscore-dangle": "off",
"no-whitespace-before-property": "error", "no-whitespace-before-property": "error",
"object-curly-newline": [ "error", { "multiline": true, "minProperties": 0 } ], "object-curly-newline": [ "error", { "multiline": true, "minProperties": 0, "consistent": true } ],
"one-var-declaration-per-line": [ "error", "initializations" ], "one-var-declaration-per-line": [ "error", "initializations" ],
"quote-props": [ "error", "as-needed" ], "quote-props": [ "error", "as-needed" ],
"quotes": [ "error", "single" ], "quotes": [ "error", "single" ],

View file

@ -76,5 +76,5 @@ Thanks to Chad for creating the original Pixi.js Contributing file which we adap
[1]: http://jsfiddle.net [1]: http://jsfiddle.net
[2]: http://jsbin.com/ [2]: http://jsbin.com/
[3]: http://nodejs.org [3]: http://nodejs.org
[4]: http://www.html5gamedevs.com/forum/33-phaser-3/ [4]: https://phaser.discourse.group/
[5]: https://codepen.io/pen?template=YeEWom "Phaser 3 game template" [5]: https://codepen.io/pen?template=YeEWom "Phaser 3 game template"

View file

@ -9,7 +9,7 @@ Thank you for taking the time to contribute towards Phaser. Before submitting yo
1. This repo is for Phaser 3 only. Phaser 2.x issues should be raised in the [Phaser CE](https://github.com/photonstorm/phaser-ce) repo. 1. This repo is for Phaser 3 only. Phaser 2.x issues should be raised in the [Phaser CE](https://github.com/photonstorm/phaser-ce) repo.
2. This repo should not be used for technical support. If you're struggling to use Phaser then post your question to the [forum](http://www.html5gamedevs.com/forum/33-phaser-3/), [Slack](https://phaser.io/community/slack) or [Discord](https://phaser.io/community/discord) channels. GitHub Issues are for bugs and feature requests only. 2. This repo should not be used for technical support. If you're struggling to use Phaser then post your question to the [forum](https://phaser.discourse.group/), [Slack](https://phaser.io/community/slack) or [Discord](https://phaser.io/community/discord) channels. GitHub Issues are for bugs and feature requests only.
3. Make sure your issue isn't a duplicate, or has already been fixed. 3. Make sure your issue isn't a duplicate, or has already been fixed.

View file

@ -1,33 +1,185 @@
# Change Log # Change Log
## Version 3.16.0 - Ishikawa - in development ## Version 3.17.0 - Ishikawa - in dev
### Facebook Instant Games Updates and Fixes Notes:
* Added the `Leaderboard.getConnectedScores` method, to get a list of scores from player connected entries. 1) Vertex for any GO
* The `loadPlayerPhoto` function in the Instant Games plugin now listens for the updated Loader event correctly, causing the `photocomplete` event to fire properly. 2) Body Blocked
* `Leaderboard.setScore` now emits the LeaderboardScore object with the `setscore` event, as the documentation said it did. 3) GO auto-add to Scene
* `Leaderboard.getPlayerScore` now only populates the `playerScore` property if the entry isn't `null`. 4) GO move to another Scene
* If the `setScore` or `getPlayerScore` calls fail, it will return `null` as the score instance, instead of causing a run-time error.
* You can now pass an object or a string to `setScore` and objects will be automatically stringified. ### Arcade Physics
* The `preloadAds` method will now only create an AdInstance object if the interstitial `loadSync` promise resolves.
* The `preloadVideoAds` method will now only create an AdInstance object if the interstitial `loadSync` promise resolves. #### New Features
* The `preloadAds` method will now emit the `adsnofill` event, if there are no ads in the inventory to load.
* The `preloadVideoAds` method will now emit the `adsnofill` event, if there are no ads in the inventory to load. * `overlapTiles` is a new method that allows you to check for overlaps between a physics enabled Game Object and an array of Tiles. The Tiles don't have to have been enable for collision, or even be on the same layer, for the overlap check to work. You can provide your own process callback and/or overlap callback. This is handy for testing for overlap for a specific Tile in your map, not just based on a tile index. This is available via `this.physics.overlapTiles` and the World instance.
* The `showAd` method will now emit the `adsnotloaded` event, if there are no ads loaded matching the given Placement ID. * `collideTiles` is a new method that allows you to check for collision between a physics enabled Game Object and an array of Tiles. The Tiles don't have to have been enable for collision, or even be on the same layer, for the collision to work. You can provide your own process callback and/or overlap callback. There are some limitations in using this method, please consult the API Docs for details, but on the whole, it allows for dynamic collision on small sets of Tile instances. This is available via `this.physics.collideTiles` and the World instance.
* The `showVideo` method will now emit the `adsnotloaded` event, if there are no ads loaded matching the given Placement ID. * `overlapRect` is a new method that allows you to return an array of all physics bodies within the given rectangular region of the World. It can return dynamic or static bodies and will use the RTree for super-fast searching, if enabled (which it is by default)
* Showing an ad will emit the `adfinished` event when the ad is closed, previously this event was called `showad` but the new name better reflects what has happened.
* The Facebook Plugin is now available in the `Phaser.Scene` class template under the `facebook` property (thanks @bryanwood) #### Updates
* `Body.preUpdate` is a new method that is called only once per game step. It resets all collision status properties and syncs the Body with the parent Game Object.
* `Body.update` has been rewritten to just perform one single physics step and no longer re-syncs with the Game Object. It can be called multiple times per game step, depending on the World FPS rate.
* `Body.postUpdate` has been rewritten to make it more compact. It syncs the body data back to the parent Game Object and is only called once per game step now (previously it was called whenever the Body updated)
* The `World.late` Set has been removed and is no longer populated, as it's no longer required.
* `World.update` now calls `Body.preUpdate` just once per game step, then calls `Body.update` as many times as is required as per the FPS setting, and no longer calls `Body.postUpdate` at all.
* `World.collideSpriteVsTilemapLayer` now returns a boolean if a collision or overlap happens, where-as before it didn't.
* `World.collideSpriteVsTilemapLayerHandler` is a new private method that handles all tilemap collision checks.
* The internal method `SeparateTile` now has a new argument `isLayer` which controls if the set comes from a layer or an array.
* The internal method `TileCheckX` now has a new argument `isLayer` which controls if the set comes from a layer or an array.
* The internal method `TileCheckY` now has a new argument `isLayer` which controls if the set comes from a layer or an array.
#### Bug Fixes
* The `Body.delta` values are now able to be read and acted upon during a Scene update, due to the new game step flow. This means you can now call `this.physics.collide` during a Scene `update` and it will work properly again. Fix #4370 (thanks @NokFrt)
* `ArcadePhysics.furthest` now iterates the bodies Set, rather than the RTree, which keeps it working even if the RTree has been disabled.
* `ArcadePhysics.closest` now iterates the bodies Set, rather than the RTree, which keeps it working even if the RTree has been disabled.
### New Features
* There is a new Game Config property `input.windowEvents` which is true by default. It controls if Phaser will listen for any input events on the Window. If you disable this, Phaser will stop being able to emit events like `POINTER_UP_OUTSIDE`, or be aware of anything that happens outside of the Canvas re: input.
* A Scene will now emit the new `CREATE` event after it has been created by the Scene Manager. If the Scene has a `create` method this event comes after that, so is useful to knowing when a Scene may have finished creating Game Objects, etc. (thanks @jackfreak)
* `Tilemap.removeTile` is a new method that allows you to remove a tile, or an array of tiles, by passing in references to the tiles themselves, rather than coordinates. The tiles can be replaced with new tiles of the given index, or removed entirely, and the method can optionally recalculate interesting faces on the layer.
### Updates
* Removed all references to CocoonJS from the API, including in the Device.OS object and elsewhere, as Cocoon is no longer.
* The MouseManager and TouchManager now use separate handlers for the Window level input events, which check to see if the canvas is the target or not, and redirect processing accordingly.
* `AnimationManager.generateFrameNumbers` can now accept a start number greater than the end number, and will generate them in reverse (thanks @cruzdanilo)
* The return from the `ScenePlugin.add` method has changed. Previously, it would return the ScenePlugin, but now it returns a reference to the Scene that was added to the Scene Manager, keeping it in-line with all other `add` methods in the API. Fix #4359 (thanks @BigZaphod)
* The `PluginManager.installScenePlugin` method has a new optional boolean parameter `fromLoader` which controls if the plugin is coming in from the result of a Loader operation or not. If it is, it no longer throws a console warning if the plugin already exists. This fixes an issue where if you return to a Scene that loads a Scene Plugin it would throw a warning and then not install the plugin to the Scene.
* The Scale Manager has a new event `FULLSCREEN_FAILED` which is fired if you try to enter fullscreen mode, but the browser rejects it for some reason.
### Bug Fixes
* The parent bounds are reset when exiting fullscreen mode in the Scale Manager. This fixes an issue when leaving fullscreen mode by pressing ESC (instead of programmatically) would leave the canvas in the full screen size. Fix #4357 (thanks @khutchins and @HeyStevenXu)
* `GetAdvancedValue` now uses the correct Math RND reference, which means anything that used the `randInt` or `randFloat` features of this function, such as creating a Sprite from a Config object, or Bitmap Text sizing, will no longer throw an error about a null object reference. Fix #4369 (thanks @sanadov)
* Trying to enter Fullscreen mode on Android / Chrome, or iOS / Safari, would throw an error regarding an unhandled Promise and a failure to invoke the event from a user gesture. This has been tightened up, using a proper Promise handler internally and the documentation clarified to explicitly say that you must call the function from a `pointerup` handler, and not `pointerdown`. Fix #4355 (thanks @matrizet)
### Examples, Documentation and TypeScript
My thanks to the following for helping with the Phaser 3 Examples, Docs and TypeScript definitions, either by reporting errors, fixing them or helping author the docs:
@sky-coding @G-Rath @S4n60w3n @rootasjey @englercj @josephmbustamante
## Version 3.16.2 - Ishikawa - 11th February 2019
This is point release primarily fixes a few important issues that surfaced in 3.16.0.
### Matter Pointer Constraint Changes
The following changes all effect the Matter JS Pointer Constraint class:
* Pointer handling has been changed to make more sense. In the previous version, pressing down and then moving the Pointer _over_ a body would start it being dragged, even if the pointer was pressed down well outside of the body bounds. Now, a body can only be dragged by actually pressing down on it, or any of its parts, which is more in-line with how input events should work.
* Previously, releasing ANY pointer would stop an object being dragged, even if it wasn't the one actually dragging a body, as in a multi-touch game. Bodies are now bound to the pointer which started their drag and only the release of that pointer will stop them.
* There is a new Matter Physics Event `DRAG_START` which is emitted by a Pointer Constraint when it starts dragging a body. Listen for this event from the Matter World instance.
* There is a new Matter Physics Event `DRAG` which is emitted by a Pointer Constraint as it drags a body. Listen for this event from the Matter World instance.
* There is a new Matter Physics Event `DRAG_END` which is emitted by a Pointer Constraint when it stops dragging a body. Listen for this event from the Matter World instance.
* The `camera` property can no longer be set in the config object. Instead it is set every time the Pointer is pressed down on a Body, this resolves issues where you have a multi-camera Scene and want to drag a body in the non-main camera.
* `body` is a new property that holds a reference to the Body being dragged, if any.
* `part` is a new property that holds a reference to the Body part that was clicked on which started the drag.
* The internal `getBodyPart` method has been renamed to `hitTestBody` to more accurately reflect what it does.
* The class no longer listens for the pointer `up` event, instead of tracks the active pointer and waits for that to be released. This has reduced the complexity and size of the `update` method considerably.
* `stopDrag` is a new method that allows you to manually stop an object being dragged, even if the pointer isn't released.
* This class now has 100% JSDocs.
### Updates
* `TileSprite.setTileScale` has been updated so that the `y` argument is optional and set to match the `x` argument, like `setScale` elsewhere in the API.
* `InputManager.time` is a new property that holds the most recent time it was updated from the Game step, which plugins can access.
* `InputManager.preStep` is a new method that populates some internal properties every step.
* `KeyboardPlugin.time` has moved from being a property to being a getter, which returns the time from the InputManager.
* The `scale` property has been added to the `Scene` class (thanks @strangeweekend)
* `Matter.World.remove` now uses the `Composite.remove` method internally. Previously, it used `Composite.removeBody` which only allowed it to remove bodies from the simulation. Now, it can remove any type of Matter object.
* When the Matter World creates its wall bounds, the left and right walls now extend further up and down than before, so that in a 4-wall setting there are no gaps in the corners, which previously allowed for fast moving objects that hit a corner intersection point to sometimes travel through it.
* Touch inputs will now trigger a `POINTER_OUT` event if they leave the game (i.e. are released), where-as before they would only trigger the `POINTER_UP` event. Now, both happen (thanks @rgk)
### Bug Fixes
* The `Mesh.setAlpha` method has been restored, even though it's empty and does nothing, to prevent runtime errors when adding a Mesh or Quad object to a Container. Fix #4338 #4343 (thanks @pfdtravalmatic @charmingny)
* `KeyboardPlugin.checkDown` would always fail if using the new event system, because the time value it was checking wasn't updated.
* Entering `Fullscreen` mode in the Scale Manager and then pressing ESC would leave the injected fullsceen div in the DOM, causing it to throw a node insertion failure the second time you wanted to enter fullscreen mode. Fix #4352 (thanks @ngdevr)
* Due to the changes in the Input event system, the `GAME_OUT` event would never fire unless the input system was in legacy mode. The OUT and OVER handlers have been refactored and will now fire as soon as the DOM event happens. As a result the `InputManager._emitIsOverEvent` property has been removed, as the native event is sent directly to the handler and doesn't need storing locally any more. Fix #4344 (thanks @RademCZ)
* Added `Zone.setBlendMode` method as a NOOP function, fixing a bug where if you added a Zone to a Container when running under Canvas it would fail. Fix #4295 (thanks @emanuel15)
### Examples, Documentation and TypeScript
My thanks to the following for helping with the Phaser 3 Examples, Docs and TypeScript definitions, either by reporting errors, fixing them or helping author the docs:
@maretana @CipSoft-Components @brian-lui
## Version 3.16.0 / 3.16.1 - Ishikawa - 5th February 2019
Phaser 3.16 is a massive update. The single largest in the history of Phaser 3 and it contains _breaking changes_. If you're upgrading from an earlier version please do check the log entries below.
Please note: there is no difference between 3.16.0 and 3.16.1. The version bump was just to get around a stupid npm semver policy.
### Important Namespace Changes
* The `Phaser.Boot` namespace has been renamed to `Phaser.Core`. As a result, the `boot` folder has been renamed to `core`. This impacts the `TimeStep` class and `VisibilityHandler` function, which have been moved to be under the new namespace.
* The `Phaser.Animations` namespace was incorrectly exposed in the Phaser entrypoints as `Animation` (note the lack of plural). This means that if you are creating any custom classes that extend Animation objects using the Phaser namespace, then please update them from `Phaser.Animation` to `Phaser.Animations`, i.e. `Phaser.Animation.AnimationFrame` to `Phaser.Animations.AnimationFrame`. This doesn't impact you if you created animations directly via the Animation Manager.
* The keyed Data Manager change data event string has changed from `changedata_` to `changedata-` to keep it consistent with other keyed events. Note the change from `_` to `-`.
* The Keyboard Plugin `keydown` dynamic event string has changed from `keydown_` to `keydown-` to keep it consistent with other keyed events. Note the change from `_` to `-`.
* The Keyboard Plugin `keyup` dynamic event string has changed from `keyup_` to `keyup-` to keep it consistent with other keyed events. Note the change from `_` to `-`.
* The `texturesready` event emitted by the Texture Manager has been renamed to `ready`.
* The `loadcomplete` event emitted by the Loader Plugin has been renamed to `postprocess` to be reflect what it's used for.
* Game Objects used to emit a `collide` event if they had an Arcade Physics Body with `onCollide` set, that collided with a Tile. This has changed. The event has been renamed to `tilecollide` and you should now listen for this event from the Arcade Physics World itself: `this.physics.world.on('tilecollide')`. Game Objects no longer emit this event.
* Game Objects used to emit an `overlap` event if they had an Arcade Physics Body with `onOverlap` set, that overlapped with a Tile. This has changed. The event has been renamed to `tileoverlap` and you should now listen for this event from the Arcade Physics World itself: `this.physics.world.on('tileoverlap')`. Game Objects no longer emit this event.
* The function `Phaser.Physics.Impact.SeperateX` has been renamed to `SeparateX` to correct the spelling mistake.
* The function `Phaser.Physics.Impact.SeperateY` has been renamed to `SeparateY` to correct the spelling mistake.
* The `ended` event in `WebAudioSound` has been renamed to `complete` to make it more consistent with the rest of the API.
* The `ended` event in `HTML5AudioSound` has been renamed to `complete` to make it more consistent with the rest of the API.
* The `Phaser.Utils.Objects` namespace was incorrectly exposed in the Phaser entrypoints as `Object` (note the lack of plural), this has now been fixed so all associated functions are properly namespaced.
* `Phaser.GameObjects.Blitter.Bob` has been renamed to `Phaser.GameObjects.Bob` to avoid namespace conflicts in TypeScript.
* `Phaser.GameObjects.Text.TextStyle` has been renamed to `Phaser.GameObjects.TextStyle` to avoid namespace conflicts in TypeScript.
### Important Changes to the Input System
In Phaser 3.15 and earlier the Input system worked using an event queue. All native DOM input events, such as from the Mouse, Touch or Keyboard, were picked up by event handlers and stored in a queue within the Input Manager. This queue was then processed during the next game step, all the events were dealt with and then it was cleared, ready to receive more events. As they were processed, the internal Phaser events such as `pointerdown` or `keyup` were dispatched to your game code.
This worked fine in that you were able to guarantee _exactly_ when the events would arrive, because it was always at the same time in the game step. However, it had the side effect of you not being able to do things like open external browser windows, or go into Full Screen mode, during your event handlers - because they weren't "real" events, so didn't pass the browser security checks. To this end, methods like `addUpCallback` were added to try and provide this support (although it was never possible for keyboard events).
In 3.16 this has changed. The DOM Events now trigger the respective internal events immediately, in the same invocation. So if you click on the canvas, the `pointerdown` event you receive in your game is still part of the 'native' event handler, so you're now free to do things like go into full screen mode, or open external windows, without any browser warnings or work-arounds.
It does, however, mean that the point at which these handlers are called is no longer always consistent, and is no longer bound to the speed of the Request Animation Frame update. We've tested as much as possible, and so far, things carry on working as before. We've noticed a slight increase in responsiveness, due to the removal of the fractional delay in processing the events, which feels good. However, if for whatever reason this change has broken your game then you're able to easily switch back to the previous version. In your Game Config, create an `input` object and give it the property `queue: true`. This will tell Phaser to use the legacy event queue system.
Please note that we _will_ remove this legacy system in the near future. So, please try and adapt your games to use the new system. If you've found an edge-case where something breaks because of it, please report it so we can look into it.
As a result of this change, the following are now deprecated:
* `InputPlugin.addUpCallback` method.
* `InputPlugin.addDownCallback` method.
* `InputPlugin.addMoveCallback` method.
* `InputManager.queue` property.
* `InputManager.domCallbacks` property.
* `InputManager._hasUpCallback` property.
* `InputManager._hasDownCallback` property.
* `InputManager._hasMoveCallback` property.
* `InputManager.processDomCallbacks` method.
* `InputManager.addUpCallback` method.
* `InputManager.addDownCallback` method.
* `InputManager.addMoveCallback` method.
### keydown and keyup changes
Due to unification across the event system, the `keydown_` and `keyup_` dynamic event strings have changed.
* In all cases the `keydown_KEY` event name has changed to `keydown-KEY`. Note the change from an underscore to a hyphen.
* In all cases the `keyup_KEY` event name has changed to `keyup-KEY`. Note the change from an underscore to a hyphen.
You should update your game code accordingly.
### Keyboard Input - New Features ### Keyboard Input - New Features
The specificity of the Keyboard events has been changed to allow you more control over event handling. Previously, the Keyboard Plugin would emit the global `keydown_CODE` event first (where CODE was a keycode string, like `keydown_A`), then it would emit the global `keydown` event. In previous versions, `Key` objects, created via `this.input.keyboard.addKey()`, didn't emit events. The specificity of the Keyboard events has been changed to allow you more control over event handling. Previously, the Keyboard Plugin would emit the global `keydown-CODE` event first (where CODE was a keycode string, like `keydown-A`), then it would emit the global `keydown` event. In previous versions, `Key` objects, created via `this.input.keyboard.addKey()`, didn't emit events.
The `Key` class now extends EventEmitter and emits two new events directly: `down` and `up`. This means you can listen for an event from a Key you've created, i.e.: `yourKey.on('up', handler)`. The `Key` class now extends EventEmitter and emits two new events directly: `down` and `up`. This means you can listen for an event from a Key you've created, i.e.: `yourKey.on('up', handler)`.
The order has also now changed. If it exists, the Key object will dispatch its `down` event first. Then the Keyboard Plugin will dispatch `keydown_CODE` and finally the least specific of them all, `keydown` will be dispatched. The order has also now changed. If it exists, the Key object will dispatch its `down` event first. Then the Keyboard Plugin will dispatch `keydown_CODE` and finally the least specific of them all, `keydown` will be dispatched.
You also now have the ability to cancel this at any stage either on a local or global level. All events handlers are sent an event object which you can call `event.stopImmediatePropagation()` on. This will immediately stop any further listeners from being invoked in the current Scene. Therefore, if you call `stopImmediatePropagation()` in the `Key.on` handler, then the Keyboard Plugin will not emit either the `keydown_CODE` or `keydown` global events. You can also call `stopImmediatePropagation()` during the `keydown_CODE` handler, to stop it reaching the global `keydown` handler. As `keydown` is last, calling it there has no effect. You also now have the ability to cancel this at any stage either on a local or global level. All event handlers are sent an event object which you can call `event.stopImmediatePropagation()` on. This will immediately stop any further listeners from being invoked in the current Scene. Therefore, if you call `stopImmediatePropagation()` in the `Key.on` handler, then the Keyboard Plugin will not emit either the `keydown-CODE` or `keydown` global events. You can also call `stopImmediatePropagation()` during the `keydown-CODE` handler, to stop it reaching the global `keydown` handler. As `keydown` is last, calling it there has no effect.
There is also the `stopPropagation()` function. This works in the same way as `stopImmediatePropagation` but instead of being local, it works across all of the Scenes in your game. For example, if you had 3 active Scenes (A, B and C, with A at the top of the Scene list), all listening for the same key, calling `stopPropagation()` in Scene A would stop the event from reaching any handlers in Scenes B or C. Remember that events flow down the Scene list from top to bottom. So, the top-most rendering Scene in the Scene list has priority over any Scene below it. There is also the `stopPropagation()` function. This works in the same way as `stopImmediatePropagation` but instead of being local, it works across all of the Scenes in your game. For example, if you had 3 active Scenes (A, B and C, with A at the top of the Scene list), all listening for the same key, calling `stopPropagation()` in Scene A would stop the event from reaching any handlers in Scenes B or C. Remember that events flow down the Scene list from top to bottom. So, the top-most rendering Scene in the Scene list has priority over any Scene below it.
@ -58,10 +210,11 @@ Default captures can be defined in the Game Config in the `input.keyboard.captur
#### Other Keyboard Updates and Fixes #### Other Keyboard Updates and Fixes
* There is a new class called `KeyboardManager`. This class is created by the global Input Manager, if keyboard access has been enabled in the Game config. It's responsible for handling all browser keyboard events. Previously, the `KeyboardPlugin` did this. Which meant that every Scene that had its own Keyboard Plugin was binding more native keyboard events. This was causing problems with parallel Scenes when needing to capture keys. the `KeyboardPlugin` class still exists, and is still the main point of interface when you call `this.input.keyboard` in a Scene, but DOM event handling responsibility has been taken away from it. This means there's no only * There is a new class called `KeyboardManager`. This class is created by the global Input Manager if keyboard access has been enabled in the Game config. It's responsible for handling all browser keyboard events. Previously, the `KeyboardPlugin` did this which meant that every Scene that had its own Keyboard Plugin was binding more native keyboard events. This was causing problems with parallel Scenes when needing to capture keys. the `KeyboardPlugin` class still exists, and is still the main point of interface when you call `this.input.keyboard` in a Scene, but DOM event handling responsibility has been taken away from it. This means there's now only
one set of bindings ever created, which makes things a lot cleaner. one set of bindings ever created, which makes things a lot cleaner.
* There is a new Game and Scene Config setting `input.keyboard.capture` which is an array of KeyCodes that the Keyboard Plugin will capture all non-modified key events on. By default it is empty. You can populate it in the config, or use the new capture methods. * There is a new Game and Scene Config setting `input.keyboard.capture` which is an array of KeyCodes that the Keyboard Plugin will capture all non-modified key events on. By default it is empty. You can populate it in the config, or use the new capture methods.
* The Keyboard Manager will now call `preventDefault` only on non-modified key presses, stopping the keyboard event from hitting the browser. Previously, capturing the R key, for example, would block a CTRL+R page reload, but it now ignores it because of the key modifier. * The Keyboard Manager will now call `preventDefault` only on non-modified key presses, stopping the keyboard event from hitting the browser. Previously, capturing the R key, for example, would block a CTRL+R page reload, but it now ignores it because of the key modifier.
* If the browser Window loses focus, either from switching to another app, or another tab, all active Keys will be reset. This prevents issues with keys still reporting as being held down after leaving the game and returning to it again. Fix #4134 (thanks @Simplonium)
* `Key.emitOnRepeat` is a new boolean property that controls if the Key will continuously emit a `down` event while being held down (true), or emit the event just once, on first press, and then skip future events (false). * `Key.emitOnRepeat` is a new boolean property that controls if the Key will continuously emit a `down` event while being held down (true), or emit the event just once, on first press, and then skip future events (false).
* `Key.setEmitOnRepeat` is a new chainable method for setting the `emitOnRepeat` property. * `Key.setEmitOnRepeat` is a new chainable method for setting the `emitOnRepeat` property.
* The `KeyboardPlugin.addKeys` method has a new optional boolean `emitOnRepeat` which sets that property on all Key objects it creates as part of the call. It defaults to `false`. * The `KeyboardPlugin.addKeys` method has a new optional boolean `emitOnRepeat` which sets that property on all Key objects it creates as part of the call. It defaults to `false`.
@ -83,60 +236,121 @@ one set of bindings ever created, which makes things a lot cleaner.
* `KeyboardPlugin.target` has been removed as it's no longer used by the class. * `KeyboardPlugin.target` has been removed as it's no longer used by the class.
* `KeyboardPlugin.queue` has been removed as it's no longer used by the class. * `KeyboardPlugin.queue` has been removed as it's no longer used by the class.
* `KeyboardPlugin.onKeyHandler` has been removed as it's no longer used by the class. * `KeyboardPlugin.onKeyHandler` has been removed as it's no longer used by the class.
* `KeyboardPlugin.startListeners` has been removed as it's no longer used by the class.
* `KeyboardPlugin.stopListeners` has been removed as it's no longer used by the class.
### Mouse and Touch Input - New Features, Updates and Fixes ### Mouse and Touch Input - New Features, Updates and Fixes
* The Mouse Manager class has been updated to remove some commented out code and refine the `startListeners` method. * The Mouse Manager class has been updated to remove some commented out code and refine the `startListeners` method.
* When enabling a Game Object for input it will now use the `width` and `height` properties of the Game Object first, falling back to the frame size if not found. This stops a bug when enabling BitmapText objects for input and it using the font texture as the hit area size, rather than the text itself. * When enabling a Game Object for input it will now use the `width` and `height` properties of the Game Object first, falling back to the frame size if not found. This stops a bug when enabling BitmapText objects for input and it using the font texture as the hit area size, rather than the text itself.
* `Pointer.smoothFactor` is a float-value that allows you to automatically apply smoothing to the Pointer position as it moves. This is ideal when you want something smoothly tracking a pointer in a game, or are need a smooth drawing motion for an art package. The default value is zero, meaning disabled. Set to a small number, such as 0.2, to enable. * `Pointer.smoothFactor` is a float-value that allows you to automatically apply smoothing to the Pointer position as it moves. This is ideal when you want something smoothly tracking a pointer in a game, or are need a smooth drawing motion for an art package. The default value is zero, meaning disabled. Set to a small number, such as 0.2, to enable.
* `Config.inputSmoothFactor` is a new property that allows you to set the smoothing factor for all Pointers the game creators. The default value is zero, which is disabled. Set in the game config as `input: { smoothFactor: value }`. * `Config.inputSmoothFactor` is a new property that allows you to set the smoothing factor for all Pointers the game creates. The default value is zero, which is disabled. Set in the game config as `input: { smoothFactor: value }`.
* `InputManager.transformPointer` has a new boolean argument `wasMove`, which controls if the pointer is being transformed after a move or up/down event. * `InputManager.transformPointer` has a new boolean argument `wasMove`, which controls if the pointer is being transformed after a move or up/down event.
* `Pointer.velocity` is a new Vector2 that contains the velocity of the Pointer, based on the current and previous positions. The velocity is smoothed out each frame, according to the `Pointer.motionFactor` property. This is done for more accurate gesture recognition. The velocity is updated based on Pointer movement, it doesn't require a button to be pressed first. * `Pointer.velocity` is a new Vector2 that contains the velocity of the Pointer, based on the current and previous positions. The velocity is smoothed out each frame according to the `Pointer.motionFactor` property. This is done for more accurate gesture recognition. The velocity is updated based on Pointer movement and doesn't require a button to be pressed first.
* `Pointer.angle` is a new property that contains the angle of the Pointer, in radians, based on the current and previous positions. The angle is smoothed out each frame, according to the `Pointer.motionFactor` property. This is done for more accurate gesture recognition. The angle is updated based on Pointer movement, it doesn't require a button to be pressed first. * `Pointer.angle` is a new property that contains the angle of the Pointer, in radians, based on the current and previous positions. The angle is smoothed out each frame according to the `Pointer.motionFactor` property. This is done for more accurate gesture recognition. The angle is updated based on Pointer movement and doesn't require a button to be pressed first.
* `Pointer.distance` is a new property that contains the distance of the Pointer, in radians, based on the current and previous positions. The distance is smoothed out each frame, according to the `Pointer.motionFactor` property. This is done for more accurate gesture recognition. The distance is updated based on Pointer movement, it doesn't require a button to be pressed first. * `Pointer.distance` is a new property that contains the distance of the Pointer, in radians, based on the current and previous positions. The distance is smoothed out each frame according to the `Pointer.motionFactor` property. This is done for more accurate gesture recognition. The distance is updated based on Pointer movement and doesn't require a button to be pressed first.
* `Pointer.motionFactor` is a new property that controls how much smoothing to apply to the Pointer positions each frame. This value is passed to the Smooth Step Interpolation that is used to calculate the velocity, angle and distance of the Pointer. It's applied every frame, until the midPoint reaches the current position of the Pointer. The default value is 0.2. * `Pointer.motionFactor` is a new property that controls how much smoothing to apply to the Pointer positions each frame. This value is passed to the Smooth Step Interpolation that is used to calculate the velocity, angle and distance of the Pointer. It's applied every frame until the midPoint reaches the current position of the Pointer. The default value is 0.2.
* The Input Plugin was emitting a `preUpdate` event, with the capital U, instead of `preupdate`. This has now been corrected. Fix #4185 (thanks @gadelan) * The Input Plugin was emitting a `preUpdate` event, with the capital U, instead of `preupdate`. This has now been corrected. Fix #4185 (thanks @gadelan)
* `Pointer.updateMotion` is a new method that is called automatically, each step, by the Input Manager. It's responsible for calculating the Pointer velocity, angle and distance properties. * `Pointer.updateMotion` is a new method that is called automatically, each step, by the Input Manager. It's responsible for calculating the Pointer velocity, angle and distance properties.
* `Pointer.time` is a new property that holds the time the Pointer was last updated by the Game step. * `Pointer.time` is a new property that holds the time the Pointer was last updated by the Game step.
* `Pointer.getDistance` has been updated. If called while a button is being held down, it will return the distance between the Pointer's current position and it's down position. If called when a Pointer doesn't have a button down, it will return the historic distance between the up and down positions. * `Pointer.getDistance` has been updated. If called while a button is being held down, it will return the distance between the Pointer's current position and it's down position. If called when a Pointer doesn't have a button down, it will return the historic distance between the up and down positions.
* `Pointer.getDistanceX` is a new method that will return the horizontal distance between the Pointer's previous and current coordinates. If called while a button is being held down, it will return the distance between the Pointer's current position and it's down position. If called when a Pointer doesn't have a button down, it will return the historic distance between the up and down positions. * `Pointer.getDistanceX` is a new method that will return the horizontal distance between the Pointer's previous and current coordinates. If called while a button is being held down, it will return the distance between the Pointer's current position and it's down position. If called when a Pointer doesn't have a button down, it will return the historic distance between the up and down positions.
* `Pointer.getDistanceY` is a new method that will return the horizontal distance between the Pointer's previous and current coordinates. If called while a button is being held down, it will return the distance between the Pointer's current position and it's down position. If called when a Pointer doesn't have a button down, it will return the historic distance between the up and down positions. * `Pointer.getDistanceY` is a new method that will return the horizontal distance between the Pointer's previous and current coordinates. If called while a button is being held down, it will return the distance between the Pointer's current position and it's down position. If called when a Pointer doesn't have a button down, it will return the historic distance between the up and down positions.
* `Pointer.getDuration` is a new method that will return the duration the Pointer was held down for. If the Pointer has a button pressed down at the time this method is called, it will return the duration since the Pointer's was pressed down. If no button is held down, it will return the last recorded duration, based on the time the Pointer button was released. * `Pointer.getDuration` is a new method that will return the duration the Pointer was held down for. If the Pointer has a button pressed down at the time this method is called, it will return the duration since the Pointer's button was pressed down. If no button is held down, it will return the last recorded duration, based on the time the Pointer button was released.
* `Pointer.getAngle` is a new method that will return the angle between the Pointer coordinates. If the Pointer has a button pressed down at the time this method is called, it will return the angle between the Pointer's `downX` and `downY` values and the current position. If no button is held down, it will return the last recorded angle, based on where the Pointer was when the button was released. * `Pointer.getAngle` is a new method that will return the angle between the Pointer coordinates. If the Pointer has a button pressed down at the time this method is called, it will return the angle between the Pointer's `downX` and `downY` values and the current position. If no button is held down, it will return the last recorded angle, based on where the Pointer was when the button was released.
* In previous versions, the VisibilityHandler would create a `mousedown` listener for the game canvas and then call `window.focus` when detected (assuming the game config `autoFocus` property was `true`). Responsibility for this has now been handled to the Mouse Manager `onMouseDown` handler. * In previous versions, the VisibilityHandler would create a `mousedown` listener for the game canvas and then call `window.focus` when detected (assuming the game config `autoFocus` property was `true`). Responsibility for this has now been moved to the Mouse Manager `onMouseDown` handler.
* In previous versions, the VisibilityHandler would create a `mouseout` listener for the game canvas and then set `game.isOver` when detected. Responsibility for this has now been handled to the Mouse Manager, which sets the new Input Manager `isOver` property directly. * In previous versions, the VisibilityHandler would create a `mouseout` listener for the game canvas and then set `game.isOver` when detected. Responsibility for this has now been moved to the Mouse Manager, which sets the new Input Manager `isOver` property directly.
* In previous versions, the VisibilityHandler would create a `mouseover` listener for the game canvas and then set `game.isOver` when detected. Responsibility for this has now been handled to the Mouse Manager, which sets the new Input Manager `isOver` property directly. * In previous versions, the VisibilityHandler would create a `mouseover` listener for the game canvas and then set `game.isOver` when detected. Responsibility for this has now been moved to the Mouse Manager, which sets the new Input Manager `isOver` property directly.
* The `Phaser.Game.isOver` property has been moved. You can now find it in the Input Manager and it's also accessible via the Input Plugin, which means you can do `this.input.isOver` from within a Scene. This makes more sense as it's input related and not a game level property. * The `Phaser.Game.isOver` property has been moved. You can now find it in the Input Manager and it's also accessible via the Input Plugin, which means you can do `this.input.isOver` from within a Scene. This makes more sense as it's input related and not a game level property.
* The Input Plugin has a new event you can listen to: `gameover`, which is triggered whenever the mouse or a pointer is moved over the Game canvas. Listen to it with `this.input.on('gameover')` from within a Scene. * The Input Plugin has a new event you can listen to: `gameover`, which is triggered whenever the mouse or a pointer is moved over the Game canvas. Listen to it with `this.input.on('gameover')` from within a Scene.
* The Input Plugin has a new event you can listen to: `gameout`, which is triggered whenever the mouse or a pointer leaves the Game canvas. Listen to it with `this.input.on('gameout')` from within a Scene. * The Input Plugin has a new event you can listen to: `gameout`, which is triggered whenever the mouse or a pointer leaves the Game canvas. Listen to it with `this.input.on('gameout')` from within a Scene.
* The Game used to emit a `mouseover` event when the mouse entered the game canvas. This is no longer emitted by the Game itself and can instead be listened for using the new Input Plugin event `gameover`. * The Game used to emit a `mouseover` event when the mouse entered the game canvas. This is no longer emitted by the Game itself and can instead be listened for using the new Input Plugin event `gameover`.
* The Game used to emit a `mouseout` event when the mouse left the game canvas. This is no longer emitted by the Game itself and can instead be listened for using the new Input Plugin event `gameout`. * The Game used to emit a `mouseout` event when the mouse left the game canvas. This is no longer emitted by the Game itself and can instead be listened for using the new Input Plugin event `gameout`.
* If the `window` object exists (which it will in normal browser environments) new `mouseup` and `touchend` event listeners are bound to it and trigger the normal `mouseup` or `touchend` events within the internal input system. This means if you will now get a `pointerup` event from the Input Plugin even if the pointer is released outside of the game canvas. Pointers will also no longer think they are still 'down' if released outside the canvas and then moved inside again in their new state. * If the `window` object exists (which it will in normal browser environments) new `mouseup` and `touchend` event listeners are bound to it and trigger the normal `mouseup` or `touchend` events within the internal input system. This means you will now get a `pointerup` event from the Input Plugin even if the pointer is released outside of the game canvas. Pointers will also no longer think they are still 'down' if released outside the canvas and then moved inside again in their new state.
* The window will now have focus called on it by the Touch Manager, as well as the Mouse Manager, is the `autoFocus` game config property is enabled. * The window will now have focus called on it by the Touch Manager, as well as the Mouse Manager, if the `autoFocus` game config property is enabled.
* The Input Plugin has a new event you can listen to: `pointerdownoutside`, which is triggered whenever the mouse or a pointer is pressed down while outside of the Game canvas. Listen to it with `this.input.on('pointerdownoutside')` from within a Scene. * The Input Plugin has a new event you can listen to: `pointerdownoutside`, which is triggered whenever the mouse or a pointer is pressed down while outside of the Game canvas. Listen to it with `this.input.on('pointerdownoutside')` from within a Scene.
* The Input Plugin has a new event you can listen to: `pointerupoutside`, which is triggered whenever the mouse or a pointer is released while outside of the Game canvas. Listen to it with `this.input.on('pointerupoutside')` from within a Scene. * The Input Plugin has a new event you can listen to: `pointerupoutside`, which is triggered whenever the mouse or a pointer is released while outside of the Game canvas. Listen to it with `this.input.on('pointerupoutside')` from within a Scene.
* `Pointer.downElement` is a new property that holds the target of the DOM Event that triggered when the Pointer was pressed down. If this is within the game, this will be the game canvas element. * `Pointer.downElement` is a new property that holds the target of the DOM Event that triggered when the Pointer was pressed down. If this is within the game, this will be the game canvas element.
* `Pointer.upElement` is a new property that holds the target of the DOM Event that triggered when the Pointer was released. If this is within the game, this will be the game canvas element. * `Pointer.upElement` is a new property that holds the target of the DOM Event that triggered when the Pointer was released. If this is within the game, this will be the game canvas element.
* The `Pointer.dragState` property has been removed. This is no longer used internally as it has to be tracked per Scene, not on a global level.
* `InputPlugin.setDragState` is a new internal method that sets the drag state for the given Pointer.
* `InputPlugin.getDragState` is a new internal method that gets the drag state for the given Pointer.
* Draggable Game Objects would not work if you had multiple Scenes running in parallel, with draggable objects in both of them. Only the top-most Scene would work fully. Items in the bottom Scene would never finish their drag cycle, causing them to get stuck. Fix #4249 #4278 (thanks @probt @iArePJ)
* `Pointer.leftButtonDown` will now return an actual boolean, rather than the result of the bitwise op (which still evaluated as a boolean, but this is cleaner).
* `Pointer.rightButtonDown` will now return an actual boolean, rather than the result of the bitwise op (which still evaluated as a boolean, but this is cleaner).
* `Pointer.middleButtonDown` will now return an actual boolean, rather than the result of the bitwise op (which still evaluated as a boolean, but this is cleaner).
* `Pointer.backButtonDown` will now return an actual boolean, rather than the result of the bitwise op (which still evaluated as a boolean, but this is cleaner).
* `Pointer.forwardButtonDown` will now return an actual boolean, rather than the result of the bitwise op (which still evaluated as a boolean, but this is cleaner).
* `Pointer.up`, `Pointer.move` and `Pointer.down` now use `in` to check for the existance of the `buttons` property on the event, causing it to be set even if equal to zero, which it is when there are no buttons down. This also fixes an issue where the buttons didn't update during a move event (thanks @SonnyCampbell @rexrainbow)
### Changes as a result of the new Scale Manager
3.16 introduces the completed Scale Manager. This is fully documented, but the class, all methods and all properties. It also includes a folder full of examples in the Phaser Labs, so you're strongly recommended to start there.
* If you set the Game Config property `zoom` to be > 1 then it will automatically enable `pixelArt` mode, unless you set `pixelArt: false` in the config.
* There is a new property in the Game Config called `autoRound`, which controls if the canvas size and style sizes are passed through Math.floor or not. On some devices this can help with performance and anti-aliasing. The default is `false` (turned off).
* The Game Config property `autoResize` has been removed as it's now redundant.
* The WebGL and Canvas Renderers no longer change the Canvas size in their `resize` methods. They just update internal properties.
* The WebGL and Canvas Renderers now read the `width`, `height` and `resolution` values from the Scale Manager, not the Game Config.
* `CameraManager.baseScale` property has been removed as it's no longer used anywhere.
* The BaseCamera and Camera `preRender` methods now only take a resolution argument and use it internally for their transforms.
* `InputManager.scaleManager` is a new property that is a reference to the Scale Manager. This is populated in the `boot` method.
* The `InputManager.transformX` method has been removed. This is now available in the ScaleManager.
* The `InputManager.transformY` method has been removed. This is now available in the ScaleManager.
* The `InputManager.scale` property has been removed. This is now available in the ScaleManager under `displayScale`.
* The `InputManager.resize` method has been removed as this process is now handled by the ScaleManager.
* The `InputManager.bounds` property has been removed as this process is now handled by the ScaleManager.
* The `InputManager.updateBounds` method has been removed as this process is now handled by the ScaleManager.
* The `InputManager.getOffsetX` method has been removed as it's no longer required.
* The `InputManager.getOffsetY` method has been removed as it's no longer required.
* The `InputManager.getScaleX` method has been removed as it's no longer required.
* The `InputManager.getScaleY` method has been removed as it's no longer required.
* The `SceneManager.resize` method has been removed as it's no longer required.
* The `Scene.Systems.resize` method has been removed as it's no longer required.
* Scenes will no longer dispatch the `resize` event. You should now listen for this event from the Scale Manager instead.
* `BaseCamera.config` has been removed as it's no longer required.
* `BaseCamera.scaleManager` is a new property that references the Scale Manager and is used internally for size checks.
* The `Game.resize` method has been removed as it's no longer required. You should now call `ScaleManager.resize` instead.
* The Game will no longer dispatch the `resize` event. You should now listen for this event from the Scale Manager instead.
### Facebook Instant Games Updates and Fixes
* Added the `Leaderboard.getConnectedScores` method, to get a list of scores from player connected entries.
* The `loadPlayerPhoto` function in the Instant Games plugin now listens for the updated Loader event correctly, causing the `photocomplete` event to fire properly.
* `Leaderboard.setScore` now emits the LeaderboardScore object with the `setscore` event, as the documentation said it did.
* `Leaderboard.getPlayerScore` now only populates the `playerScore` property if the entry isn't `null`.
* If the `setScore` or `getPlayerScore` calls fail, it will return `null` as the score instance, instead of causing a run-time error.
* You can now pass an object or a string to `setScore` and objects will be automatically stringified.
* The `preloadAds` method will now only create an AdInstance object if the interstitial `loadSync` promise resolves.
* The `preloadVideoAds` method will now only create an AdInstance object if the interstitial `loadSync` promise resolves.
* The `preloadAds` method will now emit the `adsnofill` event, if there are no ads in the inventory to load.
* The `preloadVideoAds` method will now emit the `adsnofill` event, if there are no ads in the inventory to load.
* The `showAd` method will now emit the `adsnotloaded` event, if there are no ads loaded matching the given Placement ID.
* The `showVideo` method will now emit the `adsnotloaded` event, if there are no ads loaded matching the given Placement ID.
* Showing an ad will emit the `adfinished` event when the ad is closed, previously this event was called `showad` but the new name better reflects what has happened.
* The Facebook Plugin is now available in the `Phaser.Scene` class template under the `facebook` property (thanks @bryanwood)
* Fixed the `Leaderboard.getScores` method to now take the arguments into account. Fix #4271 (thanks @Oramy)
* Fixed an API validation error in the `chooseContext` method. Fix #4248 (thanks @yadurajiv)
### New Features ### New Features
* You can now load external Scene files using the new `load.sceneFile` method. This allows you to dynamically load a Scene into the Scene Manager of your game, and swap to it at will. Please see the documentation and examples for further details. * You can now load external Scene files using the new `load.sceneFile` method. This allows you to dynamically load a Scene into the Scene Manager of your game, and swap to it at will. Please see the documentation and examples for further details.
* The data object being sent to the Dynamic Bitmap Text callback now has a new property `parent`, which is a reference to the Bitmap Text instance that owns the data object (thanks ornyth) * The data object being sent to the Dynamic Bitmap Text callback now has a new property `parent`, which is a reference to the Bitmap Text instance that owns the data object (thanks ornyth)
* The WebGL Renderer has a new method `clearPipeline`, which will clear down the current pipeline and reset the blend mode, ready for the context to be passed to a 3rd party library. * The WebGL Renderer has a new method `clearPipeline`, which will clear down the current pipeline and reset the blend mode, ready for the context to be passed to a 3rd party library.
* The WebGL Renderer has a new method `rebindPipeline`, which will rebind the given pipeline instance, reset the blank texture and reset the blend mode. Which is useful for recovering from 3rd party libs that have modified the gl context. * The WebGL Renderer has a new method `rebindPipeline`, which will rebind the given pipeline instance, reset the blank texture and reset the blend mode. This is useful for recovering from 3rd party libs that have modified the gl context.
* Game Objects have a new property called `state`. Use this to track the state of a Game Object during its lifetime. For example, it could move from a state of 'moving', to 'attacking', to 'dead'. Phaser itself will never set this property, although plugins are allowed to. * Game Objects have a new property called `state`. Use this to track the state of a Game Object during its lifetime. For example, it could move from a state of 'moving', to 'attacking', to 'dead'. Phaser itself will never set this property, although plugins are allowed to.
* Game Objects have a new method called `setState` which will set the state property in a chainable call. * Game Objects have a new method called `setState` which will set the state property in a chainable call.
* `BlendModes.ERASE` is a new blend mode that will erase the object being drawn. When used in conjunction with a Render Texture it allows for effects that let you erase parts of the texture, in either Canvas or WebGL. When used with a transparent game canvas, it allows you to erase parts of the canvas, showing the web page background through. * `BlendModes.ERASE` is a new blend mode that will erase the object being drawn. When used in conjunction with a Render Texture it allows for effects that require you to erase parts of the texture, in either Canvas or WebGL. When used with a transparent game canvas, it allows you to erase parts of the canvas, showing the web page background through.
* `BlendModes.SOURCE_IN` is a new Canvas-only blend mode, that allows you to use the `source-in` composite operation when rendering Game Objects. * `BlendModes.SOURCE_IN` is a new Canvas-only blend mode that allows you to use the `source-in` composite operation when rendering Game Objects.
* `BlendModes.SOURCE_OUT` is a new Canvas-only blend mode, that allows you to use the `source-out` composite operation when rendering Game Objects. * `BlendModes.SOURCE_OUT` is a new Canvas-only blend mode that allows you to use the `source-out` composite operation when rendering Game Objects.
* `BlendModes.SOURCE_ATOP` is a new Canvas-only blend mode, that allows you to use the `source-atop` composite operation when rendering Game Objects. * `BlendModes.SOURCE_ATOP` is a new Canvas-only blend mode that allows you to use the `source-atop` composite operation when rendering Game Objects.
* `BlendModes.DESTINATION_OVER` is a new Canvas-only blend mode, that allows you to use the `destination-over` composite operation when rendering Game Objects. * `BlendModes.DESTINATION_OVER` is a new Canvas-only blend mode that allows you to use the `destination-over` composite operation when rendering Game Objects.
* `BlendModes.DESTINATION_IN` is a new Canvas-only blend mode, that allows you to use the `destination-in` composite operation when rendering Game Objects. * `BlendModes.DESTINATION_IN` is a new Canvas-only blend mode that allows you to use the `destination-in` composite operation when rendering Game Objects.
* `BlendModes.DESTINATION_OUT` is a new Canvas-only blend mode, that allows you to use the `destination-out` composite operation when rendering Game Objects. * `BlendModes.DESTINATION_OUT` is a new Canvas-only blend mode that allows you to use the `destination-out` composite operation when rendering Game Objects.
* `BlendModes.DESTINATION_ATOP` is a new Canvas-only blend mode, that allows you to use the `destination-atop` composite operation when rendering Game Objects. * `BlendModes.DESTINATION_ATOP` is a new Canvas-only blend mode that allows you to use the `destination-atop` composite operation when rendering Game Objects.
* `BlendModes.LIGHTER` is a new Canvas-only blend mode, that allows you to use the `lighter` composite operation when rendering Game Objects. * `BlendModes.LIGHTER` is a new Canvas-only blend mode that allows you to use the `lighter` composite operation when rendering Game Objects.
* `BlendModes.COPY` is a new Canvas-only blend mode, that allows you to use the `copy` composite operation when rendering Game Objects. * `BlendModes.COPY` is a new Canvas-only blend mode that allows you to use the `copy` composite operation when rendering Game Objects.
* `BlendModes.XOR` is a new Canvas-only blend mode, that allows you to use the `xor` composite operation when rendering Game Objects. * `BlendModes.XOR` is a new Canvas-only blend mode that allows you to use the `xor` composite operation when rendering Game Objects.
* `RenderTexture.erase` is a new method that will take an object, or array of objects, and draw them to the Render Texture using an ERASE blend mode, resulting in them being removed from the Render Texture. This is really handy for making a bitmap masked texture in Canvas or WebGL (without using an actual mask), or for 'cutting away' part of a texture. * `RenderTexture.erase` is a new method that will take an object, or array of objects, and draw them to the Render Texture using an ERASE blend mode, resulting in them being removed from the Render Texture. This is really handy for making a bitmap masked texture in Canvas or WebGL (without using an actual mask), or for 'cutting away' part of a texture.
* There is a new boolean Game Config property called `customEnvironment`. If set to `true` it will skip the internal Feature checks when working out which type of renderer to create, allowing you to run Phaser under non-native web environments. If using this value, you _must_ set an explicit `renderType` of either CANVAS or WEBGL. It cannot be left as AUTO. Fix #4166 (thanks @jcyuan) * There is a new boolean Game Config property called `customEnvironment`. If set to `true` it will skip the internal Feature checks when working out which type of renderer to create, allowing you to run Phaser under non-native web environments. If using this value, you _must_ set an explicit `renderType` of either CANVAS or WEBGL. It cannot be left as AUTO. Fix #4166 (thanks @jcyuan)
* `Animation.nextFrame` will advance an animation to the next frame in the sequence instantly, regardless of the animation time or state. You can call this on a Sprite: `sprite.anims.nextFrame()` (thanks rgk25) * `Animation.nextFrame` will advance an animation to the next frame in the sequence instantly, regardless of the animation time or state. You can call this on a Sprite: `sprite.anims.nextFrame()` (thanks rgk25)
@ -145,8 +359,8 @@ one set of bindings ever created, which makes things a lot cleaner.
* `Geom.Line.GetNearestPoint` is a new static method that will return the nearest point on a line to the given point. * `Geom.Line.GetNearestPoint` is a new static method that will return the nearest point on a line to the given point.
* `Geom.Line.GetShortestDistance` is a new static method that will return the shortest distance from a line to the given point. * `Geom.Line.GetShortestDistance` is a new static method that will return the shortest distance from a line to the given point.
* `Camera.getBounds` is a new method that will return a rectangle containing the bounds of the camera. * `Camera.getBounds` is a new method that will return a rectangle containing the bounds of the camera.
* `Camera.centerOnX` will move the camera horizontally to be centered on the given coordinate, without changing its vertical placement. * `Camera.centerOnX` will move the camera horizontally to be centered on the given coordinate without changing its vertical placement.
* `Camera.centerOnY` will move the camera vertically to be centered on the given coordinate, without changing its horizontally placement. * `Camera.centerOnY` will move the camera vertically to be centered on the given coordinate without changing its horizontally placement.
* `AnimationManager.exists` is a new method that will check to see if an Animation using the given key already exists or not and returns a boolean. * `AnimationManager.exists` is a new method that will check to see if an Animation using the given key already exists or not and returns a boolean.
* `animationstart-key` is a new Animation key specific event emitted by a Game Object. For example, if you had an animation with a key of 'explode' you can now listen for `animationstart-explode`. * `animationstart-key` is a new Animation key specific event emitted by a Game Object. For example, if you had an animation with a key of 'explode' you can now listen for `animationstart-explode`.
* `animationrestart-key` is a new Animation key specific event emitted by a Game Object. For example, if you had an animation with a key of 'explode' you can now listen for `animationrestart-explode`. * `animationrestart-key` is a new Animation key specific event emitted by a Game Object. For example, if you had an animation with a key of 'explode' you can now listen for `animationrestart-explode`.
@ -163,6 +377,29 @@ one set of bindings ever created, which makes things a lot cleaner.
* `CanvasTexture.setPixel` is a new method that sets the given pixel in the CanvasTexture to the color and alpha values provided. * `CanvasTexture.setPixel` is a new method that sets the given pixel in the CanvasTexture to the color and alpha values provided.
* `CanvasTexture.getData` is a new method that will extract an ImageData block from the CanvasTexture from the region given. * `CanvasTexture.getData` is a new method that will extract an ImageData block from the CanvasTexture from the region given.
* `CanvasTexture.putData` is a new method that will put an ImageData block at the given coordinates in a CanvasTexture. * `CanvasTexture.putData` is a new method that will put an ImageData block at the given coordinates in a CanvasTexture.
* `Line.Extend` is a new static function that allows you extend the start and/or end points of a Line by the given amounts.
* `Vector2.LEFT` is a new constant that can be used in Vector comparison operations (thanks @Aedalus)
* `Vector2.RIGHT` is a new constant that can be used in Vector comparison operations (thanks @Aedalus)
* `Vector2.UP` is a new constant that can be used in Vector comparison operations (thanks @Aedalus)
* `Vector2.DOWN` is a new constant that can be used in Vector comparison operations (thanks @Aedalus)
* `Vector2.ONE` is a new constant that can be used in Vector comparison operations (thanks @Aedalus)
* `Vector3.ZERO` is a new constant that can be used in Vector comparison operations (thanks @Aedalus)
* `Vector3.LEFT` is a new constant that can be used in Vector comparison operations (thanks @Aedalus)
* `Vector3.RIGHT` is a new constant that can be used in Vector comparison operations (thanks @Aedalus)
* `Vector3.UP` is a new constant that can be used in Vector comparison operations (thanks @Aedalus)
* `Vector3.DOWN` is a new constant that can be used in Vector comparison operations (thanks @Aedalus)
* `Vector3.FORWARD` is a new constant that can be used in Vector comparison operations (thanks @Aedalus)
* `Vector3.BACK` is a new constant that can be used in Vector comparison operations (thanks @Aedalus)
* `Vector3.ONE` is a new constant that can be used in Vector comparison operations (thanks @Aedalus)
* Geometery Mask has a new property called `invertAlpha` in WebGL, which works in the same way as the flag on the Bitmap Mask and allows you to invert the function of the stencil buffer, i.e. non-drawn shapes become invisible, and drawn shapes visible (thanks @tfelix)
* The Arcade Physics Body has a new property `maxSpeed` which limits the vector length of the Body velocity. You can set it via the method `setMaxSpeed` and it is applied in the `World.computeVelocity` method (thanks @Edwin222 @rexrainbow)
* `WebGLRenderer.snapshotArea` is a new method that allows you to grab an image of the given region of the canvas during the post-render step and have it sent to your defined callback. This is the same as `snapshot` except you control the area being grabbed, so is more efficient if you only need a smaller area.
* `WebGLRenderer.snapshotPixel` is a new method that allows you to grab a single pixel from the game canvas, post-render. It returns the result as a `Color` object to your specified callback.
* `CanvasRenderer.snapshotArea` is a new method that allows you to grab an image of the given region of the canvas during the post-render step and have it sent to your defined callback. This is the same as `snapshot` except you control the area being grabbed, so is more efficient if you only need a smaller area.
* `CanvasRenderer.snapshotPixel` is a new method that allows you to grab a single pixel from the game canvas, post-render. It returns the result as a `Color` object to your specified callback.
* `SceneManager.getScenes` is a new method that will return all current Scenes being managed by the Scene Manager. You can optionally return only active scenes and reverse the order in which they are returned in the array.
* `DOM.GetTarget` is a new helper function that will return a reference to a DOM Element based on the given string or node.
* `GameObjects.Extern` is a new special type of Game Object that allows you to pass rendering off to a 3rd party. When you create an Extern and place it in the display list of a Scene, the renderer will process the list as usual. When it finds an Extern it will flush the current batch, clear down the pipeline and prepare a transform matrix which your render function can take advantage of, if required. The Extern Game Object is used heavily by the Spine Plugin, but can also be used by other libraries such as three.js, allowing them to render directly into a Phaser game.
### Updates ### Updates
@ -176,8 +413,8 @@ one set of bindings ever created, which makes things a lot cleaner.
* MATH_CONST no longer requires or sets the Random Data Generator, this is now done in the Game Config, allowing you to require the math constants without pulling in a whole copy of the RNG with it. * MATH_CONST no longer requires or sets the Random Data Generator, this is now done in the Game Config, allowing you to require the math constants without pulling in a whole copy of the RNG with it.
* The Dynamic Bitmap Text Canvas Renderer was creating a new data object every frame for the callback. It now uses the `callbackData` object instead, like the WebGL renderer does. * The Dynamic Bitmap Text Canvas Renderer was creating a new data object every frame for the callback. It now uses the `callbackData` object instead, like the WebGL renderer does.
* `WebGLRenderer.setBlendMode` has a new optional argument `force`, which will force the given blend mode to be set, regardless of the current settings. * `WebGLRenderer.setBlendMode` has a new optional argument `force`, which will force the given blend mode to be set, regardless of the current settings.
* The method `DisplayList.sortGameObjects` has been removed. It has thrown a runtime error since v3.3.0! which no-one even spotted, a good indication of how little the method is used. The display list is automatically sorted anyway, so if you need to sort a small section of it, just use the standard JavaScript Array sort method (thanks ornyth) * The method `DisplayList.sortGameObjects` has been removed. It has thrown a runtime error since v3.3.0(!) which no-one even spotted which is a good indication of how little the method was used. The display list is automatically sorted anyway, so if you need to sort a small section of it, just use the standard JavaScript Array sort method (thanks ornyth)
* The method `DisplayList.getTopGameObject` has been removed. It has thrown a runtime error since v3.3.0! which no-one even spotted, a good indication of how little the method is used (thanks ornyth) * The method `DisplayList.getTopGameObject` has been removed. It has thrown a runtime error since v3.3.0(!) which no-one even spotted which is a good indication of how little the method was used (thanks ornyth)
* `WebGLRenderer.setFramebuffer` has a new optional boolean argument `updateScissor`, which will reset the scissor to match the framebuffer size, or clear it. * `WebGLRenderer.setFramebuffer` has a new optional boolean argument `updateScissor`, which will reset the scissor to match the framebuffer size, or clear it.
* `WebAudioSoundManager.onFocus` will not try to resume the Audio Context if it's still locked. * `WebAudioSoundManager.onFocus` will not try to resume the Audio Context if it's still locked.
* `WebAudioSoundManager.onBlur` will not try to suspend the Audio Context if it's still locked. * `WebAudioSoundManager.onBlur` will not try to suspend the Audio Context if it's still locked.
@ -203,6 +440,24 @@ one set of bindings ever created, which makes things a lot cleaner.
* `WebGLRenderer.pushScissor` now has a new optional argument `drawingBufferHeight` which allows you to specify the drawing buffer height, rather than use the renderers default value. * `WebGLRenderer.pushScissor` now has a new optional argument `drawingBufferHeight` which allows you to specify the drawing buffer height, rather than use the renderers default value.
* `WebGLRenderer.preRender` now calls `gl.clearColor` in order to restore the background clear color in case something, like a Render Texture, has changed it. * `WebGLRenderer.preRender` now calls `gl.clearColor` in order to restore the background clear color in case something, like a Render Texture, has changed it.
* `Map.set` will now update an existing value if you provide it with a key that already exists within the Map. Previously, if you tried to set the value of a key that existed it would be skipped. * `Map.set` will now update an existing value if you provide it with a key that already exists within the Map. Previously, if you tried to set the value of a key that existed it would be skipped.
* `MatterSprite` would set its `type` property to be `Image`. It now sets it to be `Sprite` as it should do.
* `Matter.TileBody.setFromTileCollision` no longer checks if the shape is concave or convex before modifying the vertices, as the update to the Matter.js lib in 3.12 stopped this from working with Tiled collision shapes.
* The Scene `transitionstart` event is now dispatched by the Target Scene of a transition, regardless if the Scene has a `create` method or not. Previously, it was only dispatched if the Scene had a create method.
* The Loader will now allow an XHR status of 0 as success too. Normally only status 200 would be accepted as success, but 0 is returned when a file is loaded from the local filesystem (file://). This happens, for example, when opening the index.html of a game in a browser directly, or when using Cordova on iOS. Fix #3464 (thanks @Ithamar)
* `Tween.restart` now returns the Tween instance (thanks @rexrainbow)
* `Tween.play` now returns the Tween instance (thanks @rexrainbow)
* `Tween.seek` now returns the Tween instance (thanks @rexrainbow)
* `Tween.complete` now returns the Tween instance (thanks @rexrainbow)
* `Tween.stop` now returns the Tween instance (thanks @rexrainbow)
* `List.sort` now has an optional parameter `handler` which allows you to provide your own sort handling function (thanks @jcyuan)
* `Container.sort` now has an optional parameter `handler` which allows you to provide your own sort handling function (thanks @jcyuan)
* The WebGLRenderer method `canvasToTexture` will now only set the filter to be `NEAREST` if `antialias` is disabled in the game config (i.e. when running in pixelArt mode). This means that Text objects, and other Canvas backed textures, now render with anti-aliasing if everything else does. You can disable this on a per-object basis by calling `texture.setFilter(1)` on them.
* `CanvasRenderer.snapshotCallback`, `snapshotType` and `snapshotEncoder` have all been removed as they are no longer required.
* `CanvasRenderer.snapshotState` is a new object that contains the snapshot configuration data, the same as the WebGL Renderer.
* The signature of the `WebGLSnapshot` function has changed. It now takes a Snapshot Configuration object as the second parameter.
* The signature of the `CanvasSnapshot` function has changed. It now takes a Snapshot Configuration object as the second parameter.
* A Tween Timeline will now set it's internal destroy state _before_ calling either the `onComplete` callback or sending the `COMPLETE` event. This means you can now call methods that will change the state of the Timeline, such as `play`, during the callback handlers, where-as before doing this would have had the internal state changed immediately, preventing it (thanks Lucas Knight)
* The `AddToDOM` method has had the `overflowHidden` argument removed. The DOM element the canvas is inserted into no longer has `overflow: hidden` applied to its style. If you wish to have this, please add it directly via CSS.
### Bug Fixes ### Bug Fixes
@ -212,7 +467,7 @@ one set of bindings ever created, which makes things a lot cleaner.
* Disabling camera bounds and then moving the camera to an area in a Tilemap that did not have any tile information would throw an `Uncaught Reference error` as it tried to access tiles that did not exist (thanks @Siyalatas) * Disabling camera bounds and then moving the camera to an area in a Tilemap that did not have any tile information would throw an `Uncaught Reference error` as it tried to access tiles that did not exist (thanks @Siyalatas)
* Fixed an issue where Sprite Sheets being extracted from a texture atlas would fail if the sheet was either just a single column or single row of sprites. Fix #4096 (thanks @Cirras) * Fixed an issue where Sprite Sheets being extracted from a texture atlas would fail if the sheet was either just a single column or single row of sprites. Fix #4096 (thanks @Cirras)
* If you created an Arcade Physics Group without passing a configuration object, and passing an array of non-standard children, it would throw a classType runtime error. It now creates a default config object correctly (thanks @pierpo) * If you created an Arcade Physics Group without passing a configuration object, and passing an array of non-standard children, it would throw a classType runtime error. It now creates a default config object correctly (thanks @pierpo)
* The `Camera.cull` method has been restructured so it now calculates if a Game Object is correctly in view or not, before culling it. Although not used internally, if you need to cull objects for a camera, you can now safely use this method. Fix #4092 (thanks @Cirras) * The `Camera.cull` method has been restructured so it now calculates if a Game Object is correctly in view or not before culling it. Although not used internally, if you need to cull objects for a camera, you can now safely use this method. Fix #4092 (thanks @Cirras)
* The Tiled Parser would ignore animated tile data if it was in the new Tiled 1.2 format. This is now accounted for, as well as 1.0 (thanks @nkholski) * The Tiled Parser would ignore animated tile data if it was in the new Tiled 1.2 format. This is now accounted for, as well as 1.0 (thanks @nkholski)
* `Array.Matrix.ReverseRows` was actually reversing the columns, but now reverses the rows. * `Array.Matrix.ReverseRows` was actually reversing the columns, but now reverses the rows.
* `Array.Matrix.ReverseColumns` was actually reversing the rows, but now reverses the columns. * `Array.Matrix.ReverseColumns` was actually reversing the rows, but now reverses the columns.
@ -221,52 +476,62 @@ one set of bindings ever created, which makes things a lot cleaner.
* Render Textures created larger than the size of the default canvas would be automatically clipped when drawn to in WebGL. They now reset the gl scissor and drawing height property in order to draw to their full size, regardless of the canvas size. Fix #4139 (thanks @chaoyang805 @iamchristopher) * Render Textures created larger than the size of the default canvas would be automatically clipped when drawn to in WebGL. They now reset the gl scissor and drawing height property in order to draw to their full size, regardless of the canvas size. Fix #4139 (thanks @chaoyang805 @iamchristopher)
* The `cameraFilter` property of a Game Object will now allow full bitmasks to be set (a value of -1), instead of just those > 0 (thanks @stuartkeith) * The `cameraFilter` property of a Game Object will now allow full bitmasks to be set (a value of -1), instead of just those > 0 (thanks @stuartkeith)
* The `PathFollower.startFollow` method now properly uses the `startAt` argument to the method, so you can start a follower off at any point along the path. Fix #3688 (thanks @DannyT @diteix) * The `PathFollower.startFollow` method now properly uses the `startAt` argument to the method, so you can start a follower off at any point along the path. Fix #3688 (thanks @DannyT @diteix)
* Static Circular Arcade Physics Bodies now render as circles in the debug display, instead of showing their rectangle bounds (thanks @maikthomas) * Static Circular Arcade Physics Bodies now render as circles in the debug display instead of showing their rectangle bounds (thanks @maikthomas)
* Changing the mute flag on an `HTML5AudioSound` instance, via the `mute` setter, now works, as it does via the Sound Manager (thanks @Waclaw-I @neon-dev) * Changing the mute flag on an `HTML5AudioSound` instance, via the `mute` setter, now works as it does via the Sound Manager (thanks @Waclaw-I @neon-dev)
* Changing the volume on an `HTML5AudioSound` instance, via the `volume` setter, now works, as it does via the Sound Manager (thanks @Waclaw-I) * Changing the volume on an `HTML5AudioSound` instance, via the `volume` setter, now works as it does via the Sound Manager (thanks @Waclaw-I)
* The Dynamic Tilemap Layer WebGL renderer was drawing tiles at the incorrect position if the layer was scaled. Fix #4104 (thanks @the-realest-stu) * The Dynamic Tilemap Layer WebGL renderer was drawing tiles at the incorrect position if the layer was scaled. Fix #4104 (thanks @the-realest-stu)
* `Tile.tileset` now returns the specific Tileset associated with the tile, rather than an array of them. Fix #4095 (thanks @quadrupleslap) * `Tile.tileset` now returns the specific Tileset associated with the tile rather than an array of them. Fix #4095 (thanks @quadrupleslap)
* `Tile.getCollisionGroup` wouldn't return the correct Group after the change to support multiple Tilesets. It now returns the group properly (thanks @jbpuryear) * `Tile.getCollisionGroup` wouldn't return the correct Group after the change to support multiple Tilesets. It now returns the group properly (thanks @jbpuryear)
* `Tile.getTileData` wouldn't return the correct data after the change to support multiple Tilesets. It now returns the tile data properly (thanks @jbpuryear) * `Tile.getTileData` wouldn't return the correct data after the change to support multiple Tilesets. It now returns the tile data properly (thanks @jbpuryear)
* The `GetTileAt` and `RemoveTileAt` components would error with "Cannot read property 'index' of undefined" if the tile was undefined rather than null. It now handles both cases (thanks @WaSa42) * The `GetTileAt` and `RemoveTileAt` components would error with "Cannot read property 'index' of undefined" if the tile was undefined rather than null. It now handles both cases (thanks @WaSa42)
* Changing `TileSprite.width` or `TileSprite.height` will now flag the texture as dirty and call `updateDisplayOrigin`, allowing you to resize TileSprites dynamically in both Canvas and WebGL. * Changing `TileSprite.width` or `TileSprite.height` will now flag the texture as dirty and call `updateDisplayOrigin`, allowing you to resize TileSprites dynamically in both Canvas and WebGL.
* `RandomDataGenerator.shuffle` has been fixed to use the proper modifier in the calculation, allowing for a more even distribution (thanks wayfinder) * `RandomDataGenerator.shuffle` has been fixed to use the proper modifier in the calculation allowing for a more even distribution (thanks wayfinder)
* The Particle Emitter was not recycling dead particles correctly, so it was creating new objects every time it emitted (the old particles were then left to the browsers gc to clear up). This has now been recoded, so the emitter will properly keep track of dead particles and re-use them (thanks @Waclaw-I for the initial PR) * The Particle Emitter was not recycling dead particles correctly so it was creating new objects every time it emitted (the old particles were then left to the browsers gc to clear up). This has now been recoded so the emitter will properly keep track of dead particles and re-use them (thanks @Waclaw-I for the initial PR)
* `ParticleEmitter.indexSortCallback` has been removed as it's no longer required. * `ParticleEmitter.indexSortCallback` has been removed as it's no longer required.
* `Particle.index` has been removed, as it's no longer required. Particles don't need to keep track of their index any more. * `Particle.index` has been removed as it's no longer required. Particles don't need to keep track of their index any more.
* The Particle Emitter no longer needs to call the StableSort.inplace during its preUpdate, saving cpu. * The Particle Emitter no longer needs to call the StableSort.inplace during its preUpdate, saving cpu.
* `Particle.resetPosition` is a new method that is called when a particle dies, preparing it ready for firing again in the future. * `Particle.resetPosition` is a new method that is called when a particle dies preparing it for firing again in the future.
* The Canvas `SetTransform` method would save the context state, but it wasn't restored at the end in the following Game Objects: Dynamic Bitmap Text, Graphics, Arc, Curve, Ellipse, Grid, IsoBox, IsoTriangle, Line, Polygon, Rectangle, Star and Triangle. These now all restore the context, meaning if you're using non-canvas sized cameras in Canvas mode, it will now render beyond just the first custom camera. * The Canvas `SetTransform` method would save the context state, but it wasn't restored at the end in the following Game Objects: Dynamic Bitmap Text, Graphics, Arc, Curve, Ellipse, Grid, IsoBox, IsoTriangle, Line, Polygon, Rectangle, Star and Triangle. These now all restore the context, meaning if you're using non-canvas sized cameras in Canvas mode, it will now render beyond just the first custom camera.
* `Utils.Array.MoveUp` wouldn't let you move an array element to the top-most index in the array. This also impacted `Container.moveUp`. * `Utils.Array.MoveUp` wouldn't let you move an array element to the top-most index in the array. This also impacted `Container.moveUp`.
* The Texture Tint Pipeline had a logic error that would cause every 2001st quad to either be invisible, or pick-up the texture of the 2000th quad by mistake. The `batchQuad` and `batchTri` methods how handle re-assigning the batch texture if they cause a batch flush as part of their process. * The Texture Tint Pipeline had a logic error that would cause every 2001st quad to either be invisible, or pick-up the texture of the 2000th quad by mistake. The `batchQuad` and `batchTri` methods how handle re-assigning the batch texture if they cause a batch flush as part of their process.
* Rotating Sprites that used a Normal Map wouldn't rotate the normal map with it, causing the lighting effects to become irregular. The normal map vectors are now rotated correctly (thanks @sercant for the PR and @fazzamatazz and @ysraelJMM for the report) * Rotating Sprites that used a Normal Map wouldn't rotate the normal map with it causing the lighting effects to become irregular. The normal map vectors are now rotated correctly (thanks @sercant for the PR and @fazzamatazz and @ysraelJMM for the report)
* Changing `scaleX` or `scaleY` on a `MatterImage` or `MatterSprite` would cause the body scale to become distorted as the setters didn't use the correct factor when resetting the initial scale. Fix #4206 (thanks @YannCaron) * Changing `scaleX` or `scaleY` on a `MatterImage` or `MatterSprite` would cause the body scale to become distorted as the setters didn't use the correct factor when resetting the initial scale. Fix #4206 (thanks @YannCaron)
* `StaticBody.reset` in Arcade Physics would ignore the `x` and `y` values given to it. If given, they're now used to reset the parent Game Object before the body is updated. Fix #4224 (thanks @samme) * `StaticBody.reset` in Arcade Physics would ignore the `x` and `y` values given to it. If given, they're now used to reset the parent Game Object before the body is updated. Fix #4224 (thanks @samme)
* Static Tilemap Layers wouldn't render correctly if the layer used a tileset with a different size to the base map data (set via `setBaseTileSize`). They now render correctly in WebGL and Canvas, regardless of the base tile size. * Static Tilemap Layers wouldn't render correctly if the layer used a tileset with a different size to the base map data (set via `setBaseTileSize`). They now render correctly in WebGL and Canvas regardless of the base tile size.
* When using `RenderTexture.fill`, the `alpha` argument would be ignored in Canvas mode. It's now used when filling the RenderTexture. * When using `RenderTexture.fill`, the `alpha` argument would be ignored in Canvas mode. It's now used when filling the RenderTexture.
* Fixed an issue in `WebGLRenderer.setScissor` where it was possible to try and compare the scissor size to a non-current scissor, if called outside of the render loop (i.e. from `RenderTexture.fill`) (thanks @hackhat) * Fixed an issue in `WebGLRenderer.setScissor` where it was possible to try and compare the scissor size to a non-current scissor if called outside of the render loop (i.e. from `RenderTexture.fill`) (thanks @hackhat)
* `RenderTexture.fill` in WebGL would use `gl.clear` and a clear color to try and fill the Render Texture. This only worked for full-canvas sized RenderTextures that didn't have a camera zoom applied. It has now been swapped to use the `drawFillRect` method of the Texture Tint Pipeline, allowing it to work properly regardless of camera zoom or size. * `RenderTexture.fill` in WebGL would use `gl.clear` and a clear color to try and fill the Render Texture. This only worked for full-canvas sized RenderTextures that didn't have a camera zoom applied. It has now been swapped to use the `drawFillRect` method of the Texture Tint Pipeline, allowing it to work properly regardless of camera zoom or size.
* `Container.getFirst` was using an incorrect Array Utils function `GetFirstElement`, when it should have been using `GetFirst`. It now uses the correct function. Fix #4244 (thanks @miran248) * `Container.getFirst` was using an incorrect Array Utils function `GetFirstElement` when it should have been using `GetFirst`. It now uses the correct function. Fix #4244 (thanks @miran248)
* `List.getFirst` was using an incorrect Array Utils function `GetFirstElement`, when it should have been using `GetFirst`. It now uses the correct function. Fix #4244 (thanks @miran248) * `List.getFirst` was using an incorrect Array Utils function `GetFirstElement` when it should have been using `GetFirst`. It now uses the correct function. Fix #4244 (thanks @miran248)
* Fixed an issue where changing the viewport or size of a Camera belonging to a RenderTexture, it wouldn't impact the rendering and objects will still render outside of the viewport range. It's now converted to a proper gl scissor rect by the renderer, meaning you can limit the area rendered to by adjusting the internal Render Texture cameras viewport. Fix #4243 (thanks @hackhat) * Fixed an issue where changing the viewport or size of a Camera belonging to a RenderTexture wouldn't impact the rendering and objects will still render outside of the viewport range. It's now converted to a proper gl scissor rect by the renderer, meaning you can limit the area rendered to by adjusting the internal Render Texture cameras viewport. Fix #4243 (thanks @hackhat)
* `CanvasTexture.destroy` is a new method that specifically handles the destruction of the CanvasTexture and all of its associated typed arrays. This prevents a memory leak when creating and destroying lots of RenderTextures (which are CanvasTexture backed). Fix #4239 (thanks @sjb933) * `CanvasTexture.destroy` is a new method that specifically handles the destruction of the CanvasTexture and all of its associated typed arrays. This prevents a memory leak when creating and destroying lots of RenderTextures (which are CanvasTexture backed). Fix #4239 (thanks @sjb933)
* The Alpha, Flip and Origin components have been removed from the Mesh Game Object (and by extension, Quad as well) as they are not used in the renderer and should be manipulated via the Mesh properties. Fix #4188 (thanks @enriqueto) * The Alpha, Flip and Origin components have been removed from the Mesh Game Object (and by extension, Quad as well) as they are not used in the renderer and should be manipulated via the Mesh properties. Fix #4188 (thanks @enriqueto)
* The `processDomCallbacks` method in the Input Manager wasn't correctly clearing the `once` arrays. Responsibility for this has now been passed to the queue methods `queueTouchStart`, `queueTouchMove`, `queueTouchEnd`, `queueMouseDown`, `queueMouseMove` and `queueMouseUp`. Fix #4257 (thanks @iArePJ)
* Arcade Physics now manages when `postUpdate` should be applied better, stopping it from gaining a zero delta during a further check in the same frame. This fixes various issues, including the mass collision test demo. Fix #4154 (thanks @samme)
* Arcade Physics could trigger a `collide` event on a Body even if it performing an overlap check, if the `onCollide` property was true (thanks @samme)
* TileSprites no longer cause a crash when using the Headless mode renderer. Fix #4297 (thanks @clesquir)
* The WebGLRenderer will now apply a transparent background if `transparent = true` in the game config (thanks @gomachan7)
* `List.sort` was missing the scope required for the sort handler, this is now correctly provided internally. Fix #4241 (thanks @jcyuan)
* `Container.sort` was missing the scope required for the sort handler, this is now correctly provided internally. Fix #4241 (thanks @jcyuan)
* `DataManager.pop` would emit the DataManager instance, instead of the parent, as the first event argument. It now emits the parent as it should do. Fix #4186 (thanks @gadelan)
* The `GetValue` function wasn't checking for the existance of '.' in the config property name correctly, causing the branch to always be taken (thanks @kyranet)
* Safari had permission problems playing HTML5 Audio files on Mac OS. Due to the changes in the input event system audio now plays properly based on user interactions. You still can't play it automatically, though, it will always require a user gesture to begin. Fix #4217 (thanks @increpare)
### Examples and TypeScript ### Examples and TypeScript
Thanks to the following for helping with the Phaser 3 Examples and TypeScript definitions, either by reporting errors, or even better, fixing them: Thanks to the following for helping with the Phaser 3 Examples and TypeScript definitions, either by reporting errors, or even better, fixing them:
@guilhermehto @samvieten @darkwebdev @RoryO @snowbillr @slothyrulez @jcyuan @jestarray @guilhermehto @samvieten @darkwebdev @RoryO @snowbillr @slothyrulez @jcyuan @jestarray @CzBiX
### Phaser Doc Jam ### Phaser Doc Jam
The Phaser Doc Jam was a community-backed effort to try and get the Phaser 3 API documentation to 100% coverage. The Doc Jam is now over and I offer my thanks to the following who helped with docs in this release: The Phaser Doc Jam was a community-backed effort to try and get the Phaser 3 API documentation to 100% coverage. The Doc Jam is now over and I offer my thanks to the following who helped with docs in this release:
16patsle - @gurungrahul2 - @icbat - @samme - @telinc1 - anandu pavanan - blackhawx - candelibas - Diego Romero - doronlinder - Elliott Wallace - eric - Georges Gabereau - Haobo Zhang - henriacle - jak6jak - Jake Jensen - James Van Roose - JamesSkemp - joelahoover - Joey - madclaws - marc136 - Mihail Ilinov - naum303 - NicolasRoehm - nuane - rejacobson - Robert Kowalski - rodri042 - rootasjey - sawamara - scottwestover - sir13tommy - stetso - therealsamf - Tigran - willblackmore - zenwaichi @16patsle - @gurungrahul2 - @icbat - @samme - @telinc1 - anandu pavanan - blackhawx - candelibas - Diego Romero - doronlinder - Elliott Wallace - eric - Georges Gabereau - Haobo Zhang - henriacle - jak6jak - Jake Jensen - James Van Roose - JamesSkemp - joelahoover - Joey - madclaws - marc136 - Mihail Ilinov - naum303 - NicolasRoehm - nuane - rejacobson - Robert Kowalski - rodri042 - rootasjey - sawamara - scottwestover - sir13tommy - stetso - therealsamf - Tigran - willblackmore - zenwaichi
Also, the following helped with the docs outside of the Doc Jam: Also, the following helped with the docs outside of the Doc Jam:
@bryanwood @jestarray @matosummer @tfelix @imilo @bryanwood @jestarray @matosummer @tfelix @imilo @BigZaphod @OmarShehata @16patsle @jcyuan @iam13islucky @FractalBobz Endre
## Version 3.15.1 - Batou - 16th October 2018 ## Version 3.15.1 - Batou - 16th October 2018
@ -280,7 +545,7 @@ Note: We are releasing this version ahead of schedule in order to make some very
* You can now set the `maxLights` value in the Game Config, which controls the total number of lights the Light2D shader can render in a single pass. The default is 10. Be careful about pushing this too far. More lights = less performance. Close #4081 (thanks @FrancescoNegri) * You can now set the `maxLights` value in the Game Config, which controls the total number of lights the Light2D shader can render in a single pass. The default is 10. Be careful about pushing this too far. More lights = less performance. Close #4081 (thanks @FrancescoNegri)
* `Rectangle.SameDimensions` determines if the two objects (either Rectangles or Rectangle-like) have the same width and height values under strict equality. * `Rectangle.SameDimensions` determines if the two objects (either Rectangles or Rectangle-like) have the same width and height values under strict equality.
* An ArcadePhysics Group can now pass `{ enable: false }`` in its config to disable all the member bodies (thanks @samme) * An ArcadePhysics Group can now pass `{ enable: false }` in its config to disable all the member bodies (thanks @samme)
* `Body.setEnable` is a new chainable method that allows you to toggle the enable state of an Arcade Physics Body (thanks @samme) * `Body.setEnable` is a new chainable method that allows you to toggle the enable state of an Arcade Physics Body (thanks @samme)
* `KeyboardPlugin.resetKeys` is a new method that will reset the state of any Key object created by a Scene's Keyboard Plugin. * `KeyboardPlugin.resetKeys` is a new method that will reset the state of any Key object created by a Scene's Keyboard Plugin.
* `Pointer.wasCanceled` is a new boolean property that allows you to tell if a Pointer was cleared due to a `touchcancel` event. This flag is reset during the next `touchstart` event for the Pointer. * `Pointer.wasCanceled` is a new boolean property that allows you to tell if a Pointer was cleared due to a `touchcancel` event. This flag is reset during the next `touchstart` event for the Pointer.

115
README.md
View file

@ -24,25 +24,19 @@ Grab the source and join the fun!
<div align="center"><img src="https://phaser.io/images/github/news.jpg"></div> <div align="center"><img src="https://phaser.io/images/github/news.jpg"></div>
> 16th October 2018 > 11th February 2019
Phaser 3.15 is now available. This is slightly ahead of schedule because we needed to get some important performance and iOS input related fixes released, without waiting for new features to be completed first. With a new version as large as 3.16.0 was, there were bound to be some bugs that got overlooked. With 3.16.2 we address some of the more important ones. Please see the Change Log below for full details. If you're using 3.16, then please upgrade to 3.16.2.
This means that the new Scale Manager and Spine support have been moved to release 3.16 due towards the end of October. Please read the weekly Dev Logs for details about development. 5th February 2019:
> 1st October 2018 I'm pleased to announce that Phaser 3.16 is now available. This version represents a significant milestone in the project as Phaser 3 is now 100% feature complete with all of the initially planned systems now in place. The most significant additions in 3.16 is the overhaul of the Input event handling, the long-awaited introduction of the Scale Manager, and the Extern Game Object, which allows for 3rd party rendering support, as required by Spine. Spine animation support is being handled exclusively through a Phaser Plugin. The current build of the Spine plugin can be found in this repo in the `plugins` folder, along with examples in the Phaser Labs. The Spine plugin will be developed independently of Phaser in the coming weeks.
I'm pleased to announce that Phaser 3.14 is now out. Hot on the heels of the massive 3.13 release, 3.14 brings some sought-after new features to the party, including support for the new Tiled Map Editor 1.2 file formats, as well as the long-requested feature allowing use of multiple tilesets per single tilemap layer. This is the single largest update of Phaser 3 yet, and as such, there _are_ breaking changes. I have painstakingly listed all of them in the Change Log, so please do read it if you're upgrading from an earlier version. I know there is a lot to take in, so I'll be covering the new features in the Phaser World newsletter in the coming weeks.
There are also new features to make Matter JS debugging easier and body creation when using lists of vertices is now much cleaner too. It's never just features though. There are lots of important fixes and updates in 3.14, including a fix causing gl canvas resizing to fail, better handling of the game shutdown process and fixes for an issue with Graphics.generateTexture. 3.16 also brings together all of the hard work from the community that went in to the documentation. They're in a much better state than ever before, and very nearly 100% complete. I also completely reworked the internal event system, so event names, callback arguments and more are easy to find in one central place in the docs and can be reference in your code with either strings or properly name-spaced constants.
If you're building an active project on 3.13 then please upgrade to 3.14 and, as usual, report any issues you find on GitHub so we can look at them immediately. Also, in the 3.14 release we have completed over 1000 new areas of documentation. At the time of writing there are now just 1900 items in the API left to document, which may sound like a lot, but is a fraction of the tens of thousands already done! With our current progress we should have 100% documentation coverage within the next couple of months. A massive thank-you to everyone who supports Phaser on Patreon and PayPal. It's your backing that allows me to work on this full-time. If you've ever considered becoming a backer, now is the perfect time!
In case you missed the notice, Phaser 3.13 introduced the Facebook Instant Games Plugin. The plugin provides a seamless bridge between Phaser and version 6.2 of the Facebook Instant Games SDK. Every single SDK function is available via the plugin and we will keep track of the official SDK to make sure they stay in sync. My thanks to Facebook for helping make this possible.
Also new in 3.13 were the Shape Game Objects, which allows for quick addition of geometry onto the display list. Easily add rectangles, triangles, curves, stars and more into your game and treat them just like any other Game Object. Perfect for place-holder art, abstract style games or just really fast iterations game-jam style.
3.14 continues to represent the tireless effort on my part to get it fully production ready. I'm seeing lots more games being released with Phaser 3 and stacks of tutorials and plugins are starting to surface. My aim has always been to continue the mission of enhancing Phaser 3 as quickly as I can. It means releasing significant updates in relatively short periods of time. But it also means I'm jumping on bug reports as quickly as I can, keeping the issues list total nice and low (the vast majority of the items in there are feature requests now!) - a massive thank-you to all of you who support Phaser on Patreon and PayPal. It's your support that allows me to work on this full-time, to the benefit of everyone.
As always, please check out the [Change Log](#changelog) for comprehensive details about what recent versions contain. As always, please check out the [Change Log](#changelog) for comprehensive details about what recent versions contain.
@ -62,15 +56,17 @@ Rich - [@photonstorm](https://twitter.com/photonstorm)
![Support Phaser](https://phaser.io/images/github/div-support-phaser.png "Support Phaser") ![Support Phaser](https://phaser.io/images/github/div-support-phaser.png "Support Phaser")
Developing Phaser takes a lot of time, effort and money. There are monthly running costs as well as countless hours of development time, community support, and assistance resolving issues. Because Phaser is an open source project, we cannot charge for it in the same way as traditional retail software. What's more, we don't ever want to. After all, it's built on, and was born from, open web standards. It's part of our manifesto that the core framework will always be free, even if you use it commercially, as many of you do.
If you have found Phaser useful in your development life or have made income as a result of it please support our work via: **You may not realize it, but because of this, we rely 100% on community backing to fund development.**
* A monthly contribution on [Patreon](https://www.patreon.com/photonstorm). Those funds allow Phaser to improve, and when it improves, everyone involved benefits. Your support helps secure a constant cycle of updates, fixes, new features and planning for the future.
* A [one-off donation](https://phaser.io/community/donate) with PayPal.
* Purchase any of our [plugins or books](https://phaser.io/shop).
It all helps and genuinely contributes towards future development. There are other benefits to [backing Phaser](https://www.patreon.com/join/photonstorm), too:
![Backers Perks](https://phaser.io/images/github/patreon-perk-chart.png)
I use [Patreon](https://www.patreon.com/photonstorm) to manage the backing and you can [support Phaser](https://www.patreon.com/join/photonstorm?) from $1 per month. The amount you pledge is entirely up to you and can be changed as often as you like. Patreon renews monthly, just like Netflix. You can, of course, cancel at any point. Tears will be shed on this end, but that's not your concern.
Extra special thanks to our top-tier sponsors: [Orange Games](http://orangegames.com) and [CrossInstall](https://crossinstall.com). Extra special thanks to our top-tier sponsors: [Orange Games](http://orangegames.com) and [CrossInstall](https://crossinstall.com).
@ -82,7 +78,7 @@ Extra special thanks to our top-tier sponsors: [Orange Games](http://orangegames
We publish the [Phaser World](https://phaser.io/community/newsletter) newsletter. It's packed full of the latest Phaser games, tutorials, videos, meet-ups, talks, and more. The newsletter also contains our weekly Development Progress updates which let you know about the new features we're working on. We publish the [Phaser World](https://phaser.io/community/newsletter) newsletter. It's packed full of the latest Phaser games, tutorials, videos, meet-ups, talks, and more. The newsletter also contains our weekly Development Progress updates which let you know about the new features we're working on.
Over 120 previous editions can be found on our [Back Issues](https://phaser.io/community/backissues) page. Over 130 previous editions can be found on our [Back Issues](https://phaser.io/community/backissues) page.
![Download Phaser](https://phaser.io/images/github/div-download.png "Download Phaser") ![Download Phaser](https://phaser.io/images/github/div-download.png "Download Phaser")
<a name="download"></a> <a name="download"></a>
@ -108,13 +104,13 @@ npm install phaser
[Phaser is on jsDelivr](https://www.jsdelivr.com/projects/phaser) which is a "super-fast CDN for developers". Include the following in your html: [Phaser is on jsDelivr](https://www.jsdelivr.com/projects/phaser) which is a "super-fast CDN for developers". Include the following in your html:
```html ```html
<script src="//cdn.jsdelivr.net/npm/phaser@3.15/dist/phaser.js"></script> <script src="//cdn.jsdelivr.net/npm/phaser@3.16.2/dist/phaser.js"></script>
``` ```
or the minified version: or the minified version:
```html ```html
<script src="//cdn.jsdelivr.net/npm/phaser@3.15/dist/phaser.min.js"></script> <script src="//cdn.jsdelivr.net/npm/phaser@3.16.2/dist/phaser.min.js"></script>
``` ```
### API Documentation ### API Documentation
@ -186,13 +182,13 @@ We've 3 tutorials related to Facebook Instant Games and Phaser:
A special build of Phaser with the Facebook Instant Games Plugin ready-enabled is [available on jsDelivr](https://www.jsdelivr.com/projects/phaser). Include the following in your html: A special build of Phaser with the Facebook Instant Games Plugin ready-enabled is [available on jsDelivr](https://www.jsdelivr.com/projects/phaser). Include the following in your html:
```html ```html
<script src="//cdn.jsdelivr.net/npm/phaser@3.15/dist/phaser-facebook-instant-games.js"></script> <script src="//cdn.jsdelivr.net/npm/phaser@3.16.2/dist/phaser-facebook-instant-games.js"></script>
``` ```
or the minified version: or the minified version:
```html ```html
<script src="//cdn.jsdelivr.net/npm/phaser@3.15/dist/phaser-facebook-instant-games.min.js"></script> <script src="//cdn.jsdelivr.net/npm/phaser@3.16.2/dist/phaser-facebook-instant-games.min.js"></script>
``` ```
The build files are in the git repository in the `dist` folder, and you can also include the plugin in custom builds. The build files are in the git repository in the `dist` folder, and you can also include the plugin in custom builds.
@ -209,7 +205,7 @@ Create an `index.html` page locally and paste the following code into it:
<!DOCTYPE html> <!DOCTYPE html>
<html> <html>
<head> <head>
<script src="https://labs.phaser.io/build/phaser-arcade-physics.min.js"></script> <script src="https://cdn.jsdelivr.net/npm/phaser@3.16.2/dist/phaser-arcade-physics.min.js"></script>
</head> </head>
<body> <body>
@ -320,42 +316,51 @@ You can then run `webpack` to create a development build in the `build` folder w
# Change Log # Change Log
## Version 3.15.1 - Batou - 16th October 2018 ## Version 3.16.2 - Ishikawa - 11th February 2019
Note: We are releasing this version ahead of schedule in order to make some very important iOS performance and input related fixes available. It does not contain the new Scale Manager or Spine support, both of which have been moved to 3.16 as they require a few more weeks of development. This is point release primarily fixes a few important issues that surfaced in 3.16.0. Please be sure to read the [Change Log](https://github.com/photonstorm/phaser/blob/master/CHANGELOG.md) if you are coming from a version < 3.16.0 as it contains lots of important updates.
### New Features ### Matter Pointer Constraint Changes
* You can now set the `maxLights` value in the Game Config, which controls the total number of lights the Light2D shader can render in a single pass. The default is 10. Be careful about pushing this too far. More lights = less performance. Close #4081 (thanks @FrancescoNegri) The following changes all effect the Matter JS Pointer Constraint class:
* `Rectangle.SameDimensions` determines if the two objects (either Rectangles or Rectangle-like) have the same width and height values under strict equality.
* An ArcadePhysics Group can now pass `{ enable: false }`` in its config to disable all the member bodies (thanks @samme) * Pointer handling has been changed to make more sense. In the previous version, pressing down and then moving the Pointer _over_ a body would start it being dragged, even if the pointer was pressed down well outside of the body bounds. Now, a body can only be dragged by actually pressing down on it, or any of its parts, which is more in-line with how input events should work.
* `Body.setEnable` is a new chainable method that allows you to toggle the enable state of an Arcade Physics Body (thanks @samme) * Previously, releasing ANY pointer would stop an object being dragged, even if it wasn't the one actually dragging a body, as in a multi-touch game. Bodies are now bound to the pointer which started their drag and only the release of that pointer will stop them.
* `KeyboardPlugin.resetKeys` is a new method that will reset the state of any Key object created by a Scene's Keyboard Plugin. * There is a new Matter Physics Event `DRAG_START` which is emitted by a Pointer Constraint when it starts dragging a body. Listen for this event from the Matter World instance.
* `Pointer.wasCanceled` is a new boolean property that allows you to tell if a Pointer was cleared due to a `touchcancel` event. This flag is reset during the next `touchstart` event for the Pointer. * There is a new Matter Physics Event `DRAG` which is emitted by a Pointer Constraint as it drags a body. Listen for this event from the Matter World instance.
* `Pointer.touchcancel` is a new internal method specifically for handling touch cancel events. It has the same result as `touchend` without setting any of the up properties, to avoid triggering up event handlers. It will also set the `wasCanceled` property to `true`. * There is a new Matter Physics Event `DRAG_END` which is emitted by a Pointer Constraint when it stops dragging a body. Listen for this event from the Matter World instance.
* The `camera` property can no longer be set in the config object. Instead it is set every time the Pointer is pressed down on a Body, this resolves issues where you have a multi-camera Scene and want to drag a body in the non-main camera.
* `body` is a new property that holds a reference to the Body being dragged, if any.
* `part` is a new property that holds a reference to the Body part that was clicked on which started the drag.
* The internal `getBodyPart` method has been renamed to `hitTestBody` to more accurately reflect what it does.
* The class no longer listens for the pointer `up` event, instead of tracks the active pointer and waits for that to be released. This has reduced the complexity and size of the `update` method considerably.
* `stopDrag` is a new method that allows you to manually stop an object being dragged, even if the pointer isn't released.
* This class now has 100% JSDocs.
### Updates ### Updates
* `WebGLRenderer.deleteTexture` will check to see if the texture it is being asked to delete is the currently bound texture or not. If it is, it'll set the blank texture to be bound after deletion. This should stop `RENDER WARNING: there is no texture bound to the unit 0` errors if you destroy a Game Object, such as Text or TileSprite, from an async or timed process (thanks jamespierce) * `TileSprite.setTileScale` has been updated so that the `y` argument is optional and set to match the `x` argument, like `setScale` elsewhere in the API.
* The `RequestAnimationFrame.step` and `stepTimeout` functions have been updated so that the new Frame is requested from raf before the main game step is called. This allows you to now stop the raf callback from within the game update or render loop. Fix #3952 (thanks @tolimeh) * `InputManager.time` is a new property that holds the most recent time it was updated from the Game step, which plugins can access.
* If you pass zero as the width or height when creating a TileSprite it will now use the dimensions of the texture frame as the size of the TileSprite. Fix #4073 (thanks @jcyuan) * `InputManager.preStep` is a new method that populates some internal properties every step.
* `TileSprite.setFrame` has had both the `updateSize` and `updateOrigin` arguments removed as they didn't do anything for TileSprites and were misleading. * `KeyboardPlugin.time` has moved from being a property to being a getter, which returns the time from the InputManager.
* `CameraManager.remove` has a new argument `runDestroy` which, if set, will automatically call `Camera.destroy` on the Cameras removed from the Camera Manager. You should nearly always allow this to happen (thanks jamespierce) * The `scale` property has been added to the `Scene` class (thanks @strangeweekend)
* Device.OS has been restructured to allow fake UAs from Chrome dev tools to register iOS devices. * `Matter.World.remove` now uses the `Composite.remove` method internally. Previously, it used `Composite.removeBody` which only allowed it to remove bodies from the simulation. Now, it can remove any type of Matter object.
* Texture batching during the batch flush has been implemented in the TextureTintPipeline which resolves the issues of very low frame rates, especially on iOS devices, when using non-batched textures such as those used by Text or TileSprites. Fix #4110 #4086 (thanks @ivanpopelyshev @sachinhosmani @maximtsai @alexeymolchan) * When the Matter World creates its wall bounds, the left and right walls now extend further up and down than before, so that in a 4-wall setting there are no gaps in the corners, which previously allowed for fast moving objects that hit a corner intersection point to sometimes travel through it.
* The WebGLRenderer method `canvasToTexture` has a new optional argument `noRepeat` which will stop it from using `gl.REPEAT` entirely. This is now used by the Text object to avoid it potentially switching between a REPEAT and CLAMP texture, causing texture black-outs (thanks @ivanpopelyshev) * Touch inputs will now trigger a `POINTER_OUT` event if they leave the game (i.e. are released), where-as before they would only trigger the `POINTER_UP` event. Now, both happen (thanks @rgk)
* `KeyboardPlugin.resetKeys` is now called automatically as part of the Keyboard Plugin `shutdown` method. This means, when the plugin shuts down, such as when stopping a Scene, it will reset the state of any key held in the plugin. It will also clear the queue of any pending events.
* The `Touch Manager` has been rewritten to use declared functions for all touch event handlers, rather than bound functions. This means they will now clear properly when the TouchManager is shut down.
* There is a new Input constant `TOUCH_CANCEL` which represents canceled touch events.
### Bug Fixes ### Bug Fixes
* Fixed a bug in the canvas rendering of both the Static and Dynamic Tilemap Layers where the camera matrix was being multiplied twice with the layer, causing the scale and placement to be off (thanks galerijanamar) * The `Mesh.setAlpha` method has been restored, even though it's empty and does nothing, to prevent runtime errors when adding a Mesh or Quad object to a Container. Fix #4338 #4343 (thanks @pfdtravalmatic @charmingny)
* If you set `pixelArt` to true in your game config (or `antialias` to false) then TileSprites will now respect this when using the Canvas Renderer and disable smoothing on the internal fill canvas. * `KeyboardPlugin.checkDown` would always fail if using the new event system, because the time value it was checking wasn't updated.
* TileSprites that were set to be interactive before they had rendered once wouldn't receive a valid input hit area, causing input to fail. They now define their size immediately, allowing them to be made interactive without having rendered. Fix #4085 (thanks @DotTheGreat) * Entering `Fullscreen` mode in the Scale Manager and then pressing ESC would leave the injected fullsceen div in the DOM, causing it to throw a node insertion failure the second time you wanted to enter fullscreen mode. Fix #4352 (thanks @ngdevr)
* The Particle Emitter Manager has been given a NOOP method called `setBlendMode` to stop warnings from being thrown if you added an emitter to a Container in the Canvas renderer. Fix #4083 (thanks @maximtsai) * Due to the changes in the Input event system, the `GAME_OUT` event would never fire unless the input system was in legacy mode. The OUT and OVER handlers have been refactored and will now fire as soon as the DOM event happens. As a result the `InputManager._emitIsOverEvent` property has been removed, as the native event is sent directly to the handler and doesn't need storing locally any more. Fix #4344 (thanks @RademCZ)
* The `game.context` property would be incorrectly set to `null` after the WebGLRenderer instance was created (thanks @samme) * Added `Zone.setBlendMode` method as a NOOP function, fixing a bug where if you added a Zone to a Container when running under Canvas it would fail. Fix #4295 (thanks @emanuel15)
* The Touch Manager, Input Manager and Pointer classes all now handle the `touchcancel` event, such as triggered on iOS when activating an out of browser UI gesture, or in Facebook Instant Games when displaying an overlay ad. This should prevent issues with touch input becoming locked on iOS specifically. Fix #3756 (thanks @sftsk @sachinhosmani @kooappsdevs)
### Examples, Documentation and TypeScript
My thanks to the following for helping with the Phaser 3 Examples, Docs and TypeScript definitions, either by reporting errors, fixing them or helping author the docs:
@maretana @CipSoft-Components @brian-lui
Please see the complete [Change Log](https://github.com/photonstorm/phaser/blob/master/CHANGELOG.md) for previous releases. Please see the complete [Change Log](https://github.com/photonstorm/phaser/blob/master/CHANGELOG.md) for previous releases.
@ -382,14 +387,14 @@ Phaser is a [Photon Storm](http://www.photonstorm.com) production.
Created by [Richard Davey](mailto:rich@photonstorm.com). Powered by coffee, anime, pixels and love. Created by [Richard Davey](mailto:rich@photonstorm.com). Powered by coffee, anime, pixels and love.
The Phaser logo and characters are &copy; 2018 Photon Storm Limited. The Phaser logo and characters are &copy; 2019 Photon Storm Limited.
All rights reserved. All rights reserved.
"Above all, video games are meant to be just one thing: fun. Fun for everyone." - Satoru Iwata "Above all, video games are meant to be just one thing: fun. Fun for everyone." - Satoru Iwata
[get-js]: https://github.com/photonstorm/phaser/releases/download/v3.15.1/phaser.js [get-js]: https://github.com/photonstorm/phaser/releases/download/v3.16.2/phaser.js
[get-minjs]: https://github.com/photonstorm/phaser/releases/download/v3.15.1/phaser.min.js [get-minjs]: https://github.com/photonstorm/phaser/releases/download/v3.16.2/phaser.min.js
[clone-http]: https://github.com/photonstorm/phaser.git [clone-http]: https://github.com/photonstorm/phaser.git
[clone-ssh]: git@github.com:photonstorm/phaser.git [clone-ssh]: git@github.com:photonstorm/phaser.git
[clone-ghwin]: github-windows://openRepo/https://github.com/photonstorm/phaser [clone-ghwin]: github-windows://openRepo/https://github.com/photonstorm/phaser

File diff suppressed because it is too large Load diff

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load diff

File diff suppressed because one or more lines are too long

62111
dist/phaser.js vendored

File diff suppressed because it is too large Load diff

2
dist/phaser.min.js vendored

File diff suppressed because one or more lines are too long

View file

@ -1,6 +1,6 @@
{ {
"name": "phaser", "name": "phaser",
"version": "3.16.0", "version": "3.16.3",
"release": "Ishikawa", "release": "Ishikawa",
"description": "A fast, free and fun HTML5 Game Framework for Desktop and Mobile web browsers.", "description": "A fast, free and fun HTML5 Game Framework for Desktop and Mobile web browsers.",
"author": "Richard Davey <rich@photonstorm.com> (http://www.photonstorm.com)", "author": "Richard Davey <rich@photonstorm.com> (http://www.photonstorm.com)",

View file

@ -1322,7 +1322,7 @@ var FacebookInstantGamesPlugin = new Class({
*/ */
chooseContext: function (options) chooseContext: function (options)
{ {
if (!this.checkAPI('contextChoseAsync')) if (!this.checkAPI('contextChooseAsync'))
{ {
return this; return this;
} }
@ -1624,7 +1624,7 @@ var FacebookInstantGamesPlugin = new Class({
* @param {string} cta - The call to action text. * @param {string} cta - The call to action text.
* @param {object} text - The text object. * @param {object} text - The text object.
* @param {string} key - The key of the texture to use as the share image. * @param {string} key - The key of the texture to use as the share image.
* @param {(string|integer)} [frame] - The frame of the texture to use as the share image. Set to `null` if you don't require a frame, but do need to set session data. * @param {?(string|integer)} frame - The frame of the texture to use as the share image. Set to `null` if you don't require a frame, but do need to set session data.
* @param {string} template - The update template key. * @param {string} template - The update template key.
* @param {object} updateData - The update data object payload. * @param {object} updateData - The update data object payload.
* *
@ -1662,7 +1662,7 @@ var FacebookInstantGamesPlugin = new Class({
* @param {string} cta - The call to action text. * @param {string} cta - The call to action text.
* @param {object} text - The text object. * @param {object} text - The text object.
* @param {string} key - The key of the texture to use as the share image. * @param {string} key - The key of the texture to use as the share image.
* @param {(string|integer)} [frame] - The frame of the texture to use as the share image. Set to `null` if you don't require a frame, but do need to set session data. * @param {?(string|integer)} frame - The frame of the texture to use as the share image. Set to `null` if you don't require a frame, but do need to set session data.
* @param {string} template - The update template key. * @param {string} template - The update template key.
* @param {object} updateData - The update data object payload. * @param {object} updateData - The update data object payload.
* *
@ -1684,7 +1684,7 @@ var FacebookInstantGamesPlugin = new Class({
* @param {string} cta - The call to action text. * @param {string} cta - The call to action text.
* @param {object} text - The text object. * @param {object} text - The text object.
* @param {string} key - The key of the texture to use as the share image. * @param {string} key - The key of the texture to use as the share image.
* @param {(string|integer)} [frame] - The frame of the texture to use as the share image. Set to `null` if you don't require a frame, but do need to set session data. * @param {?(string|integer)} frame - The frame of the texture to use as the share image. Set to `null` if you don't require a frame, but do need to set session data.
* @param {string} template - The update template key. * @param {string} template - The update template key.
* @param {object} updateData - The update data object payload. * @param {object} updateData - The update data object payload.
* *

View file

@ -248,7 +248,7 @@ var Leaderboard = new Class({
var _this = this; var _this = this;
this.ref.getEntriesAsync().then(function (entries) this.ref.getEntriesAsync(count, offset).then(function (entries)
{ {
_this.scores = []; _this.scores = [];

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,15 +1,9 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */
/**
* @callback CallCallback
*
* @param {Phaser.GameObjects.GameObject} item - The Game Object to run the callback on.
*/
/** /**
* Takes an array of objects and passes each of them to the given callback. * Takes an array of objects and passes each of them to the given callback.
* *
@ -19,7 +13,7 @@
* @generic {Phaser.GameObjects.GameObject[]} G - [items,$return] * @generic {Phaser.GameObjects.GameObject[]} G - [items,$return]
* *
* @param {(array|Phaser.GameObjects.GameObject[])} items - The array of items to be updated by this action. * @param {(array|Phaser.GameObjects.GameObject[])} items - The array of items to be updated by this action.
* @param {CallCallback} callback - The callback to be invoked. It will be passed just one argument: the item from the array. * @param {Phaser.Actions.Types.CallCallback} callback - The callback to be invoked. It will be passed just one argument: the item from the array.
* @param {*} context - The scope in which the callback will be invoked. * @param {*} context - The scope in which the callback will be invoked.
* *
* @return {(array|Phaser.GameObjects.GameObject[])} The array of objects that was passed to this Action. * @return {(array|Phaser.GameObjects.GameObject[])} The array of objects that was passed to this Action.

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */
@ -12,20 +12,6 @@ var Zone = require('../gameobjects/zone/Zone');
var tempZone = new Zone({ sys: { queueDepthSort: NOOP, events: { once: NOOP } } }, 0, 0, 1, 1); var tempZone = new Zone({ sys: { queueDepthSort: NOOP, events: { once: NOOP } } }, 0, 0, 1, 1);
/**
* @typedef {object} GridAlignConfig
*
* @property {integer} [width=-1] - The width of the grid in items (not pixels). -1 means lay all items out horizontally, regardless of quantity.
* If both this value and height are set to -1 then this value overrides it and the `height` value is ignored.
* @property {integer} [height=-1] - The height of the grid in items (not pixels). -1 means lay all items out vertically, regardless of quantity.
* If both this value and `width` are set to -1 then `width` overrides it and this value is ignored.
* @property {integer} [cellWidth=1] - The width of the cell, in pixels, in which the item is positioned.
* @property {integer} [cellHeight=1] - The height of the cell, in pixels, in which the item is positioned.
* @property {integer} [position=0] - The alignment position. One of the Phaser.Display.Align consts such as `TOP_LEFT` or `RIGHT_CENTER`.
* @property {number} [x=0] - Optionally place the top-left of the final grid at this coordinate.
* @property {number} [y=0] - Optionally place the top-left of the final grid at this coordinate.
*/
/** /**
* Takes an array of Game Objects, or any objects that have public `x` and `y` properties, * Takes an array of Game Objects, or any objects that have public `x` and `y` properties,
* and then aligns them based on the grid configuration given to this action. * and then aligns them based on the grid configuration given to this action.
@ -36,7 +22,7 @@ var tempZone = new Zone({ sys: { queueDepthSort: NOOP, events: { once: NOOP } }
* @generic {Phaser.GameObjects.GameObject[]} G - [items,$return] * @generic {Phaser.GameObjects.GameObject[]} G - [items,$return]
* *
* @param {(array|Phaser.GameObjects.GameObject[])} items - The array of items to be updated by this action. * @param {(array|Phaser.GameObjects.GameObject[])} items - The array of items to be updated by this action.
* @param {GridAlignConfig} options - The GridAlign Configuration object. * @param {Phaser.Actions.Types.GridAlignConfig} options - The GridAlign Configuration object.
* *
* @return {(array|Phaser.GameObjects.GameObject[])} The array of objects that were passed to this Action. * @return {(array|Phaser.GameObjects.GameObject[])} The array of objects that were passed to this Action.
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */
@ -16,7 +16,7 @@
* *
* @param {(array|Phaser.GameObjects.GameObject[])} items - An array of Game Objects. The contents of this array are updated by this Action. * @param {(array|Phaser.GameObjects.GameObject[])} items - An array of Game Objects. The contents of this array are updated by this Action.
* @param {*} hitArea - Either an input configuration object, or a geometric shape that defines the hit area for the Game Object. If not specified a Rectangle will be used. * @param {*} hitArea - Either an input configuration object, or a geometric shape that defines the hit area for the Game Object. If not specified a Rectangle will be used.
* @param {HitAreaCallback} hitAreaCallback - A callback to be invoked when the Game Object is interacted with. If you provide a shape you must also provide a callback. * @param {Phaser.Input.Types.HitAreaCallback} hitAreaCallback - A callback to be invoked when the Game Object is interacted with. If you provide a shape you must also provide a callback.
* *
* @return {(array|Phaser.GameObjects.GameObject[])} The array of Game Objects that was passed to this Action. * @return {(array|Phaser.GameObjects.GameObject[])} The array of Game Objects that was passed to this Action.
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,7 +1,7 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @author samme <samme.npm@gmail.com> * @author samme <samme.npm@gmail.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */

View file

@ -0,0 +1,6 @@
/**
* @callback Phaser.Actions.Types.CallCallback
* @since 3.0.0
*
* @param {Phaser.GameObjects.GameObject} item - The Game Object to run the callback on.
*/

View file

@ -0,0 +1,14 @@
/**
* @typedef {object} Phaser.Actions.Types.GridAlignConfig
* @since 3.0.0
*
* @property {integer} [width=-1] - The width of the grid in items (not pixels). -1 means lay all items out horizontally, regardless of quantity.
* If both this value and height are set to -1 then this value overrides it and the `height` value is ignored.
* @property {integer} [height=-1] - The height of the grid in items (not pixels). -1 means lay all items out vertically, regardless of quantity.
* If both this value and `width` are set to -1 then `width` overrides it and this value is ignored.
* @property {integer} [cellWidth=1] - The width of the cell, in pixels, in which the item is positioned.
* @property {integer} [cellHeight=1] - The height of the cell, in pixels, in which the item is positioned.
* @property {integer} [position=0] - The alignment position. One of the Phaser.Display.Align consts such as `TOP_LEFT` or `RIGHT_CENTER`.
* @property {number} [x=0] - Optionally place the top-left of the final grid at this coordinate.
* @property {number} [y=0] - Optionally place the top-left of the final grid at this coordinate.
*/

View file

@ -0,0 +1,9 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* @namespace Phaser.Actions.Types
*/

View file

@ -1,59 +1,17 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */
var Clamp = require('../math/Clamp'); var Clamp = require('../math/Clamp');
var Class = require('../utils/Class'); var Class = require('../utils/Class');
var EventEmitter = require('eventemitter3'); var EventEmitter = require('eventemitter3');
var Events = require('./events');
var FindClosestInSorted = require('../utils/array/FindClosestInSorted'); var FindClosestInSorted = require('../utils/array/FindClosestInSorted');
var Frame = require('./AnimationFrame'); var Frame = require('./AnimationFrame');
var GetValue = require('../utils/object/GetValue'); var GetValue = require('../utils/object/GetValue');
/**
* @typedef {object} JSONAnimation
*
* @property {string} key - The key that the animation will be associated with. i.e. sprite.animations.play(key)
* @property {string} type - A frame based animation (as opposed to a bone based animation)
* @property {JSONAnimationFrame[]} frames - [description]
* @property {integer} frameRate - The frame rate of playback in frames per second (default 24 if duration is null)
* @property {integer} duration - How long the animation should play for in milliseconds. If not given its derived from frameRate.
* @property {boolean} skipMissedFrames - Skip frames if the time lags, or always advanced anyway?
* @property {integer} delay - Delay before starting playback. Value given in milliseconds.
* @property {integer} repeat - Number of times to repeat the animation (-1 for infinity)
* @property {integer} repeatDelay - Delay before the animation repeats. Value given in milliseconds.
* @property {boolean} yoyo - Should the animation yoyo? (reverse back down to the start) before repeating?
* @property {boolean} showOnStart - Should sprite.visible = true when the animation starts to play?
* @property {boolean} hideOnComplete - Should sprite.visible = false when the animation finishes?
*/
/**
* @typedef {object} AnimationFrameConfig
*
* @property {string} key - The key that the animation will be associated with. i.e. sprite.animations.play(key)
* @property {(string|number)} frame - [description]
* @property {number} [duration=0] - [description]
* @property {boolean} [visible] - [description]
*/
/**
* @typedef {object} AnimationConfig
*
* @property {string} [key] - The key that the animation will be associated with. i.e. sprite.animations.play(key)
* @property {AnimationFrameConfig[]} [frames] - An object containing data used to generate the frames for the animation
* @property {string} [defaultTextureKey=null] - The key of the texture all frames of the animation will use. Can be overridden on a per frame basis.
* @property {integer} [frameRate] - The frame rate of playback in frames per second (default 24 if duration is null)
* @property {integer} [duration] - How long the animation should play for in milliseconds. If not given its derived from frameRate.
* @property {boolean} [skipMissedFrames=true] - Skip frames if the time lags, or always advanced anyway?
* @property {integer} [delay=0] - Delay before starting playback. Value given in milliseconds.
* @property {integer} [repeat=0] - Number of times to repeat the animation (-1 for infinity)
* @property {integer} [repeatDelay=0] - Delay before the animation repeats. Value given in milliseconds.
* @property {boolean} [yoyo=false] - Should the animation yoyo? (reverse back down to the start) before repeating?
* @property {boolean} [showOnStart=false] - Should sprite.visible = true when the animation starts to play?
* @property {boolean} [hideOnComplete=false] - Should sprite.visible = false when the animation finishes?
*/
/** /**
* @classdesc * @classdesc
* A Frame based Animation. * A Frame based Animation.
@ -70,9 +28,9 @@ var GetValue = require('../utils/object/GetValue');
* @constructor * @constructor
* @since 3.0.0 * @since 3.0.0
* *
* @param {Phaser.Animations.AnimationManager} manager - [description] * @param {Phaser.Animations.AnimationManager} manager - A reference to the global Animation Manager
* @param {string} key - [description] * @param {string} key - The unique identifying string for this animation.
* @param {AnimationConfig} config - [description] * @param {Phaser.Animations.Types.Animation} config - The Animation configuration.
*/ */
var Animation = new Class({ var Animation = new Class({
@ -85,7 +43,7 @@ var Animation = new Class({
EventEmitter.call(this); EventEmitter.call(this);
/** /**
* A reference to the global Animation Manager * A reference to the global Animation Manager.
* *
* @name Phaser.Animations.Animation#manager * @name Phaser.Animations.Animation#manager
* @type {Phaser.Animations.AnimationManager} * @type {Phaser.Animations.AnimationManager}
@ -94,7 +52,7 @@ var Animation = new Class({
this.manager = manager; this.manager = manager;
/** /**
* The unique identifying string for this animation * The unique identifying string for this animation.
* *
* @name Phaser.Animations.Animation#key * @name Phaser.Animations.Animation#key
* @type {string} * @type {string}
@ -113,7 +71,7 @@ var Animation = new Class({
this.type = 'frame'; this.type = 'frame';
/** /**
* Extract all the frame data into the frames array * Extract all the frame data into the frames array.
* *
* @name Phaser.Animations.Animation#frames * @name Phaser.Animations.Animation#frames
* @type {Phaser.Animations.AnimationFrame[]} * @type {Phaser.Animations.AnimationFrame[]}
@ -207,7 +165,7 @@ var Animation = new Class({
this.repeat = GetValue(config, 'repeat', 0); this.repeat = GetValue(config, 'repeat', 0);
/** /**
* The delay in ms before the a repeat playthrough starts. * The delay in ms before the a repeat play starts.
* *
* @name Phaser.Animations.Animation#repeatDelay * @name Phaser.Animations.Animation#repeatDelay
* @type {integer} * @type {integer}
@ -217,7 +175,7 @@ var Animation = new Class({
this.repeatDelay = GetValue(config, 'repeatDelay', 0); this.repeatDelay = GetValue(config, 'repeatDelay', 0);
/** /**
* Should the animation yoyo? (reverse back down to the start) before repeating? * Should the animation yoyo (reverse back down to the start) before repeating?
* *
* @name Phaser.Animations.Animation#yoyo * @name Phaser.Animations.Animation#yoyo
* @type {boolean} * @type {boolean}
@ -227,7 +185,7 @@ var Animation = new Class({
this.yoyo = GetValue(config, 'yoyo', false); this.yoyo = GetValue(config, 'yoyo', false);
/** /**
* Should sprite.visible = true when the animation starts to play? * Should the GameObject's `visible` property be set to `true` when the animation starts to play?
* *
* @name Phaser.Animations.Animation#showOnStart * @name Phaser.Animations.Animation#showOnStart
* @type {boolean} * @type {boolean}
@ -237,7 +195,7 @@ var Animation = new Class({
this.showOnStart = GetValue(config, 'showOnStart', false); this.showOnStart = GetValue(config, 'showOnStart', false);
/** /**
* Should sprite.visible = false when the animation finishes? * Should the GameObject's `visible` property be set to `false` when the animation finishes?
* *
* @name Phaser.Animations.Animation#hideOnComplete * @name Phaser.Animations.Animation#hideOnComplete
* @type {boolean} * @type {boolean}
@ -256,8 +214,8 @@ var Animation = new Class({
*/ */
this.paused = false; this.paused = false;
this.manager.on('pauseall', this.pause, this); this.manager.on(Events.PAUSE_ALL, this.pause, this);
this.manager.on('resumeall', this.resume, this); this.manager.on(Events.RESUME_ALL, this.resume, this);
}, },
/** /**
@ -266,7 +224,7 @@ var Animation = new Class({
* @method Phaser.Animations.Animation#addFrame * @method Phaser.Animations.Animation#addFrame
* @since 3.0.0 * @since 3.0.0
* *
* @param {(string|AnimationFrameConfig[])} config - [description] * @param {(string|Phaser.Animations.Types.AnimationFrame[])} config - [description]
* *
* @return {Phaser.Animations.Animation} This Animation object. * @return {Phaser.Animations.Animation} This Animation object.
*/ */
@ -281,8 +239,8 @@ var Animation = new Class({
* @method Phaser.Animations.Animation#addFrameAt * @method Phaser.Animations.Animation#addFrameAt
* @since 3.0.0 * @since 3.0.0
* *
* @param {integer} index - [description] * @param {integer} index - The index to insert the frame at within the animation.
* @param {(string|AnimationFrameConfig[])} config - [description] * @param {(string|Phaser.Animations.Types.AnimationFrame[])} config - [description]
* *
* @return {Phaser.Animations.Animation} This Animation object. * @return {Phaser.Animations.Animation} This Animation object.
*/ */
@ -395,7 +353,7 @@ var Animation = new Class({
* @since 3.0.0 * @since 3.0.0
* *
* @param {Phaser.Textures.TextureManager} textureManager - [description] * @param {Phaser.Textures.TextureManager} textureManager - [description]
* @param {(string|AnimationFrameConfig[])} frames - [description] * @param {(string|Phaser.Animations.Types.AnimationFrame[])} frames - [description]
* @param {string} [defaultTextureKey] - [description] * @param {string} [defaultTextureKey] - [description]
* *
* @return {Phaser.Animations.AnimationFrame[]} [description] * @return {Phaser.Animations.AnimationFrame[]} [description]
@ -774,6 +732,9 @@ var Animation = new Class({
* [description] * [description]
* *
* @method Phaser.Animations.Animation#repeatAnimation * @method Phaser.Animations.Animation#repeatAnimation
* @fires Phaser.Animations.Events#ANIMATION_REPEAT
* @fires Phaser.Animations.Events#SPRITE_ANIMATION_REPEAT
* @fires Phaser.Animations.Events#SPRITE_ANIMATION_KEY_REPEAT
* @since 3.0.0 * @since 3.0.0
* *
* @param {Phaser.GameObjects.Components.Animation} component - [description] * @param {Phaser.GameObjects.Components.Animation} component - [description]
@ -806,11 +767,11 @@ var Animation = new Class({
var frame = component.currentFrame; var frame = component.currentFrame;
var parent = component.parent; var parent = component.parent;
this.emit('repeat', this, frame); this.emit(Events.ANIMATION_REPEAT, this, frame);
parent.emit('animationrepeat-' + this.key, this, frame, component.repeatCounter, parent); parent.emit(Events.SPRITE_ANIMATION_KEY_REPEAT + this.key, this, frame, component.repeatCounter, parent);
parent.emit('animationrepeat', this, frame, component.repeatCounter, parent); parent.emit(Events.SPRITE_ANIMATION_REPEAT, this, frame, component.repeatCounter, parent);
} }
} }
}, },
@ -842,7 +803,7 @@ var Animation = new Class({
* @method Phaser.Animations.Animation#toJSON * @method Phaser.Animations.Animation#toJSON
* @since 3.0.0 * @since 3.0.0
* *
* @return {JSONAnimation} [description] * @return {Phaser.Animations.Types.JSONAnimation} [description]
*/ */
toJSON: function () toJSON: function ()
{ {
@ -954,8 +915,8 @@ var Animation = new Class({
{ {
this.removeAllListeners(); this.removeAllListeners();
this.manager.off('pauseall', this.pause, this); this.manager.off(Events.PAUSE_ALL, this.pause, this);
this.manager.off('resumeall', this.resume, this); this.manager.off(Events.RESUME_ALL, this.resume, this);
this.manager.remove(this.key); this.manager.remove(this.key);

View file

@ -1,19 +1,11 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */
var Class = require('../utils/Class'); var Class = require('../utils/Class');
/**
* @typedef {object} JSONAnimationFrame
*
* @property {string} key - The key of the Texture this AnimationFrame uses.
* @property {(string|integer)} frame - The key of the Frame within the Texture that this AnimationFrame uses.
* @property {number} duration - Additional time (in ms) that this frame should appear for during playback.
*/
/** /**
* @classdesc * @classdesc
* A single frame in an Animation sequence. * A single frame in an Animation sequence.
@ -149,7 +141,7 @@ var AnimationFrame = new Class({
* @method Phaser.Animations.AnimationFrame#toJSON * @method Phaser.Animations.AnimationFrame#toJSON
* @since 3.0.0 * @since 3.0.0
* *
* @return {JSONAnimationFrame} The AnimationFrame data. * @return {Phaser.Animations.Types.JSONAnimationFrame} The AnimationFrame data.
*/ */
toJSON: function () toJSON: function ()
{ {

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */
@ -8,16 +8,11 @@ var Animation = require('./Animation');
var Class = require('../utils/Class'); var Class = require('../utils/Class');
var CustomMap = require('../structs/Map'); var CustomMap = require('../structs/Map');
var EventEmitter = require('eventemitter3'); var EventEmitter = require('eventemitter3');
var Events = require('./events');
var GameEvents = require('../core/events');
var GetValue = require('../utils/object/GetValue'); var GetValue = require('../utils/object/GetValue');
var Pad = require('../utils/string/Pad'); var Pad = require('../utils/string/Pad');
/**
* @typedef {object} JSONAnimationManager
*
* @property {JSONAnimation[]} anims - An array of all Animations added to the Animation Manager.
* @property {number} globalTimeScale - The global time scale of the Animation Manager.
*/
/** /**
* @classdesc * @classdesc
* The Animation Manager. * The Animation Manager.
@ -109,27 +104,28 @@ var AnimationManager = new Class({
*/ */
this.name = 'AnimationManager'; this.name = 'AnimationManager';
game.events.once('boot', this.boot, this); game.events.once(GameEvents.BOOT, this.boot, this);
}, },
/** /**
* Registers event listeners after the Game boots. * Registers event listeners after the Game boots.
* *
* @method Phaser.Animations.AnimationManager#boot * @method Phaser.Animations.AnimationManager#boot
* @listens Phaser.Core.Events#DESTROY
* @since 3.0.0 * @since 3.0.0
*/ */
boot: function () boot: function ()
{ {
this.textureManager = this.game.textures; this.textureManager = this.game.textures;
this.game.events.once('destroy', this.destroy, this); this.game.events.once(GameEvents.DESTROY, this.destroy, this);
}, },
/** /**
* Adds an existing Animation to the Animation Manager. * Adds an existing Animation to the Animation Manager.
* *
* @method Phaser.Animations.AnimationManager#add * @method Phaser.Animations.AnimationManager#add
* @fires AddAnimationEvent * @fires Phaser.Animations.Events#ADD_ANIMATION
* @since 3.0.0 * @since 3.0.0
* *
* @param {string} key - The key under which the Animation should be added. The Animation will be updated with it. Must be unique. * @param {string} key - The key under which the Animation should be added. The Animation will be updated with it. Must be unique.
@ -141,7 +137,8 @@ var AnimationManager = new Class({
{ {
if (this.anims.has(key)) if (this.anims.has(key))
{ {
console.warn('Animation with key', key, 'already exists'); console.warn('Animation key exists: ' + key);
return; return;
} }
@ -149,7 +146,7 @@ var AnimationManager = new Class({
this.anims.set(key, animation); this.anims.set(key, animation);
this.emit('add', key, animation); this.emit(Events.ADD_ANIMATION, key, animation);
return this; return this;
}, },
@ -185,10 +182,10 @@ var AnimationManager = new Class({
* If you wish to re-use an existing key, call `AnimationManager.remove` first, then this method. * If you wish to re-use an existing key, call `AnimationManager.remove` first, then this method.
* *
* @method Phaser.Animations.AnimationManager#create * @method Phaser.Animations.AnimationManager#create
* @fires AddAnimationEvent * @fires Phaser.Animations.Events#ADD_ANIMATION
* @since 3.0.0 * @since 3.0.0
* *
* @param {AnimationConfig} config - The configuration settings for the Animation. * @param {Phaser.Animations.Types.Animation} config - The configuration settings for the Animation.
* *
* @return {(Phaser.Animations.Animation|false)} The Animation that was created, or `false` is the key is already in use. * @return {(Phaser.Animations.Animation|false)} The Animation that was created, or `false` is the key is already in use.
*/ */
@ -208,7 +205,7 @@ var AnimationManager = new Class({
this.anims.set(key, anim); this.anims.set(key, anim);
this.emit('add', key, anim); this.emit(Events.ADD_ANIMATION, key, anim);
} }
} }
@ -221,7 +218,7 @@ var AnimationManager = new Class({
* @method Phaser.Animations.AnimationManager#fromJSON * @method Phaser.Animations.AnimationManager#fromJSON
* @since 3.0.0 * @since 3.0.0
* *
* @param {(string|JSONAnimationManager|JSONAnimation)} data - The JSON object to parse. * @param {(string|Phaser.Animations.Types.JSONAnimations|Phaser.Animations.Types.JSONAnimation)} data - The JSON object to parse.
* @param {boolean} [clearCurrentAnimations=false] - If set to `true`, the current animations will be removed (`anims.clear()`). If set to `false` (default), the animations in `data` will be added. * @param {boolean} [clearCurrentAnimations=false] - If set to `true`, the current animations will be removed (`anims.clear()`). If set to `false` (default), the animations in `data` will be added.
* *
* @return {Phaser.Animations.Animation[]} An array containing all of the Animation objects that were created as a result of this call. * @return {Phaser.Animations.Animation[]} An array containing all of the Animation objects that were created as a result of this call.
@ -264,18 +261,6 @@ var AnimationManager = new Class({
return output; return output;
}, },
/**
* @typedef {object} GenerateFrameNamesConfig
*
* @property {string} [prefix=''] - The string to append to every resulting frame name if using a range or an array of `frames`.
* @property {integer} [start=0] - If `frames` is not provided, the number of the first frame to return.
* @property {integer} [end=0] - If `frames` is not provided, the number of the last frame to return.
* @property {string} [suffix=''] - The string to append to every resulting frame name if using a range or an array of `frames`.
* @property {integer} [zeroPad=0] - The minimum expected lengths of each resulting frame's number. Numbers will be left-padded with zeroes until they are this long, then prepended and appended to create the resulting frame name.
* @property {AnimationFrameConfig[]} [outputArray=[]] - The array to append the created configuration objects to.
* @property {boolean} [frames=false] - If provided as an array, the range defined by `start` and `end` will be ignored and these frame numbers will be used.
*/
/** /**
* [description] * [description]
* *
@ -283,9 +268,9 @@ var AnimationManager = new Class({
* @since 3.0.0 * @since 3.0.0
* *
* @param {string} key - The key for the texture containing the animation frames. * @param {string} key - The key for the texture containing the animation frames.
* @param {GenerateFrameNamesConfig} [config] - The configuration object for the animation frame names. * @param {Phaser.Animations.Types.GenerateFrameNames} [config] - The configuration object for the animation frame names.
* *
* @return {AnimationFrameConfig[]} The array of {@link AnimationFrameConfig} objects. * @return {Phaser.Animations.Types.AnimationFrame[]} The array of {@link Phaser.Animations.Types.AnimationFrame} objects.
*/ */
generateFrameNames: function (key, config) generateFrameNames: function (key, config)
{ {
@ -352,27 +337,17 @@ var AnimationManager = new Class({
}, },
/** /**
* @typedef {object} GenerateFrameNumbersConfig * Generate an array of {@link Phaser.Animations.Types.AnimationFrame} objects from a texture key and configuration object.
* *
* @property {integer} [start=0] - The starting frame of the animation. * Generates objects with numbered frame names, as configured by the given {@link Phaser.Animations.Types.GenerateFrameNumbers}.
* @property {integer} [end=-1] - The ending frame of the animation.
* @property {(boolean|integer)} [first=false] - A frame to put at the beginning of the animation, before `start` or `outputArray` or `frames`.
* @property {AnimationFrameConfig[]} [outputArray=[]] - An array to concatenate the output onto.
* @property {(boolean|integer[])} [frames=false] - A custom sequence of frames.
*/
/**
* Generate an array of {@link AnimationFrameConfig} objects from a texture key and configuration object.
*
* Generates objects with numbered frame names, as configured by the given {@link GenerateFrameNumbersConfig}.
* *
* @method Phaser.Animations.AnimationManager#generateFrameNumbers * @method Phaser.Animations.AnimationManager#generateFrameNumbers
* @since 3.0.0 * @since 3.0.0
* *
* @param {string} key - The key for the texture containing the animation frames. * @param {string} key - The key for the texture containing the animation frames.
* @param {GenerateFrameNumbersConfig} config - The configuration object for the animation frames. * @param {Phaser.Animations.Types.GenerateFrameNumbers} config - The configuration object for the animation frames.
* *
* @return {AnimationFrameConfig[]} The array of {@link AnimationFrameConfig} objects. * @return {Phaser.Animations.Types.AnimationFrame[]} The array of {@link Phaser.Animations.Types.AnimationFrame} objects.
*/ */
generateFrameNumbers: function (key, config) generateFrameNumbers: function (key, config)
{ {
@ -415,7 +390,12 @@ var AnimationManager = new Class({
endFrame = texture.frameTotal; endFrame = texture.frameTotal;
} }
for (i = startFrame; i <= endFrame; i++) var diff = (startFrame < endFrame) ? 1 : -1;
// Adjust because we use i !== end in the for loop
endFrame += diff;
for (i = startFrame; i !== endFrame; i += diff)
{ {
if (texture.has(i)) if (texture.has(i))
{ {
@ -470,7 +450,7 @@ var AnimationManager = new Class({
* Pause all animations. * Pause all animations.
* *
* @method Phaser.Animations.AnimationManager#pauseAll * @method Phaser.Animations.AnimationManager#pauseAll
* @fires PauseAllAnimationEvent * @fires Phaser.Animations.Events#PAUSE_ALL
* @since 3.0.0 * @since 3.0.0
* *
* @return {Phaser.Animations.AnimationManager} This Animation Manager. * @return {Phaser.Animations.AnimationManager} This Animation Manager.
@ -481,7 +461,7 @@ var AnimationManager = new Class({
{ {
this.paused = true; this.paused = true;
this.emit('pauseall'); this.emit(Events.PAUSE_ALL);
} }
return this; return this;
@ -524,7 +504,7 @@ var AnimationManager = new Class({
* Remove an animation. * Remove an animation.
* *
* @method Phaser.Animations.AnimationManager#remove * @method Phaser.Animations.AnimationManager#remove
* @fires RemoveAnimationEvent * @fires Phaser.Animations.Events#REMOVE_ANIMATION
* @since 3.0.0 * @since 3.0.0
* *
* @param {string} key - The key of the animation to remove. * @param {string} key - The key of the animation to remove.
@ -537,7 +517,7 @@ var AnimationManager = new Class({
if (anim) if (anim)
{ {
this.emit('remove', key, anim); this.emit(Events.REMOVE_ANIMATION, key, anim);
this.anims.delete(key); this.anims.delete(key);
} }
@ -549,7 +529,7 @@ var AnimationManager = new Class({
* Resume all paused animations. * Resume all paused animations.
* *
* @method Phaser.Animations.AnimationManager#resumeAll * @method Phaser.Animations.AnimationManager#resumeAll
* @fires ResumeAllAnimationEvent * @fires Phaser.Animations.Events#RESUME_ALL
* @since 3.0.0 * @since 3.0.0
* *
* @return {Phaser.Animations.AnimationManager} This Animation Manager. * @return {Phaser.Animations.AnimationManager} This Animation Manager.
@ -560,7 +540,7 @@ var AnimationManager = new Class({
{ {
this.paused = false; this.paused = false;
this.emit('resumeall'); this.emit(Events.RESUME_ALL);
} }
return this; return this;
@ -614,7 +594,7 @@ var AnimationManager = new Class({
* *
* @param {string} key - [description] * @param {string} key - [description]
* *
* @return {JSONAnimationManager} [description] * @return {Phaser.Animations.Types.JSONAnimations} [description]
*/ */
toJSON: function (key) toJSON: function (key)
{ {

View file

@ -0,0 +1,21 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Add Animation Event.
*
* This event is dispatched when a new animation is added to the global Animation Manager.
*
* This can happen either as a result of an animation instance being added to the Animation Manager,
* or the Animation Manager creating a new animation directly.
*
* @event Phaser.Animations.Events#ADD_ANIMATION
* @since 3.0.0
*
* @param {string} key - The key of the Animation that was added to the global Animation Manager.
* @param {Phaser.Animations.Animation} animation - An instance of the newly created Animation.
*/
module.exports = 'add';

View file

@ -0,0 +1,22 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Animation Complete Event.
*
* This event is dispatched by an Animation instance when it completes, i.e. finishes playing or is manually stopped.
*
* Be careful with the volume of events this could generate. If a group of Sprites all complete the same
* animation at the same time, this event will invoke its handler for each one of them.
*
* @event Phaser.Animations.Events#ANIMATION_COMPLETE
* @since 3.16.1
*
* @param {Phaser.Animations.Animation} animation - A reference to the Animation that completed.
* @param {Phaser.Animations.AnimationFrame} frame - The current Animation Frame that the Animation completed on.
* @param {Phaser.GameObjects.Sprite} gameObject - A reference to the Game Object on which the animation completed.
*/
module.exports = 'complete';

View file

@ -0,0 +1,21 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Animation Repeat Event.
*
* This event is dispatched when a currently playing animation repeats.
*
* The event is dispatched directly from the Animation object itself. Which means that listeners
* bound to this event will be invoked every time the Animation repeats, for every Game Object that may have it.
*
* @event Phaser.Animations.Events#ANIMATION_REPEAT
* @since 3.16.1
*
* @param {Phaser.Animations.Animation} animation - A reference to the Animation that repeated.
* @param {Phaser.Animations.AnimationFrame} frame - The current Animation Frame that the Animation was on when it repeated.
*/
module.exports = 'repeat';

View file

@ -0,0 +1,22 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Animation Restart Event.
*
* This event is dispatched by an Animation instance when it restarts.
*
* Be careful with the volume of events this could generate. If a group of Sprites all restart the same
* animation at the same time, this event will invoke its handler for each one of them.
*
* @event Phaser.Animations.Events#ANIMATION_RESTART
* @since 3.16.1
*
* @param {Phaser.Animations.Animation} animation - A reference to the Animation that restarted playing.
* @param {Phaser.Animations.AnimationFrame} frame - The current Animation Frame that the Animation restarted with.
* @param {Phaser.GameObjects.Sprite} gameObject - A reference to the Game Object on which the animation restarted playing.
*/
module.exports = 'restart';

View file

@ -0,0 +1,22 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Animation Start Event.
*
* This event is dispatched by an Animation instance when it starts playing.
*
* Be careful with the volume of events this could generate. If a group of Sprites all play the same
* animation at the same time, this event will invoke its handler for each one of them.
*
* @event Phaser.Animations.Events#ANIMATION_START
* @since 3.16.1
*
* @param {Phaser.Animations.Animation} animation - A reference to the Animation that started playing.
* @param {Phaser.Animations.AnimationFrame} frame - The current Animation Frame that the Animation started with.
* @param {Phaser.GameObjects.Sprite} gameObject - A reference to the Game Object on which the animation started playing.
*/
module.exports = 'start';

View file

@ -0,0 +1,18 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Pause All Animations Event.
*
* This event is dispatched when the global Animation Manager is told to pause.
*
* When this happens all current animations will stop updating, although it doesn't necessarily mean
* that the game has paused as well.
*
* @event Phaser.Animations.Events#PAUSE_ALL
* @since 3.0.0
*/
module.exports = 'pauseall';

View file

@ -0,0 +1,18 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Remove Animation Event.
*
* This event is dispatched when an animation is removed from the global Animation Manager.
*
* @event Phaser.Animations.Events#REMOVE_ANIMATION
* @since 3.0.0
*
* @param {string} key - The key of the Animation that was removed from the global Animation Manager.
* @param {Phaser.Animations.Animation} animation - An instance of the removed Animation.
*/
module.exports = 'remove';

View file

@ -0,0 +1,17 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Resume All Animations Event.
*
* This event is dispatched when the global Animation Manager resumes, having been previously paused.
*
* When this happens all current animations will continue updating again.
*
* @event Phaser.Animations.Events#RESUME_ALL
* @since 3.0.0
*/
module.exports = 'resumeall';

View file

@ -0,0 +1,23 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Sprite Animation Complete Event.
*
* This event is dispatched by a Sprite when an animation finishes playing on it.
*
* Listen for it on the Sprite using `sprite.on('animationcomplete', listener)`
*
* This same event is dispatched for all animations. To listen for a specific animation, use the `SPRITE_ANIMATION_KEY_COMPLETE` event.
*
* @event Phaser.Animations.Events#SPRITE_ANIMATION_COMPLETE
* @since 3.16.1
*
* @param {Phaser.Animations.Animation} animation - A reference to the Animation that completed.
* @param {Phaser.Animations.AnimationFrame} frame - The current Animation Frame that the Animation completed on.
* @param {Phaser.GameObjects.Sprite} gameObject - A reference to the Game Object on which the animation completed.
*/
module.exports = 'animationcomplete';

View file

@ -0,0 +1,22 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Sprite Animation Key Complete Event.
*
* This event is dispatched by a Sprite when a specific animation finishes playing on it.
*
* Listen for it on the Sprite using `sprite.on('animationcomplete-key', listener)` where `key` is the key of
* the animation. For example, if you had an animation with the key 'explode' you should listen for `animationcomplete-explode`.
*
* @event Phaser.Animations.Events#SPRITE_ANIMATION_KEY_COMPLETE
* @since 3.16.1
*
* @param {Phaser.Animations.Animation} animation - A reference to the Animation that completed.
* @param {Phaser.Animations.AnimationFrame} frame - The current Animation Frame that the Animation completed on.
* @param {Phaser.GameObjects.Sprite} gameObject - A reference to the Game Object on which the animation completed.
*/
module.exports = 'animationcomplete-';

View file

@ -0,0 +1,23 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Sprite Animation Key Repeat Event.
*
* This event is dispatched by a Sprite when a specific animation repeats playing on it.
*
* Listen for it on the Sprite using `sprite.on('animationrepeat-key', listener)` where `key` is the key of
* the animation. For example, if you had an animation with the key 'explode' you should listen for `animationrepeat-explode`.
*
* @event Phaser.Animations.Events#SPRITE_ANIMATION_KEY_REPEAT
* @since 3.16.1
*
* @param {Phaser.Animations.Animation} animation - A reference to the Animation that is repeating on the Sprite.
* @param {Phaser.Animations.AnimationFrame} frame - The current Animation Frame that the Animation started with.
* @param {integer} repeatCount - The number of times the Animation has repeated so far.
* @param {Phaser.GameObjects.Sprite} gameObject - A reference to the Game Object on which the animation repeated playing.
*/
module.exports = 'animationrepeat-';

View file

@ -0,0 +1,22 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Sprite Animation Key Restart Event.
*
* This event is dispatched by a Sprite when a specific animation restarts playing on it.
*
* Listen for it on the Sprite using `sprite.on('animationrestart-key', listener)` where `key` is the key of
* the animation. For example, if you had an animation with the key 'explode' you should listen for `animationrestart-explode`.
*
* @event Phaser.Animations.Events#SPRITE_ANIMATION_KEY_RESTART
* @since 3.16.1
*
* @param {Phaser.Animations.Animation} animation - A reference to the Animation that was restarted on the Sprite.
* @param {Phaser.Animations.AnimationFrame} frame - The current Animation Frame that the Animation restarted with.
* @param {Phaser.GameObjects.Sprite} gameObject - A reference to the Game Object on which the animation restarted playing.
*/
module.exports = 'animationrestart-';

View file

@ -0,0 +1,22 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Sprite Animation Key Start Event.
*
* This event is dispatched by a Sprite when a specific animation starts playing on it.
*
* Listen for it on the Sprite using `sprite.on('animationstart-key', listener)` where `key` is the key of
* the animation. For example, if you had an animation with the key 'explode' you should listen for `animationstart-explode`.
*
* @event Phaser.Animations.Events#SPRITE_ANIMATION_KEY_START
* @since 3.16.1
*
* @param {Phaser.Animations.Animation} animation - A reference to the Animation that was started on the Sprite.
* @param {Phaser.Animations.AnimationFrame} frame - The current Animation Frame that the Animation started with.
* @param {Phaser.GameObjects.Sprite} gameObject - A reference to the Game Object on which the animation started playing.
*/
module.exports = 'animationstart-';

View file

@ -0,0 +1,23 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Sprite Animation Key Update Event.
*
* This event is dispatched by a Sprite when a specific animation playing on it updates. This happens when the animation changes frame,
* based on the animation frame rate and other factors like `timeScale` and `delay`.
*
* Listen for it on the Sprite using `sprite.on('animationupdate-key', listener)` where `key` is the key of
* the animation. For example, if you had an animation with the key 'explode' you should listen for `animationupdate-explode`.
*
* @event Phaser.Animations.Events#SPRITE_ANIMATION_KEY_UPDATE
* @since 3.16.1
*
* @param {Phaser.Animations.Animation} animation - A reference to the Animation that has updated on the Sprite.
* @param {Phaser.Animations.AnimationFrame} frame - The current Animation Frame of the Animation.
* @param {Phaser.GameObjects.Sprite} gameObject - A reference to the Game Object on which the animation updated.
*/
module.exports = 'animationupdate-';

View file

@ -0,0 +1,24 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Sprite Animation Repeat Event.
*
* This event is dispatched by a Sprite when an animation repeats playing on it.
*
* Listen for it on the Sprite using `sprite.on('animationrepeat', listener)`
*
* This same event is dispatched for all animations. To listen for a specific animation, use the `SPRITE_ANIMATION_KEY_REPEAT` event.
*
* @event Phaser.Animations.Events#SPRITE_ANIMATION_REPEAT
* @since 3.16.1
*
* @param {Phaser.Animations.Animation} animation - A reference to the Animation that is repeating on the Sprite.
* @param {Phaser.Animations.AnimationFrame} frame - The current Animation Frame that the Animation started with.
* @param {integer} repeatCount - The number of times the Animation has repeated so far.
* @param {Phaser.GameObjects.Sprite} gameObject - A reference to the Game Object on which the animation repeated playing.
*/
module.exports = 'animationrepeat';

View file

@ -0,0 +1,23 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Sprite Animation Restart Event.
*
* This event is dispatched by a Sprite when an animation restarts playing on it.
*
* Listen for it on the Sprite using `sprite.on('animationrestart', listener)`
*
* This same event is dispatched for all animations. To listen for a specific animation, use the `SPRITE_ANIMATION_KEY_RESTART` event.
*
* @event Phaser.Animations.Events#SPRITE_ANIMATION_RESTART
* @since 3.16.1
*
* @param {Phaser.Animations.Animation} animation - A reference to the Animation that was restarted on the Sprite.
* @param {Phaser.Animations.AnimationFrame} frame - The current Animation Frame that the Animation restarted with.
* @param {Phaser.GameObjects.Sprite} gameObject - A reference to the Game Object on which the animation restarted playing.
*/
module.exports = 'animationrestart';

View file

@ -0,0 +1,23 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Sprite Animation Start Event.
*
* This event is dispatched by a Sprite when an animation starts playing on it.
*
* Listen for it on the Sprite using `sprite.on('animationstart', listener)`
*
* This same event is dispatched for all animations. To listen for a specific animation, use the `SPRITE_ANIMATION_KEY_START` event.
*
* @event Phaser.Animations.Events#SPRITE_ANIMATION_START
* @since 3.16.1
*
* @param {Phaser.Animations.Animation} animation - A reference to the Animation that was started on the Sprite.
* @param {Phaser.Animations.AnimationFrame} frame - The current Animation Frame that the Animation started with.
* @param {Phaser.GameObjects.Sprite} gameObject - A reference to the Game Object on which the animation started playing.
*/
module.exports = 'animationstart';

View file

@ -0,0 +1,24 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* The Sprite Animation Update Event.
*
* This event is dispatched by a Sprite when an animation playing on it updates. This happens when the animation changes frame,
* based on the animation frame rate and other factors like `timeScale` and `delay`.
*
* Listen for it on the Sprite using `sprite.on('animationupdate', listener)`
*
* This same event is dispatched for all animations. To listen for a specific animation, use the `SPRITE_ANIMATION_KEY_UPDATE` event.
*
* @event Phaser.Animations.Events#SPRITE_ANIMATION_UPDATE
* @since 3.16.1
*
* @param {Phaser.Animations.Animation} animation - A reference to the Animation that has updated on the Sprite.
* @param {Phaser.Animations.AnimationFrame} frame - The current Animation Frame of the Animation.
* @param {Phaser.GameObjects.Sprite} gameObject - A reference to the Game Object on which the animation updated.
*/
module.exports = 'animationupdate';

View file

@ -0,0 +1,32 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* @namespace Phaser.Animations.Events
*/
module.exports = {
ADD_ANIMATION: require('./ADD_ANIMATION_EVENT'),
ANIMATION_COMPLETE: require('./ANIMATION_COMPLETE_EVENT'),
ANIMATION_REPEAT: require('./ANIMATION_REPEAT_EVENT'),
ANIMATION_RESTART: require('./ANIMATION_RESTART_EVENT'),
ANIMATION_START: require('./ANIMATION_START_EVENT'),
PAUSE_ALL: require('./PAUSE_ALL_EVENT'),
REMOVE_ANIMATION: require('./REMOVE_ANIMATION_EVENT'),
RESUME_ALL: require('./RESUME_ALL_EVENT'),
SPRITE_ANIMATION_COMPLETE: require('./SPRITE_ANIMATION_COMPLETE_EVENT'),
SPRITE_ANIMATION_KEY_COMPLETE: require('./SPRITE_ANIMATION_KEY_COMPLETE_EVENT'),
SPRITE_ANIMATION_KEY_REPEAT: require('./SPRITE_ANIMATION_KEY_REPEAT_EVENT'),
SPRITE_ANIMATION_KEY_RESTART: require('./SPRITE_ANIMATION_KEY_RESTART_EVENT'),
SPRITE_ANIMATION_KEY_START: require('./SPRITE_ANIMATION_KEY_START_EVENT'),
SPRITE_ANIMATION_KEY_UPDATE: require('./SPRITE_ANIMATION_KEY_UPDATE_EVENT'),
SPRITE_ANIMATION_REPEAT: require('./SPRITE_ANIMATION_REPEAT_EVENT'),
SPRITE_ANIMATION_RESTART: require('./SPRITE_ANIMATION_RESTART_EVENT'),
SPRITE_ANIMATION_START: require('./SPRITE_ANIMATION_START_EVENT'),
SPRITE_ANIMATION_UPDATE: require('./SPRITE_ANIMATION_UPDATE_EVENT')
};

View file

@ -1,6 +1,6 @@
/** /**
* @author Richard Davey <rich@photonstorm.com> * @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd. * @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License} * @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/ */
@ -12,6 +12,7 @@ module.exports = {
Animation: require('./Animation'), Animation: require('./Animation'),
AnimationFrame: require('./AnimationFrame'), AnimationFrame: require('./AnimationFrame'),
AnimationManager: require('./AnimationManager') AnimationManager: require('./AnimationManager'),
Events: require('./events')
}; };

View file

@ -0,0 +1,17 @@
/**
* @typedef {object} Phaser.Animations.Types.Animation
* @since 3.0.0
*
* @property {string} [key] - The key that the animation will be associated with. i.e. sprite.animations.play(key)
* @property {Phaser.Animations.Types.AnimationFrame[]} [frames] - An object containing data used to generate the frames for the animation
* @property {string} [defaultTextureKey=null] - The key of the texture all frames of the animation will use. Can be overridden on a per frame basis.
* @property {integer} [frameRate] - The frame rate of playback in frames per second (default 24 if duration is null)
* @property {integer} [duration] - How long the animation should play for in milliseconds. If not given its derived from frameRate.
* @property {boolean} [skipMissedFrames=true] - Skip frames if the time lags, or always advanced anyway?
* @property {integer} [delay=0] - Delay before starting playback. Value given in milliseconds.
* @property {integer} [repeat=0] - Number of times to repeat the animation (-1 for infinity)
* @property {integer} [repeatDelay=0] - Delay before the animation repeats. Value given in milliseconds.
* @property {boolean} [yoyo=false] - Should the animation yoyo? (reverse back down to the start) before repeating?
* @property {boolean} [showOnStart=false] - Should sprite.visible = true when the animation starts to play?
* @property {boolean} [hideOnComplete=false] - Should sprite.visible = false when the animation finishes?
*/

View file

@ -0,0 +1,9 @@
/**
* @typedef {object} Phaser.Animations.Types.AnimationFrame
* @since 3.0.0
*
* @property {string} key - The key that the animation will be associated with. i.e. sprite.animations.play(key)
* @property {(string|number)} frame - [description]
* @property {number} [duration=0] - [description]
* @property {boolean} [visible] - [description]
*/

View file

@ -0,0 +1,12 @@
/**
* @typedef {object} Phaser.Animations.Types.GenerateFrameNames
* @since 3.0.0
*
* @property {string} [prefix=''] - The string to append to every resulting frame name if using a range or an array of `frames`.
* @property {integer} [start=0] - If `frames` is not provided, the number of the first frame to return.
* @property {integer} [end=0] - If `frames` is not provided, the number of the last frame to return.
* @property {string} [suffix=''] - The string to append to every resulting frame name if using a range or an array of `frames`.
* @property {integer} [zeroPad=0] - The minimum expected lengths of each resulting frame's number. Numbers will be left-padded with zeroes until they are this long, then prepended and appended to create the resulting frame name.
* @property {Phaser.Animations.Types.AnimationFrame[]} [outputArray=[]] - The array to append the created configuration objects to.
* @property {boolean} [frames=false] - If provided as an array, the range defined by `start` and `end` will be ignored and these frame numbers will be used.
*/

View file

@ -0,0 +1,10 @@
/**
* @typedef {object} Phaser.Animations.Types.GenerateFrameNumbers
* @since 3.0.0
*
* @property {integer} [start=0] - The starting frame of the animation.
* @property {integer} [end=-1] - The ending frame of the animation.
* @property {(boolean|integer)} [first=false] - A frame to put at the beginning of the animation, before `start` or `outputArray` or `frames`.
* @property {Phaser.Animations.Types.AnimationFrame[]} [outputArray=[]] - An array to concatenate the output onto.
* @property {(boolean|integer[])} [frames=false] - A custom sequence of frames.
*/

View file

@ -0,0 +1,17 @@
/**
* @typedef {object} Phaser.Animations.Types.JSONAnimation
* @since 3.0.0
*
* @property {string} key - The key that the animation will be associated with. i.e. sprite.animations.play(key)
* @property {string} type - A frame based animation (as opposed to a bone based animation)
* @property {Phaser.Animations.Types.JSONAnimationFrame[]} frames - [description]
* @property {integer} frameRate - The frame rate of playback in frames per second (default 24 if duration is null)
* @property {integer} duration - How long the animation should play for in milliseconds. If not given its derived from frameRate.
* @property {boolean} skipMissedFrames - Skip frames if the time lags, or always advanced anyway?
* @property {integer} delay - Delay before starting playback. Value given in milliseconds.
* @property {integer} repeat - Number of times to repeat the animation (-1 for infinity)
* @property {integer} repeatDelay - Delay before the animation repeats. Value given in milliseconds.
* @property {boolean} yoyo - Should the animation yoyo? (reverse back down to the start) before repeating?
* @property {boolean} showOnStart - Should sprite.visible = true when the animation starts to play?
* @property {boolean} hideOnComplete - Should sprite.visible = false when the animation finishes?
*/

View file

@ -0,0 +1,8 @@
/**
* @typedef {object} Phaser.Animations.Types.JSONAnimationFrame
* @since 3.0.0
*
* @property {string} key - The key of the Texture this AnimationFrame uses.
* @property {(string|integer)} frame - The key of the Frame within the Texture that this AnimationFrame uses.
* @property {number} duration - Additional time (in ms) that this frame should appear for during playback.
*/

View file

@ -0,0 +1,7 @@
/**
* @typedef {object} Phaser.Animations.Types.JSONAnimations
* @since 3.0.0
*
* @property {Phaser.Animations.Types.JSONAnimation[]} anims - An array of all Animations added to the Animation Manager.
* @property {number} globalTimeScale - The global time scale of the Animation Manager.
*/

View file

@ -0,0 +1,9 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2019 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* @namespace Phaser.Animations.Types
*/

View file

@ -1,746 +0,0 @@
/**
* @author Richard Davey <rich@photonstorm.com>
* @copyright 2018 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
var Class = require('../utils/Class');
var CONST = require('../const');
var Device = require('../device');
var GetFastValue = require('../utils/object/GetFastValue');
var GetValue = require('../utils/object/GetValue');
var IsPlainObject = require('../utils/object/IsPlainObject');
var PhaserMath = require('../math/');
var NOOP = require('../utils/NOOP');
var DefaultPlugins = require('../plugins/DefaultPlugins');
var ValueToColor = require('../display/color/ValueToColor');
/**
* This callback type is completely empty, a no-operation.
*
* @callback NOOP
*/
/**
* @callback BootCallback
*
* @param {Phaser.Game} game - The game.
*/
/**
* Config object containing various sound settings.
*
* @typedef {object} AudioConfig
*
* @property {boolean} [disableWebAudio=false] - Use HTML5 Audio instead of Web Audio.
* @property {AudioContext} [context] - An existing Web Audio context.
* @property {boolean} [noAudio=false] - Disable all audio output.
*
* @see Phaser.Sound.SoundManagerCreator
*/
/**
* @typedef {object} InputConfig
*
* @property {(boolean|KeyboardInputConfig)} [keyboard=true] - Keyboard input configuration. `true` uses the default configuration and `false` disables keyboard input.
* @property {(boolean|MouseInputConfig)} [mouse=true] - Mouse input configuration. `true` uses the default configuration and `false` disables mouse input.
* @property {(boolean|TouchInputConfig)} [touch=true] - Touch input configuration. `true` uses the default configuration and `false` disables touch input.
* @property {(boolean|GamepadInputConfig)} [gamepad=false] - Gamepad input configuration. `true` enables gamepad input.
* @property {integer} [activePointers=1] - The maximum number of touch pointers. See {@link Phaser.Input.InputManager#pointers}.
* @property {number} [smoothFactor=0] - The smoothing factor to apply during Pointer movement. See {@link Phaser.Input.Pointer#smoothFactor}.
*/
/**
* @typedef {object} MouseInputConfig
*
* @property {*} [target=null] - Where the Mouse Manager listens for mouse input events. The default is the game canvas.
* @property {boolean} [capture=true] - Whether mouse input events have `preventDefault` called on them.
*/
/**
* @typedef {object} KeyboardInputConfig
*
* @property {*} [target=window] - Where the Keyboard Manager listens for keyboard input events.
* @property {?integer} [capture] - `preventDefault` will be called on every non-modified key which has a key code in this array. By default it is empty.
*/
/**
* @typedef {object} TouchInputConfig
*
* @property {*} [target=null] - Where the Touch Manager listens for touch input events. The default is the game canvas.
* @property {boolean} [capture=true] - Whether touch input events have preventDefault() called on them.
*/
/**
* @typedef {object} GamepadInputConfig
*
* @property {*} [target=window] - Where the Gamepad Manager listens for gamepad input events.
*/
/**
* @typedef {object} BannerConfig
*
* @property {boolean} [hidePhaser=false] - Omit Phaser's name and version from the banner.
* @property {string} [text='#ffffff'] - The color of the banner text.
* @property {string[]} [background] - The background colors of the banner.
*/
/**
* @typedef {object} FPSConfig
*
* @property {integer} [min=5] - The minimum acceptable rendering rate, in frames per second.
* @property {integer} [target=60] - The optimum rendering rate, in frames per second.
* @property {boolean} [forceSetTimeOut=false] - Use setTimeout instead of requestAnimationFrame to run the game loop.
* @property {integer} [deltaHistory=10] - Calculate the average frame delta from this many consecutive frame intervals.
* @property {integer} [panicMax=120] - The amount of frames the time step counts before we trust the delta values again.
*/
/**
* @typedef {object} RenderConfig
*
* @property {boolean} [antialias=true] - When set to `true`, WebGL uses linear interpolation to draw scaled or rotated textures, giving a smooth appearance. When set to `false`, WebGL uses nearest-neighbor interpolation, giving a crisper appearance. `false` also disables antialiasing of the game canvas itself, if the browser supports it, when the game canvas is scaled.
* @property {boolean} [pixelArt=false] - Sets `antialias` and `roundPixels` to true. This is the best setting for pixel-art games.
* @property {boolean} [autoResize=true] - Automatically resize the Game Canvas if you resize the renderer.
* @property {boolean} [roundPixels=false] - Draw texture-based Game Objects at only whole-integer positions. Game Objects without textures, like Graphics, ignore this property.
* @property {boolean} [transparent=false] - Whether the game canvas will be transparent.
* @property {boolean} [clearBeforeRender=true] - Whether the game canvas will be cleared between each rendering frame.
* @property {boolean} [premultipliedAlpha=true] - In WebGL mode, the drawing buffer contains colors with pre-multiplied alpha.
* @property {boolean} [failIfMajorPerformanceCaveat=false] - Let the browser abort creating a WebGL context if it judges performance would be unacceptable.
* @property {string} [powerPreference='default'] - "high-performance", "low-power" or "default". A hint to the browser on how much device power the game might use.
* @property {integer} [batchSize=2000] - The default WebGL batch size.
* @property {integer} [maxLights=10] - The maximum number of lights allowed to be visible within range of a single Camera in the LightManager.
*/
/**
* @typedef {object} ScaleConfig
*
* @property {(integer|string)} [width=1024] - The base width of your game.
* @property {(integer|string)} [height=768] - The base height of your game.
* @property {integer} [zoom=1] - The zoom value of the game canvas.
* @property {number} [resolution=1] - The rendering resolution of the canvas.
* @property {(HTMLElement|string)} [parent] - The DOM element that will contain the game canvas, or its `id`. If null (the default) or if the named element doesn't exist, the game canvas is inserted directly into the document body.
* @property {integer} [mode=0] - The scale mode to apply to the canvas. SHOW_ALL, EXACT_FIT, USER_SCALE, or RESIZE.
* @property {integer} [minWidth] - The minimum width the canvas can be scaled down to.
* @property {integer} [minHeight] - The minimum height the canvas can be scaled down to.
* @property {integer} [maxWidth] - The maximum width the canvas can be scaled up to.
* @property {integer} [maxHeight] - The maximum height the canvas can be scaled up to.
*/
/**
* @typedef {object} CallbacksConfig
*
* @property {BootCallback} [preBoot=NOOP] - A function to run at the start of the boot sequence.
* @property {BootCallback} [postBoot=NOOP] - A function to run at the end of the boot sequence. At this point, all the game systems have started and plugins have been loaded.
*/
/**
* @typedef {object} LoaderConfig
*
* @property {string} [baseURL] - A URL used to resolve paths given to the loader. Example: 'http://labs.phaser.io/assets/'.
* @property {string} [path] - A URL path used to resolve relative paths given to the loader. Example: 'images/sprites/'.
* @property {integer} [maxParallelDownloads=32] - The maximum number of resources the loader will start loading at once.
* @property {(string|undefined)} [crossOrigin=undefined] - 'anonymous', 'use-credentials', or `undefined`. If you're not making cross-origin requests, leave this as `undefined`. See {@link https://developer.mozilla.org/en-US/docs/Web/HTML/CORS_settings_attributes}.
* @property {string} [responseType] - The response type of the XHR request, e.g. `blob`, `text`, etc.
* @property {boolean} [async=true] - Should the XHR request use async or not?
* @property {string} [user] - Optional username for all XHR requests.
* @property {string} [password] - Optional password for all XHR requests.
* @property {integer} [timeout=0] - Optional XHR timeout value, in ms.
*/
/**
* @typedef {object} DOMContainerConfig
*
* @property {boolean} [createContainer=false] - Create a div element in which DOM Elements will be contained. You must also provide a parent.
* @property {boolean} [behindCanvas=false] - Place the DOM Container behind the Phaser Canvas. The default is to place it over the Canvas.
*/
/**
* @typedef {object} ImagesConfig
*
* @property {string} [default] - URL to use for the 'default' texture.
* @property {string} [missing] - URL to use for the 'missing' texture.
*/
/**
* @typedef {object} PhysicsConfig
*
* @property {string} [default] - The default physics system. It will be started for each scene. Phaser provides 'arcade', 'impact', and 'matter'.
* @property {ArcadeWorldConfig} [arcade] - Arcade Physics configuration.
* @property {Phaser.Physics.Impact.WorldConfig} [impact] - Impact Physics configuration.
* @property {object} [matter] - Matter Physics configuration.
*/
/**
* @typedef {object} PluginObjectItem
*
* @property {string} [key] - A key to identify the plugin in the Plugin Manager.
* @property {*} [plugin] - The plugin itself. Usually a class/constructor.
* @property {boolean} [start] - Whether the plugin should be started automatically.
* @property {string} [systemKey] - For a scene plugin, add the plugin to the scene's systems object under this key (`this.sys.KEY`, from the scene).
* @property {string} [sceneKey] - For a scene plugin, add the plugin to the scene object under this key (`this.KEY`, from the scene).
* @property {string} [mapping] - If this plugin is to be injected into the Scene Systems, this is the property key map used.
* @property {*} [data] - Arbitrary data passed to the plugin's init() method.
*
* @example
* // Global plugin
* { key: 'BankPlugin', plugin: BankPluginV3, start: true, data: { gold: 5000 } }
* @example
* // Scene plugin
* { key: 'WireFramePlugin', plugin: WireFramePlugin, systemKey: 'wireFramePlugin', sceneKey: 'wireframe' }
*/
/**
* @typedef {object} PluginObject
*
* @property {?PluginObjectItem[]} [global] - Global plugins to install.
* @property {?PluginObjectItem[]} [scene] - Scene plugins to install.
* @property {string[]} [default] - The default set of scene plugins (names).
* @property {string[]} [defaultMerge] - Plugins to *add* to the default set of scene plugins.
*/
/**
* @typedef {object} GameConfig
*
* @property {(integer|string)} [width=1024] - The width of the game, in game pixels.
* @property {(integer|string)} [height=768] - The height of the game, in game pixels.
* @property {number} [zoom=1] - Simple scale applied to the game canvas. 2 is double size, 0.5 is half size, etc.
* @property {number} [resolution=1] - The size of each game pixel, in canvas pixels. Values larger than 1 are "high" resolution.
* @property {number} [type=CONST.AUTO] - Which renderer to use. Phaser.AUTO, Phaser.CANVAS, Phaser.HEADLESS, or Phaser.WEBGL. AUTO picks WEBGL if available, otherwise CANVAS.
* @property {(HTMLElement|string)} [parent=null] - The DOM element that will contain the game canvas, or its `id`. If null (the default) or if the named element doesn't exist, the game canvas is inserted directly into the document body.
* @property {HTMLCanvasElement} [canvas=null] - Provide your own Canvas element for Phaser to use instead of creating one.
* @property {string} [canvasStyle=null] - CSS styles to apply to the game canvas instead of Phaser's default styles.
* @property {CanvasRenderingContext2D} [context] - Provide your own Canvas Context for Phaser to use, instead of creating one.
* @property {object} [scene=null] - A scene or scenes to add to the game. If several are given, the first is started; the remainder are started only if they have { active: true }.
* @property {string[]} [seed] - Seed for the random number generator.
* @property {string} [title=''] - The title of the game. Shown in the browser console.
* @property {string} [url='http://phaser.io'] - The URL of the game. Shown in the browser console.
* @property {string} [version=''] - The version of the game. Shown in the browser console.
* @property {boolean} [autoFocus=true] - Automatically call window.focus() when the game boots. Usually necessary to capture input events if the game is in a separate frame.
* @property {(boolean|InputConfig)} [input] - Input configuration, or `false` to disable all game input.
* @property {boolean} [disableContextMenu=false] - Disable the browser's default 'contextmenu' event (usually triggered by a right-button mouse click).
* @property {(boolean|BannerConfig)} [banner=false] - Configuration for the banner printed in the browser console when the game starts.
* @property {DOMContainerConfig} [dom] - The DOM Container configuration object.
* @property {FPSConfig} [fps] - Game loop configuration.
* @property {RenderConfig} [render] - Game renderer configuration.
* @property {(string|number)} [backgroundColor=0x000000] - The background color of the game canvas. The default is black.
* @property {CallbacksConfig} [callbacks] - Optional callbacks to run before or after game boot.
* @property {LoaderConfig} [loader] - Loader configuration.
* @property {ImagesConfig} [images] - Images configuration.
* @property {object} [physics] - Physics configuration.
* @property {PluginObject|PluginObjectItem[]} [plugins] - Plugins to install.
*/
/**
* @classdesc
* The active game configuration settings, parsed from a {@link GameConfig} object.
*
* @class Config
* @memberof Phaser.Boot
* @constructor
* @since 3.0.0
*
* @param {GameConfig} [GameConfig] - The configuration object for your Phaser Game instance.
*
* @see Phaser.Game#config
*/
var Config = new Class({
initialize:
function Config (config)
{
if (config === undefined) { config = {}; }
var defaultBannerColor = [
'#ff0000',
'#ffff00',
'#00ff00',
'#00ffff',
'#000000'
];
var defaultBannerTextColor = '#ffffff';
/**
* @const {(integer|string)} Phaser.Boot.Config#width - The width of the underlying canvas, in pixels.
*/
this.width = GetValue(config, 'width', 1024);
/**
* @const {(integer|string)} Phaser.Boot.Config#height - The height of the underlying canvas, in pixels.
*/
this.height = GetValue(config, 'height', 768);
/**
* @const {number} Phaser.Boot.Config#zoom - The zoom factor, as used by the Scale Manager.
*/
this.zoom = GetValue(config, 'zoom', 1);
/**
* @const {number} Phaser.Boot.Config#resolution - The canvas device pixel resolution.
*/
this.resolution = GetValue(config, 'resolution', 1);
/**
* @const {?*} Phaser.Boot.Config#parent - A parent DOM element into which the canvas created by the renderer will be injected.
*/
this.parent = GetValue(config, 'parent', null);
/**
* @const {integer} Phaser.Boot.Config#scaleMode - The scale mode as used by the Scale Manager. The default is zero, which is no scaling.
*/
this.scaleMode = GetValue(config, 'scaleMode', 0);
/**
* @const {boolean} Phaser.Boot.Config#expandParent - Is the Scale Manager allowed to adjust the size of the parent container?
*/
this.expandParent = GetValue(config, 'expandParent', false);
/**
* @const {integer} Phaser.Boot.Config#minWidth - The minimum width, in pixels, the canvas will scale down to. A value of zero means no minimum.
*/
this.minWidth = GetValue(config, 'minWidth', 0);
/**
* @const {integer} Phaser.Boot.Config#maxWidth - The maximum width, in pixels, the canvas will scale up to. A value of zero means no maximum.
*/
this.maxWidth = GetValue(config, 'maxWidth', 0);
/**
* @const {integer} Phaser.Boot.Config#minHeight - The minimum height, in pixels, the canvas will scale down to. A value of zero means no minimum.
*/
this.minHeight = GetValue(config, 'minHeight', 0);
/**
* @const {integer} Phaser.Boot.Config#maxHeight - The maximum height, in pixels, the canvas will scale up to. A value of zero means no maximum.
*/
this.maxHeight = GetValue(config, 'maxHeight', 0);
// Scale Manager - Anything set in here over-rides anything set above
var scaleConfig = GetValue(config, 'scale', null);
if (scaleConfig)
{
this.width = GetValue(scaleConfig, 'width', this.width);
this.height = GetValue(scaleConfig, 'height', this.height);
this.zoom = GetValue(scaleConfig, 'zoom', this.zoom);
this.resolution = GetValue(scaleConfig, 'resolution', this.resolution);
this.parent = GetValue(scaleConfig, 'parent', this.parent);
this.scaleMode = GetValue(scaleConfig, 'mode', this.scaleMode);
this.expandParent = GetValue(scaleConfig, 'mode', this.expandParent);
this.minWidth = GetValue(scaleConfig, 'min.width', this.minWidth);
this.maxWidth = GetValue(scaleConfig, 'max.width', this.maxWidth);
this.minHeight = GetValue(scaleConfig, 'min.height', this.minHeight);
this.maxHeight = GetValue(scaleConfig, 'max.height', this.maxHeight);
}
/**
* @const {number} Phaser.Boot.Config#renderType - Force Phaser to use a specific renderer. Can be `CONST.CANVAS`, `CONST.WEBGL`, `CONST.HEADLESS` or `CONST.AUTO` (default)
*/
this.renderType = GetValue(config, 'type', CONST.AUTO);
/**
* @const {?HTMLCanvasElement} Phaser.Boot.Config#canvas - Force Phaser to use your own Canvas element instead of creating one.
*/
this.canvas = GetValue(config, 'canvas', null);
/**
* @const {?(CanvasRenderingContext2D|WebGLRenderingContext)} Phaser.Boot.Config#context - Force Phaser to use your own Canvas context instead of creating one.
*/
this.context = GetValue(config, 'context', null);
/**
* @const {?string} Phaser.Boot.Config#canvasStyle - Optional CSS attributes to be set on the canvas object created by the renderer.
*/
this.canvasStyle = GetValue(config, 'canvasStyle', null);
/**
* @const {boolean} Phaser.Boot.Config#customEnvironment - Is Phaser running under a custom (non-native web) environment? If so, set this to `true` to skip internal Feature detection. If `true` the `renderType` cannot be left as `AUTO`.
*/
this.customEnvironment = GetValue(config, 'customEnvironment', false);
/**
* @const {?object} Phaser.Boot.Config#sceneConfig - The default Scene configuration object.
*/
this.sceneConfig = GetValue(config, 'scene', null);
/**
* @const {string[]} Phaser.Boot.Config#seed - A seed which the Random Data Generator will use. If not given, a dynamic seed based on the time is used.
*/
this.seed = GetValue(config, 'seed', [ (Date.now() * Math.random()).toString() ]);
PhaserMath.RND = new PhaserMath.RandomDataGenerator(this.seed);
/**
* @const {string} Phaser.Boot.Config#gameTitle - The title of the game.
*/
this.gameTitle = GetValue(config, 'title', '');
/**
* @const {string} Phaser.Boot.Config#gameURL - The URL of the game.
*/
this.gameURL = GetValue(config, 'url', 'https://phaser.io');
/**
* @const {string} Phaser.Boot.Config#gameVersion - The version of the game.
*/
this.gameVersion = GetValue(config, 'version', '');
/**
* @const {boolean} Phaser.Boot.Config#autoFocus - If `true` the window will automatically be given focus immediately and on any future mousedown event.
*/
this.autoFocus = GetValue(config, 'autoFocus', true);
// DOM Element Container
/**
* @const {?boolean} Phaser.Boot.Config#domCreateContainer - EXPERIMENTAL: Do not currently use.
*/
this.domCreateContainer = GetValue(config, 'dom.createContainer', false);
/**
* @const {?boolean} Phaser.Boot.Config#domBehindCanvas - EXPERIMENTAL: Do not currently use.
*/
this.domBehindCanvas = GetValue(config, 'dom.behindCanvas', false);
// Input
/**
* @const {boolean} Phaser.Boot.Config#inputKeyboard - Enable the Keyboard Plugin. This can be disabled in games that don't need keyboard input.
*/
this.inputKeyboard = GetValue(config, 'input.keyboard', true);
/**
* @const {*} Phaser.Boot.Config#inputKeyboardEventTarget - The DOM Target to listen for keyboard events on. Defaults to `window` if not specified.
*/
this.inputKeyboardEventTarget = GetValue(config, 'input.keyboard.target', window);
/**
* @const {?integer[]} Phaser.Boot.Config#inputKeyboardCapture - `preventDefault` will be called on every non-modified key which has a key code in this array. By default, it is empty.
*/
this.inputKeyboardCapture = GetValue(config, 'input.keyboard.capture', []);
/**
* @const {(boolean|object)} Phaser.Boot.Config#inputMouse - Enable the Mouse Plugin. This can be disabled in games that don't need mouse input.
*/
this.inputMouse = GetValue(config, 'input.mouse', true);
/**
* @const {?*} Phaser.Boot.Config#inputMouseEventTarget - The DOM Target to listen for mouse events on. Defaults to the game canvas if not specified.
*/
this.inputMouseEventTarget = GetValue(config, 'input.mouse.target', null);
/**
* @const {boolean} Phaser.Boot.Config#inputMouseCapture - Should mouse events be captured? I.e. have prevent default called on them.
*/
this.inputMouseCapture = GetValue(config, 'input.mouse.capture', true);
/**
* @const {boolean} Phaser.Boot.Config#inputTouch - Enable the Touch Plugin. This can be disabled in games that don't need touch input.
*/
this.inputTouch = GetValue(config, 'input.touch', Device.input.touch);
/**
* @const {?*} Phaser.Boot.Config#inputTouchEventTarget - The DOM Target to listen for touch events on. Defaults to the game canvas if not specified.
*/
this.inputTouchEventTarget = GetValue(config, 'input.touch.target', null);
/**
* @const {boolean} Phaser.Boot.Config#inputTouchCapture - Should touch events be captured? I.e. have prevent default called on them.
*/
this.inputTouchCapture = GetValue(config, 'input.touch.capture', true);
/**
* @const {integer} Phaser.Boot.Config#inputActivePointers - The number of Pointer objects created by default. In a mouse-only, or non-multi touch game, you can leave this as 1.
*/
this.inputActivePointers = GetValue(config, 'input.activePointers', 1);
/**
* @const {integer} Phaser.Boot.Config#inputSmoothFactor - The smoothing factor to apply during Pointer movement. See {@link Phaser.Input.Pointer#smoothFactor}.
*/
this.inputSmoothFactor = GetValue(config, 'input.smoothFactor', 0);
/**
* @const {boolean} Phaser.Boot.Config#inputGamepad - Enable the Gamepad Plugin. This can be disabled in games that don't need gamepad input.
*/
this.inputGamepad = GetValue(config, 'input.gamepad', false);
/**
* @const {*} Phaser.Boot.Config#inputGamepadEventTarget - The DOM Target to listen for gamepad events on. Defaults to `window` if not specified.
*/
this.inputGamepadEventTarget = GetValue(config, 'input.gamepad.target', window);
/**
* @const {boolean} Phaser.Boot.Config#disableContextMenu - Set to `true` to disable the right-click context menu.
*/
this.disableContextMenu = GetValue(config, 'disableContextMenu', false);
/**
* @const {AudioConfig} Phaser.Boot.Config#audio - The Audio Configuration object.
*/
this.audio = GetValue(config, 'audio');
// If you do: { banner: false } it won't display any banner at all
/**
* @const {boolean} Phaser.Boot.Config#hideBanner - Don't write the banner line to the console.log.
*/
this.hideBanner = (GetValue(config, 'banner', null) === false);
/**
* @const {boolean} Phaser.Boot.Config#hidePhaser - Omit Phaser's name and version from the banner.
*/
this.hidePhaser = GetValue(config, 'banner.hidePhaser', false);
/**
* @const {string} Phaser.Boot.Config#bannerTextColor - The color of the banner text.
*/
this.bannerTextColor = GetValue(config, 'banner.text', defaultBannerTextColor);
/**
* @const {string[]} Phaser.Boot.Config#bannerBackgroundColor - The background colors of the banner.
*/
this.bannerBackgroundColor = GetValue(config, 'banner.background', defaultBannerColor);
if (this.gameTitle === '' && this.hidePhaser)
{
this.hideBanner = true;
}
/**
* @const {?FPSConfig} Phaser.Boot.Config#fps - The Frame Rate Configuration object, as parsed by the Timestep class.
*/
this.fps = GetValue(config, 'fps', null);
// Renderer Settings
// These can either be in a `render` object within the Config, or specified on their own
var renderConfig = GetValue(config, 'render', config);
/**
* @const {boolean} Phaser.Boot.Config#autoResize - Automatically resize the Game Canvas if you resize the renderer.
*/
this.autoResize = GetValue(renderConfig, 'autoResize', true);
/**
* @const {boolean} Phaser.Boot.Config#antialias - When set to `true`, WebGL uses linear interpolation to draw scaled or rotated textures, giving a smooth appearance. When set to `false`, WebGL uses nearest-neighbor interpolation, giving a crisper appearance. `false` also disables antialiasing of the game canvas itself, if the browser supports it, when the game canvas is scaled.
*/
this.antialias = GetValue(renderConfig, 'antialias', true);
/**
* @const {boolean} Phaser.Boot.Config#roundPixels - Draw texture-based Game Objects at only whole-integer positions. Game Objects without textures, like Graphics, ignore this property.
*/
this.roundPixels = GetValue(renderConfig, 'roundPixels', false);
/**
* @const {boolean} Phaser.Boot.Config#pixelArt - Prevent pixel art from becoming blurred when scaled. It will remain crisp (tells the WebGL renderer to automatically create textures using a linear filter mode).
*/
this.pixelArt = GetValue(renderConfig, 'pixelArt', false);
if (this.pixelArt)
{
this.antialias = false;
this.roundPixels = true;
}
/**
* @const {boolean} Phaser.Boot.Config#transparent - Whether the game canvas will have a transparent background.
*/
this.transparent = GetValue(renderConfig, 'transparent', false);
/**
* @const {boolean} Phaser.Boot.Config#clearBeforeRender - Whether the game canvas will be cleared between each rendering frame. You can disable this if you have a full-screen background image or game object.
*/
this.clearBeforeRender = GetValue(renderConfig, 'clearBeforeRender', true);
/**
* @const {boolean} Phaser.Boot.Config#premultipliedAlpha - In WebGL mode, sets the drawing buffer to contain colors with pre-multiplied alpha.
*/
this.premultipliedAlpha = GetValue(renderConfig, 'premultipliedAlpha', true);
/**
* @const {boolean} Phaser.Boot.Config#failIfMajorPerformanceCaveat - Let the browser abort creating a WebGL context if it judges performance would be unacceptable.
*/
this.failIfMajorPerformanceCaveat = GetValue(renderConfig, 'failIfMajorPerformanceCaveat', false);
/**
* @const {string} Phaser.Boot.Config#powerPreference - "high-performance", "low-power" or "default". A hint to the browser on how much device power the game might use.
*/
this.powerPreference = GetValue(renderConfig, 'powerPreference', 'default');
/**
* @const {integer} Phaser.Boot.Config#batchSize - The default WebGL Batch size.
*/
this.batchSize = GetValue(renderConfig, 'batchSize', 2000);
/**
* @const {integer} Phaser.Boot.Config#maxLights - The maximum number of lights allowed to be visible within range of a single Camera in the LightManager.
*/
this.maxLights = GetValue(renderConfig, 'maxLights', 10);
var bgc = GetValue(config, 'backgroundColor', 0);
/**
* @const {Phaser.Display.Color} Phaser.Boot.Config#backgroundColor - The background color of the game canvas. The default is black. This value is ignored if `transparent` is set to `true`.
*/
this.backgroundColor = ValueToColor(bgc);
if (bgc === 0 && this.transparent)
{
this.backgroundColor.alpha = 0;
}
/**
* @const {BootCallback} Phaser.Boot.Config#preBoot - Called before Phaser boots. Useful for initializing anything not related to Phaser that Phaser may require while booting.
*/
this.preBoot = GetValue(config, 'callbacks.preBoot', NOOP);
/**
* @const {BootCallback} Phaser.Boot.Config#postBoot - A function to run at the end of the boot sequence. At this point, all the game systems have started and plugins have been loaded.
*/
this.postBoot = GetValue(config, 'callbacks.postBoot', NOOP);
/**
* @const {PhysicsConfig} Phaser.Boot.Config#physics - The Physics Configuration object.
*/
this.physics = GetValue(config, 'physics', {});
/**
* @const {(boolean|string)} Phaser.Boot.Config#defaultPhysicsSystem - The default physics system. It will be started for each scene. Either 'arcade', 'impact' or 'matter'.
*/
this.defaultPhysicsSystem = GetValue(this.physics, 'default', false);
/**
* @const {string} Phaser.Boot.Config#loaderBaseURL - A URL used to resolve paths given to the loader. Example: 'http://labs.phaser.io/assets/'.
*/
this.loaderBaseURL = GetValue(config, 'loader.baseURL', '');
/**
* @const {string} Phaser.Boot.Config#loaderPath - A URL path used to resolve relative paths given to the loader. Example: 'images/sprites/'.
*/
this.loaderPath = GetValue(config, 'loader.path', '');
/**
* @const {integer} Phaser.Boot.Config#loaderMaxParallelDownloads - Maximum parallel downloads allowed for resources (Default to 32).
*/
this.loaderMaxParallelDownloads = GetValue(config, 'loader.maxParallelDownloads', 32);
/**
* @const {(string|undefined)} Phaser.Boot.Config#loaderCrossOrigin - 'anonymous', 'use-credentials', or `undefined`. If you're not making cross-origin requests, leave this as `undefined`. See {@link https://developer.mozilla.org/en-US/docs/Web/HTML/CORS_settings_attributes}.
*/
this.loaderCrossOrigin = GetValue(config, 'loader.crossOrigin', undefined);
/**
* @const {string} Phaser.Boot.Config#loaderResponseType - The response type of the XHR request, e.g. `blob`, `text`, etc.
*/
this.loaderResponseType = GetValue(config, 'loader.responseType', '');
/**
* @const {boolean} Phaser.Boot.Config#loaderAsync - Should the XHR request use async or not?
*/
this.loaderAsync = GetValue(config, 'loader.async', true);
/**
* @const {string} Phaser.Boot.Config#loaderUser - Optional username for all XHR requests.
*/
this.loaderUser = GetValue(config, 'loader.user', '');
/**
* @const {string} Phaser.Boot.Config#loaderPassword - Optional password for all XHR requests.
*/
this.loaderPassword = GetValue(config, 'loader.password', '');
/**
* @const {integer} Phaser.Boot.Config#loaderTimeout - Optional XHR timeout value, in ms.
*/
this.loaderTimeout = GetValue(config, 'loader.timeout', 0);
/*
* Allows `plugins` property to either be an array, in which case it just replaces
* the default plugins like previously, or a config object.
*
* plugins: {
* global: [
* { key: 'TestPlugin', plugin: TestPlugin, start: true, data: { msg: 'The plugin is alive' } },
* ],
* scene: [
* { key: 'WireFramePlugin', plugin: WireFramePlugin, systemKey: 'wireFramePlugin', sceneKey: 'wireframe' }
* ],
* default: [], OR
* defaultMerge: [
* 'ModPlayer'
* ]
* }
*/
/**
* @const {any} Phaser.Boot.Config#installGlobalPlugins - An array of global plugins to be installed.
*/
this.installGlobalPlugins = [];
/**
* @const {any} Phaser.Boot.Config#installScenePlugins - An array of Scene level plugins to be installed.
*/
this.installScenePlugins = [];
var plugins = GetValue(config, 'plugins', null);
var defaultPlugins = DefaultPlugins.DefaultScene;
if (plugins)
{
// Old 3.7 array format?
if (Array.isArray(plugins))
{
this.defaultPlugins = plugins;
}
else if (IsPlainObject(plugins))
{
this.installGlobalPlugins = GetFastValue(plugins, 'global', []);
this.installScenePlugins = GetFastValue(plugins, 'scene', []);
if (Array.isArray(plugins.default))
{
defaultPlugins = plugins.default;
}
else if (Array.isArray(plugins.defaultMerge))
{
defaultPlugins = defaultPlugins.concat(plugins.defaultMerge);
}
}
}
/**
* @const {any} Phaser.Boot.Config#defaultPlugins - The plugins installed into every Scene (in addition to CoreScene and Global).
*/
this.defaultPlugins = defaultPlugins;
// Default / Missing Images
var pngPrefix = 'data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAg';
/**
* @const {string} Phaser.Boot.Config#defaultImage - A base64 encoded PNG that will be used as the default blank texture.
*/
this.defaultImage = GetValue(config, 'images.default', pngPrefix + 'AQMAAABJtOi3AAAAA1BMVEX///+nxBvIAAAAAXRSTlMAQObYZgAAABVJREFUeF7NwIEAAAAAgKD9qdeocAMAoAABm3DkcAAAAABJRU5ErkJggg==');
/**
* @const {string} Phaser.Boot.Config#missingImage - A base64 encoded PNG that will be used as the default texture when a texture is assigned that is missing or not loaded.
*/
this.missingImage = GetValue(config, 'images.missing', pngPrefix + 'CAIAAAD8GO2jAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAJ9JREFUeNq01ssOwyAMRFG46v//Mt1ESmgh+DFmE2GPOBARKb2NVjo+17PXLD8a1+pl5+A+wSgFygymWYHBb0FtsKhJDdZlncG2IzJ4ayoMDv20wTmSMzClEgbWYNTAkQ0Z+OJ+A/eWnAaR9+oxCF4Os0H8htsMUp+pwcgBBiMNnAwF8GqIgL2hAzaGFFgZauDPKABmowZ4GL369/0rwACp2yA/ttmvsQAAAABJRU5ErkJggg==');
if (window)
{
if (window.FORCE_WEBGL)
{
this.renderType = CONST.WEBGL;
}
else if (window.FORCE_CANVAS)
{
this.renderType = CONST.CANVAS;
}
}
}
});
module.exports = Config;

Some files were not shown because too many files have changed in this diff Show more