export const FORMATIONS: Record = { "4-3-3": { def: 4, mid: 3, fwd: 3 }, "4-4-2": { def: 4, mid: 4, fwd: 2 }, "4-5-1": { def: 4, mid: 5, fwd: 1 }, "3-5-2": { def: 3, mid: 5, fwd: 2 }, "3-4-3": { def: 3, mid: 4, fwd: 3 }, "5-3-2": { def: 5, mid: 3, fwd: 2 }, "5-4-1": { def: 5, mid: 4, fwd: 1 }, }; export type FormationKey = keyof typeof FORMATIONS; // تعداد مورد نیاز هر پست = ترکیب + 1 ذخیره export function requiredPerPosition(formation: string) { const fmt = FORMATIONS[formation] ?? FORMATIONS["4-3-3"]; return { GK: 2, // 1 اصلی + 1 ذخیره DEF: fmt.def + 1, MID: fmt.mid + 1, FWD: fmt.fwd + 1, }; } export type PlayerLike = { position: string; isBench: boolean }; export function validateTeamComposition( players: PlayerLike[], formation: string ): { valid: boolean; errors: string[] } { const fmt = FORMATIONS[formation] ?? FORMATIONS["4-3-3"]; const errors: string[] = []; const starters = players.filter((p) => !p.isBench); const bench = players.filter((p) => p.isBench); // تعداد کل if (players.length !== 15) { errors.push(`تیم باید دقیقاً ۱۵ بازیکن داشته باشد (الان: ${players.length})`); } // ترکیب اصلی const startersByPos = countByPos(starters); if (startersByPos.GK !== 1) errors.push("باید دقیقاً ۱ دروازه‌بان اصلی داشته باشی"); if (startersByPos.DEF !== fmt.def) errors.push(`باید ${fmt.def} مدافع اصلی داشته باشی (الان: ${startersByPos.DEF ?? 0})`); if (startersByPos.MID !== fmt.mid) errors.push(`باید ${fmt.mid} هافبک اصلی داشته باشی (الان: ${startersByPos.MID ?? 0})`); if (startersByPos.FWD !== fmt.fwd) errors.push(`باید ${fmt.fwd} مهاجم اصلی داشته باشی (الان: ${startersByPos.FWD ?? 0})`); // ذخیره‌ها - هر پست باید ۱ ذخیره داشته باشه const benchByPos = countByPos(bench); if ((benchByPos.GK ?? 0) < 1) errors.push("باید ۱ دروازه‌بان ذخیره داشته باشی"); if ((benchByPos.DEF ?? 0) < 1) errors.push("باید حداقل ۱ مدافع ذخیره داشته باشی"); if ((benchByPos.MID ?? 0) < 1) errors.push("باید حداقل ۱ هافبک ذخیره داشته باشی"); if ((benchByPos.FWD ?? 0) < 1) errors.push("باید حداقل ۱ مهاجم ذخیره داشته باشی"); return { valid: errors.length === 0, errors }; } function countByPos(players: PlayerLike[]): Record { return players.reduce((acc, p) => { acc[p.position] = (acc[p.position] ?? 0) + 1; return acc; }, {} as Record); } // وقتی ترکیب عوض میشه، چک کن آیا بازیکنان فعلی با ترکیب جدید سازگارن export function getFormationChangeIssues( players: PlayerLike[], oldFormation: string, newFormation: string ): string[] { const oldFmt = FORMATIONS[oldFormation] ?? FORMATIONS["4-3-3"]; const newFmt = FORMATIONS[newFormation] ?? FORMATIONS["4-3-3"]; const issues: string[] = []; const starters = players.filter((p) => !p.isBench); const byPos = countByPos(starters); if ((byPos.DEF ?? 0) > newFmt.def) issues.push(`باید ${(byPos.DEF ?? 0) - newFmt.def} مدافع رو به ذخیره ببری یا حذف کنی`); if ((byPos.MID ?? 0) > newFmt.mid) issues.push(`باید ${(byPos.MID ?? 0) - newFmt.mid} هافبک رو به ذخیره ببری یا حذف کنی`); if ((byPos.FWD ?? 0) > newFmt.fwd) issues.push(`باید ${(byPos.FWD ?? 0) - newFmt.fwd} مهاجم رو به ذخیره ببری یا حذف کنی`); return issues; }