| Scripts/laveAcademy_dockingBuoy.js | "use strict";
this.name = "LaveAcademy_dockingBuoy";
this.author = "Thargoid";
this.copyright = "Creative Commons Attribution - Non-Commercial - Share Alike 3.0 license with clauses - see readme.txt.";
this.description = "Control of academy docking practice buoys in the Lave system";
this.version = "1.3";
this.examStart = function () {
	this.examStartTime = clock.absoluteSeconds;
	this.buoyPosition = this.ship.position;
	missionVariables.laveAcademy_droneCount = 0;
	missionVariables.laveAcademy_droneAbort = null;
	player.consoleMessage(expandDescription("[academy_docking_exam_started]"), 6);
	if (this.launchCheckTimer) {
		this.launchCheckTimer.start();
	}
	else {
		this.launchCheckTimer = new Timer(this, this.droneCheck, 0, 1);
	}
}
this.droneCheck = function droneCheck() {
	if (player.ship.docked) {// if the player is docked (at the Academy) then stop the test quietly
		this.launchCheckTimer.stop();
		missionVariables.laveAcademy_droneAbort = true;
		this.ship.AIState = "LIGHTS_OFF";
		missionVariables.laveAcademyExam = null;
		return;
	}
	function isPlayer(entity) { return entity.isShip && entity.isPlayer };
	this.playerInRange = system.filteredEntities(this, isPlayer, this.ship, 25600).length;
	if (this.playerInRange == 0) {
		this.launchCheckTimer.stop();
		missionVariables.laveAcademy_droneCount -= 1;
		this.cancelExam();
	}
	if (missionVariables.laveAcademy_droneAbort) {
		this.launchCheckTimer.stop();
		return;
	}
	function isDockingDrone(entity) { return entity.isShip && entity.hasRole("laveAcademy_dockingDrone") };
	if (system.filteredEntities(this, isDockingDrone, this.ship, 25600).length == 0) {
		if (missionVariables.laveAcademy_droneCount == 10) {
			this.endExam();
		}
		else {
			missionVariables.laveAcademy_droneCount += 1;
			switch (true) {
				case (missionVariables.laveAcademy_droneCount == 1):
					{
						this.ship.commsMessage(expandDescription("[academy_level_one]"), player.ship);
						//system.legacy_addShipsWithinRadius("laveAcademy_dockingDroneL1", 1, "abs", this.buoyPosition, 14000);
						system.addShips("laveAcademy_dockingDroneL1", 1, this.buoyPosition, 14000);
						break;
					}
				case (missionVariables.laveAcademy_droneCount == 2 || missionVariables.laveAcademy_droneCount == 3):
					{
						//system.legacy_addShipsWithinRadius("laveAcademy_dockingDroneL1", 1, "abs", this.buoyPosition, 14000);
						system.addShips("laveAcademy_dockingDroneL1", 1, this.buoyPosition, 14000);
						break;
					}
				case (missionVariables.laveAcademy_droneCount == 4):
					{
						this.ship.commsMessage(expandDescription("[academy_level_two]"), player.ship);
						//system.legacy_addShipsWithinRadius("laveAcademy_dockingDroneL2a", 1, "abs", this.buoyPosition, 14000);
						system.addShips("laveAcademy_dockingDroneL2a", 1, this.buoyPosition, 14000);
						break;
					}
				case (missionVariables.laveAcademy_droneCount == 5):
					{
						//system.legacy_addShipsWithinRadius("laveAcademy_dockingDroneL2b", 1, "abs", this.buoyPosition, 14000);
						system.addShips("laveAcademy_dockingDroneL2b", 1, this.buoyPosition, 14000);
						break;
					}
				case (missionVariables.laveAcademy_droneCount == 6):
					{
						//system.legacy_addShipsWithinRadius("laveAcademy_dockingDroneL2c", 1, "abs", this.buoyPosition, 14000);
						system.addShips("laveAcademy_dockingDroneL2c", 1, this.buoyPosition, 14000);
						break;
					}
				case (missionVariables.laveAcademy_droneCount == 7):
					{
						this.ship.commsMessage(expandDescription("[academy_level_three]"), player.ship);
						//system.legacy_addShipsWithinRadius("laveAcademy_dockingDroneL3a", 1, "abs", this.buoyPosition, 14000);
						system.addShips("laveAcademy_dockingDroneL3a", 1, this.buoyPosition, 14000);
						break;
					}
				case (missionVariables.laveAcademy_droneCount == 8):
					{
						//system.legacy_addShipsWithinRadius("laveAcademy_dockingDroneL3b", 1, "abs", this.buoyPosition, 14000);
						system.addShips("laveAcademy_dockingDroneL3b", 1, this.buoyPosition, 14000);
						break;
					}
				case (missionVariables.laveAcademy_droneCount == 9):
					{
						//system.legacy_addShipsWithinRadius("laveAcademy_dockingDroneL3c", 1, "abs", this.buoyPosition, 14000);
						system.addShips("laveAcademy_dockingDroneL3c", 1, this.buoyPosition, 14000);
						break;
					}
			}
		}
	}
}
this.endExam = function () {
	this.launchCheckTimer.stop();
	if (worldScripts["Welcome Information Script"]) { // if Welcome Mat has been disabled earlier, restart it
		if (!worldScripts["Welcome Information Script"].welcomeTimer.isRunning) {
			worldScripts["Welcome Information Script"].welcomeTimer.start();
			if (player.ship.equipmentStatus("EQ_WELCOME_MAT") == "EQUIPMENT_OK") {
				player.consoleMessage(expandDescription("[academy_welcome_mat_enabled]"), 6);
			}
		}
	}
	this.examStopTime = clock.absoluteSeconds;
	this.examElapsedTime = Math.floor(this.examStopTime - this.examStartTime);
	this.examTimeMinutes = Math.floor(this.examElapsedTime / 60);
	this.examTimeSeconds = this.examElapsedTime - (60 * this.examTimeMinutes);
	missionVariables.laveAcademy_droneAbort = true;
	this.ship.commsMessage(expandDescription("[academy_exam_complete]", { mins: this.examTimeMinutes, secs: this.examTimeSeconds }), player.ship);
	this.ship.AIState = "LIGHTS_OFF";
	missionVariables.laveAcademyExam = null;
	this.bestTime = (missionVariables.laveAcademy_bestDockingTimeM * 60) + missionVariables.laveAcademy_bestDockingTimeS;
	if (this.bestTime == 0 && this.examElapsedTime > 0) {
		this.ship.commsMessage(expandDescription("[academy_new_best_time]"), player.ship);
		missionVariables.laveAcademy_bestDockingTimeM = Math.floor(this.examElapsedTime / 60);
		missionVariables.laveAcademy_bestDockingTimeS = this.examElapsedTime - (60 * (Math.floor(this.examElapsedTime / 60)));
		return;
	}
	if (this.bestTime > this.examElapsedTime) {
		this.ship.commsMessage(expandDescription("[academy_beat_best_time]"), player.ship);
		missionVariables.laveAcademy_bestDockingTimeM = Math.floor(this.examElapsedTime / 60);
		missionVariables.laveAcademy_bestDockingTimeS = this.examElapsedTime - (60 * (Math.floor(this.examElapsedTime / 60)));
		return;
	}
}
this.cancelExam = function () {
	this.examStopTime = clock.absoluteSeconds;
	this.examElapsedTime = Math.floor(this.examStopTime - this.examStartTime);
	this.examTimeMinutes = Math.floor(this.examElapsedTime / 60);
	this.examTimeSeconds = this.examElapsedTime - (60 * this.examTimeMinutes);
	missionVariables.laveAcademy_droneAbort = true;
	this.droneArray = system.shipsWithRole("laveAcademy_dockingDrone")
	if (this.droneArray.length > 0) {
		this.droneArray.forEach(
			function (drone) {
				drone.remove()
			}
		)
	}
	player.commsMessage(expandDescription("[academy_dock_test_abort]", { mins: this.examTimeMinutes, secs: this.examTimeSeconds }), 10);
	this.ship.AIState = "LIGHTS_OFF";
	missionVariables.laveAcademyExam = null;
	if (worldScripts["Welcome Information Script"]) { // if Welcome Mat has been disabled earlier, restart it
		if (!worldScripts["Welcome Information Script"].welcomeTimer.isRunning) {
			worldScripts["Welcome Information Script"].welcomeTimer.start();
			if (player.ship.equipmentStatus("EQ_WELCOME_MAT") == "EQUIPMENT_OK") {
				player.consoleMessage(expandDescription("[academy_welcome_mat_enabled]"), 6);
			}
		}
	}
}
this.playerWillEnterWitchspace = function () {
	if (worldScripts["Welcome Information Script"] && !worldScripts["Welcome Information Script"].welcomeTimer.isRunning) {
		worldScripts["Welcome Information Script"].welcomeTimer.start();
	}
	if (this.launchCheckTimer) {
		this.launchCheckTimer.stop();
	}
}
 | 
                
                    | Scripts/laveAcademy_pilotBuoy.js | "use strict";
