Files
OpenFrontIO/src/client/graphics/AnimatedSprite.ts
T
DevelopingTom 902a0b42ac Remove useless sprite setting (#3363)
## Description:

Redundant animated sprite setting: the sprite frame width can be
computed directly.

## Please complete the following:

- [x] I have added screenshots for all UI updates
- [x] I process any text displayed to the user through translateText()
and I've added it to the en.json file
- [x] I have added relevant tests to the test directory
- [x] I confirm I have thoroughly tested these changes and take full
responsibility for any bugs introduced

## Please put your Discord username so you can be contacted if a bug or
regression is found:

IngloriousTom
2026-03-06 19:58:14 -08:00

87 lines
2.1 KiB
TypeScript

export class AnimatedSprite {
private frameHeight: number;
private frameWidth: number;
private currentFrame: number = 0;
private elapsedTime: number = 0;
private active: boolean = true;
constructor(
private image: CanvasImageSource,
private frameCount: number,
private frameDuration: number, // in milliseconds
private looping: boolean = false,
private originX: number,
private originY: number,
) {
if (frameCount <= 0) {
throw new Error("Animated sprite should at least have one frame");
}
if ("height" in image && "width" in image) {
this.frameHeight = (image as HTMLImageElement | HTMLCanvasElement).height;
this.frameWidth = Math.floor(
(image as HTMLImageElement | HTMLCanvasElement).width / frameCount,
);
} else {
throw new Error(
"Image source must have 'width' and 'height' properties.",
);
}
}
update(deltaTime: number) {
if (!this.active) return;
this.elapsedTime += deltaTime;
if (this.elapsedTime >= this.frameDuration) {
this.elapsedTime -= this.frameDuration;
this.currentFrame++;
if (this.currentFrame >= this.frameCount) {
if (this.looping) {
this.currentFrame = 0;
} else {
this.currentFrame = this.frameCount - 1;
this.active = false;
}
}
}
}
isActive(): boolean {
return this.active;
}
lifeTime(): number | undefined {
if (this.looping) {
return undefined;
}
return this.frameDuration * this.frameCount;
}
draw(ctx: CanvasRenderingContext2D, x: number, y: number) {
const drawX = x - this.originX;
const drawY = y - this.originY;
ctx.drawImage(
this.image,
this.currentFrame * this.frameWidth,
0,
this.frameWidth,
this.frameHeight,
drawX,
drawY,
this.frameWidth,
this.frameHeight,
);
}
reset() {
this.currentFrame = 0;
this.elapsedTime = 0;
}
setOrigin(xRatio: number, yRatio: number) {
this.originX = xRatio;
this.originY = yRatio;
}
}