New custom woka scene full clothes (#2023)
* center grid if possible * whole outfit for every slot * switched bodyPart slots into buttons * change categories and body parts with WSAD / arrow keys Co-authored-by: Piotr 'pwh' Hanusiak <p.hanusiak@workadventu.re>
This commit is contained in:
@@ -1,4 +1,3 @@
|
||||
import { MathUtils } from "../../../Utils/MathUtils";
|
||||
import { getPlayerAnimations, PlayerAnimationDirections, PlayerAnimationTypes } from "../../Player/Animation";
|
||||
|
||||
export enum CustomWokaBodyPart {
|
||||
@@ -54,7 +53,7 @@ export class CustomWokaPreviewer extends Phaser.GameObjects.Container {
|
||||
[CustomWokaBodyPart.Hat]: this.scene.add.sprite(this.config.bodyPartsOffsetX, 0, "").setVisible(false),
|
||||
};
|
||||
|
||||
this.background = this.scene.add.image(0, 0, "floorTexture");
|
||||
this.background = this.scene.add.image(0, 0, "floorTexture1");
|
||||
this.frame = this.scene.add.graphics();
|
||||
this.drawFrame();
|
||||
this.setSize(this.SIZE, this.SIZE);
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
import { GridItem } from "@home-based-studio/phaser3-utils";
|
||||
import { GridItemEvent } from "@home-based-studio/phaser3-utils/lib/utils/gui/containers/grids/GridItem";
|
||||
import { CustomWokaBodyPart } from "./CustomWokaPreviewer";
|
||||
|
||||
export interface WokaBodyPartSlotConfig {
|
||||
color: number;
|
||||
@@ -8,9 +9,8 @@ export interface WokaBodyPartSlotConfig {
|
||||
borderSelectedColor: number;
|
||||
offsetX: number;
|
||||
offsetY: number;
|
||||
bodyImageKey?: string;
|
||||
textureKeys: Record<CustomWokaBodyPart, string>;
|
||||
categoryImageKey?: string;
|
||||
imageKey?: string;
|
||||
selected?: boolean;
|
||||
}
|
||||
|
||||
@@ -22,8 +22,7 @@ export class WokaBodyPartSlot extends GridItem {
|
||||
private background: Phaser.GameObjects.Image;
|
||||
private frame: Phaser.GameObjects.Graphics;
|
||||
private categoryImage?: Phaser.GameObjects.Image;
|
||||
private bodyImage: Phaser.GameObjects.Image;
|
||||
private image: Phaser.GameObjects.Image;
|
||||
private sprites: Record<CustomWokaBodyPart, Phaser.GameObjects.Sprite>;
|
||||
|
||||
private config: WokaBodyPartSlotConfig;
|
||||
|
||||
@@ -36,12 +35,43 @@ export class WokaBodyPartSlot extends GridItem {
|
||||
|
||||
this.config = config;
|
||||
|
||||
const textures = this.config.textureKeys;
|
||||
this.sprites = {
|
||||
[CustomWokaBodyPart.Accessory]: this.scene.add
|
||||
.sprite(this.config.offsetX, this.config.offsetY, textures.Accessory)
|
||||
.setVisible(textures.Accessory !== ""),
|
||||
[CustomWokaBodyPart.Body]: this.scene.add
|
||||
.sprite(this.config.offsetX, this.config.offsetY, textures.Body)
|
||||
.setVisible(textures.Body !== ""),
|
||||
[CustomWokaBodyPart.Clothes]: this.scene.add
|
||||
.sprite(this.config.offsetX, this.config.offsetY, textures.Clothes)
|
||||
.setVisible(textures.Clothes !== ""),
|
||||
[CustomWokaBodyPart.Eyes]: this.scene.add
|
||||
.sprite(this.config.offsetX, this.config.offsetY, textures.Eyes)
|
||||
.setVisible(textures.Eyes !== ""),
|
||||
[CustomWokaBodyPart.Hair]: this.scene.add
|
||||
.sprite(this.config.offsetX, this.config.offsetY, textures.Hair)
|
||||
.setVisible(textures.Hair !== ""),
|
||||
[CustomWokaBodyPart.Hat]: this.scene.add
|
||||
.sprite(this.config.offsetX, this.config.offsetY, textures.Hat)
|
||||
.setVisible(textures.Hat !== ""),
|
||||
};
|
||||
|
||||
this.selected = this.config.selected ?? false;
|
||||
|
||||
this.background = this.background = this.scene.add.image(0, 0, "floorTexture");
|
||||
this.background = this.background = this.scene.add.image(0, 0, `floorTexture1`);
|
||||
this.frame = this.scene.add.graphics();
|
||||
this.drawFrame();
|
||||
this.add([this.background, this.frame]);
|
||||
this.add([
|
||||
this.background,
|
||||
this.frame,
|
||||
this.sprites.Body,
|
||||
this.sprites.Eyes,
|
||||
this.sprites.Hair,
|
||||
this.sprites.Clothes,
|
||||
this.sprites.Hat,
|
||||
this.sprites.Accessory,
|
||||
]);
|
||||
|
||||
if (this.config.categoryImageKey) {
|
||||
this.categoryImage = this.scene.add
|
||||
@@ -52,18 +82,7 @@ export class WokaBodyPartSlot extends GridItem {
|
||||
this.add(this.categoryImage);
|
||||
}
|
||||
|
||||
this.bodyImage = this.scene.add
|
||||
.image(this.config.offsetX, this.config.offsetY, this.config.bodyImageKey ?? "")
|
||||
.setVisible(this.config.imageKey !== undefined);
|
||||
|
||||
this.image = this.scene.add
|
||||
.image(this.config.offsetX, this.config.offsetY, this.config.imageKey ?? "")
|
||||
.setVisible(this.config.bodyImageKey !== undefined);
|
||||
|
||||
this.setSize(WokaBodyPartSlot.SIZE, WokaBodyPartSlot.SIZE);
|
||||
|
||||
this.add([this.bodyImage, this.image]);
|
||||
|
||||
this.setInteractive({ cursor: "pointer" });
|
||||
this.scene.input.setDraggable(this);
|
||||
|
||||
@@ -72,29 +91,18 @@ export class WokaBodyPartSlot extends GridItem {
|
||||
this.scene.add.existing(this);
|
||||
}
|
||||
|
||||
public getContentData(): { bodyImageKey?: string; key?: string } {
|
||||
return { bodyImageKey: this.config.bodyImageKey, key: this.config.imageKey };
|
||||
public getContentData(): Record<CustomWokaBodyPart, string> {
|
||||
return this.config.textureKeys;
|
||||
}
|
||||
|
||||
public setTextures(bodyTextureKey?: string, imageTextureKey?: string): void {
|
||||
this.setBodyTexture(bodyTextureKey);
|
||||
this.setImageTexture(imageTextureKey);
|
||||
}
|
||||
|
||||
public setBodyTexture(textureKey?: string, frame?: string | number): void {
|
||||
this.bodyImage.setVisible(textureKey !== undefined && textureKey !== "");
|
||||
if (textureKey) {
|
||||
this.bodyImage.setTexture(textureKey, frame);
|
||||
this.config.bodyImageKey = textureKey;
|
||||
}
|
||||
}
|
||||
|
||||
public setImageTexture(textureKey?: string, frame?: string | number): void {
|
||||
this.image.setVisible(textureKey !== undefined && textureKey !== "");
|
||||
if (textureKey) {
|
||||
this.image.setTexture(textureKey, frame);
|
||||
this.config.imageKey = textureKey;
|
||||
}
|
||||
public setTextures(textureKeys: Record<CustomWokaBodyPart, string>): void {
|
||||
this.config.textureKeys = textureKeys;
|
||||
this.sprites.Accessory.setTexture(textureKeys.Accessory).setVisible(textureKeys.Accessory !== "");
|
||||
this.sprites.Body.setTexture(textureKeys.Body).setVisible(textureKeys.Body !== "");
|
||||
this.sprites.Clothes.setTexture(textureKeys.Clothes).setVisible(textureKeys.Clothes !== "");
|
||||
this.sprites.Eyes.setTexture(textureKeys.Eyes).setVisible(textureKeys.Eyes !== "");
|
||||
this.sprites.Hair.setTexture(textureKeys.Hair).setVisible(textureKeys.Hair !== "");
|
||||
this.sprites.Hat.setTexture(textureKeys.Hat).setVisible(textureKeys.Hat !== "");
|
||||
}
|
||||
|
||||
public select(select: boolean = true): void {
|
||||
|
||||
@@ -0,0 +1,115 @@
|
||||
export interface IconButtonConfig {
|
||||
width: number;
|
||||
height: number;
|
||||
iconTextureKey: string;
|
||||
idle: IconButtonAppearanceConfig;
|
||||
hover: IconButtonAppearanceConfig;
|
||||
pressed: IconButtonAppearanceConfig;
|
||||
selected: IconButtonAppearanceConfig;
|
||||
}
|
||||
|
||||
export interface IconButtonAppearanceConfig {
|
||||
color: number;
|
||||
borderThickness: number;
|
||||
borderColor: number;
|
||||
}
|
||||
|
||||
export enum IconButtonEvent {
|
||||
Clicked = "IconButton:Clicked",
|
||||
}
|
||||
|
||||
export class IconButton extends Phaser.GameObjects.Container {
|
||||
private background: Phaser.GameObjects.Graphics;
|
||||
private icon: Phaser.GameObjects.Image;
|
||||
|
||||
private config: IconButtonConfig;
|
||||
|
||||
private hovered: boolean = false;
|
||||
private pressed: boolean = false;
|
||||
private selected: boolean = false;
|
||||
|
||||
constructor(scene: Phaser.Scene, x: number, y: number, config: IconButtonConfig) {
|
||||
super(scene, x, y);
|
||||
|
||||
this.config = config;
|
||||
|
||||
this.background = this.scene.add.graphics();
|
||||
this.icon = this.scene.add.image(0, 0, this.config.iconTextureKey);
|
||||
this.drawBackground(this.config.idle);
|
||||
|
||||
this.add([this.background, this.icon]);
|
||||
|
||||
this.setSize(this.config.width, this.config.height);
|
||||
this.setInteractive({ cursor: "pointer" });
|
||||
|
||||
this.bindEventHandlers();
|
||||
|
||||
this.scene.add.existing(this);
|
||||
}
|
||||
|
||||
public select(select: boolean = true): void {
|
||||
if (this.selected === select) {
|
||||
return;
|
||||
}
|
||||
this.selected = select;
|
||||
this.updateButtonAppearance();
|
||||
}
|
||||
|
||||
private updateButtonAppearance(): void {
|
||||
if (this.selected) {
|
||||
this.drawBackground(this.config.selected);
|
||||
return;
|
||||
}
|
||||
if (this.pressed) {
|
||||
this.drawBackground(this.config.pressed);
|
||||
return;
|
||||
}
|
||||
if (this.hovered) {
|
||||
this.drawBackground(this.config.hover);
|
||||
return;
|
||||
}
|
||||
this.drawBackground(this.config.idle);
|
||||
}
|
||||
|
||||
private drawBackground(appearance: IconButtonAppearanceConfig): void {
|
||||
this.background.clear();
|
||||
this.background.fillStyle(appearance.color);
|
||||
this.background.lineStyle(appearance.borderThickness, appearance.borderColor);
|
||||
|
||||
const w = this.config.width;
|
||||
const h = this.config.height;
|
||||
|
||||
this.background.fillRect(-w / 2, -h / 2, w, h);
|
||||
this.background.strokeRect(-w / 2, -h / 2, w, h);
|
||||
}
|
||||
|
||||
private bindEventHandlers(): void {
|
||||
this.on(Phaser.Input.Events.POINTER_OVER, () => {
|
||||
if (this.selected) {
|
||||
return;
|
||||
}
|
||||
this.hovered = true;
|
||||
this.updateButtonAppearance();
|
||||
});
|
||||
this.on(Phaser.Input.Events.POINTER_OUT, () => {
|
||||
this.hovered = false;
|
||||
this.pressed = false;
|
||||
this.updateButtonAppearance();
|
||||
});
|
||||
this.on(Phaser.Input.Events.POINTER_DOWN, () => {
|
||||
if (this.selected) {
|
||||
return;
|
||||
}
|
||||
this.pressed = true;
|
||||
this.updateButtonAppearance();
|
||||
});
|
||||
this.on(Phaser.Input.Events.POINTER_UP, () => {
|
||||
if (this.selected) {
|
||||
return;
|
||||
}
|
||||
this.pressed = false;
|
||||
this.updateButtonAppearance();
|
||||
this.emit(IconButtonEvent.Clicked, this.selected);
|
||||
});
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user