this.name = "LaveAcademy_pilotBuoy";
this.author = "Thargoid";
this.copyright = "Creative Commons Attribution - Non-Commercial - Share Alike 3.0 license with clauses - see readme.txt.";
this.description = "Control of academy pilot practice course in the Lave system";
this.version = "1.3";
this.examStart = function () { // first set up the asteroids and rings
	this.removeCourse(); // just in case we're repeating the exam and we've still got debris around.
	this.buoy1Position = this.ship.position.add([-20000, 0, 0]);
	this.buoy2Position = this.buoy1Position.add([0, 20000, 0]);
	this.buoy3Position = this.buoy2Position.add([0, 0, -20000]);
	this.buoy4Position = this.buoy3Position.add([-20000, 0, 0]);
	this.buoy5Position = this.buoy4Position.add([0, -20000, 0]);
	this.buoy6Position = this.buoy5Position.add([20000, 0, 0]);
	this.buoy7Position = this.buoy6Position.add([20000, 0, 0]);
	this.ring1Position = this.buoy1Position.add([0, 10000, 0]);
	this.ring2Position = this.buoy3Position.add([-10000, 0, 0]);
	this.ring3Position = this.buoy5Position.add([10000, 0, 0]);
	//system.legacy_addShipsWithinRadius("laveAcademy_pilotAsteroid", 5, "abs", this.buoy2Position, 7000); // 5 rocks around buoy 2.
	system.addShips("laveAcademy_pilotAsteroid", 5, this.buoy2Position, 7000);
	//system.legacy_addShipsWithinRadius("laveAcademy_pilotRing", 1, "abs", this.ring1Position, 7000); // 1 bonus ring between buoys 1 & 2.
	system.addShips("laveAcademy_pilotRing", 1, this.ring1Position, 7000);
	//system.legacy_addShipsWithinRadius("laveAcademy_pilotAsteroid", 7, "abs", this.buoy3Position, 7000); // 7 rocks around buoy 3.
	system.addShips("laveAcademy_pilotAsteroid", 7, this.buoy3Position, 7000);
	//system.legacy_addShipsWithinRadius("laveAcademy_pilotAsteroid", 12, "abs", this.buoy4Position, 7000); // 12 rocks around buoy 4.
	system.addShips("laveAcademy_pilotAsteroid", 12, this.buoy4Position, 7000);
	//system.legacy_addShipsWithinRadius("laveAcademy_pilotRing", 2, "abs", this.ring2Position, 7000); // 2 bonus rings between buoys 3 & 4.
	system.addShips("laveAcademy_pilotRing", 2, this.ring2Position, 7000);
	//system.legacy_addShipsWithinRadius("laveAcademy_pilotAsteroid", 7, "abs", this.buoy5Position, 7000); // 7 rocks around buoy 5.
	system.addShips("laveAcademy_pilotAsteroid", 7, this.buoy5Position, 7000);
	//system.legacy_addShipsWithinRadius("laveAcademy_pilotAsteroid", 5, "abs", this.buoy6Position, 7000); // 5 rocks around buoy 6.
	system.addShips("laveAcademy_pilotAsteroid", 5, this.buoy6Position, 7000);
	//system.legacy_addShipsWithinRadius("laveAcademy_pilotRing", 1, "abs", this.ring3Position, 7000); // 1 bonus rings between buoys 5 & 6.
	system.addShips("laveAcademy_pilotRing", 1, this.ring3Position, 7000);
	// Reset the mission variables, start the clock and tell the player we're underway
	this.examStartTime = clock.absoluteSeconds;
	missionVariables.laveAcademy_pilotScore = 0; // bonus and penalty counter
	missionVariables.laveAcademy_pilotCurrentBuoy = 0; // the number of the buoy we are currently at
	missionVariables.laveAcademy_pilotNextBuoy = 1; //  the number of the next buoy to be reached
	missionVariables.laveAcademy_pilotNextBuoyName = "pilotBuoy1";
	player.consoleMessage(expandDescription("[academy_piloting_exam_started]"), 6);
	if (this.pilotCourseTimer) {
		this.pilotCourseTimer.start();
	}
	else {
		this.pilotCourseTimer = new Timer(this, this.runCourse, 0, 1);
	}
}
this.runCourse = function runCourse() {
	if (player.ship.docked) { // if the player is docked then stop the test quietly
		this.quietEnd();
		return;
	}
	this.examElapsedTime = Math.floor(clock.absoluteSeconds - this.examStartTime); // absolute time since test began, without penalties or bonuses 
	if (this.examElapsedTime > 900) { // if we've been at the test for over 15 minutes
		this.ship.commsMessage(expandDescription("[academy_piloting_expired]"), player.ship);
		this.quietEnd();
		return;
	}
	if (missionVariables.laveAcademy_pilotNextBuoy == 8 || missionVariables.laveAcademy_pilotNextBuoyName == "FinishLine") { // if we reached the 7th buoy
		this.pilotCourseTimer.stop();
		this.finishLine();
		return;
	}
	if (missionVariables.laveAcademy_pilotCurrentBuoy < missionVariables.laveAcademy_pilotNextBuoy) { // if we reached a buoy successfully spawn & set next
		missionVariables.laveAcademy_pilotCurrentBuoy += 1;
		switch (missionVariables.laveAcademy_pilotNextBuoyName) {
			case "pilotBuoy1":
				{
					let pilotBuoy1 = this.ship.spawnOne('laveAcademy_pilotCircuitBuoy1');
					pilotBuoy1.position = this.buoy1Position;
					pilotBuoy1.AIState = "LIGHTS_ON";
					pilotBuoy1.scannerDisplayColor1 = "redColor";
					pilotBuoy1.scannerDisplayColor2 = "whiteColor";
					break;
				}
			case "pilotBuoy2":
				{
					let pilotBuoy2 = this.ship.spawnOne('laveAcademy_pilotCircuitBuoy2');
					pilotBuoy2.position = this.buoy2Position;
					pilotBuoy2.AIState = "LIGHTS_ON";
					pilotBuoy2.scannerDisplayColor1 = "redColor";
					pilotBuoy2.scannerDisplayColor2 = "whiteColor";
					break;
				}
			case "pilotBuoy3":
				{
					let pilotBuoy3 = this.ship.spawnOne('laveAcademy_pilotCircuitBuoy3');
					pilotBuoy3.position = this.buoy3Position;
					pilotBuoy3.AIState = "LIGHTS_ON";
					pilotBuoy3.scannerDisplayColor1 = "redColor";
					pilotBuoy3.scannerDisplayColor2 = "whiteColor";
					break;
				}
			case "pilotBuoy4":
				{
					let pilotBuoy4 = this.ship.spawnOne('laveAcademy_pilotCircuitBuoy4');
					pilotBuoy4.position = this.buoy4Position;
					pilotBuoy4.AIState = "LIGHTS_ON";
					pilotBuoy4.scannerDisplayColor1 = "redColor";
					pilotBuoy4.scannerDisplayColor2 = "whiteColor";
					break;
				}
			case "pilotBuoy5":
				{
					let pilotBuoy5 = this.ship.spawnOne('laveAcademy_pilotCircuitBuoy5');
					pilotBuoy5.position = this.buoy5Position;
					pilotBuoy5.AIState = "LIGHTS_ON";
					pilotBuoy5.scannerDisplayColor1 = "redColor";
					pilotBuoy5.scannerDisplayColor2 = "whiteColor";
					break;
				}
			case "pilotBuoy6":
				{
					let pilotBuoy6 = this.ship.spawnOne('laveAcademy_pilotCircuitBuoy6');
					pilotBuoy6.position = this.buoy6Position;
					pilotBuoy6.AIState = "LIGHTS_ON";
					pilotBuoy6.scannerDisplayColor1 = "redColor";
					pilotBuoy6.scannerDisplayColor2 = "whiteColor";
					break;
				}
			case "pilotBuoy7":
				{
					let pilotBuoy7 = this.ship.spawnOne('laveAcademy_pilotCircuitBuoy7');
					pilotBuoy7.position = this.buoy7Position;
					pilotBuoy7.AIState = "LIGHTS_ON";
					pilotBuoy7.scannerDisplayColor1 = "redColor";
					pilotBuoy7.scannerDisplayColor2 = "whiteColor";
					break;
				}
		}
	}
}
this.finishLine = function () {
	this.ship.AIState = "FINISH_LINE"; // comms message the player to return to the main buoy to finish the course
	if (this.pilotFinishTimer) {
		this.pilotFinishTimer.start();
	}
	else {
		this.pilotFinishTimer = new Timer(this, this.scanPlayer, 0, 1);
	}
}
this.scanPlayer = function scanPlayer() {
	if (player.ship.docked) { // if the player is docked then stop the test quietly
		this.quietEnd();
	}
	this.buoyDistance = player.ship.position.distanceTo(this.ship.position); // how far the player ship is from the main buoy
	if (this.buoyDistance < 1000) { // if we're within 1000m, we can end the test
		this.pilotFinishTimer.stop();
		this.ship.AIState = "LIGHTS_OFF";
		this.examEnd();
	}
}
this.examEnd = function () {
	if (worldScripts["Welcome Information Script"]) { // if Welcome Mat has been disabled earlier, restart it
		if (!worldScripts["Welcome Information Script"].welcomeTimer.isRunning) {
			worldScripts["Welcome Information Script"].welcomeTimer.start();
			if (player.ship.equipmentStatus("EQ_WELCOME_MAT") == "EQUIPMENT_OK") {
				player.consoleMessage(expandDescription("[academy_welcome_mat_enabled]"), 6);
			}
		}
	}
	this.examStopTime = clock.absoluteSeconds;
	this.examElapsedTime = Math.floor(this.examStopTime - this.examStartTime - missionVariables.laveAcademy_pilotScore);
	this.examTimeMinutes = Math.floor(this.examElapsedTime / 60);
	this.examTimeSeconds = this.examElapsedTime - (60 * this.examTimeMinutes);
	this.removeCourse();
	this.ship.AIState = "LIGHTS_OFF";
	missionVariables.laveAcademyExam = null;
	this.ship.commsMessage(expandDescription("[academy_exam_complete]", { mins: this.examTimeMinutes, secs: this.examTimeSeconds }), player.ship);
	this.bestTime = (missionVariables.laveAcademy_bestPilotTimeM * 60) + missionVariables.laveAcademy_bestPilotTimeS;
	if (this.bestTime == 0 && this.examElapsedTime > 0) {
		this.ship.commsMessage(expandDescription("[academy_new_best_time]"), player.ship);
		missionVariables.laveAcademy_bestPilotTimeM = Math.floor(this.examElapsedTime / 60);
		missionVariables.laveAcademy_bestPilotTimeS = this.examElapsedTime - (60 * (Math.floor(this.examElapsedTime / 60)));
		return;
	}
	if (this.bestTime > this.examElapsedTime) {
		this.ship.commsMessage(expandDescription("[academy_beat_best_time]"), player.ship);
		missionVariables.laveAcademy_bestPilotTimeM = Math.floor(this.examElapsedTime / 60);
		missionVariables.laveAcademy_bestPilotTimeS = this.examElapsedTime - (60 * (Math.floor(this.examElapsedTime / 60)));
		return;
	}
}
this.playerWillEnterWitchspace = this.shipDied = this.quietEnd = function () {
	if (this.pilotCourseTimer) {
		this.pilotCourseTimer.stop();
	}
	if (this.pilotFinishTimer) {
		this.pilotFinishTimer.stop();
	}
	this.removeCourse();
	missionVariables.laveAcademyExam = null;
	missionVariables.laveAcademy_pilotScore = 0;
	missionVariables.laveAcademy_pilotCurrentBuoy = 0;
	missionVariables.laveAcademy_pilotNextBuoy = 1;
	missionVariables.laveAcademy_pilotNextBuoyName = "pilotBuoy1";
	if (worldScripts["Welcome Information Script"]) // if Welcome Mat has been disabled earlier, restart it
	{
		if (!worldScripts["Welcome Information Script"].welcomeTimer.isRunning) {
			worldScripts["Welcome Information Script"].welcomeTimer.start();
		}
	}
	return;
}
this.removeCourse = function () {
	this.courseList = system.shipsWithRole("laveAcademy_pilotCourse"); // find all course entities so we can remove them
	if (this.courseList.length > 0) { // if there are parts of the course still present, loop through them and remove
		let loopCounter = 0; // reset the counter
		for (loopCounter = 0; loopCounter < this.courseList.length; loopCounter++) {
			if (this.courseList[loopCounter].scanClass == "CLASS_BUOY") {
				this.courseList[loopCounter].AIState = "REMOVE_BUOY";
			}
			else {
				this.courseList[loopCounter].remove();
			}
		}
	}
}			
 | 
                
                    | Scripts/laveAcademy_systemScript.js | "use strict";
