class Controller { #game; #drawer; #colorsBank = ['black','silver','gray','maroon','red','purple','fuchsia','green','lime','olive','yellow','navy','blue','teal','aqua']; constructor() { this.initializeGame(); } initializeGame() { let params = this.gatherMenuValues(); this.game = new Game(params.TUBESNUMBERS, params.TUBESLEVELS); this.drawer = new Drawer(params.PADDING, params.SCALE); this.drawer.computeGameParams(params.TUBESNUMBERS, params.TUBESLEVELS); this.initializeColorTubes(params.TUBESLEVELS - 1); this.needUpdate = true; } gatherMenuValues() { let inputTubesNumbers = parseInt(document.getElementById("tbNumber").value); let inputTubesLevels = parseInt(document.getElementById("tbLevel").value); let inputScale = parseInt(document.getElementById("scale").value); let inputPadding = parseInt(document.getElementById("padding").value); return { TUBESNUMBERS: inputTubesNumbers, TUBESLEVELS: inputTubesLevels, SCALE: inputScale, PADDING: inputPadding }; } initializeColorTubes(LayersPerTube) { let nbTubes = this.game.tubesNumber() - 1; let allColors = []; for (let i = 0; i < nbTubes; i++) { let coloridx = i % this.#colorsBank.length; for (let times = 0; times < LayersPerTube; times++) { allColors.push(this.#colorsBank[coloridx]); } } for (let index = allColors.length - 1; index >= 0; index--) { let randomIndex = Math.floor(Math.random() * (index + 1)); let tubeIndex = Math.floor(index / LayersPerTube); this.game.tubeAt(tubeIndex).addColorLayer(allColors[randomIndex]); allColors[randomIndex] = allColors[index]; } } clickTube(tubeIndex) { let _clickedTube = this.game.tubeAt(tubeIndex); if (_clickedTube == null) return; if (_clickedTube == this.game.selectedTube()) this.game.unselectTube(); else if (this.canPourInto(this.game.selectedTube(), _clickedTube)) { this.pourColorInto(this.game.selectedTube(), _clickedTube); this.game.unselectTube(); } else if (!_clickedTube.isEmpty()) this.game.selectTubeAt(tubeIndex); } canPourInto(sourceTube, targetTube) { return sourceTube != null && targetTube != null && sourceTube != targetTube && (targetTube.isEmpty() || sourceTube.peekTopColor() == targetTube.peekTopColor()) && !targetTube.isFull(); } pourColorInto(sourceTube, targetTube) { while (this.canPourInto(sourceTube, targetTube)) { targetTube.addColorLayer(sourceTube.removeColorLayer()); } this.checkTubeCompletion(sourceTube); this.checkTubeCompletion(targetTube); } checkTubeCompletion(tube) { if (tube.isComplete()) { this.game.removeTube(tube); this.checkGameCompletion(); } } checkGameCompletion() { if (this.game.tubesNumber() == 1 && this.game.tubeAt(0).isEmpty()) { this.game.clean(); } } mousePressed(e) { let clickedTubeId = this.drawer.getTubeIdAt(mouseX, mouseY); this.clickTube(clickedTubeId); this.needUpdate = true; } runLoop() { if (!this.needUpdate) return; this.drawer.draw(this.game); this.needUpdate = false; } }