Skip to content

Commit

Permalink
Application: new pauseOnBlur, resumeOnFocus and stopOnBlur prop…
Browse files Browse the repository at this point in the history
…erties to configure a game behavior on blur and focus events

- this will allow later to have different behavior based on game instance (see #1091)
- `pauseOnBlur`, `resumeOnFocus` and `stopOnBlur` device properties are now deprecated and replaced by their Application counterpart
  • Loading branch information
obiot committed Jun 2, 2023
1 parent f2f7489 commit 6238f73
Show file tree
Hide file tree
Showing 4 changed files with 73 additions and 35 deletions.
6 changes: 5 additions & 1 deletion CHANGELOG.md
@@ -1,9 +1,13 @@
# Changelog

## [15.4.0] (melonJS 2) - _2023-05-xx_
## [15.4.0] (melonJS 2) - _2023-06-xx_

### Added
- Application: new `pauseOnBlur`, `resumeOnFocus` and `stopOnBlur` properties to configure a game behavior on blur and focus events

### Changed
- Core: visibility and focus/blur events are now managed internally through new global `BLUR` and `FOCUS` events
- Device: `pauseOnBlur`, `resumeOnFocus` and `stopOnBlur` properties are now deprecated and replaced by their Application counterpart

### Fixed
- Renderable : fix a potential issue with a Tile Layer not being properly redrawn when adding or clearing individual tiles
Expand Down
45 changes: 45 additions & 0 deletions src/application/application.js
Expand Up @@ -85,6 +85,30 @@ import { CANVAS, WEBGL, AUTO } from "../const.js";
*/
this.settings = undefined;

/**
* Specify whether to pause this app when losing focus
* @type {boolean}
* @default true
* @example
* // keep the default game instance running even when loosing focus
* me.game.pauseOnBlur = false;
*/
this.pauseOnBlur = true;

/**
* Specify whether to unpause this app when gaining back focus
* @type {boolean}
* @default true
*/
this.resumeOnFocus = true;

/**
* Specify whether to stop this app when losing focus
* @type {boolean}
* @default false
*/
this.stopOnBlur = false;

// to know when we have to refresh the display
this.isDirty = true;

Expand Down Expand Up @@ -234,6 +258,27 @@ import { CANVAS, WEBGL, AUTO } from "../const.js";
// render all game objects
this.draw();
}, this);


// on blur event, pause the current
event.on(event.BLUR, () => {
if (this.stopOnBlur === true) {
state.stop(true);
}
if (this.pauseOnBlur === true) {
state.pause(true);
}
});

// on focus event, restart or resume the current
event.on(event.FOCUS, () => {
if (this.stopOnBlur === true) {
state.restart(true);
}
if (this.resumeOnFocus === true) {
state.resume(true);
}
});
}

/**
Expand Down
25 changes: 0 additions & 25 deletions src/state/state.js
Expand Up @@ -2,7 +2,6 @@ import { pauseTrack, resumeTrack } from "./../audio/audio.js";
import * as fctUtil from "./../utils/function.js";
import * as event from "./../system/event.js";
import { game } from "../index.js";
import * as device from "./../system/device.js";
import Stage from "./../state/stage.js";
import DefaultLoadingScreen from "./../loader/loadingscreen.js";

Expand Down Expand Up @@ -134,30 +133,6 @@ event.on(event.BOOT, () => {
event.on(event.VIDEO_INIT, () => {
state.change(state.DEFAULT, true);
});

// on blur event, pause the current
event.on(event.BLUR, () => {
if (device.stopOnBlur === true) {
state.stop(true);
}
if (device.pauseOnBlur === true) {
state.pause(true);
}
});

// on focus event, restart or resume the current
event.on(event.FOCUS, () => {
if (device.stopOnBlur === true) {
state.restart(true);
}
if (device.resumeOnFocus === true) {
state.resume(true);
}
// force focus if autofocus is on
if (device.autoFocus === true) {
device.focus();
}
});
});

/**
Expand Down
32 changes: 23 additions & 9 deletions src/system/device.js
Expand Up @@ -350,6 +350,8 @@ export let alpha = 0;
* Specify whether to pause the game when losing focus
* @name pauseOnBlur
* @memberof device
* @deprecated since 15.4.0
* @see Application.pauseOnBlur
* @type {boolean}
* @public
* @default true
Expand All @@ -360,32 +362,36 @@ export let pauseOnBlur = true;
* Specify whether to unpause the game when gaining focus
* @name resumeOnFocus
* @memberof device
* @deprecated since 15.4.0
* @see Application.resumeOnFocus
* @type {boolean}
* @public
* @default true
*/
export let resumeOnFocus = true;

/**
* Specify whether to automatically bring the window to the front
* @name autoFocus
* Specify whether to stop the game when losing focus or not.
* The engine restarts on focus if this is enabled.
* @name stopOnBlur
* @memberof device
* @deprecated since 15.4.0
* @see Application.stopOnBlur
* @type {boolean}
* @public
* @default true
* @default false
*/
export let autoFocus = true;
export let stopOnBlur = false;

/**
* Specify whether to stop the game when losing focus or not.
* The engine restarts on focus if this is enabled.
* @name stopOnBlur
* Specify whether to automatically bring the window to the front
* @name autoFocus
* @memberof device
* @type {boolean}
* @public
* @default false
* @default true
*/
export let stopOnBlur = false;
export let autoFocus = true;

/**
* specify a function to execute when the Device is fully loaded and ready
Expand Down Expand Up @@ -442,6 +448,10 @@ export function onReady(fn) {
// set restart/resume action on gaining focus
globalThis.addEventListener("focus", () => {
event.emit(event.FOCUS);
// force focus if autofocus is on
if (autoFocus === true) {
this.focus();
}
}, false);
}
if (typeof globalThis.document !== "undefined") {
Expand All @@ -450,6 +460,10 @@ export function onReady(fn) {
globalThis.document.addEventListener("visibilitychange", () => {
if (globalThis.document.visibilityState === "visible") {
event.emit(event.FOCUS);
// force focus if autofocus is on
if (autoFocus === true) {
this.focus();
}
} else {
event.emit(event.BLUR);
}
Expand Down

0 comments on commit 6238f73

Please sign in to comment.