web-player: split player, navigation and accent state into focused modules

This commit is contained in:
2026-09-24 05:25:35 +02:00
parent e89463fb83
commit 5cda7cb4c1
47 changed files with 520 additions and 457 deletions
+24
View File
@@ -0,0 +1,24 @@
export function shuffle<T>(items: T[]): T[] {
const copy = [...items];
for (let i = copy.length - 1; i > 0; i--) {
const j = Math.floor(Math.random() * (i + 1));
[copy[i], copy[j]] = [copy[j], copy[i]];
}
return copy;
}
export function appendUnique<T>(
current: T[],
incoming: T[],
keyOf: (item: T) => string | number
): T[] {
const seen = new Set(current.map(keyOf));
const added: T[] = [];
for (const item of incoming) {
const key = keyOf(item);
if (seen.has(key)) continue;
seen.add(key);
added.push(item);
}
return added.length > 0 ? [...current, ...added] : current;
}