this.name = "LaveAcademy";
this.author = "Thargoid";
this.copyright = "Creative Commons Attribution - Non-Commercial - Share Alike 3.0 license with clauses - see readme.txt.";
this.description = "Control of new additions to the Lave (and other) systems";
this.version = "2.0";
this.extraA = true;   //   Academies in all galaxies? If false only appear at Lave, nowhere else - ignore extraB
this.extraB = false;   //   Single or multiple academies if extraA set. False gives 1 per galaxy, true gives 5
this.oxpcSettings = {
	Info: { Name: this.name, Display: this.name, InfoB: expandDescription("[academy_oxpconfig_bool_info]") },
	Bool0: { Name: "extraA", Def: true, Desc: expandDescription("[academy_config_allgalaxies]") },
	Bool1: { Name: "extraB", Def: false, Desc: expandDescription("[academy_config_multiple]") }
};
this._libSettings = {
	Name: this.name,
	Alias: expandDescription("[academy_config_alias]"),
	Display: expandDescription("[academy_config_display]"),
	Alive: "_libSettings",
	Bool: {
		B0: { Name: "extraA", Def: true, Desc: expandDescription("[academy_config_allgalaxies]") },
		B1: { Name: "extraB", Def: false, Desc: expandDescription("[academy_config_multiple]") },
		Info: expandDescription("[academy_libconfig_bool_info]")
	},
};
this.startUp = function () {
	if (missionVariables.laveAcademy_bestTargetTimeM == null) { missionVariables.laveAcademy_bestTargetTimeM = 0; }
	if (missionVariables.laveAcademy_bestTargetTimeS == null) { missionVariables.laveAcademy_bestTargetTimeS = 0; }
	if (missionVariables.laveAcademy_bestPilotScore == null) { missionVariables.laveAcademy_bestPilotScore = 0; }
	if (missionVariables.laveAcademy_bestPilotTimeM == null) { missionVariables.laveAcademy_bestPilotTimeM = 0; }
	if (missionVariables.laveAcademy_bestPilotTimeS == null) { missionVariables.laveAcademy_bestPilotTimeS = 0; }
	if (missionVariables.laveAcademy_bestDockingScore == null) { missionVariables.laveAcademy_bestDockingScore = 0; }
	if (missionVariables.laveAcademy_bestDockingTimeM == null) { missionVariables.laveAcademy_bestDockingTimeM = 0; }
	if (missionVariables.laveAcademy_bestDockingTimeS == null) { missionVariables.laveAcademy_bestDockingTimeS = 0; }
	this.deactivateWIS = false;
	if (missionVariables.LaveAcademy_extraA) this.extraA = (missionVariables.LaveAcademy_extraA == "1" ? true : false);
	if (missionVariables.LaveAcademy_extraB) this.extraB = (missionVariables.LaveAcademy_extraB == "1" ? true : false);
	this.setUpArrays();
}
this.startUpComplete = function () {
	// register our settings, if Lib_Config is present
	if (worldScripts.Lib_Config) worldScripts.Lib_Config._registerSet(this._libSettings);
}
this.playerWillSaveGame = function () {
	missionVariables.LaveAcademy_extraA = (this.extraA ? "1" : "0");
	missionVariables.LaveAcademy_extraB = (this.extraB ? "1" : "0");
}
this.setUpArrays = function () {
	this.academyList = [0, 1, 2, 3, 4, 5, 6, 7]; // galaxies 0-7
	this.academyList[0] = [7, 173, 168, 133, 4]; // Lave, Esteonbi, Enonla, Esanbe, Xequerin
	this.academyList[1] = [24, 92, 210, 55, 194]; // Maesaron, Erenanri, Reveabe, Legeara, Tigebere
	this.academyList[2] = [58, 165, 106, 198, 164]; // Radiqu, Edxeri, Ceedleon, Atius,Rerebi
	this.academyList[3] = [13, 47, 130, 18, 122]; // Mavelege, Bemate, Cebitiza,  Mausra, Ensoor
	this.academyList[4] = [16, 193, 231, 92, 9]; // Zaaner, Vebi, Inenares, Azaenbi, Dioris
	this.academyList[5] = [151, 6, 85, 146, 240]; // Teesso, Oresmaa, Celaan, Ariqu, Inesbe
	this.academyList[6] = [189, 146, 130, 118, 37]; // Isdilaon, Aenbi, Ataer, Orreedon, Qutegequ
	this.academyList[7] = [177, 31, 211, 157, 20]; // Ceenza, Aarzari, Biatzate, Inbein, Oredrier
}
this.systemCheck = function (planetNum, galNum) {
	if (!this.extraA) // academy at Lave only?
	{
		if (planetNum == 7 && galNum == 0) { return true; }
		else { return false; }
	}
	else {
		if (!this.extraB)	// 1 academy per galaxy
		{
			if (planetNum == this.academyList[galNum][0]) { return true; }
			else { return false; }
		}
		else	// 5 academies per galaxy
		{
			if (this.academyList[galNum].indexOf(planetNum) != -1) { return true; }
			else { return false; }
		}
	}
}
this.setUpSystem = function () {
	if (this.systemCheck(system.ID, galaxyNumber)) {
		var posLA = system.mainStation.position.add(system.mainStation.vectorRight.multiply(50000));
		system.setPopulator("laveAcademy", {
			callback: function (pos) {
				var ws = worldScripts.LaveAcademy;
				// because we're doing the setup during "systemWillPopulate", we don't need a lot of the arrays and checks from v1.33
				// find the academy (if it already exists)
				var academyArray = system.shipsWithPrimaryRole("laveAcademy_academy");
				if (academyArray.length === 0) academyArray = system.addShips("laveAcademy_academy", 1, pos, 0);
				var academy = academyArray[0];
				academy.scannerDisplayColor1 = "greenColor";
				academy.scannerDisplayColor2 = "brownColor";
				// set up the marker buoys
				system.addShips("laveAcademy_wayBuoy", 1, system.mainStation.position.add([0, 20000, 0]));
				ws.targetBuoy = system.addShips("laveAcademy_targetBuoy", 1, academy.position.add([0, 0, 20000]))[0];
				ws.dockingBuoy = system.addShips("laveAcademy_dockingBuoy", 1, academy.position.add([20000, 0, 0]))[0];
				ws.pilotBuoy = system.addShips("laveAcademy_pilotBuoy", 1, academy.position.add([-20000, 0, 0]))[0];
				ws.targetBuoy.AIState = "LIGHTS_OFF";
				ws.dockingBuoy.AIState = "LIGHTS_OFF";
				ws.pilotBuoy.AIState = "LIGHTS_OFF";
				//	Set the academy syllabus on the F4 screen, and remove the trunk ones for this station.
				academy.setInterface("LaveAcademy",
					{
						title: expandDescription("[academy_interface_title]"),
						category: expandDescription("[academy_interface_category]"),
						summary: expandDescription("[academy_interface_summary]"),
						callback: ws.showCourses.bind(ws)
					});
				academy.setInterface("oolite-contracts-cargo", null);
				academy.setInterface("oolite-contracts-parcels", null);
				academy.setInterface("oolite-contracts-passengers", null);
			},
			location: "COORDINATES",
			coordinates: posLA,
			deterministic: true
		});
	}
}
this.showCourses = function () {
	mission.runScreen({
		title: expandDescription("[academy_syllabus_title]"),
		messageKey: "laveAcademy_examOffer",
		choicesKey: "laveAcademy_offerChoice",
		screenID: "lave_academy"
	}, this.choseExam);
}
this.shipLaunchedFromStation = function () {
	if (this.systemCheck(system.ID, galaxyNumber) && this.deactivateWIS) {
		// if Welcome Mat is loaded & running, disable it to stop data messages with the course buoys
		if (worldScripts["Welcome Information Script"]) {
			if (worldScripts["Welcome Information Script"].welcomeTimer.isRunning) {
				worldScripts["Welcome Information Script"].welcomeTimer.stop();
				if (player.ship.equipmentStatus("EQ_WELCOME_MAT") == "EQUIPMENT_OK") player.consoleMessage(expandDescription("[academy_welcome_mat_disabled]"), 6);
			}
		}
		this.deactivateWIS = false;
	}
}
this.systemWillPopulate = function () {
	this.setUpSystem()
}
this.shipWillLaunchFromStation = function (station) {
	if (station.hasRole("laveAcademy_academy")) {
		// reactivate the trumble mission if it was available before docking.
		missionVariables.trumbles = missionVariables.laveAcademy_storeTrumble;
		switch (missionVariables.laveAcademyExam) { // Get the course started by setting the buoys AI states
			case "TARGET":
				{
					this.targetBuoy.AIState = "LIGHTS_ON";
					this.dockingBuoy.AIState = "LIGHTS_OFF";
					this.pilotBuoy.AIState = "LIGHTS_OFF";
					this.buoyID = this.targetBuoy;
					this.deactivateWIS = true;
					if (this.buoyTimer) { this.buoyTimer.start(); }
					else { this.buoyTimer = new Timer(this, this.checkBuoyDistance, 0, 10); }
					break;
				}
			case "DOCKING":
				{
					this.targetBuoy.AIState = "LIGHTS_OFF";
					this.dockingBuoy.AIState = "LIGHTS_ON";
					this.pilotBuoy.AIState = "LIGHTS_OFF";
					this.buoyID = this.dockingBuoy;
					this.deactivateWIS = true;
					if (this.buoyTimer) { this.buoyTimer.start(); }
					else { this.buoyTimer = new Timer(this, this.checkBuoyDistance, 0, 10); }
					break;
				}
			case "PILOT":
				{
					this.targetBuoy.AIState = "LIGHTS_OFF";
					this.dockingBuoy.AIState = "LIGHTS_OFF";
					this.pilotBuoy.AIState = "LIGHTS_ON";
					this.buoyID = this.pilotBuoy;
					this.deactivateWIS = true;
					if (this.buoyTimer) { this.buoyTimer.start(); }
					else { this.buoyTimer = new Timer(this, this.checkBuoyDistance, 0, 2); }
					break;
				}
			default:
				{
					this.targetBuoy.AIState = "LIGHTS_OFF";
					this.dockingBuoy.AIState = "LIGHTS_OFF";
					this.pilotBuoy.AIState = "LIGHTS_OFF";
					this.deactivateWIS = false;
					break;
				}
		}
	}
}
this.stopTimers = function () {
	if (this.buoyTimer) { this.buoyTimer.stop(); }
	if (this.targetTimer) { this.targetTimer.stop(); }
	if (this.pilotTimer) { this.pilotTimer.stop(); }
	if (this.dockingTimer) { this.dockingTimer.stop(); }
	if (this.targetBuoy && this.targetBuoy.script.launchCheckTimer) this.targetBuoy.script.launchCheckTimer.stop();
	if (this.dockingBuoy && this.dockingBuoy.script.launchCheckTimer) this.dockingBuoy.script.launchCheckTimer.stop();
	if (this.pilotBuoy) {
		if (this.pilotBuoy.script.pilotCourseTimer) this.pilotBuoy.script.pilotCourseTimer.stop();
		if (this.pilotBuoy.script.pilotFinishTimer) this.pilotBuoy.script.pilotFinishTimer.stop();
	}
}
this.shipWillEnterWitchspace = this.shipDied = function () {
	if (this.systemCheck(system.ID, galaxyNumber)) {
		this.stopTimers();
		this.deactivateWIS = false;
		this.targetBuoy.explode();
		this.dockingBuoy.explode();
		this.pilotBuoy.explode();
		missionVariables.laveAcademyExam = null;
		if (worldScripts["Welcome Information Script"]) { // if Welcome Mat has been disabled earlier, restart it
			if (!worldScripts["Welcome Information Script"].welcomeTimer.isRunning) {
				worldScripts["Welcome Information Script"].welcomeTimer.start();
				if (player.ship.equipmentStatus("EQ_WELCOME_MAT") == "EQUIPMENT_OK") { player.consoleMessage(expandDescription("[academy_welcome_mat_enabled]"), 6); }
			}
		}
	}
}
this.shipWillDockWithStation = function (station) {
	if (this.systemCheck(system.ID, galaxyNumber)) {
		this.deactivateWIS = false;
		missionVariables.laveAcademyExam = null;
		this.stopTimers();
	}
	// this seems unnecessary, as the trumbles mission is only offered at main stations
	if (station.hasRole("laveAcademy_academy")) { // stop the trumble mission offering whilst docked at the academy
		missionVariables.laveAcademy_storeTrumble = missionVariables.trumbles;
		missionVariables.trumbles = "";
	}
}
this.checkBuoyDistance = function checkBuoyDistance() {
	var buoyDistance = player.ship.position.distanceTo(this.buoyID.position); // how far the player ship is from the buoy
	if (buoyDistance < 1000) { // if we're within 1000m.
		this.buoyTimer.stop();
		this.buoyID.AIState = "START_EXAM";
	}
}
this.guiScreenChanged = function () {
	// for GUI screen changes whilst in flight, which we can ignore
	if (!player.ship.docked) return;
	// if we're not at Lave Academy
	if (!player.ship.dockedStation.hasRole("laveAcademy_academy")) return;
	// replace marketplace screen with exam offering mission screen
	if (guiScreen == "GUI_SCREEN_MARKET") this.showCourses();
}
this.choseExam = function (examChoice) {
	switch (examChoice) {
		case "ACADEMY_1_TARGET":
			{
				mission.runScreen({ 
					title: expandDescription("[academy_gunnery_exam]"), 
					messageKey: "laveAcademy_targetInfo", 
					choicesKey: "laveAcademy_targetYesNo", 
					screenID: "lave_academy" }, this.examYesNo);
				break;
			}
		case "ACADEMY_2_PILOT":
			{
				mission.runScreen({ 
					title: expandDescription("[academy_piloting_exam]"), 
					messageKey: "laveAcademy_pilotInfo", 
					choicesKey: "laveAcademy_pilotYesNo", 
					screenID: "lave_academy" }, this.examYesNo);
				break;
			}
		case "ACADEMY_3_DOCKING":
			{
				mission.runScreen({ 
					title: expandDescription("[academy_docking_exam]"), 
					messageKey: "laveAcademy_dockingInfo", 
					choicesKey: "laveAcademy_dockingYesNo", 
					screenID: "lave_academy" }, this.examYesNo);
				break;
			}
		case "ACADEMY_4_RESET":
			{
				missionVariables.laveAcademyExam = null;
				missionVariables.laveAcademy_bestTargetTimeM = 0;
				missionVariables.laveAcademy_bestTargetTimeS = 0;
				missionVariables.laveAcademy_bestPilotTimeM = 0;
				missionVariables.laveAcademy_bestPilotTimeS = 0;
				missionVariables.laveAcademy_bestDockingScore = 0;
				missionVariables.laveAcademy_bestDockingTimeM = 0;
				missionVariables.laveAcademy_bestDockingTimeS = 0;
				mission.runScreen({ 
					title: expandDescription("[academy_syllabus_title]"), 
					messageKey: "laveAcademy_examOffer", 
					choicesKey: "laveAcademy_offerChoice", 
					screenID: "lave_academy" }, this.choseExam);
				break;
			}
		case "ACADEMY_5_DECLINE":
			{
				missionVariables.laveAcademyExam = null;
				break;
			}
	}
}
this.examYesNo = function (selection) {
	switch (selection) {
		case "ACADEMY_1_TARGETYES":
			{
				missionVariables.laveAcademyExam = "TARGET";
				break;
			}
		case "ACADEMY_2_TARGETNO":
			{
				mission.runScreen({ 
					title: expandDescription("[academy_syllabus_title]"), 
					messageKey: "laveAcademy_examOffer", 
					choicesKey: "laveAcademy_offerChoice", 
					screenID: "lave_academy" }, this.choseExam);
				break;
			}
		case "ACADEMY_1_PILOTYES":
			{
				missionVariables.laveAcademyExam = "PILOT";
				break;
			}
		case "ACADEMY_2_PILOTNO":
			{
				mission.runScreen({ 
					title: expandDescription("[academy_syllabus_title]"), 
					messageKey: "laveAcademy_examOffer", 
					choicesKey: "laveAcademy_offerChoice", 
					screenID: "lave_academy" }, this.choseExam);
				break;
			}
		case "ACADEMY_1_DOCKINGYES":
			{
				missionVariables.laveAcademyExam = "DOCKING";
				break;
			}
		case "ACADEMY_2_DOCKINGNO":
			{
				mission.runScreen({ 
					title: expandDescription("[academy_syllabus_title]"), 
					messageKey: "laveAcademy_examOffer", 
					choicesKey: "laveAcademy_offerChoice", 
					screenID: "lave_academy" }, this.choseExam);
				break;
			}
		default:
			{
				missionVariables.laveAcademyExam = null;
				break;
			}
	}
}
 | 
                
                    | Scripts/laveAcademy_targetBuoy.js | "use strict";
