From 835efe71a0147ff67dd7cdfe98d573d18ccdbaff Mon Sep 17 00:00:00 2001 From: Solomon Cammack Date: Mon, 15 Nov 2021 20:04:29 +0000 Subject: [PATCH] Add minileague sorting --- .../src/components/broadcast/Standings.vue | 25 +++++- website/src/utils/scenarios.js | 82 +++++++++++++++++-- 2 files changed, 97 insertions(+), 10 deletions(-) diff --git a/website/src/components/broadcast/Standings.vue b/website/src/components/broadcast/Standings.vue index 655ef3ce..f48ebfe7 100644 --- a/website/src/components/broadcast/Standings.vue +++ b/website/src/components/broadcast/Standings.vue @@ -61,18 +61,34 @@ export default { if (!this.stage) return this.allMatches; return this.allMatches.filter(match => match.match_group && match.match_group.toLowerCase() === this.stage.toLowerCase()); }, - settings() { + blocks() { if (!this.event || !this.event.blocks) return null; try { const blocks = JSON.parse(this.event.blocks); - return blocks.settings || null; + return blocks || null; } catch (e) { return null; } }, + settings() { + if (!this.blocks) return null; + return this.blocks?.settings || null; + }, useOMW() { return this.settings?.useOMW && this.stageMatches.every(m => [m.score_1, m.score_2].some(s => s === m.first_to)); }, + standingsSort() { + try { + const sorters = this.blocks.standingsSort; + if (sorters && sorters.length) { + const sorter = sorters.find(s => s.group === this.stage); + return sorter?.sort; + } + } catch (e) { + return null; + } + return null; + }, standings() { if (!this.stageMatches || !this.event) return []; if (!this.stageMatches.some(m => m.match_group)) return []; // make sure there's matches to analyse @@ -200,9 +216,10 @@ export default { teams = teams.sort(sortFunction); - console.log("[standings teams]", teams); + // console.log("[standings teams]", teams); const standings = sortTeamsIntoStandings(teams.map(t => ({ ...t, ...t.standings })), { - useOMW: this.useOMW + useOMW: this.useOMW, + sort: this.standingsSort }); // console.log("[new standings]", standings); diff --git a/website/src/utils/scenarios.js b/website/src/utils/scenarios.js index 78e004ee..a2810f70 100644 --- a/website/src/utils/scenarios.js +++ b/website/src/utils/scenarios.js @@ -45,6 +45,13 @@ export function sortByMatchDiff(a, b) { return 0; } +export function miniLeagueMatchDiff(a, b) { + const [aMatchDiff, bMatchDiff] = [a, b].map(x => x.standings.minileague.wins - x.standings.minileague.losses); + if (aMatchDiff < bMatchDiff) return 1; + if (aMatchDiff > bMatchDiff) return -1; + return 0; +} + export function sortByHeadToHead(a, b) { // console.log("h2h", a.standings, b.standings); @@ -154,7 +161,7 @@ export function sortIntoGroups2(sortFunction, standings, maxInGroup) { if (group.length <= 1) continue; // don't bother sorting if it's just one if (maxInGroup && group.length > maxInGroup) { - // console.log(`[i] cannot sort this group because ${group.length} is too big for max ${maxInGroup} for this function`); + console.log(`[i] cannot sort this group because ${group.length} is too big for max ${maxInGroup} for this function`, { group, standings }); continue; } @@ -264,8 +271,71 @@ export function sortWithinGroups(sortFunction, standings) { return standings.map(group => group.sort(sortFunction)); } +function miniLeaguePrep(standings) { + for (const group of standings) { + if (group.length <= 1) continue; + console.log("minileagueprep", group); + + const groupIDs = group.map(g => g.id); + + group.forEach(team => { + // console.log("minileague setup", team.id, groupIDs, team.standings.h2h); + team.standings.minileague = { + wins: 0, + losses: 0 + }; + groupIDs.forEach(opponentID => { + const diff = team.standings.h2h[opponentID]; + if (diff === 1) team.standings.minileague.wins++; + if (diff === -1) team.standings.minileague.losses++; + }); + }); + + console.log(group.sort(miniLeagueMatchDiff).map(t => `|${t.code.padStart(6, " ")} ${t.standings.minileague.wins}-${t.standings.minileague.losses}`).join("\n")); + + /* + * Set up a minileague + * - Take all the head to heads from all the teams in the tied group + * - Sort it by whatever required + * */ + } + return standings; +} + +function getSortMethod(stringMethod) { + if (stringMethod === "MatchDiff") return { method: sortByMatchDiff, max: null }; + if (stringMethod === "MapDiff") return { method: sortByMapDiff, max: null }; + if (stringMethod === "HeadToHead") return { method: sortByHeadToHead, max: 2 }; + if (stringMethod === "MapWins") return { method: sortByMapWins, max: null }; + if (stringMethod === "OMW") return { method: sortByOMW, max: null }; + if (stringMethod === "MiniLeague") return { prep: miniLeaguePrep, method: miniLeagueMatchDiff, max: null }; + return null; +} + export function sortTeamsIntoStandings(teams, settings = {}) { - // console.log("[standings]", "starting sort", teams); + const log = false; + if (log) console.log("[standings]", "starting sort", teams, settings); + + if (settings.sort) { + // Custom sort + console.log("[standings]", `Sorting in custom order: ${settings.sort}`); + let standings = [teams]; + for (const mode of settings.sort) { + const _method = getSortMethod(mode); + if (!_method) continue; + const { prep, method, max } = _method; + + if (prep) standings = prep(standings); + + if (max) { + standings = sortIntoGroups2(method, standings, max); + } else { + standings = sortIntoGroups2(method, standings); + } + } + return standings; + } + let standings = sortIntoGroups2(sortByMatchDiff, [teams]); // if (i === 4050) console.log(standings); // sortMatches(sortByMatchWins, scenario.teams, standings); @@ -285,20 +355,20 @@ export function sortTeamsIntoStandings(teams, settings = {}) { } if (!standings.every(s => s.length === 1)) { - console.log("[standings]", "not converged, trying map diff", standings); + if (log) console.log("[standings]", "not converged, trying map diff", standings); standings = sortIntoGroups2(sortByMapDiff, standings); } if (!standings.every(s => s.length === 1)) { - console.log("[standings]", "not converged, trying head to head", standings); + if (log) console.log("[standings]", "not converged, trying head to head", standings); // i don't know why [standings] works here but not for the other one standings = sortIntoGroups2(sortByHeadToHead, standings, 2); } if (!standings.every(s => s.length === 1)) { - console.log("[standings]", "not converged, trying map wins", standings); + if (log) console.log("[standings]", "not converged, trying map wins", standings); standings = sortIntoGroups2(sortByMapWins, standings); } if (!standings.every(s => s.length === 1) && settings.useOMW) { - console.log("[standings]", "not converged, trying opponent winrate", standings); + if (log) console.log("[standings]", "not converged, trying opponent winrate", standings); standings = sortIntoGroups2(sortByOMW, standings); } if (!standings.every(s => s.length === 1)) {