diff --git a/client/playback/src/gameworld.ts b/client/playback/src/gameworld.ts index 159a987a..5eabe1fb 100644 --- a/client/playback/src/gameworld.ts +++ b/client/playback/src/gameworld.ts @@ -493,6 +493,7 @@ export default class GameWorld { case schema.Action.TRANSMUTE: setAction(); + teamStatsObj.goldMined += 1; // teamStatsObj.gold += target; // teamStatsObj.lead -= 0; break; diff --git a/client/visualizer/src/constants.ts b/client/visualizer/src/constants.ts index a8ecd4a3..d6a1b767 100644 --- a/client/visualizer/src/constants.ts +++ b/client/visualizer/src/constants.ts @@ -10,7 +10,7 @@ export const SAGE = schema.BodyType.SAGE export const SOLDIER = schema.BodyType.SOLDIER export const WATCHTOWER = schema.BodyType.WATCHTOWER -export const bodyTypeList: number[] = [ARCHON, BUILDER, LABORATORY, MINER, SAGE, SOLDIER, WATCHTOWER] +export const bodyTypeList: number[] = [ARCHON, WATCHTOWER, LABORATORY, SOLDIER, BUILDER, MINER, SAGE] export const buildingTypeList: number[] = [ARCHON, LABORATORY, WATCHTOWER]; export const initialBodyTypeList: number[] = [ARCHON] export const anomalyList = [0, 1, 2, 3] @@ -68,7 +68,27 @@ export const ACTION_RADIUS_COLOR = "#46ff00" export const VISION_RADIUS_COLOR = "#0000ff" // Expected bot image size -export const IMAGE_SIZE = 50 +//export const IMAGE_SIZE = 25 + +export function bodyTypeToSize(bodyType: schema.BodyType) { + switch (bodyType) { + case ARCHON: + return 50 + case WATCHTOWER: + return 50 + case BUILDER: + return 25 + case MINER: + return 35 + case SAGE: + return 25 + case SOLDIER: + return 35 + case LABORATORY: + return 50 + default: throw new Error("invalid body type") + } +} // Game canvas rendering sizes export const INDICATOR_DOT_SIZE = .3 diff --git a/client/visualizer/src/gamearea/renderer.ts b/client/visualizer/src/gamearea/renderer.ts index 4d3dc9ca..7afb6ba4 100644 --- a/client/visualizer/src/gamearea/renderer.ts +++ b/client/visualizer/src/gamearea/renderer.ts @@ -284,7 +284,7 @@ export default class Renderer { const effectImgs: HTMLImageElement[] = this.imgs.effects[effect] const whichImg = (Math.floor(curTime / cst.EFFECT_STEP) % effectImgs.length) const effectImg = effectImgs[whichImg] - this.drawBot(effectImg, x, y, 0) + //this.drawBot(effectImg, x, y, 0) } const renderBot = (i: number) => { @@ -304,7 +304,7 @@ export default class Renderer { let img: HTMLImageElement; if (!cst.buildingTypeList.includes(types[i]) || body_status == PROTOTYPE) img = this.imgs.robots[cst.bodyTypeToString(types[i])][body_status * 2 + teams[i]]; else img = this.imgs.robots[cst.bodyTypeToString(types[i])][levels[i] * 6 + body_status * 2 + teams[i]] - this.drawBot(img, realXs[i], realYs[i], hps[i]); + this.drawBot(img, realXs[i], realYs[i], hps[i], cst.bodyTypeToSize(types[i])); // TODO: draw bot this.drawSightRadii(realXs[i], realYs[i], types[i], ids[i] === this.lastSelectedID) @@ -401,10 +401,10 @@ export default class Renderer { /** * Draws an image centered at (x, y), such that an image with default size covers a 1x1 cell */ - private drawBot(img: HTMLImageElement, x: number, y: number, c: number) { + private drawBot(img: HTMLImageElement, x: number, y: number, c: number, img_size: number) { if (this.conf.doingRotate) [x, y] = [y, x] - let realWidth = img.naturalWidth / cst.IMAGE_SIZE - let realHeight = img.naturalHeight / cst.IMAGE_SIZE + let realWidth = img.naturalWidth / img_size + let realHeight = img.naturalHeight / img_size const sigmoid = (x) => { return 1 / (1 + Math.exp(-x)) } diff --git a/client/visualizer/src/main/controls.ts b/client/visualizer/src/main/controls.ts index 305dffb1..075ebf17 100644 --- a/client/visualizer/src/main/controls.ts +++ b/client/visualizer/src/main/controls.ts @@ -453,7 +453,7 @@ export default class Controls { infoString += `DP: ${dp} | `; infoString += `Bytecodes Used: ${bytecodes}`; if (parent !== undefined) infoString += ` | Parent: ${parent}`; - infoString += `
Indicator String: ${indicatorString}`; + infoString += `
Indicator String: ${indicatorString}`; // (${bodyType})
// Location: (${x}, ${y})
diff --git a/client/visualizer/src/main/looper.ts b/client/visualizer/src/main/looper.ts index 877e1b14..f0cdd1ac 100644 --- a/client/visualizer/src/main/looper.ts +++ b/client/visualizer/src/main/looper.ts @@ -401,9 +401,14 @@ export default class Looper { const hps = world.bodies.arrays.hp; const teams = world.bodies.arrays.team; const types = world.bodies.arrays.type; - for(var i = 0; i < hps.length; i++){ - if(types[i] == ARCHON) this.stats.addEC(teams[i], hps[i]); - } + const portables = world.bodies.arrays.portable; + teamIDs.forEach((team) => { + for(var i = 0; i < hps.length; i++){ + if(types[i] == ARCHON && teams[i] == team) { + this.stats.addEC(teams[i], hps[i], portables[i]); + } + } + }); if (this.match.winner && this.match.current.turn == this.match.lastTurn) { this.stats.setWinner(this.match.winner, teamNames, teamIDs); diff --git a/client/visualizer/src/main/sidebar.ts b/client/visualizer/src/main/sidebar.ts index d29c28ff..d66f4b49 100644 --- a/client/visualizer/src/main/sidebar.ts +++ b/client/visualizer/src/main/sidebar.ts @@ -90,7 +90,7 @@ export default class Sidebar { this.modeButtons = new Map(); modePanelRow1.appendChild(this.modeButton(Mode.GAME, "Game")); - modePanelRow1.appendChild(this.modeButton(Mode.LOGS, "Logs")); + // modePanelRow1.appendChild(this.modeButton(Mode.LOGS, "Logs")); modePanelRow1.appendChild(this.modeButton(Mode.QUEUE, "Queue")); modePanelRow1.appendChild(this.modeButton(Mode.RUNNER, "Runner")); if (this.conf.useProfiler) modePanelRow2.appendChild(this.modeButton(Mode.PROFILER, "Profiler")); diff --git a/client/visualizer/src/sidebar/stats.ts b/client/visualizer/src/sidebar/stats.ts index b5786efa..130cecd5 100644 --- a/client/visualizer/src/sidebar/stats.ts +++ b/client/visualizer/src/sidebar/stats.ts @@ -67,7 +67,8 @@ export default class Stats { private tourneyUpload: HTMLDivElement; - private incomeChart: Chart; + private incomeChartLead: Chart; + private incomeChartGold: Chart; private ECs: HTMLDivElement; @@ -262,18 +263,28 @@ export default class Stats { title.colSpan = 4; const label = document.createElement('div'); label.className = "stats-header"; - label.innerText = 'Total Lead & Gold Mined Per Turn'; + label.innerText = 'Total Lead & Gold Income Per Turn'; const row = document.createElement("tr"); + const cellLead = document.createElement("td"); teamIDs.forEach((id: number) => { - const cell = document.createElement("td"); + // cell.appendChild(document.createTextNode("1.001")); // cell.appendChild(this.buffDisplays[id].numBuffs); // cell.appendChild(document.createTextNode(" = ")); - cell.appendChild(this.incomeDisplays[id].leadIncome); - cell.appendChild(this.incomeDisplays[id].goldIncome); - row.appendChild(cell); + cellLead.appendChild(this.incomeDisplays[id].leadIncome); + row.appendChild(cellLead); + }); + + const cellGold = document.createElement("td"); + teamIDs.forEach((id: number) => { + + // cell.appendChild(document.createTextNode("1.001")); + // cell.appendChild(this.buffDisplays[id].numBuffs); + // cell.appendChild(document.createTextNode(" = ")); + cellGold.appendChild(this.incomeDisplays[id].goldIncome); + row.appendChild(cellGold); }); title.appendChild(label); @@ -283,9 +294,17 @@ export default class Stats { return table; } - private getIncomeDominationGraph() { + private getIncomeLeadGraph() { const canvas = document.createElement("canvas"); - canvas.id = "myChart"; + canvas.id = "leadGraph"; + canvas.className = "graph"; + return canvas; + } + + private getIncomeGoldGraph() { + const canvas = document.createElement("canvas"); + canvas.id = "goldGraph"; + canvas.className = "graph"; return canvas; } @@ -428,9 +447,23 @@ export default class Stats { const incomeElement = this.getIncomeDisplaysElement(teamIDs); this.div.appendChild(incomeElement); - const canvasElement = this.getIncomeDominationGraph(); - this.div.appendChild(canvasElement); - this.incomeChart = new Chart(canvasElement, { + const graphs = document.createElement("div"); + graphs.style.display = 'flex'; + const leadWrapper = document.createElement("div"); + leadWrapper.style.width = "50%"; + leadWrapper.style.float = "left"; + const canvasElementLead = this.getIncomeLeadGraph(); + leadWrapper.appendChild(canvasElementLead); + graphs.appendChild(leadWrapper); + const goldWrapper = document.createElement("div"); + goldWrapper.style.width = "50%"; + goldWrapper.style.float = "right"; + const canvasElementGold = this.getIncomeGoldGraph(); + goldWrapper.appendChild(canvasElementGold); + graphs.appendChild(goldWrapper); + this.div.appendChild(graphs); + + this.incomeChartLead = new Chart(canvasElementLead, { type: 'line', data: { datasets: [{ @@ -446,7 +479,35 @@ export default class Stats { backgroundColor: 'rgba(54, 162, 235, 0)', borderColor: 'rgb(108, 140, 188)', pointRadius: 0, - }, + }] + }, + options: { + aspectRatio: 0.75, + scales: { + xAxes: [{ + type: 'linear', + ticks: { + beginAtZero: true + }, + scaleLabel: { + display: true, + labelString: "Turn" + } + }], + yAxes: [{ + type: 'linear', + ticks: { + beginAtZero: true + } + }] + } + } + }); + + this.incomeChartGold = new Chart(canvasElementGold, { + type: 'line', + data: { + datasets: [ { label: 'Red Gold', data: [], @@ -463,7 +524,7 @@ export default class Stats { }] }, options: { - aspectRatio: 1.5, + aspectRatio: 0.75, scales: { xAxes: [{ type: 'linear', @@ -569,14 +630,18 @@ export default class Stats { if (!teamTurnsIncomeSet!.has(turn)) { //@ts-ignore - this.incomeChart.data.datasets![teamID - 1].data?.push({y: leadIncome, x: turn}); + this.incomeChartLead.data.datasets![teamID - 1].data?.push({y: leadIncome, x: turn}); //@ts-ignore - this.incomeChart.data.datasets![teamID + 1].data?.push({y: goldIncome, x: turn}); - this.incomeChart.data.datasets?.forEach((d) => { + this.incomeChartGold.data.datasets![teamID - 1].data?.push({y: goldIncome, x: turn}); + this.incomeChartLead.data.datasets?.forEach((d) => { + d.data?.sort((a, b) => a.x - b.x); + }); + this.incomeChartGold.data.datasets?.forEach((d) => { d.data?.sort((a, b) => a.x - b.x); }); teamTurnsIncomeSet?.add(turn); - this.incomeChart.update(); + this.incomeChartLead.update(); + this.incomeChartGold.update(); } // update bars here //console.log(teamID, count, "fsdfsdf"); @@ -616,19 +681,24 @@ export default class Stats { } resetECs() { - // while (this.ECs.lastChild) this.ECs.removeChild(this.ECs.lastChild); + while (this.ECs.lastChild) this.ECs.removeChild(this.ECs.lastChild); // console.log(this.ECs); this.ECs.innerHTML = ""; } - addEC(teamID: number, health: number/*, img: HTMLImageElement */) { + addEC(teamID: number, health: number, body_status: number/*, img: HTMLImageElement */) { const div = document.createElement("div"); let size = 1.0/(1 + Math.exp(-(health/100))) + 0.3; - div.style.width = (35*size).toString() + "px"; - div.style.height = (35*size).toString() + "px"; - const img = /* img */this.images.robots.archon[teamID].cloneNode() as HTMLImageElement; - img.style.width = "64px"; - img.style.height = "64px"; // update dynamically later + div.style.width = (28*size).toString() + "px"; + div.style.height = (28*size).toString() + "px"; + div.style.position = 'releative'; + div.style.top = '50%'; + div.style.transform = `translateY(-${50*size - 35}%)`; + const img = /* img */this.images.robots.archon[body_status * 2 + teamID].cloneNode() as HTMLImageElement; + img.style.width = `${56 * size}px`; + img.style.height = `${56 * size}px`; // update dynamically later + // img.style.marginTop = `${28*size}px`; + div.appendChild(img); this.ECs.appendChild(div); } diff --git a/client/visualizer/src/static/css/style.css b/client/visualizer/src/static/css/style.css index 3881fa60..cb7d5995 100644 --- a/client/visualizer/src/static/css/style.css +++ b/client/visualizer/src/static/css/style.css @@ -37,6 +37,10 @@ p { color: #4f7ee6; } +/* .graph { + width: 50% !important; +} */ + .red { color: #db3627; } @@ -49,6 +53,7 @@ p { font-family: Tahoma, sans-serif; } + .robotSpriteStats img { width: 30px; } diff --git a/client/visualizer/src/static/img/robots/blue_builder.png b/client/visualizer/src/static/img/robots/blue_builder.png index 8d4d3536..55a51776 100644 Binary files a/client/visualizer/src/static/img/robots/blue_builder.png and b/client/visualizer/src/static/img/robots/blue_builder.png differ diff --git a/client/visualizer/src/static/img/robots/blue_miner.png b/client/visualizer/src/static/img/robots/blue_miner.png index 38ca1b05..534df8ca 100644 Binary files a/client/visualizer/src/static/img/robots/blue_miner.png and b/client/visualizer/src/static/img/robots/blue_miner.png differ diff --git a/client/visualizer/src/static/img/robots/blue_sage.png b/client/visualizer/src/static/img/robots/blue_sage.png index 83675c27..11c88dbc 100644 Binary files a/client/visualizer/src/static/img/robots/blue_sage.png and b/client/visualizer/src/static/img/robots/blue_sage.png differ diff --git a/client/visualizer/src/static/img/robots/blue_soldier.png b/client/visualizer/src/static/img/robots/blue_soldier.png index ad64d416..4f033de2 100644 Binary files a/client/visualizer/src/static/img/robots/blue_soldier.png and b/client/visualizer/src/static/img/robots/blue_soldier.png differ diff --git a/client/visualizer/src/static/img/robots/red_builder.png b/client/visualizer/src/static/img/robots/red_builder.png index 53bcb803..d591865e 100644 Binary files a/client/visualizer/src/static/img/robots/red_builder.png and b/client/visualizer/src/static/img/robots/red_builder.png differ diff --git a/client/visualizer/src/static/img/robots/red_miner.png b/client/visualizer/src/static/img/robots/red_miner.png index 94fe2e8c..5f2034f7 100644 Binary files a/client/visualizer/src/static/img/robots/red_miner.png and b/client/visualizer/src/static/img/robots/red_miner.png differ diff --git a/client/visualizer/src/static/img/robots/red_sage.png b/client/visualizer/src/static/img/robots/red_sage.png index b8ba3462..042604b8 100644 Binary files a/client/visualizer/src/static/img/robots/red_sage.png and b/client/visualizer/src/static/img/robots/red_sage.png differ diff --git a/client/visualizer/src/static/img/robots/red_soldier.png b/client/visualizer/src/static/img/robots/red_soldier.png index 85d52130..85a7b778 100644 Binary files a/client/visualizer/src/static/img/robots/red_soldier.png and b/client/visualizer/src/static/img/robots/red_soldier.png differ