1
0
Fork 0
polaris-task-force/src/components/frontend/minigames/chipBankSounds.ts
Z8MB1E 67971dd7e6 feat(chips): persistent chip pool economy with shared balance card
Chip service and actions, fixed ChipBankCard with delta popup, sounds, spinner, and arena integration; chip bank migration and tests. Arena diffs are the chip-card mounts and join/leave spinner dispatches.

Ultraworked with [Sisyphus](https://github.com/code-yeongyu/oh-my-openagent)

Co-authored-by: Sisyphus <clio-agent@sisyphuslabs.ai>
2026-09-14 15:38:05 -04:00

69 lines
2 KiB
TypeScript

"use client";
/**
* Chip-bank movement sounds for the fixed Chip Bank card. Independent of the
* table sound engines (the card lives on both the poker and blackjack pages,
* outside any table). Best-effort autoplay: if the browser blocks the
* AudioContext until a gesture, these simply stay silent.
*/
let ctx: AudioContext | null = null;
function getCtx(): AudioContext | null {
if (typeof window === "undefined") return null;
try {
if (!ctx) {
const Ctor =
window.AudioContext ??
(window as unknown as { webkitAudioContext?: typeof AudioContext }).webkitAudioContext;
if (!Ctor) return null;
ctx = new Ctor();
}
if (ctx.state === "suspended") {
void ctx.resume().catch(() => undefined);
}
return ctx;
} catch {
return null;
}
}
function tone(
frequency: number,
nextFrequency: number,
duration: number,
delay: number,
volume = 0.14,
): void {
const context = getCtx();
if (!context) return;
try {
const start = context.currentTime + delay;
const oscillator = context.createOscillator();
const gain = context.createGain();
oscillator.type = "sine";
oscillator.frequency.setValueAtTime(frequency, start);
oscillator.frequency.exponentialRampToValueAtTime(Math.max(1, nextFrequency), start + duration);
gain.gain.setValueAtTime(0.0001, start);
gain.gain.exponentialRampToValueAtTime(volume, start + 0.015);
gain.gain.exponentialRampToValueAtTime(0.0001, start + duration);
oscillator.connect(gain);
gain.connect(context.destination);
oscillator.start(start);
oscillator.stop(start + duration + 0.05);
} catch {
// Sound is best-effort; never throw from a balance indicator.
}
}
/** Chips arriving: short rising pair. */
export function playChipBankUp(): void {
tone(523, 523, 0.09, 0);
tone(784, 784, 0.12, 0.09);
}
/** Chips leaving: short falling pair. */
export function playChipBankDown(): void {
tone(392, 392, 0.09, 0);
tone(262, 262, 0.14, 0.09);
}