this.name = "LaveAcademy_targetBuoy";
this.author = "Thargoid";
this.copyright = "Creative Commons Attribution - Non-Commercial - Share Alike 3.0 license with clauses - see readme.txt.";
this.description = "Control of academy target practice buoys in the Lave system";
this.version = "1.3";
this.examStart = function () {
	missionVariables.laveAcademy_droneLifetime = 45;
	if (player.score < 16) { // if player is ranked harmless or mostly harmless, give another 10 seconds to the drone
		missionVariables.laveAcademy_droneLifetime += 10;
	}
	if (player.ship.equipmentStatus("EQ_FUEL_INJECTION") != "EQUIPMENT_OK") { // if player doesn't have fuel injectors, add 15 more seconds
		missionVariables.laveAcademy_droneLifetime += 15;
	}
	if (player.ship.weaponRange == 12500) { // if player has only a short range laser, add 10 more seconds
		missionVariables.laveAcademy_droneLifetime += 10;
	}
	this.examStartTime = clock.absoluteSeconds;
	this.buoyPosition = this.ship.position;
	missionVariables.laveAcademy_droneCount = 0;
	missionVariables.laveAcademy_droneAbort = null;
	player.consoleMessage(expandDescription("[academy_gunnery_exam_started]"), 6);
	player.consoleMessage(expandDescription("[academy_drone_lifetime]", { secs: missionVariables.laveAcademy_droneLifetime }), 6);
	if (this.launchCheckTimer) {
		this.launchCheckTimer.start();
	}
	else {
		this.launchCheckTimer = new Timer(this, this.droneCheck, 0, 1);
	}
}
this.droneCheck = function droneCheck() {
	if (player.ship.docked) { // if the player is docked (at the Academy) then stop the test quietly
		this.launchCheckTimer.stop();
		missionVariables.laveAcademy_droneAbort = true;
		this.ship.AIState = "LIGHTS_OFF";
		missionVariables.laveAcademyExam = null;
		return;
	}
	function isPlayer(entity) { return entity.isShip && entity.isPlayer };
	this.playerInRange = system.filteredEntities(this, isPlayer, this.ship, 25600).length;
	if (this.playerInRange == 0) {
		missionVariables.laveAcademy_droneAbort = true;
		missionVariables.laveAcademy_droneCount -= 1;
		this.cancelExam();
	}
	if (missionVariables.laveAcademy_droneAbort) {
		this.launchCheckTimer.stop();
		return;
	}
	function isTargetDrone(entity) { return entity.isShip && entity.hasRole("laveAcademy_targetDrone") };
	if (system.filteredEntities(this, isTargetDrone, this.ship, 25600).length == 0) {
		if (missionVariables.laveAcademy_droneCount == 15) {
			this.endExam();
		}
		else {
			missionVariables.laveAcademy_droneCount += 1;
			switch (true) {
				case (missionVariables.laveAcademy_droneCount == 1):
					{
						this.ship.commsMessage(expandDescription("[academy_level_one]"), player.ship);
						break;
					}
				case (missionVariables.laveAcademy_droneCount == 6):
					{
						this.ship.commsMessage(expandDescription("[academy_level_two]"), player.ship);
						break;
					}
				case (missionVariables.laveAcademy_droneCount == 11):
					{
						this.ship.commsMessage(expandDescription("[academy_level_three]"), player.ship);
						break;
					}
			}
			this.examLevel = (Math.ceil(missionVariables.laveAcademy_droneCount * 0.2));
			this.droneRole = "laveAcademy_targetDroneL" + this.examLevel;
			//system.legacy_addShipsWithinRadius(this.droneRole, 1, "abs", this.buoyPosition, 12000);
			var dr = system.addShips(this.droneRole, 1, this.buoyPosition, 12000)[0];
		}
	}
}
this.endExam = function () {
	this.launchCheckTimer.stop();
	if (worldScripts["Welcome Information Script"]) { // if Welcome Mat has been disabled earlier, restart it
		if (!worldScripts["Welcome Information Script"].welcomeTimer.isRunning) {
			worldScripts["Welcome Information Script"].welcomeTimer.start();
			if (player.ship.equipmentStatus("EQ_WELCOME_MAT") == "EQUIPMENT_OK") {
				player.consoleMessage(expandDescription("[academy_welcome_mat_enabled]"), 6);
			}
		}
	}
	this.examStopTime = clock.absoluteSeconds;
	this.examElapsedTime = Math.floor(this.examStopTime - this.examStartTime);
	this.examTimeMinutes = Math.floor(this.examElapsedTime / 60);
	this.examTimeSeconds = this.examElapsedTime - (60 * this.examTimeMinutes);
	missionVariables.laveAcademy_droneAbort = true;
	this.ship.commsMessage(expandDescription("[academy_exam_complete]", { mins: this.examTimeMinutes, secs: this.examTimeSeconds }), player.ship);
	this.ship.AIState = "LIGHTS_OFF";
	missionVariables.laveAcademyExam = null;
	this.bestTime = (missionVariables.laveAcademy_bestTargetTimeM * 60) + missionVariables.laveAcademy_bestTargetTimeS;
	if (this.bestTime == 0 && this.examElapsedTime > 0) {
		this.ship.commsMessage(expandDescription("[academy_new_best_time]"), player.ship);
		missionVariables.laveAcademy_bestTargetTimeM = Math.floor(this.examElapsedTime / 60);
		missionVariables.laveAcademy_bestTargetTimeS = this.examElapsedTime - (60 * (Math.floor(this.examElapsedTime / 60)));
		return;
	}
	if (this.bestTime > this.examElapsedTime) {
		this.ship.commsMessage(expandDescription("[academy_beat_best_time]"), player.ship);
		missionVariables.laveAcademy_bestTargetTimeM = Math.floor(this.examElapsedTime / 60);
		missionVariables.laveAcademy_bestTargetTimeS = this.examElapsedTime - (60 * (Math.floor(this.examElapsedTime / 60)));
		return;
	}
}
this.cancelExam = function () {
	this.launchCheckTimer.stop();
	this.examStopTime = clock.absoluteSeconds;
	this.examElapsedTime = Math.floor(this.examStopTime - this.examStartTime);
	this.examTimeMinutes = Math.floor(this.examElapsedTime / 60);
	this.examTimeSeconds = this.examElapsedTime - (60 * this.examTimeMinutes);
	missionVariables.laveAcademy_droneAbort = true;
	this.droneArray = system.shipsWithRole("laveAcademy_targetDrone")
	if (this.droneArray.length > 0) {
		this.droneArray.forEach(
			function (drone) {
				drone.remove()
			}
		)
	}
	this.ship.commsMessage(expandDescription("[academy_gunnery_test_abort", { mins: this.examTimeMinutes, secs: this.examTimeSeconds }), player.ship);
	this.ship.AIState = "LIGHTS_OFF";
	missionVariables.laveAcademyExam = null;
	if (worldScripts["Welcome Information Script"]) { // if Welcome Mat has been disabled earlier, restart it
		if (!worldScripts["Welcome Information Script"].welcomeTimer.isRunning) {
			worldScripts["Welcome Information Script"].welcomeTimer.start();
			if (player.ship.equipmentStatus("EQ_WELCOME_MAT") == "EQUIPMENT_OK") {
				player.consoleMessage(expandDescription("[academy_welcome_mat_enabled]"), 6);
			}
		}
	}
}
this.playerWillEnterWitchspace = function () {
	if (worldScripts["Welcome Information Script"] && !worldScripts["Welcome Information Script"].welcomeTimer.isRunning) {
		worldScripts["Welcome Information Script"].welcomeTimer.start();
	}
	if (this.launchCheckTimer) {
		this.launchCheckTimer.stop();
	}
} |