Working on end-game menu
This commit is contained in:
parent
f6879046fa
commit
2e1c73c9dc
@ -41,7 +41,6 @@ export class Engine {
|
|||||||
|
|
||||||
export default class GameMaster {
|
export default class GameMaster {
|
||||||
public currentScene: Scene;
|
public currentScene: Scene;
|
||||||
private GameObjects: GameObject[] = [];
|
|
||||||
|
|
||||||
constructor() {
|
constructor() {
|
||||||
Engine.GameMaster = this;
|
Engine.GameMaster = this;
|
||||||
@ -61,9 +60,6 @@ export default class GameMaster {
|
|||||||
if (this.currentScene) {
|
if (this.currentScene) {
|
||||||
this.currentScene.destroy();
|
this.currentScene.destroy();
|
||||||
}
|
}
|
||||||
this.GameObjects.forEach((element) => {
|
|
||||||
element.destroy();
|
|
||||||
});
|
|
||||||
this.currentScene = newScene;
|
this.currentScene = newScene;
|
||||||
this.currentScene.init();
|
this.currentScene.init();
|
||||||
}
|
}
|
||||||
|
@ -28,9 +28,3 @@ export enum StatsEvents {
|
|||||||
export enum GemEvents {
|
export enum GemEvents {
|
||||||
TowerPanelSelectGem = 'towerTabSelectGem',
|
TowerPanelSelectGem = 'towerTabSelectGem',
|
||||||
}
|
}
|
||||||
|
|
||||||
export enum EndMissionDialogEvents {
|
|
||||||
NextMission = 'nextMission',
|
|
||||||
RetryMission = 'retryMission',
|
|
||||||
MainMenu = 'mainMenu',
|
|
||||||
}
|
|
||||||
|
@ -3,7 +3,9 @@ import { Engine } from './Bastion';
|
|||||||
export default class GameUIConstants {
|
export default class GameUIConstants {
|
||||||
public static SidebarRect: PIXI.Rectangle;
|
public static SidebarRect: PIXI.Rectangle;
|
||||||
public static ChangeRoundButtonRect: PIXI.Rectangle;
|
public static ChangeRoundButtonRect: PIXI.Rectangle;
|
||||||
public static EndGameDialogRect: PIXI.Rectangle;
|
public static StandardDialogWidth: number;
|
||||||
|
public static StandardDialogHeight: number;
|
||||||
|
public static MaximumPlayerNameLength = 20;
|
||||||
|
|
||||||
public static init() {
|
public static init() {
|
||||||
GameUIConstants.SidebarRect = new PIXI.Rectangle(
|
GameUIConstants.SidebarRect = new PIXI.Rectangle(
|
||||||
@ -13,13 +15,7 @@ export default class GameUIConstants {
|
|||||||
Engine.app.canvas.height
|
Engine.app.canvas.height
|
||||||
);
|
);
|
||||||
GameUIConstants.ChangeRoundButtonRect = new PIXI.Rectangle(50, Engine.app.canvas.height - 100, 310, 100);
|
GameUIConstants.ChangeRoundButtonRect = new PIXI.Rectangle(50, Engine.app.canvas.height - 100, 310, 100);
|
||||||
const endGameDialogWidth = 600;
|
GameUIConstants.StandardDialogWidth = 600;
|
||||||
const endGameDialogHeight = 800;
|
GameUIConstants.StandardDialogHeight = 800;
|
||||||
GameUIConstants.EndGameDialogRect = new PIXI.Rectangle(
|
|
||||||
(Engine.app.canvas.width - endGameDialogWidth) / 2,
|
|
||||||
(Engine.app.canvas.height - endGameDialogHeight) / 2,
|
|
||||||
endGameDialogWidth,
|
|
||||||
endGameDialogHeight
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -2,45 +2,42 @@
|
|||||||
* Handles keyboard events.
|
* Handles keyboard events.
|
||||||
*/
|
*/
|
||||||
class KeyboardManager {
|
class KeyboardManager {
|
||||||
private static listeners: Map<string, ((event: KeyboardEvent) => void)[]> = new Map();
|
private static listeners: ((event: KeyboardEvent) => void)[] = [];
|
||||||
|
|
||||||
public static init() {
|
public static init() {
|
||||||
window.addEventListener('keydown', KeyboardManager.handleKeyDown);
|
window.addEventListener('keydown', KeyboardManager.handleKeyDown);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add a callback to be called when the specified key is pressed.
|
* Add a callback to be called when a key is pressed.
|
||||||
* Note: Calling preventDefault() on the event will prevent other callbacks from being called.
|
* Note: Calling preventDefault() on the event will prevent other callbacks from being called.
|
||||||
* @param key The key to listen for.
|
* @param key The key to listen for.
|
||||||
* @param callback The callback to call when the key is pressed.
|
* @param callback The callback to call when the key is pressed.
|
||||||
* @returns A function that can be called to remove the callback.
|
* @returns A function that can be called to remove the callback.
|
||||||
*/
|
*/
|
||||||
public static onKey(key: string, callback: (event: KeyboardEvent) => void) {
|
public static onKeyPressed(callback: (event: KeyboardEvent) => void) {
|
||||||
if (!KeyboardManager.listeners.has(key)) {
|
KeyboardManager.listeners = [...KeyboardManager.listeners, callback];
|
||||||
KeyboardManager.listeners.set(key, []);
|
return () => KeyboardManager.offKey(callback);
|
||||||
}
|
|
||||||
KeyboardManager.listeners.get(key).push(callback);
|
|
||||||
return () => KeyboardManager.offKey(key, callback);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Remove a callback from the specified key.
|
* Remove a callback.
|
||||||
*/
|
*/
|
||||||
public static offKey(key: string, callback: (event: KeyboardEvent) => void) {
|
public static offKey(callback: (event: KeyboardEvent) => void) {
|
||||||
if (KeyboardManager.listeners.has(key)) {
|
const index = KeyboardManager.listeners.indexOf(callback);
|
||||||
const index = KeyboardManager.listeners.get(key).indexOf(callback);
|
|
||||||
if (index >= 0) {
|
if (index >= 0) {
|
||||||
KeyboardManager.listeners.get(key).splice(index, 1);
|
KeyboardManager.listeners = [
|
||||||
}
|
...KeyboardManager.listeners.slice(0, index),
|
||||||
|
...KeyboardManager.listeners.slice(index + 1),
|
||||||
|
];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static handleKeyDown(event: KeyboardEvent) {
|
private static handleKeyDown(event: KeyboardEvent) {
|
||||||
if (KeyboardManager.listeners.has(event.key)) {
|
if (KeyboardManager.listeners.length > 0) {
|
||||||
console.log(`Key down: ${event.key}`);
|
console.log(`Key down: ${event.key}`);
|
||||||
const callbacks = KeyboardManager.listeners.get(event.key);
|
for (let i = KeyboardManager.listeners.length - 1; i >= 0; i--) {
|
||||||
for (let i = callbacks.length - 1; i >= 0; i--) {
|
KeyboardManager.listeners[i](event);
|
||||||
callbacks[i](event);
|
|
||||||
if (event.defaultPrevented) {
|
if (event.defaultPrevented) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -1,119 +1,91 @@
|
|||||||
import * as PIXI from 'pixi.js';
|
import * as PIXI from 'pixi.js';
|
||||||
import GuiObject from '../GuiObject';
|
|
||||||
import GameAssets from '../Assets';
|
import GameAssets from '../Assets';
|
||||||
import GameUIConstants from '../GameUIConstants';
|
import GameUIConstants from '../GameUIConstants';
|
||||||
import Button, { ButtonTexture } from './Button';
|
import ModalDialogBase from './ModalDialog';
|
||||||
import { Engine } from '../Bastion';
|
import TextInput from './TextInput';
|
||||||
import { EndMissionDialogEvents } from '../Events';
|
|
||||||
import MessageBox from './MessageBox';
|
import MessageBox from './MessageBox';
|
||||||
import KeyboardManager from '../game/KeyboardManager';
|
|
||||||
|
|
||||||
export default class EndGameDialog extends GuiObject {
|
export const EndGameDialogButtons = {
|
||||||
private dialogSprite: PIXI.NineSliceSprite;
|
Confirm: 'OK',
|
||||||
|
Skip: 'Skip',
|
||||||
|
};
|
||||||
|
|
||||||
|
export default class EndGameDialog extends ModalDialogBase {
|
||||||
private dialogCaption: PIXI.Text;
|
private dialogCaption: PIXI.Text;
|
||||||
private nextMissionButton: Button;
|
private playerNameTextInput: TextInput;
|
||||||
private retryButton: Button;
|
|
||||||
private mainMenuButton: Button;
|
|
||||||
private overlay: PIXI.Graphics;
|
|
||||||
private lost: boolean;
|
private lost: boolean;
|
||||||
private keyboardManagerUnsubscribe: () => void;
|
|
||||||
|
|
||||||
constructor(bounds: PIXI.Rectangle, lost: boolean) {
|
constructor(lost: boolean) {
|
||||||
super();
|
super(
|
||||||
|
[EndGameDialogButtons.Confirm, EndGameDialogButtons.Skip],
|
||||||
|
EndGameDialogButtons.Confirm,
|
||||||
|
EndGameDialogButtons.Skip
|
||||||
|
);
|
||||||
this.lost = lost;
|
this.lost = lost;
|
||||||
// Show overlay to prevent user from interacting with the game
|
}
|
||||||
this.overlay = new PIXI.Graphics();
|
|
||||||
this.overlay.rect(0, 0, bounds.width, bounds.height);
|
|
||||||
this.overlay.fill({ color: 0x000000, alpha: 0.5 });
|
|
||||||
// Prevent interaction with the underlying scene
|
|
||||||
this.overlay.interactive = true;
|
|
||||||
this.container.addChild(this.overlay);
|
|
||||||
|
|
||||||
this.dialogSprite = new PIXI.NineSliceSprite({
|
protected override generate(): void {
|
||||||
|
super.generate();
|
||||||
|
this.dialogCaption = new PIXI.Text({
|
||||||
|
text: this.lost ? 'You lost!' : 'You won!',
|
||||||
|
style: new PIXI.TextStyle({
|
||||||
|
fill: 0xffffff,
|
||||||
|
fontSize: 36,
|
||||||
|
}),
|
||||||
|
});
|
||||||
|
this.dialogContainer.addChild(this.dialogCaption);
|
||||||
|
this.dialogCaption.anchor.set(0.5, 0.5);
|
||||||
|
this.dialogCaption.x = this.dialogContainer.width / 2;
|
||||||
|
this.dialogCaption.y = 50;
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override createDialogBackground(width: number, height: number): PIXI.Container {
|
||||||
|
const background = new PIXI.NineSliceSprite({
|
||||||
texture: GameAssets.EndScreenDialog,
|
texture: GameAssets.EndScreenDialog,
|
||||||
leftWidth: 50,
|
leftWidth: 50,
|
||||||
topHeight: 100,
|
topHeight: 100,
|
||||||
rightWidth: 50,
|
rightWidth: 50,
|
||||||
bottomHeight: 50,
|
bottomHeight: 50,
|
||||||
});
|
});
|
||||||
this.dialogSprite.x = GameUIConstants.EndGameDialogRect.x;
|
background.x = 0;
|
||||||
this.dialogSprite.y = GameUIConstants.EndGameDialogRect.y;
|
background.y = 0;
|
||||||
this.dialogSprite.width = GameUIConstants.EndGameDialogRect.width;
|
background.width = width;
|
||||||
this.dialogSprite.height = GameUIConstants.EndGameDialogRect.height;
|
background.height = height;
|
||||||
this.container.addChild(this.dialogSprite);
|
return background;
|
||||||
this.dialogCaption = new PIXI.Text({
|
}
|
||||||
text: lost ? 'You lost!' : 'You won!',
|
|
||||||
|
protected override createContent(): PIXI.Container {
|
||||||
|
const container = new PIXI.Container();
|
||||||
|
const caption = new PIXI.Text({
|
||||||
|
text: 'Enter your name:',
|
||||||
style: new PIXI.TextStyle({
|
style: new PIXI.TextStyle({
|
||||||
fill: 0xffffff,
|
fill: 0xffffff,
|
||||||
fontSize: 36,
|
fontSize: 24,
|
||||||
}),
|
}),
|
||||||
});
|
});
|
||||||
this.container.addChild(this.dialogCaption);
|
container.addChild(caption);
|
||||||
this.dialogCaption.anchor.set(0.5, 0.5);
|
this.playerNameTextInput = new TextInput(
|
||||||
this.dialogCaption.x = GameUIConstants.EndGameDialogRect.x + GameUIConstants.EndGameDialogRect.width / 2;
|
GameUIConstants.MaximumPlayerNameLength * 20,
|
||||||
this.dialogCaption.y = GameUIConstants.EndGameDialogRect.y + 50;
|
GameUIConstants.MaximumPlayerNameLength
|
||||||
//this.setupButtons(lost);
|
);
|
||||||
this.keyboardManagerUnsubscribe = KeyboardManager.onKey('Escape', (e) => {
|
this.playerNameTextInput.container.y = caption.height + 10;
|
||||||
if (e.key === 'Escape') {
|
container.addChild(this.playerNameTextInput.container);
|
||||||
this.onMainMission();
|
return container;
|
||||||
}
|
|
||||||
});
|
|
||||||
this.container.on('destroyed', () => {
|
|
||||||
this.keyboardManagerUnsubscribe();
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private showButtons(lost: boolean) {
|
override close(button?: string): void {
|
||||||
const buttonContainer = new PIXI.Container();
|
if (button === EndGameDialogButtons.Confirm && this.playerNameTextInput.getText().length == 0) {
|
||||||
const buttonWidth = 200;
|
MessageBox.show('Please enter your name.', ['OK']);
|
||||||
const buttonHeight = 80;
|
|
||||||
const buttonPadding = 10;
|
|
||||||
if (lost) {
|
|
||||||
this.retryButton = new Button(
|
|
||||||
new PIXI.Rectangle(0, 0, buttonWidth, buttonHeight),
|
|
||||||
'Retry',
|
|
||||||
ButtonTexture.Button01
|
|
||||||
);
|
|
||||||
this.retryButton.onClick = () => {
|
|
||||||
Engine.GameScene.events.emit(EndMissionDialogEvents.RetryMission);
|
|
||||||
};
|
|
||||||
buttonContainer.addChild(this.retryButton.container);
|
|
||||||
} else {
|
} else {
|
||||||
this.nextMissionButton = new Button(
|
super.close(button);
|
||||||
new PIXI.Rectangle(0, 0, buttonWidth, buttonHeight),
|
|
||||||
'Next Mission',
|
|
||||||
ButtonTexture.Button01
|
|
||||||
);
|
|
||||||
this.nextMissionButton.onClick = () => {
|
|
||||||
Engine.GameScene.events.emit(EndMissionDialogEvents.NextMission);
|
|
||||||
};
|
|
||||||
buttonContainer.addChild(this.nextMissionButton.container);
|
|
||||||
}
|
}
|
||||||
this.mainMenuButton = new Button(
|
|
||||||
new PIXI.Rectangle(0, buttonHeight + buttonPadding, buttonWidth, buttonHeight),
|
|
||||||
'Main Menu',
|
|
||||||
ButtonTexture.Button01
|
|
||||||
);
|
|
||||||
this.mainMenuButton.onClick = this.onMainMission.bind(this);
|
|
||||||
buttonContainer.addChild(this.mainMenuButton.container);
|
|
||||||
this.container.addChild(buttonContainer);
|
|
||||||
buttonContainer.x =
|
|
||||||
GameUIConstants.EndGameDialogRect.x +
|
|
||||||
GameUIConstants.EndGameDialogRect.width / 2 -
|
|
||||||
buttonContainer.width / 2;
|
|
||||||
buttonContainer.y =
|
|
||||||
GameUIConstants.EndGameDialogRect.y + GameUIConstants.EndGameDialogRect.height - buttonContainer.height;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private showingMessageBox: boolean;
|
protected override getWidth(): number | undefined {
|
||||||
|
return GameUIConstants.StandardDialogWidth;
|
||||||
|
}
|
||||||
|
|
||||||
private async onMainMission() {
|
protected override getHeight(): number | undefined {
|
||||||
if (this.showingMessageBox) return;
|
return GameUIConstants.StandardDialogHeight;
|
||||||
this.showingMessageBox = true;
|
|
||||||
const result = await MessageBox.show('Are you sure you want to return to the main menu?', ['Yes', 'No']);
|
|
||||||
this.showingMessageBox = false;
|
|
||||||
if (result === 'Yes') {
|
|
||||||
Engine.GameScene.events.emit(EndMissionDialogEvents.MainMenu);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
78
src/classes/gui/HighScoreDialog.ts
Normal file
78
src/classes/gui/HighScoreDialog.ts
Normal file
@ -0,0 +1,78 @@
|
|||||||
|
import * as PIXI from 'pixi.js';
|
||||||
|
import GameAssets from '../Assets';
|
||||||
|
import GameUIConstants from '../GameUIConstants';
|
||||||
|
import ModalDialogBase from './ModalDialog';
|
||||||
|
import TextInput from './TextInput';
|
||||||
|
|
||||||
|
export const HighScoreDialogButtons = {
|
||||||
|
Retry: 'Retry',
|
||||||
|
MainMenu: 'Main Menu',
|
||||||
|
NextMission: 'Next Mission',
|
||||||
|
};
|
||||||
|
|
||||||
|
export default class HighScoreDialog extends ModalDialogBase {
|
||||||
|
private dialogCaption: PIXI.Text;
|
||||||
|
private playerNameTextInput: TextInput;
|
||||||
|
private lost: boolean;
|
||||||
|
|
||||||
|
constructor(nextMissionAvailable: boolean) {
|
||||||
|
super(
|
||||||
|
nextMissionAvailable
|
||||||
|
? [HighScoreDialogButtons.Retry, HighScoreDialogButtons.NextMission, HighScoreDialogButtons.MainMenu]
|
||||||
|
: [HighScoreDialogButtons.Retry, HighScoreDialogButtons.MainMenu],
|
||||||
|
nextMissionAvailable ? HighScoreDialogButtons.NextMission : HighScoreDialogButtons.Retry,
|
||||||
|
HighScoreDialogButtons.MainMenu
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override generate(): void {
|
||||||
|
super.generate();
|
||||||
|
this.dialogCaption = new PIXI.Text({
|
||||||
|
text: 'Highscore',
|
||||||
|
style: new PIXI.TextStyle({
|
||||||
|
fill: 0xffffff,
|
||||||
|
fontSize: 36,
|
||||||
|
}),
|
||||||
|
});
|
||||||
|
this.dialogContainer.addChild(this.dialogCaption);
|
||||||
|
this.dialogCaption.anchor.set(0.5, 0.5);
|
||||||
|
this.dialogCaption.x = this.dialogContainer.width / 2;
|
||||||
|
this.dialogCaption.y = 50;
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override createDialogBackground(width: number, height: number): PIXI.Container {
|
||||||
|
const background = new PIXI.NineSliceSprite({
|
||||||
|
texture: GameAssets.EndScreenDialog,
|
||||||
|
leftWidth: 50,
|
||||||
|
topHeight: 100,
|
||||||
|
rightWidth: 50,
|
||||||
|
bottomHeight: 50,
|
||||||
|
});
|
||||||
|
background.x = 0;
|
||||||
|
background.y = 0;
|
||||||
|
background.width = width;
|
||||||
|
background.height = height;
|
||||||
|
return background;
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override createContent(): PIXI.Container {
|
||||||
|
const container = new PIXI.Container();
|
||||||
|
const caption = new PIXI.Text({
|
||||||
|
text: 'Leaderboard:',
|
||||||
|
style: new PIXI.TextStyle({
|
||||||
|
fill: 0xffffff,
|
||||||
|
fontSize: 24,
|
||||||
|
}),
|
||||||
|
});
|
||||||
|
container.addChild(caption);
|
||||||
|
return container;
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override getWidth(): number | undefined {
|
||||||
|
return GameUIConstants.StandardDialogWidth;
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override getHeight(): number | undefined {
|
||||||
|
return GameUIConstants.StandardDialogHeight;
|
||||||
|
}
|
||||||
|
}
|
@ -5,12 +5,15 @@ import GuiObject from '../GuiObject';
|
|||||||
export default class MessageBox extends ModalDialogBase {
|
export default class MessageBox extends ModalDialogBase {
|
||||||
private caption: string;
|
private caption: string;
|
||||||
|
|
||||||
constructor(caption: string, buttons: string[], escapeKeyIndex: number = buttons.length - 1) {
|
constructor(caption: string, buttons: string[], escapeKeyButton?: string | null, enterKeyButton?: string | null) {
|
||||||
super(buttons, escapeKeyIndex);
|
if (!enterKeyButton && buttons.length > 0) enterKeyButton = buttons[0];
|
||||||
|
if (!escapeKeyButton && buttons.length > 0) escapeKeyButton = buttons[buttons.length - 1];
|
||||||
|
|
||||||
|
super(buttons, escapeKeyButton, enterKeyButton);
|
||||||
this.caption = caption;
|
this.caption = caption;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected override createContent(): PIXI.Container | GuiObject {
|
protected override createContent(): PIXI.Container {
|
||||||
const text = new PIXI.Text({
|
const text = new PIXI.Text({
|
||||||
text: this.caption,
|
text: this.caption,
|
||||||
style: new PIXI.TextStyle({
|
style: new PIXI.TextStyle({
|
||||||
|
@ -7,25 +7,97 @@ import Button, { ButtonTexture } from './Button';
|
|||||||
import KeyboardManager from '../game/KeyboardManager';
|
import KeyboardManager from '../game/KeyboardManager';
|
||||||
|
|
||||||
export default abstract class ModalDialogBase extends GuiObject {
|
export default abstract class ModalDialogBase extends GuiObject {
|
||||||
private overlay: PIXI.Graphics;
|
protected overlay: PIXI.Graphics;
|
||||||
private dialogPadding = 40;
|
protected dialogPadding = 40;
|
||||||
private contentPadding = 10;
|
protected contentPadding = 10;
|
||||||
private buttonPadding = 10;
|
protected buttonPadding = 10;
|
||||||
private buttonAreaHeight = 40;
|
protected buttonAreaHeight = 40;
|
||||||
private buttonHeight = 60;
|
protected buttonHeight = 60;
|
||||||
private buttonCaptions: string[];
|
protected buttonCaptions: string[];
|
||||||
private buttons: Button[] = [];
|
protected buttons: Button[] = [];
|
||||||
private escapeKeyIndex: number;
|
protected dialogContent: PIXI.Container;
|
||||||
private keyboardManagerUnsubscribe: () => void;
|
protected dialogContainer: PIXI.Container;
|
||||||
private pixiContent: PIXI.Container;
|
|
||||||
private guiContent: GuiObject;
|
|
||||||
private generated = false;
|
|
||||||
|
|
||||||
constructor(buttonCaptions: string[], escapeKeyIndex: number = buttonCaptions.length - 1) {
|
private generated = false;
|
||||||
|
private escapeKeyButton?: string | null;
|
||||||
|
private enterKeyButton?: string | null;
|
||||||
|
private keyboardManagerUnsubscribe: () => void;
|
||||||
|
|
||||||
|
protected constructor(buttons: string[], enterKeyButton?: string | null, escapeKeyButton?: string | null) {
|
||||||
super();
|
super();
|
||||||
this.escapeKeyIndex = escapeKeyIndex;
|
this.buttonCaptions = buttons;
|
||||||
this.buttonCaptions = buttonCaptions;
|
if (escapeKeyButton && !buttons.includes(escapeKeyButton))
|
||||||
this.keyboardManagerUnsubscribe = KeyboardManager.onKey('Escape', this.onKeyPress.bind(this));
|
throw new Error(`Escape key button "${escapeKeyButton}" not found in buttons: ${buttons}`);
|
||||||
|
this.escapeKeyButton = escapeKeyButton;
|
||||||
|
if (enterKeyButton && !buttons.includes(enterKeyButton))
|
||||||
|
throw new Error(`Enter key button "${enterKeyButton}" not found in buttons: ${buttons}`);
|
||||||
|
this.enterKeyButton = enterKeyButton;
|
||||||
|
this.keyboardManagerUnsubscribe = KeyboardManager.onKeyPressed(this.onKeyPress.bind(this));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Show the dialog and await the user's response.
|
||||||
|
* @param width The width of the dialog (optional, if not provided then it is automatically calculated).
|
||||||
|
* @param height The height of the dialog (optional, if not provided then it is automatically calculated).
|
||||||
|
* @returns Button that was clicked or null if dialog was closed without clicking a button (potentially no buttons defined).
|
||||||
|
*/
|
||||||
|
public show(): Promise<string | null> {
|
||||||
|
this.generate();
|
||||||
|
console.debug(
|
||||||
|
`ModalDialogBase.show(content: ${this.dialogContainer.width}x${this.dialogContainer.height}, buttons: ${this.buttonCaptions})`
|
||||||
|
);
|
||||||
|
return new Promise((resolve, reject) => {
|
||||||
|
Engine.app.stage.addChild(this.container);
|
||||||
|
this.onClosed = (button) => {
|
||||||
|
this.destroy();
|
||||||
|
resolve(button);
|
||||||
|
};
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Event that is triggered when the dialog is closed.
|
||||||
|
* @param button The button that was clicked or null if the dialog was closed without clicking a button.
|
||||||
|
*/
|
||||||
|
public onClosed: (button?: string) => void;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create the content of the dialog.
|
||||||
|
*/
|
||||||
|
protected abstract createContent(): PIXI.Container;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates dialog background.
|
||||||
|
*/
|
||||||
|
protected createDialogBackground(width: number, height: number): PIXI.Container {
|
||||||
|
const background = new PIXI.NineSliceSprite({
|
||||||
|
texture: GameAssets.Frame04Texture,
|
||||||
|
leftWidth: 60,
|
||||||
|
topHeight: 60,
|
||||||
|
rightWidth: 60,
|
||||||
|
bottomHeight: 60,
|
||||||
|
});
|
||||||
|
background.x = 0;
|
||||||
|
background.y = 0;
|
||||||
|
background.width = width;
|
||||||
|
background.height = height;
|
||||||
|
return background;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the width of the dialog.
|
||||||
|
* If not overridden, the width is automatically calculated.
|
||||||
|
*/
|
||||||
|
protected getWidth(): number | undefined {
|
||||||
|
return undefined;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the height of the dialog.
|
||||||
|
* If not overridden, the height is automatically calculated.
|
||||||
|
*/
|
||||||
|
protected getHeight(): number | undefined {
|
||||||
|
return undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected generate() {
|
protected generate() {
|
||||||
@ -39,30 +111,22 @@ export default abstract class ModalDialogBase extends GuiObject {
|
|||||||
this.overlay.interactive = true;
|
this.overlay.interactive = true;
|
||||||
this.container.addChild(this.overlay);
|
this.container.addChild(this.overlay);
|
||||||
|
|
||||||
const content = this.createContent();
|
this.dialogContent = this.createContent();
|
||||||
if (content instanceof GuiObject) {
|
|
||||||
this.guiContent = content;
|
|
||||||
this.pixiContent = content.container;
|
|
||||||
} else {
|
|
||||||
this.pixiContent = content;
|
|
||||||
}
|
|
||||||
|
|
||||||
const buttonDefs = this.buttonCaptions.map((btnCaption) => ({
|
const buttonDefs = this.buttonCaptions.map((btnCaption) => ({
|
||||||
caption: btnCaption,
|
caption: btnCaption,
|
||||||
width: btnCaption.length * 16 + 40,
|
width: btnCaption.length * 16 + 40,
|
||||||
height: this.buttonHeight,
|
height: this.buttonHeight,
|
||||||
click: () => this.buttonClickHandler(btnCaption),
|
click: () => this.close(btnCaption),
|
||||||
}));
|
}));
|
||||||
let buttonTotalWidth = 0;
|
let buttonTotalWidth = 0;
|
||||||
for (const buttonDef of buttonDefs) {
|
for (const buttonDef of buttonDefs) {
|
||||||
if (buttonTotalWidth > 0) buttonTotalWidth += this.buttonPadding;
|
if (buttonTotalWidth > 0) buttonTotalWidth += this.buttonPadding;
|
||||||
buttonTotalWidth += buttonDef.width;
|
buttonTotalWidth += buttonDef.width;
|
||||||
}
|
}
|
||||||
const contentWidth = this.pixiContent.width + this.contentPadding * 2;
|
const contentWidth = this.dialogContent.width + this.contentPadding * 2;
|
||||||
const contentHeight = this.pixiContent.height + this.contentPadding * 2;
|
const contentHeight = this.dialogContent.height + this.contentPadding * 2;
|
||||||
let width = Math.max(buttonTotalWidth, contentWidth) + this.dialogPadding * 2;
|
let width = this.getWidth() || Math.max(buttonTotalWidth, contentWidth) + this.dialogPadding * 2;
|
||||||
|
let height = this.getHeight() || contentHeight + this.buttonAreaHeight + this.dialogPadding * 2;
|
||||||
const height = contentHeight + this.buttonAreaHeight + this.dialogPadding * 2;
|
|
||||||
const modalBounds = new PIXI.Rectangle(
|
const modalBounds = new PIXI.Rectangle(
|
||||||
Engine.app.canvas.width / 2 - width / 2,
|
Engine.app.canvas.width / 2 - width / 2,
|
||||||
Engine.app.canvas.height / 2 - height / 2,
|
Engine.app.canvas.height / 2 - height / 2,
|
||||||
@ -70,28 +134,18 @@ export default abstract class ModalDialogBase extends GuiObject {
|
|||||||
height
|
height
|
||||||
);
|
);
|
||||||
|
|
||||||
const modalContainer = new PIXI.Container();
|
this.dialogContainer = new PIXI.Container();
|
||||||
modalContainer.x = modalBounds.x;
|
this.dialogContainer.x = modalBounds.x;
|
||||||
modalContainer.y = modalBounds.y;
|
this.dialogContainer.y = modalBounds.y;
|
||||||
|
|
||||||
const background = new PIXI.NineSliceSprite({
|
const background = this.createDialogBackground(modalBounds.width, modalBounds.height);
|
||||||
texture: GameAssets.Frame04Texture,
|
this.dialogContainer.addChild(background);
|
||||||
leftWidth: 60,
|
|
||||||
topHeight: 60,
|
|
||||||
rightWidth: 60,
|
|
||||||
bottomHeight: 60,
|
|
||||||
});
|
|
||||||
background.x = 0;
|
|
||||||
background.y = 0;
|
|
||||||
background.width = modalBounds.width;
|
|
||||||
background.height = modalBounds.height;
|
|
||||||
modalContainer.addChild(background);
|
|
||||||
|
|
||||||
if (this.pixiContent.width < modalBounds.width)
|
if (this.dialogContent.width < modalBounds.width)
|
||||||
this.pixiContent.x = modalBounds.width / 2 - this.pixiContent.width / 2;
|
this.dialogContent.x = modalBounds.width / 2 - this.dialogContent.width / 2;
|
||||||
if (this.pixiContent.height < modalBounds.height - this.buttonAreaHeight)
|
if (this.dialogContent.height < modalBounds.height - this.buttonAreaHeight)
|
||||||
this.pixiContent.y = (modalBounds.height - this.buttonAreaHeight) / 2 - this.pixiContent.height / 2;
|
this.dialogContent.y = (modalBounds.height - this.buttonAreaHeight) / 2 - this.dialogContent.height / 2;
|
||||||
modalContainer.addChild(this.pixiContent);
|
this.dialogContainer.addChild(this.dialogContent);
|
||||||
|
|
||||||
let buttonXPos = modalBounds.width / 2 - buttonTotalWidth / 2;
|
let buttonXPos = modalBounds.width / 2 - buttonTotalWidth / 2;
|
||||||
for (const buttonDef of buttonDefs) {
|
for (const buttonDef of buttonDefs) {
|
||||||
@ -107,52 +161,36 @@ export default abstract class ModalDialogBase extends GuiObject {
|
|||||||
);
|
);
|
||||||
button.onClick = buttonDef.click;
|
button.onClick = buttonDef.click;
|
||||||
this.buttons.push(button);
|
this.buttons.push(button);
|
||||||
modalContainer.addChild(button.container);
|
this.dialogContainer.addChild(button.container);
|
||||||
buttonXPos += buttonDef.width + this.buttonPadding;
|
buttonXPos += buttonDef.width + this.buttonPadding;
|
||||||
}
|
}
|
||||||
this.container.addChild(modalContainer);
|
this.container.addChild(this.dialogContainer);
|
||||||
}
|
|
||||||
|
|
||||||
protected abstract createContent(): PIXI.Container | GuiObject;
|
|
||||||
|
|
||||||
public show(): Promise<string> {
|
|
||||||
this.generate();
|
|
||||||
console.debug(
|
|
||||||
`ModalDialogBase.show(content: ${this.pixiContent.width}x${this.pixiContent.height}, buttons: ${this.buttonCaptions})`
|
|
||||||
);
|
|
||||||
return new Promise((resolve, reject) => {
|
|
||||||
Engine.app.stage.addChild(this.container);
|
|
||||||
this.onButtonClicked = (button) => {
|
|
||||||
this.destroy();
|
|
||||||
resolve(button);
|
|
||||||
};
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Event that is triggered when the button is clicked.
|
* Close the dialog.
|
||||||
|
* Only use this method if you want to close the dialog without clicking a button.
|
||||||
*/
|
*/
|
||||||
public onButtonClicked: (button: string) => void;
|
public close(button?: string) {
|
||||||
|
this.destroy();
|
||||||
|
if (this.onClosed) this.onClosed(button);
|
||||||
|
}
|
||||||
|
|
||||||
override destroy(): void {
|
override destroy(): void {
|
||||||
this.keyboardManagerUnsubscribe();
|
this.keyboardManagerUnsubscribe();
|
||||||
this.guiContent?.destroy();
|
|
||||||
super.destroy();
|
super.destroy();
|
||||||
}
|
}
|
||||||
|
|
||||||
protected buttonClickHandler(button: string) {
|
|
||||||
if (this.onButtonClicked) this.onButtonClicked(button);
|
|
||||||
this.destroy();
|
|
||||||
}
|
|
||||||
|
|
||||||
private onKeyPress(event: KeyboardEvent) {
|
private onKeyPress(event: KeyboardEvent) {
|
||||||
if (this.buttons.length === 0) return;
|
if (this.buttons.length === 0) return;
|
||||||
|
if (this.escapeKeyButton && event.key === 'Escape') {
|
||||||
// Message box is modal, so we can safely prevent the default behavior
|
// Message box is modal, so we can safely prevent the default behavior
|
||||||
event.preventDefault();
|
event.preventDefault();
|
||||||
if (event.key === 'Escape') {
|
this.close(this.escapeKeyButton);
|
||||||
this.buttonClickHandler(this.buttons[this.escapeKeyIndex].getCaption());
|
} else if (this.enterKeyButton && event.key === 'Enter') {
|
||||||
} else if (event.key === 'Enter') {
|
// Message box is modal, so we can safely prevent the default behavior
|
||||||
this.buttonClickHandler(this.buttons[0].getCaption());
|
event.preventDefault();
|
||||||
|
this.close(this.enterKeyButton);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,45 +0,0 @@
|
|||||||
import * as PIXI from 'pixi.js';
|
|
||||||
import { Engine } from '../Bastion';
|
|
||||||
import ModalDialogBase from './ModalDialog';
|
|
||||||
import TextInput from './TextInput';
|
|
||||||
import GuiObject from '../GuiObject';
|
|
||||||
|
|
||||||
const maxNameLength = 20;
|
|
||||||
|
|
||||||
export default class PlayerNameInput extends ModalDialogBase {
|
|
||||||
private textInput: TextInput;
|
|
||||||
|
|
||||||
constructor(content: PIXI.Container) {
|
|
||||||
super(['OK', 'Cancel']);
|
|
||||||
}
|
|
||||||
|
|
||||||
public getName(): string {
|
|
||||||
return this.textInput.getText();
|
|
||||||
}
|
|
||||||
|
|
||||||
protected override createContent(): PIXI.Container | GuiObject {
|
|
||||||
const container = new PIXI.Container();
|
|
||||||
const caption = new PIXI.Text({
|
|
||||||
text: 'Enter your name:',
|
|
||||||
style: new PIXI.TextStyle({
|
|
||||||
fill: 0xffffff,
|
|
||||||
fontSize: 24,
|
|
||||||
}),
|
|
||||||
});
|
|
||||||
container.addChild(caption);
|
|
||||||
this.textInput = new TextInput(new PIXI.Rectangle(0, 0, maxNameLength * 20, 40), maxNameLength);
|
|
||||||
this.textInput.container.y = caption.height + 10;
|
|
||||||
container.addChild(this.textInput.container);
|
|
||||||
return container;
|
|
||||||
}
|
|
||||||
|
|
||||||
override buttonClickHandler(button: string) {
|
|
||||||
if (button === 'OK') {
|
|
||||||
if (this.textInput.getText().length > 0) {
|
|
||||||
super.buttonClickHandler(button);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
super.buttonClickHandler(button);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -2,25 +2,21 @@ import * as PIXI from 'pixi.js';
|
|||||||
import GuiObject from '../GuiObject';
|
import GuiObject from '../GuiObject';
|
||||||
import Assets from '../Assets';
|
import Assets from '../Assets';
|
||||||
import GameAssets from '../Assets';
|
import GameAssets from '../Assets';
|
||||||
|
import KeyboardManager from '../game/KeyboardManager';
|
||||||
|
|
||||||
export default class TextInput extends GuiObject {
|
export default class TextInput extends GuiObject {
|
||||||
private bounds: PIXI.Rectangle;
|
|
||||||
private backgroundSprite: PIXI.NineSliceSprite;
|
private backgroundSprite: PIXI.NineSliceSprite;
|
||||||
private text: PIXI.Text;
|
private text: PIXI.Text;
|
||||||
private maxLength: number;
|
private maxLength: number;
|
||||||
|
private keyboardManagerUnsubscribe: () => void;
|
||||||
|
|
||||||
public getText(): string {
|
public getText(): string {
|
||||||
return this.text.text;
|
return this.text.text;
|
||||||
}
|
}
|
||||||
|
|
||||||
constructor(bounds: PIXI.Rectangle, maxLength: number) {
|
constructor(width: number, maxLength: number) {
|
||||||
super();
|
super();
|
||||||
this.bounds = bounds;
|
|
||||||
this.maxLength = maxLength;
|
this.maxLength = maxLength;
|
||||||
this.container.x = this.bounds.x;
|
|
||||||
this.container.y = this.bounds.y;
|
|
||||||
this.container.width = this.bounds.width;
|
|
||||||
this.container.height = this.bounds.height;
|
|
||||||
this.backgroundSprite = new PIXI.NineSliceSprite({
|
this.backgroundSprite = new PIXI.NineSliceSprite({
|
||||||
texture: GameAssets.Frame01Texture,
|
texture: GameAssets.Frame01Texture,
|
||||||
leftWidth: 20,
|
leftWidth: 20,
|
||||||
@ -30,21 +26,20 @@ export default class TextInput extends GuiObject {
|
|||||||
});
|
});
|
||||||
this.backgroundSprite.x = 0;
|
this.backgroundSprite.x = 0;
|
||||||
this.backgroundSprite.y = 0;
|
this.backgroundSprite.y = 0;
|
||||||
this.backgroundSprite.width = this.bounds.width;
|
this.backgroundSprite.width = width;
|
||||||
this.backgroundSprite.height = this.bounds.height;
|
this.backgroundSprite.height = 60;
|
||||||
this.container.addChild(this.backgroundSprite);
|
this.container.addChild(this.backgroundSprite);
|
||||||
this.container.x = this.bounds.x;
|
|
||||||
this.container.y = this.bounds.y;
|
|
||||||
this.text = new PIXI.Text({
|
this.text = new PIXI.Text({
|
||||||
text: '',
|
text: '',
|
||||||
style: new PIXI.TextStyle({
|
style: new PIXI.TextStyle({
|
||||||
fill: 0xffffff,
|
fill: 0xffffff,
|
||||||
fontSize: 16,
|
fontSize: 24,
|
||||||
}),
|
}),
|
||||||
});
|
});
|
||||||
this.text.x = 10;
|
this.text.x = 20;
|
||||||
this.text.y = 10;
|
this.text.y = 20;
|
||||||
this.container.addChild(this.text);
|
this.container.addChild(this.text);
|
||||||
|
this.keyboardManagerUnsubscribe = KeyboardManager.onKeyPressed(this.onKeyPress.bind(this));
|
||||||
}
|
}
|
||||||
|
|
||||||
private onKeyPress(event: KeyboardEvent) {
|
private onKeyPress(event: KeyboardEvent) {
|
||||||
|
@ -4,7 +4,7 @@ import { MissionDefinition } from '../classes/Definitions';
|
|||||||
import Creep from '../classes/game/Creep';
|
import Creep from '../classes/game/Creep';
|
||||||
import { Grid } from '../classes/game/Grid';
|
import { Grid } from '../classes/game/Grid';
|
||||||
import WaveManager from '../classes/game/WaveManager';
|
import WaveManager from '../classes/game/WaveManager';
|
||||||
import { WaveManagerEvents, CreepEvents, GemEvents, EndMissionDialogEvents } from '../classes/Events';
|
import { WaveManagerEvents, CreepEvents, GemEvents } from '../classes/Events';
|
||||||
import Sidebar from '../classes/gui/Sidebar';
|
import Sidebar from '../classes/gui/Sidebar';
|
||||||
import Button, { ButtonTexture } from '../classes/gui/Button';
|
import Button, { ButtonTexture } from '../classes/gui/Button';
|
||||||
import Scene from './Scene';
|
import Scene from './Scene';
|
||||||
@ -17,6 +17,7 @@ import Tooltip from '../classes/gui/Tooltip';
|
|||||||
import TowerPanel, { VisualGemSlot } from '../classes/gui/TowerPanel';
|
import TowerPanel, { VisualGemSlot } from '../classes/gui/TowerPanel';
|
||||||
import Gem from '../classes/game/Gem';
|
import Gem from '../classes/game/Gem';
|
||||||
import EndGameDialog from '../classes/gui/EndGameDialog';
|
import EndGameDialog from '../classes/gui/EndGameDialog';
|
||||||
|
import HighScoreDialog, { HighScoreDialogButtons } from '../classes/gui/HighScoreDialog';
|
||||||
|
|
||||||
enum RoundMode {
|
enum RoundMode {
|
||||||
Purchase = 0,
|
Purchase = 0,
|
||||||
@ -41,7 +42,6 @@ export class GameScene extends Scene {
|
|||||||
private playerWon: boolean = false;
|
private playerWon: boolean = false;
|
||||||
private destroyTicker: boolean = false;
|
private destroyTicker: boolean = false;
|
||||||
private offerGemsSprite: PIXI.NineSliceSprite;
|
private offerGemsSprite: PIXI.NineSliceSprite;
|
||||||
private endGameDialog: EndGameDialog;
|
|
||||||
private dimGraphics: PIXI.Graphics = new PIXI.Graphics({
|
private dimGraphics: PIXI.Graphics = new PIXI.Graphics({
|
||||||
x: 0,
|
x: 0,
|
||||||
y: 0,
|
y: 0,
|
||||||
@ -119,9 +119,6 @@ export class GameScene extends Scene {
|
|||||||
}
|
}
|
||||||
this.sidebar.gemTab.TowerPanelSelectingGem(gem, index, tower);
|
this.sidebar.gemTab.TowerPanelSelectingGem(gem, index, tower);
|
||||||
});
|
});
|
||||||
this.events.on(EndMissionDialogEvents.MainMenu, this.onEndMissionDialogMainMenuClicked.bind(this));
|
|
||||||
this.events.on(EndMissionDialogEvents.RetryMission, this.onEndMissionDialogRetryMissionClicked.bind(this));
|
|
||||||
this.events.on(EndMissionDialogEvents.NextMission, this.onEndMissionDialogNextMissionClicked.bind(this));
|
|
||||||
this.ticker = new PIXI.Ticker();
|
this.ticker = new PIXI.Ticker();
|
||||||
this.ticker.maxFPS = 60;
|
this.ticker.maxFPS = 60;
|
||||||
this.ticker.minFPS = 30;
|
this.ticker.minFPS = 30;
|
||||||
@ -168,10 +165,10 @@ export class GameScene extends Scene {
|
|||||||
|
|
||||||
if (this.MissionStats.getHP() <= 0) {
|
if (this.MissionStats.getHP() <= 0) {
|
||||||
this.isGameOver = true;
|
this.isGameOver = true;
|
||||||
this.ShowScoreScreen(true);
|
this.ShowEndgameDialog(true);
|
||||||
} else if (this.playerWon) {
|
} else if (this.playerWon) {
|
||||||
this.isGameOver = true;
|
this.isGameOver = true;
|
||||||
this.ShowScoreScreen(false);
|
this.ShowEndgameDialog(false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
public DarkenScreen() {
|
public DarkenScreen() {
|
||||||
@ -247,10 +244,18 @@ export class GameScene extends Scene {
|
|||||||
this.setRoundMode(RoundMode.Purchase);
|
this.setRoundMode(RoundMode.Purchase);
|
||||||
}
|
}
|
||||||
|
|
||||||
private ShowScoreScreen(lost) {
|
private async ShowEndgameDialog(lost) {
|
||||||
const bounds = new PIXI.Rectangle(0, 0, Engine.app.canvas.width, Engine.app.canvas.height);
|
const endGameDialog = new EndGameDialog(lost);
|
||||||
this.endGameDialog = new EndGameDialog(bounds, lost);
|
await endGameDialog.show();
|
||||||
Engine.GameMaster.currentScene.stage.addChild(this.endGameDialog.container);
|
const highScore = new HighScoreDialog(this.missionIndex + 1 < GameAssets.Missions.length);
|
||||||
|
const result = await highScore.show();
|
||||||
|
if (result === HighScoreDialogButtons.MainMenu) {
|
||||||
|
this.ReturnToMain();
|
||||||
|
} else if (result === HighScoreDialogButtons.NextMission) {
|
||||||
|
Engine.GameMaster.changeScene(new GameScene(GameAssets.Missions[this.missionIndex + 1].name));
|
||||||
|
} else if (result === HighScoreDialogButtons.Retry) {
|
||||||
|
Engine.GameMaster.changeScene(new GameScene(this.mission.name));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public onCreepEscaped(creep: Creep) {
|
public onCreepEscaped(creep: Creep) {
|
||||||
@ -266,14 +271,6 @@ export class GameScene extends Scene {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private onEndMissionDialogMainMenuClicked() {
|
|
||||||
this.ReturnToMain();
|
|
||||||
}
|
|
||||||
|
|
||||||
private onEndMissionDialogRetryMissionClicked() {}
|
|
||||||
|
|
||||||
private onEndMissionDialogNextMissionClicked() {}
|
|
||||||
|
|
||||||
public destroy(): void {
|
public destroy(): void {
|
||||||
super.destroy();
|
super.destroy();
|
||||||
this.isGameOver = true;
|
this.isGameOver = true;
|
||||||
@ -282,8 +279,6 @@ export class GameScene extends Scene {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private ReturnToMain() {
|
private ReturnToMain() {
|
||||||
this.destroy();
|
|
||||||
Engine.GameMaster.currentScene.stage.removeChildren();
|
|
||||||
Engine.GameMaster.changeScene(new MissionPickerScene());
|
Engine.GameMaster.changeScene(new MissionPickerScene());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user