From de99a1813d45faba9f0f0ba28c06759466b4cbd6 Mon Sep 17 00:00:00 2001 From: Andrey Prokhorov Date: Fri, 12 Jul 2019 12:28:26 +0300 Subject: [PATCH] Add 'level4.md' --- level4.md | 192 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 192 insertions(+) create mode 100644 level4.md diff --git a/level4.md b/level4.md new file mode 100644 index 0000000..7d44b2d --- /dev/null +++ b/level4.md @@ -0,0 +1,192 @@ +## v0.1 + +There was an error in elevator events. Replacing `elevator` with `this` inside event declaration solves the problem. +Works with previous levels also. + +```js +{ + init: function(elevators, floors) { + console.clear(); + + const DIR_UP = 2; + const DIR_DOWN = 1; + const DIR_STOP = 0; + + const MAX_FLOOR = floors.length - 1; + + for (var i = 0; i < elevators.length; i++) { + elevators[i].name = "Elevator " + i; + console.log(elevators[i].name); + } + + var elev_state = []; + + // Initialize elevator states + if (elev_state == []) { + for (var i = 0; i < elevators.length; i++) { + elev_state.push(DIR_STOP); + } + } + + // HELPER functions + // Command elevator to move to floor + sendElevator = function(floor, dir) { + // debug + for (var i = 0; i < elevators.length; i++) { + var elevator = elevators[i]; + + //console.log("Elevator " + elev + " pressed floors:"); + //console.log(elevator.getPressedFloors()); + } + + // At first trying to find closest empty elevator and send it + if (!getFreeElevator(floor)) { + // We didn't found free elevator + var less_loaded = getLessLoaded()[0]; + if (!less_loaded.destinationQueue.includes(floor)) { + //less_loaded.destinationQueue.push(floor); + //less_loaded.checkDestinationQueue(); + less_loaded.goToFloor(floor); + // debug + console.log("Added floor " + floor + " to less loaded elevator"); + //console.log("Elevator queue: "); + //console.log(less_loaded.destinationQueue); + } + } + } + + // Get distance of elevator from floor + getDistance = function(elevator, floor) { + return Math.abs(elevator.currentFloor() - floor); + } + + // Found free elevator closer to required floor and send it there + getFreeElevator = function(floorRequired = 0) { + // closest empty elevator + var best = null; + // get zero-loaded elevators + var zero = []; + for (var elev = 0; elev < elevators.length; elev++) { + var elevator = elevators[elev]; + if (elevator.loadFactor() == 0) { + zero.push(elevator); + } + } + // Found closer elevator from those who had 0 load + for (var elev = 0; elev < zero.length; elev++) { + var elevator = zero[elev]; + + if (best == null) { + best = elevator; + } + if (getDistance(elevator, floorRequired) < getDistance(best, floorRequired)) { + best = elevator; + } + } + if (best != null) { + // debug + console.log("Empty elevator moving to floor " + floorRequired); + + // If we found one command to move to requested floor + best.goToFloor(floorRequired); + return true; + } + return false; + } + + // Get less loaded elevator + getLessLoaded = function() { + return elevators.sort( (a,b) => (a.destinationQueue.length - b.destinationQueue.length) ); + } + + // ELEVATOR events + for (var elev = 0; elev < elevators.length; elev++) { + var elevator = elevators[elev]; + + // Elevator is not doing anything + elevator.on("idle", function() { + // When idle move to 0 floor + // elevator.goToFloor(0); + }); + + // Passenger requested floor + elevator.on("floor_button_pressed", function(floor) { + // debug + //console.log("Elevator " + elevator.name + " pressed floors:"); + //console.log(elevator.getPressedFloors()); + console.log(this.name + ": pressed floor " + floor); + + //elevator.goToFloor(floor); + if (!this.destinationQueue.includes(floor)) { + //elevator.destinationQueue.push(floor); + //elevator.checkDestinationQueue(); + this.goToFloor(floor); + } + }); + + // Stopped on a particulat floor + elevator.on("stopped_at_floor", function(floorNum) { + // debug + // console.log("Elevator " + elev + " pressed floors:"); + // console.log(elevator.getPressedFloors()); + // console.log("Elevator stopped at floor: " + floorNum); + + elev_state[elev] = DIR_STOP; + + // Change direction arrows lights + var state_up, state_down = false; + switch (floorNum) { + case 0: + state_up = true; + state_down = false; + break; + case MAX_FLOOR: + state_up = false; + state_down = true; + break; + default: + state_up = true; + state_down = true; + break; + } + this.goingUpIndicator(state_up); + this.goingDownIndicator(state_down); + }); + + // Passing floor + elevator.on("passing_floor", function(floor, dir) { + switch (dir) { + case "up": elev_state[elev] = DIR_UP; + break; + case "down": elev_state[elev] = DIR_DOWN; + break; + } + }); + } + + // FLOOR events + for (var fl = 0; fl < floors.length; fl++) { + var floor = floors[fl]; + + // DOWN button pressed on a floor + floor.on("down_button_pressed", function() { + // debug + //console.log("Button DOWN pressed on a floor " + this.floorNum()); + + sendElevator(this.floorNum(), DIR_DOWN); + }); + + // UP button pressed on a floor + floor.on("up_button_pressed", function() { + // debug + //console.log("Button UP pressed on a floor " + this.floorNum()); + + sendElevator(this.floorNum(), DIR_UP); + }); + } + }, + update: function(dt, elevators, floors) { + // We normally don't need to do anything here + } +} +``` \ No newline at end of file