timeTravel(temporalDistance) { // don't let the player travel too far in any one direction if (this.currentTick + temporalDistance < 0 || Math.abs(temporalDistance) > 50) { game.log.message("Your watch won't go that far."); return; } // add a TimeTravel action to current player's timeline to synchronize them with // the current time of the game world this.player.do(new TimeTravelAction({ destination: this.currentTick, distance: temporalDistance })); setTimeout(() => { // store the current tick so we can compare whatever the future tick ends up // being against it in order to determine if we've traveled into the past or into // the future let lastTick = this.currentTick; // set the current tick of the entire game to the tick defined by the last tick // plus the distance traveled, whether that be forward or backward this.currentTick += temporalDistance; // generate all lava from beginning of time up until this tick this.map.generateLava(this.startTime, this.currentTick + this.startTime); // if the current tick is now less than the last tick, the player has traveled // back in time if (this.currentTick < lastTick) { // ...so we need to clone them in order to keep all their actions in the // timeline, and by leaving the player alone allow them to create a new // span of time in which to act let actor = this.player, clone = this.player.clone(); game.player = clone; actor.color = new Color("lightgrey"); this.actors.push(actor); } // make sure that only levers that have already been thrown stay that way this.updateLevers(); // play all actors from beginning of time up until this tick this.actors.forEach(actor => actor.timeline.replayUntil(this.currentTick)); this.player.tile.actor = this.player; this.input.waiting = false; this.updateMemories(); }, 400); this.updateMemories(); this.render(); this.input.waiting = true; }
setTimeout(() => { // store the current tick so we can compare whatever the future tick ends up // being against it in order to determine if we've traveled into the past or into // the future let lastTick = this.currentTick; // set the current tick of the entire game to the tick defined by the last tick // plus the distance traveled, whether that be forward or backward this.currentTick += temporalDistance; // generate all lava from beginning of time up until this tick this.map.generateLava(this.startTime, this.currentTick + this.startTime); // if the current tick is now less than the last tick, the player has traveled // back in time if (this.currentTick < lastTick) { // ...so we need to clone them in order to keep all their actions in the // timeline, and by leaving the player alone allow them to create a new // span of time in which to act let actor = this.player, clone = this.player.clone(); game.player = clone; actor.color = new Color("lightgrey"); this.actors.push(actor); } // make sure that only levers that have already been thrown stay that way this.updateLevers(); // play all actors from beginning of time up until this tick this.actors.forEach(actor => actor.timeline.replayUntil(this.currentTick)); this.player.tile.actor = this.player; this.input.waiting = false; this.updateMemories(); }, 400);
resolveParadox(actor, currentParadox) { this.input.waiting = true; let oldPos = this.player.position; this.centerCamera(oldPos); this.player.remove(); this.player = actor; this.player.color = new Color("white"); // loop through actors including this one and remove them from the map and // the future, because their timeline has been actually completely erased let i = this.actors.indexOf(actor), end = this.actors.length; while (i < end) { if (this.actors[i] !== this.player) { this.actors[i].remove(); } this.map.levers.forEach(lever => { if (lever.thrower == this.actors[i]) { lever.thrower = null; lever.thrownTime = null; this.updateLevers(); } }); i++; } this.actors.length = this.actors.indexOf(actor); actor.timeline.clearFuture(); this.log.message("Your temporal paradox collapse alert chimes..."); if (currentParadox) { this.log.message("You suddenly remember watching yourself vanish", "as you feel reality warping around you, time", "itself bending to set things right."); } else { this.log.message("You ruefully realize you made a paradox earlier", "as the walls of reality collapse about you."); } // animate the position of the viewport to the other player i = 0; let steps = 5, lastPos = oldPos, interval = setInterval(() => { i++; let pos = oldPos.interpolate(this.player.position, i / steps); while (pos.equals(lastPos)) { i++; pos = oldPos.interpolate(this.player.position, i / steps); } this.centerCamera(pos, true); lastPos = pos; if (i === steps) { clearInterval(interval); this.animatingCamera = false; this.input.waiting = false; return; } }, 400); this.animatingCamera = true; this.input.waiting = true; // update lighting this.render(); }