Files
SpaceRace/tv/src/objects/ShipSprite.ts
T

73 lines
2.0 KiB
TypeScript

import Phaser from 'phaser';
import { Ship as ShipType } from '@spacerace/shared';
import { FONTS } from '@spacerace/shared';
export class ShipSprite extends Phaser.GameObjects.Container {
private shipData: ShipType;
private label: Phaser.GameObjects.Text;
private glow: Phaser.GameObjects.Arc;
private body: Phaser.GameObjects.Sprite;
constructor(
scene: Phaser.Scene,
x: number,
y: number,
ship: ShipType,
color: number,
) {
super(scene, x, y);
this.shipData = ship;
const angles: Record<string, number> = { N: 0, E: 90, S: 180, W: 270 };
const baseAngle = angles[ship.direction] || 0;
// Glow halo behind the ship (uses player's color)
this.glow = scene.add.circle(0, 0, 28, color, 0.35);
this.glow.setBlendMode(Phaser.BlendModes.ADD);
this.glow.setDepth(-1);
// Ship body — uses the procedurally generated 'ship' texture
this.body = scene.add.sprite(0, 0, 'ship');
// Recolor the cyan body to the player's color via tint (preserves the white outline)
this.body.setTint(color);
this.add([this.glow, this.body]);
// Player name label in a pill below
const name = ship.playerName || ship.playerId.substring(0, 6);
const labelBg = scene.add.rectangle(0, 30, Math.max(48, name.length * 7 + 14), 18, 0x000000, 0.7);
labelBg.setStrokeStyle(1, color, 0.9);
this.label = scene.add.text(0, 30, name, {
fontFamily: FONTS.body,
fontSize: '12px',
color: '#ffffff',
fontStyle: 'bold',
}).setOrigin(0.5);
this.add([labelBg, this.label]);
this.setAngle(baseAngle);
// Gentle pulse on the halo
scene.tweens.add({
targets: this.glow,
scaleX: { from: 0.85, to: 1.15 },
scaleY: { from: 0.85, to: 1.15 },
alpha: { from: 0.25, to: 0.5 },
duration: 1400,
yoyo: true,
repeat: -1,
});
scene.add.existing(this);
this.setDepth(10);
}
updateState(ship: ShipType): void {
this.shipData = ship;
if (!ship.alive) {
this.setAlpha(0.3);
}
}
}