refactor blackjack hit animation to use individual card rendering

Refactors `animateSingleCard` to accept a specific card object instead of seat/index parameters, simplifying the logic for determining hand position and card index. Updates hit actions for both player and AI to animate the new card individually, revealing its face-up state at the destination upon completion. This replaces the previous bulk `renderSeatCards` call with a more granular visual update.
This commit is contained in:
Brian Fertig 2026-05-16 16:14:46 -06:00
parent 712956a841
commit 48f7ade241
1 changed files with 48 additions and 28 deletions

View File

@ -624,15 +624,17 @@ export default class BlackjackGame extends Phaser.Scene {
});
}
animateSingleCard(seat, isDealer, cardIdx, onComplete) {
const pos = isDealer ? { x: DEALER_X, y: DEALER_Y } : SEAT_POS[seat];
const hand = isDealer ? this.gs.dealer.hand : this.gs.players[seat].hand;
animateSingleCard(seat, card, onComplete) {
const pos = SEAT_POS[seat];
const p = this.gs.players[seat];
const isH2 = p.activeHand === 1;
const hand = isH2 ? p.hand2 : p.hand;
const total = hand.length;
const tx = isDealer
? this.cardX(DEALER_X, cardIdx, total)
: this.cardX(pos.x, cardIdx, total);
const ty = isDealer ? DEALER_Y : pos.y;
const cardIdx = total - 1;
const tx = this.cardX(pos.x, cardIdx, total);
const ty = pos.y;
// Flying card-back
const flying = this.add.container(CX + 200, 50).setDepth(D.cards + 10);
this.addCardBackToContainer(flying);
@ -640,7 +642,13 @@ export default class BlackjackGame extends Phaser.Scene {
targets: flying, x: tx, y: ty, duration: 200, ease: 'Power2',
onComplete: () => {
flying.destroy();
this.renderSeatCards(seat);
// Reveal the card face-up at the destination
const cardConts = this.cardGraphics[seat] ?? [];
const targetCont = cardConts[cardIdx];
if (targetCont) {
targetCont.setAlpha(1);
this.drawCard(targetCont, card, true);
}
onComplete();
},
});
@ -918,16 +926,22 @@ export default class BlackjackGame extends Phaser.Scene {
this.hideActionButtons();
this.animating = true;
this.gs = applyHit(this.gs, this.gs.currentSeat, this.shoe);
this.renderSeatCards(this.gs.currentSeat);
this.time.delayedCall(200, () => {
this.animating = false;
const p = this.gs.players[this.gs.currentSeat];
if (isBust(p.activeHand === 1 ? p.hand2 : p.hand)) {
this.onPlayerBust(this.gs.currentSeat);
this.time.delayedCall(380, () => this.playerDone(this.gs.currentSeat));
} else {
this.showActionButtons();
}
const p = this.gs.players[this.gs.currentSeat];
const newCard = p.activeHand === 1
? p.hand2[p.hand2.length - 1]
: p.hand[p.hand.length - 1];
this.animateSingleCard(this.gs.currentSeat, newCard, () => {
this.renderSeatCards(this.gs.currentSeat);
this.time.delayedCall(200, () => {
this.animating = false;
if (isBust(p.activeHand === 1 ? p.hand2 : p.hand)) {
this.onPlayerBust(this.gs.currentSeat);
this.time.delayedCall(380, () => this.playerDone(this.gs.currentSeat));
} else {
this.showActionButtons();
}
});
});
}
@ -1012,16 +1026,22 @@ export default class BlackjackGame extends Phaser.Scene {
switch (action) {
case 'hit':
this.gs = applyHit(this.gs, seat, this.shoe);
this.renderSeatCards(seat);
this.time.delayedCall(400, () => {
this.animating = false;
const pp = this.gs.players[seat];
if (isBust(pp.activeHand === 1 ? pp.hand2 : pp.hand)) {
this.onPlayerBust(seat);
this.time.delayedCall(400, () => this.playerDone(seat));
} else {
this.time.delayedCall(600, () => this.runAITurn(seat));
}
const pp = this.gs.players[seat];
const aiNewCard = pp.activeHand === 1
? pp.hand2[pp.hand2.length - 1]
: pp.hand[pp.hand.length - 1];
this.animateSingleCard(seat, aiNewCard, () => {
this.renderSeatCards(seat);
this.time.delayedCall(400, () => {
this.animating = false;
const pp2 = this.gs.players[seat];
if (isBust(pp2.activeHand === 1 ? pp2.hand2 : pp2.hand)) {
this.onPlayerBust(seat);
this.time.delayedCall(400, () => this.playerDone(seat));
} else {
this.time.delayedCall(600, () => this.runAITurn(seat));
}
});
});
break;
case 'double':