Files
ResistanceRacing2k97/src/3d/levels/lvlQuadRingsTest.js
T
2026-10-23 00:24:27 +02:00

2293 lines
96 KiB
JavaScript
Executable File

import GL_Vec3 from "../../additionalMath/gl_vec3.js";
import PanelEndOfRace from "../../ui/panelEndOfRace.js";
import PanelEndOfCanyon from "../../ui/panelEndOfCanyon.js";
import PanelEscapeMenu from "../../ui/panelEscapeMenu.js";
import PanelRaceTutorial from "../../ui/panelRaceTutorial.js";
import PanelWelcome from "../../ui/panelWelcome.js";
import UI from "../../ui/racing/ui.js";
import ShipManager from "../racing/shipManager.js";
import TrackBuilder from "../racing/trackBuilder.js";
import Transform from "../transform.js";
export default class LevelQuadRingsTest {
constructor(_scene, _params) {
this.scene = _scene;
this.params = _params;
this.startFromHangar = this.params.startFromHangar; //set false if switching track without going back to hangar
this.states = {
startFromHangar: 0,
countDown: 1,
race: 2,
pause: 3,
//finished: 4,//maybe not needed as race and pause needs to happen still
};
this.state = this.states.countDown;
this.raceModes = {
hotlap: 0, //get the best time (practice?)
timetrial: 1, //arcade timer runs down and gets extra time when passing checkpoints or collected
obstacle: 2, //gain points by near misses
qualifying: 3, //three laps to set the fastest time
qualifyingTraffic: 4, //same as above but with enemies that could impede you
grandprix: 5, //normal race against the ai
canyon: 6, //1v1 rack up points as the hunter by slipstreaming, lose them when being hunted
knockout: 7, //each lap or after a timer, the last position is elimated
hunt: 8, //runout the enemies (sprint track?)
passthebomb: 9, //pass the bomb by slipstream to someone before the timer runs out
crazy: 10, //each lap you have to crack a harder time
overtake: 11, //get pointns for each overtake within a time,
tutorial: 99,
};
this.raceMode = this.params.raceMode !== undefined ? this.params.raceMode : 5;
//this.raceMode = this.raceModes.canyon;//hotlap grandprix canyon
this.raceModeData = {};
this.maxLaps = this.params.maxLaps !== undefined ? this.params.maxLaps : 5;
this.stopAfterRingId = this.params.stopAfterRingId !== undefined ? this.params.stopAfterRingId : 0;
this.countdown = {
current: Date.now(),
start: Date.now(),
texts: ["THREE", "TWO", "ONE", "GO!", ""],
step: 0,
knockout: 0,
go: false,
};
this.finishedRace = false;
this.grid = [];
this.tutorialStep = -1;
this.tutorialHoldVar = 0;
this.tutorialHoldVarMax = 500;
//this.scene.player.jumpToPosition({ x: 0, y: 0, z: -128 });
//this.scene.player.dir.pitch = 0;
this.scene.player = this.scene.playerGame;
this.scene.cam = this.scene.camGame;
/*
console.log("--DATA--")
console.log(this.scene.player);
console.log(this.scene.player.id);
console.log(this.scene.player.mode);
console.log(this.scene.player.moveMode);
*/
//INFOif no difference try locking the mouse / well maybe unlocking?
//this.scene.player.setMode(PLAYERMODE.INTERACT);
//this.scene.player.panel = new PanelWelcome(this.scene);
this.trackBuilder = new TrackBuilder(this.scene, this);
this.ui = new UI(this.scene, this);
this.camRig = this.scene.geometryController.loadModel("hoverShip", "modDebugTile", { x: 0, y: 64, z: 256 });
this.camRig.quadDate = [];
//this.camRig.flags.draw = true;
this.playerShip = new ShipManager(this.scene, this, 999, true, false, this.params.playerShipModel);
this.playerShip.name = "Player";
this.playerShip.ship.data = {
slipstreamLength: 2024,
name: "Player"
};
this.playerIsShip = true;
this.ui.registerShip(this.playerShip);
this.aiShips = [];
switch (this.raceMode) {
case this.raceModes.hotlap:
case this.raceModes.timetrial:
case this.raceModes.obstacle:
case this.raceModes.qualifying:
break;
case this.raceModes.qualifyingTraffic:
case this.raceModes.grandprix:
case this.raceModes.knockout:
case this.raceModes.passthebomb:
let names = ["Bonez", "Foxxy", "Glaze", "Roki", "Hog", "Roach", "Scooter", "Jay"];
//let names = ["Jay", "Jay", "Jay", "Jay", "Jay", "Jay", "Jay", "Jay"];
let colors = ["Yellow", "Blue", "Green", "Red"];
for (let i = 0; i < 7; i++) {
this.aiShips.push(new ShipManager(this.scene, this, i, false, true));
this.aiShips[this.aiShips.length - 1].autopilot = true;
this.aiShips[this.aiShips.length - 1].ai.prefRoll = Math.random() > 0.5 ? -1 : 1;
this.aiShips[this.aiShips.length - 1].speedMax += -0.5 + Math.random() * 2;
this.aiShips[this.aiShips.length - 1].rollAcceleration += Math.random() * 0.01;
this.aiShips[this.aiShips.length - 1].acceleration += Math.random() * 0.01;
this.aiShips[this.aiShips.length - 1].setShipColor(colors[i % 4]);
this.aiShips[this.aiShips.length - 1].name = names[i];
this.aiShips[this.aiShips.length - 1].ship.data = {
slipstreamLength: 2024,
name: names[i]
};
//add ship to the ui (minimap)
//this.ui.registerShip(this.aiShips[this.aiShips.length - 1]);
}
break;
case this.raceModes.canyon:
this.aiShips.push(new ShipManager(this.scene, this, 0, false, true, "modHoverCarTinnemann00"));
this.aiShips[this.aiShips.length - 1].autopilot = true;
this.aiShips[this.aiShips.length - 1].ai.prefRoll = Math.random() > 0.5 ? -1 : 1;
//this.aiShips[this.aiShips.length - 1].speedMax += -0.5 + (Math.random() * 2);
//this.aiShips[this.aiShips.length - 1].speedMax += 1;
this.aiShips[this.aiShips.length - 1].rollAcceleration += 0.01;
this.aiShips[this.aiShips.length - 1].rollSpeedMax += 0.1;
this.aiShips[this.aiShips.length - 1].rollSpeedMin -= 0.1;
this.aiShips[this.aiShips.length - 1].acceleration += 0.01;
this.aiShips[this.aiShips.length - 1].setShipColor("Yellow");
this.aiShips[this.aiShips.length - 1].name = "Roki";
this.aiShips[this.aiShips.length - 1].ship.data = {
slipstreamLength: 2024,
name: "Roki"
};
//add ship to the ui (minimap)
//this.ui.registerShip(this.aiShips[this.aiShips.length - 1]);
this.raceModeData = {
playerIsHunter: true,
points: {
overall: 0,
rounds: [0, 0]
}
}
break;
case this.raceModes.hunt:
break;
case this.raceModes.crazy:
break;
case this.raceModes.tutorial:
this.aiShips.push(new ShipManager(this.scene, this, 0, false, true, "modHoverCarTinnemann00")); //modHoverCarWipeOutStyle
this.aiShips[this.aiShips.length - 1].autopilot = true;
this.aiShips[this.aiShips.length - 1].ai.prefRoll = Math.random() > 0.5 ? -1 : 1;
//this.aiShips[this.aiShips.length - 1].speedMax = 8;
this.aiShips[this.aiShips.length - 1].rollAcceleration += Math.random() * 0.01;
this.aiShips[this.aiShips.length - 1].acceleration += Math.random() * 0.01;
this.aiShips[this.aiShips.length - 1].setShipColor("Yellow");
this.aiShips[this.aiShips.length - 1].name = "Roki";
this.aiShips[this.aiShips.length - 1].ship.data = {
slipstreamLength: 2024,
name: "Roki",
conversation: {
fileName: "diaDemoRaceTutorial",
treePosition: 0,
},
};
//add ship to the ui (minimap)
//this.ui.registerShip(this.aiShips[this.aiShips.length - 1]);
break;
default:
break;
}
for (let ai of this.aiShips) {
ai.character = this.scene.characters.filter(el => el.name === ai.name)[0];
this.ui.registerShip(ai);
}
this.camOffset = {
pos: { x: 0, y: 0, z: 0 },
dir: { yaw: 0, pitch: 0, roll: 0, spd: { yaw: 0.04, pitch: 0.04, roll: 0.04 } },
target: {
pos: { x: 0, y: 0, z: 0 },
dir: { yaw: 0, pitch: 0, roll: 0, spd: { yaw: 0.04, pitch: 0.04, roll: 0.04 } },
},
virtualMouse: {
delta: { x: 0, y: 0 },
lastPos: { x: 0, y: 0 },
pos: { x: 0, y: 0 },
},
};
this.situation = {
actions: {
hit: { //player bumping into ai
who: "",
priority: 0,
time: 0
}, slipstream: { //player slipstreaming ai
who: "",
priority: 0,
time: 0
}, slipstreamed: { //ai slipstreaming behind player
who: "",
priority: 0,
time: 0
}, gainPosition: { //player overtakes ai
who: "",
priority: 0,
time: 0
}, loosePosition: { //ai overtakes player
who: "",
priority: 0,
time: 0
}, mishap: { //player crashes near ai
who: "",
priority: 0,
time: 0
}, win: { //ai wins
who: "",
priority: 1,
time: 0
}, loose: { //player wins / rival looses
who: "",
priority: 0,
time: 0
}
}
}
//IMPORTANT for building models
//this.toModel = this.createDefaultRing();
this.toModel = this.scene.geometryController.loadModel("ring DEFAULT", "modRingD64R128RoundCanyon", { x: -512, y: 0, z: 0 });
this.toModel.flags.draw = true;
/*for(let j = 1 ; j < 8 ; j++){
for(let i = 0; i < 20 ; i++){
let q = this.toModel.quadData[i];
this.toModel.addQuadFromData({
type: "quad",
frame: q.frame,
texture: "atlasAll",
position: { x: 0, y: 0, z: 0 },
points: [
{//hinten rechts
x: q.points[0].x,
y: q.points[0].y,
z: q.points[0].z + (j * 64) + 0
},{//hinten links
x: q.points[1].x,
y: q.points[1].y,
z: q.points[1].z + (j * 64) + 0
},{//vorne links
x: q.points[2].x,
y: q.points[2].y,
z: q.points[2].z + (j * 64) + 0
},{//vorne rechts
x: q.points[3].x,
y: q.points[3].y,
z: q.points[3].z + (j * 64) + 0
}
]
});
}
}*/
this.helpModel0 = this.scene.geometryController.loadModel("ring DEFAULT help 0", "modRingD64R128RoundCanyon", { x: -512, y: 0, z: 64 });
this.helpModel0.flags.draw = true;
this.helpModel1 = this.scene.geometryController.loadModel("ring DEFAULT help 1", "modRingD64R128RoundCanyon", { x: -512, y: 0, z: 128 });
this.helpModel1.flags.draw = true;
//this.helpModel2 = this.scene.geometryController.loadModel("ring DEFAULT help 2", "modRingD64R128", { x: -512, y: 0, z: 128 + 64 });
//this.helpModel2.flags.draw = true;
//this.helpModel3 = this.scene.geometryController.loadModel("ring DEFAULT help 3", "modRingD64R128", { x: -512, y: 0, z: 128 + 128 });
//this.helpModel3.flags.draw = true;
//this.helpModel4 = this.scene.geometryController.loadModel("ring DEFAULT help 4", "modRingD64R128", { x: -512, y: 0, z: 128 + 192});
//this.helpModel4.flags.draw = true;
//
//this.helpModel5 = this.scene.geometryController.loadModel("ring DEFAULT help 5", "modRingD64R128", { x: -512, y: 0, z: 320 + 64 });
//this.helpModel5.flags.draw = true;
//this.helpModel6 = this.scene.geometryController.loadModel("ring DEFAULT help 6", "modRingD64R128", { x: -512, y: 0, z: 320 + 128 });
//this.helpModel6.flags.draw = true;
//this.helpModel7 = this.scene.geometryController.loadModel("ring DEFAULT help 7", "modRingD64R128", { x: -512, y: 0, z: 320 + 192 });
//this.helpModel7.flags.draw = true;
//this.helpModel1.rotateAroundAxis([0, 0, 1], Math.PI * 0.25)
//this.helpModel2 = this.scene.geometryController.loadModel("ring DEFAULT help 3", "modRingD64R128Quadrat", { x: -512, y: 0, z: 128+64 });
//this.helpModel2.flags.draw = true;
//preload Textures
let textureArray0 = this.trackBuilder.textureArrays.canyon[0];
let textureArray1 = this.trackBuilder.textureArrays.canyon[0];
let textureArray2 = this.trackBuilder.textureArrays.canyon[0];
//let textureArray3 = this.trackBuilder.textureArrays.darkMetalRing[0];
for(let [i, t] of textureArray0.entries()){this.toModel.quadData[i].setTexture(t.texture, t.frame);}
for(let [i, t] of textureArray1.entries()){this.helpModel0.quadData[i].setTexture(t.texture, t.frame);}
for(let [i, t] of textureArray2.entries()){this.helpModel1.quadData[i].setTexture(t.texture, t.frame);}
//for(let [i, t] of textureArray3.entries()){this.helpModel2.quadData[i].setTexture(t.texture, t.frame);}
//IMPORTANT end of builder
//debug change track
this.scene.keys.m.on(
"up",
(_key, _event) => {
if (this.scene.editor.enabled === false) {
let tid = this.trackBuilder.currentTrackId + 1;
if (tid >= 4) {
tid = 0;
}
this.loadTrack(tid);
//restart all ships
for (let ai of this.aiShips) {
ai.lapTimes = [];
ai.fastestLap = 0;
ai.last.fastestLap = 0;
}
this.playerShip.lapTimes = [];
this.playerShip.fastestLap = 0;
this.playerShip.last.fastestLap = 0;
this.playerShip.autopilot = false;
this.ui.show();
this.finishedRace = false;
}
},
this,
);
//get in and out of craft
this.scene.keys.z.on(
"up",
(_key, _event) => {
if (this.scene.editor.enabled === false) {
this.playerIsShip = !this.playerIsShip;
if (this.playerIsShip === false) {
this.scene.player = this.scene.playerWalk;
this.scene.cam = this.scene.camWalk;
//this.scene.player.jumpToPosition({ x: 304, y: 512 - 56, z: -160 });
this.scene.player.jumpToPosition({ x: this.playerShip.shipAnchor.pos.x, y: this.playerShip.shipAnchor.pos.y, z: this.playerShip.shipAnchor.pos.z });
this.scene.player.dir.pitch = 0;
} else {
this.scene.player = this.scene.playerGame;
this.scene.cam = this.scene.camGame;
}
}
},
this,
);
//toggle autopilot
this.scene.keys.space.on(
"up",
(_key, _event) => {
if (this.scene.editor.enabled === false) {
this.playerShip.autopilot = !this.playerShip.autopilot;
}
},
this,
);
//hide all models
for (let s of this.trackBuilder.spline) {
if (s.model !== null) {
s.model.flags.draw = false;
}
}
//debug laoding screen
this.graLoading = this.scene.add.graphics();
this.graLoading.fillStyle(0x000000, 0.9);
this.graLoading.fillRect(this.scene.left, this.scene.top, this.scene.game.config.width, this.scene.game.config.height);
this.graLoading.depth = 9998;
this.graLoading.alpha = 0;
this.txtLoading = this.scene.add.bitmapText(0, 0, "uiFont", "LOADING TRACK", 14, 0).setOrigin(0.5).setLetterSpacing(0);
this.txtLoading.depth = 9999;
this.txtLoading.alpha = 0;
this.testCounter = 0;
this.testPic = 0;
//add hangar
this.hangarDoorLeft = this.scene.geometryController.loadModel("hangar door left", "modHangarDoor", { x: -64, y: 468 - 1, z: 128 }); // x: 48, y: 56, z: 96 + 188
this.hangarDoorLeft.flags.draw = true;
this.hangarDoorRight = this.scene.geometryController.loadModel("hangar door right", "modHangarDoor", { x: 64, y: 468 - 1, z: 128 }); // x: 48, y: 56, z: 96 + 188
this.hangarDoorRight.flags.draw = true;
this.hangarDoorRight.rotateAroundAxis([0, -1, 0], Math.PI);
this.hangarMain = this.scene.geometryController.loadModel("hangar main", "modHangarMain", { x: -176, y: 568, z: 128 - 48 });
this.hangarMain.flags.draw = true;
//jump down id you start from hangar
if (this.startFromHangar === true) {
this.state = this.states.startFromHangar;
//INFO hacky way of preventing lookaround instead of pitching
this.scene.player.setMode(PLAYERMODE.INTERACT);
this.playerShip.splineId = 1;
//let splg = this.trackBuilder.spline[this.playerShip.splineId];
this.playerShip.gondula.jumpToPosition({ x: 0, y: 0 + 468 - 128 - 96, z: 64 });
this.playerShip.shipAnchor.jumpToPosition({ x: this.playerShip.gondula.pos.x, y: this.playerShip.gondula.pos.y + 96, z: this.playerShip.gondula.pos.z }, true);
this.playerShip.ship.jumpToPosition({ x: this.playerShip.gondula.pos.x, y: this.playerShip.gondula.pos.y + 96, z: this.playerShip.gondula.pos.z }, true);
//this.scene.editor.toggleEditor();
} else {
//this.playerShip.camera = this.playerShip.cameras.thirdPersonFollow;
this.playerShip.camera = OPTIONS.config.preferredCam;
//INFO this code is also used in listenToSwitchCamera
if (this.playerShip.camera === 1 || this.playerShip.camera === 2) {
if (this.playerShip.ship.flags.draw === true) {
this.playerShip.ship.flags.draw = false;
this.playerShip.ship.flags.drawn = false;
for (let q of this.playerShip.ship.quadData) {
q.clearQuads();
}
//this.playerShip.ship.depthMod = -100000;
}
} else {
if (this.playerShip.ship.flags.draw === false) {
this.playerShip.ship.flags.draw = true;
}
//this.playerShip.ship.depthMod = 48;
}
}
this.state = this.states.startFromHangar;
if (this.params.startFromHangar === false) {
this.state = this.states.countDown;
}
//todo: this lags a lot when loading in (because of the tracklength actually) but its not elegant wwhen coming from the hangar and not moving smoothly
this.loadTrack(9999);
setTimeout(() => {
this.loadTrack(this.params.track);
if (this.params.startFromHangar === false) {
this.state = this.states.countDown;
}
}, 10);
/*
setInterval(() => {
console.log(this.countdown.step + " : " + this.countdown.current);
}, 1000);
*/
//prepare music tracks in custom race
this.musicTracks = [this.scene.soundManager.musicAcidLoop00, this.scene.soundManager.musicAcidLoop01];
this.musicTrack = this.musicTracks[Math.floor(Math.random() * this.musicTracks.length)];
}
update(_delta) {
this.ui.txtDelta.setText(String(this.scene.dt.toFixed(2)));
this.resetSituation();
if (this.musicTrack.howlGroup.playing() === false) {
this.scene.soundManager.playSound(this.musicTrack);
}
//general update
this.playerShip.update();
//setup pos arr
if (this.finishedRace === false) {
this.grid = [];
this.grid.push(this.playerShip);
}
for (let ai of this.aiShips) {
ai.update();
if (this.finishedRace === false) {
this.grid.push(ai);
}
}
if (this.finishedRace === false) {
let positionPrevious = this.playerShip.position;
this.grid.sort((a, b) => {
return b.raceProgress - a.raceProgress;
});
for (let [i, shipManager] of this.grid.entries()) {
shipManager.position = i;
}
if (this.playerShip.position !== -1) {
let positionChange = this.playerShip.position - positionPrevious;
if (positionChange < 0 && this.playerShip.position < this.grid.length - 1) {//gained position(s)
this.situation.actions.gainPosition.who = this.grid[this.playerShip.position + 1].ship.data.name;
//console.log(this.situation.actions.gainPosition.who)
this.situation.actions.gainPosition.priority += 1;
}
if (positionChange > 0 && this.playerShip.position > 0) {//lost positions
this.situation.actions.loosePosition.who = this.grid[this.playerShip.position - 1].ship.data.name;
//console.log(this.situation.actions.loosePosition.who)
this.situation.actions.loosePosition.priority += 1;
}
}
}
//update ui for laptimes and position
this.ui.txtLapTime.setText("LAP: " + timeToLapTime(this.playerShip.elapsedTime));
if (this.playerShip.position > -1) {
let affix = "th";
if (this.playerShip.position === 0) {
affix = "ST";
}
if (this.playerShip.position === 1) {
affix = "ND";
}
if (this.playerShip.position === 2) {
affix = "RD";
}
this.ui.txtLapPos.setText("POS: " + String(this.playerShip.position + 1) + affix);
}
if (this.scene.player === this.scene.playerGame) {
if (this.hangarDoorRight.pos.x > 0) {
this.hangarDoorLeft.jumpToPosition({ x: Math.min(0, this.hangarDoorLeft.pos.x + 0.1 * this.scene.dt), y: this.hangarDoorLeft.pos.y, z: this.hangarDoorLeft.pos.z }, true);
this.hangarDoorRight.jumpToPosition(
{ x: Math.max(0, this.hangarDoorRight.pos.x - 0.1 * this.scene.dt), y: this.hangarDoorRight.pos.y, z: this.hangarDoorRight.pos.z },
true,
);
} else {
this.scene.geometryController.destroyModelById(this.hangarMain.id);
this.scene.geometryController.destroyModelById(this.hangarDoorLeft.id);
this.scene.geometryController.destroyModelById(this.hangarDoorRight.id);
}
switch (this.state) {
case this.states.startFromHangar:
if (this.trackBuilder.spline.length > 0) {
this.updateFromHangar();
}
break;
case this.states.countDown:
//INFO: this prevents it crashing when loading in "directly" to a race
if (this.trackBuilder.spline.length > 0) {
this.updateCountDown();
}
break;
case this.states.race:
if (this.trackBuilder.spline.length > 0) {
this.updateRacing();
//update tutorial if in tutorial obviously
if (this.raceMode === this.raceModes.tutorial) {
this.updateTutorial();
} else if (this.raceMode === this.raceModes.canyon) {
if (this.finishedRace === false) {
this.updateCanyon();
}
}
//if (this.scene.quartJustChanged === true) {
this.assessSituation();
//}
}
break;
default:
break;
}
} else {
//todo: use the ui.hide function when exiting craft
/*
this.ui.txtBestLapTime.alpha = 0;
this.ui.txtLastLapTime.alpha = 0;
this.ui.txtLapTime.alpha = 0;
this.ui.txtDelta.alpha = 0;
this.ui.txtHelper.alpha = 0;
*/
}
//this.scene.player.jumpToPosition({ x: this.ref.pos.x + (this.ref.transform.forward.x * -128), y: this.ref.pos.y + (this.ref.transform.forward.y * -128), z: this.ref.pos.z + (this.ref.transform.forward.z * -128) }, true);
this.ui.update(_delta);
if (INPUTS.btnStickLeft.justPressed === true && this.scene.player.panel === null && this.scene.paused === false) {
this.ui.toggleVisibility();
}
if (this.scene.keys.escape.isDown || INPUTS.btnStart.justPressed) {
if (this.scene.player.panel === null) {
//todo: fix auto clicking on back when it was oopen once and the mosue is still on the back button position (locked)
/*if(this.scene.input.mouse.locked === true){
this.scene.hand.setMouseLock(false);
}*/
this.ui.hide();
this.scene.player.hideUI();
this.scene.player.setMode(PLAYERMODE.INTERACT);
this.scene.player.panel = new PanelEscapeMenu(this.scene, this, this.state);
this.scene.paused = true;
this.state = this.states.pause;
//todo stop engine sound
this.scene.soundManager.stopSound(this.scene.soundManager.engineSound);
//this.scene.soundManager.stopSound(this.scene.soundManager.engineRotorSound);
this.scene.soundManager.stopSound(this.scene.soundManager.scrapeSound);
this.scene.soundManager.stopSound(this.scene.soundManager.heatWarningSound);
}
}
//hide ui for editor and photomode usage
if (this.state !== this.states.pause) {
if (this.scene.editor.enabled === true) {
this.ui.hide();
} else {
if (this.finishedRace === false && this.raceMode !== this.raceModes.tutorial) {
this.ui.show();
}
}
}
}
updateFromHangar() {
this.listenToSwitchCamera();
this.toggleDrawByViewDistance();
this.playerShip.updateFromHangar();
for (let ai of this.aiShips) {
ai.updateFromHangar();
}
//console.log(this.playerShip.gondula.pos.y)
if (this.playerShip.gondula.pos.y <= 0) {
this.playerShip.camera = this.playerShip.cameras.thirdPersonFollow;
//this.state = this.states.countDown;
}
this.moveCamera();
}
updateCountDown() {
//count down
if (this.countdown.step < 5) {
if (this.countdown.step < 4) {
this.ui.txtCountdown.alpha -= this.ui.txtCountdown.alpha * (0.05 * this.scene.dt);
} else {
//fade GO out slower then the numbers
this.ui.txtCountdown.alpha -= this.ui.txtCountdown.alpha * (0.01 * this.scene.dt);
}
//stall countdown if coming from hangar, to ensure that the player arrives in the tunnel
if (this.playerShip.gondula.pos.y < 100) {
//todo: make this a eud distance from ref spline
this.countdown.current = Date.now() - this.countdown.start;
} else {
this.countdown.start = Date.now();
}
//check if a second has passed and show countdown
if (this.countdown.current - this.countdown.step * 1000 >= 1000) {
this.ui.txtCountdown.setText(this.countdown.texts[this.countdown.step]);
this.ui.txtCountdown.alpha = 1;
this.countdown.step += 1;
this.scene.soundManager.playSpecificSound(this.scene.soundManager.raceAnnouncer, this.countdown.step);
if (this.countdown.step === 4) {
this.state = this.states.race;
if (this.raceMode === this.raceModes.tutorial && this.tutorialStep === -1) {
this.cycleTutorial();
}
}
}
}
this.listenToSwitchCamera();
this.toggleDrawByViewDistance();
if (this.startFromHangar === true) {
this.playerShip.updateFromHangar();
for (let ai of this.aiShips) {
ai.updateFromHangar();
}
let d = eud.distance(
[this.playerShip.gondula.pos.x, this.playerShip.gondula.pos.y, this.playerShip.gondula.pos.z],
[this.trackBuilder.spline[this.playerShip.splineId].x, this.trackBuilder.spline[this.playerShip.splineId].y, this.trackBuilder.spline[this.playerShip.splineId].z],
);
if (d <= this.scene.dt) {
this.playerShip.camera = this.playerShip.cameras.thirdPersonFollow;
//this.state = this.states.countDown;
}
} else {
if (this.trackBuilder.spline.length > 0) {
this.playerShip.updateRacing();
for (let ai of this.aiShips) {
ai.updateRacing();
}
}
}
//move camera
this.moveCamera();
}
updateRacing() {
//finish count down
if (this.countdown.step < 5) {
this.ui.txtCountdown.alpha -= this.ui.txtCountdown.alpha * (0.01 * this.scene.dt);
this.countdown.current = Date.now() - this.countdown.start;
if (this.countdown.current - this.countdown.step * 1000 >= 1000) {
this.ui.txtCountdown.setText(this.countdown.texts[this.countdown.step]);
this.ui.txtCountdown.alpha = 1;
this.countdown.step += 1;
if (this.countdown.step === 5) {
this.ui.txtCountdown.alpha = 0;
}
}
}
//listen to input
this.listenToSwitchCamera();
//how many rings should be rendered! viewdist
this.toggleDrawByViewDistance();
for (let o of this.trackBuilder.obstacles) {
if (o.flags.update === true) {
o.update();
}
}
this.playerShip.updateRacing();
for (let ai of this.aiShips) {
ai.updateRacing();
}
//update player ui
if (this.playerShip.temp >= 999) {
this.ui.txtLower.setText("!!!OVERHEAT WARNING!!!");
} else {
this.ui.txtLower.setText("");
}
//this.ui.txtHelper.setText("SPD: " + String(this.playerShip.speed.toFixed(2)) + " BON: " + String(this.playerShip.speedBonus.toFixed(2)) + " TMP: " + String(Math.floor(this.playerShip.temp)) + " ID: " + String(zeroPad(this.playerShip.splineId, 6)));
this.ui.txtHelper.setText(
"BON: " + String(this.playerShip.speedBonus.toFixed(2)) + " TMP: " + String(Math.floor(this.playerShip.temp)) + " ID: " + String(zeroPad(this.playerShip.splineId, 6)),
);
this.ui.txtTachoSpd.setText(String(Math.floor(this.playerShip.speed * 10)) + " SPD");
//this.ui.tachoHighlight.x = (this.scene.game.config.width * -0.5) + 16 - 133 + Math.min(133, (133 * (this.playerShip.speed / this.playerShip.speedMax)));
this.ui.tachoHighlight.x =
this.scene.game.config.width * -0.5 + 16 - 133 + Math.min(133, 133 * ((this.playerShip.speed + 0) / (this.playerShip.speedMax + this.playerShip.speedBonus)));
//ref: (this.speed + this.speedBonus) / (this.speedMax + this.speedBonus)
this.ui.tachoOverspeed.x =
this.scene.game.config.width * -0.5 +
16 -
133 +
Math.min(133, 133 * ((this.playerShip.speed + this.playerShip.speedBonus) / (this.playerShip.speedMax + this.playerShip.speedBonus)));
let curveDelta = this.playerShip.last.curveAmt - this.playerShip.curveAmt;
//this.ui.txtLower.setText("AMT: " + String(this.playerShip.curveAmt.toFixed(4)) + " DEL: " + String(curveDelta.toFixed(4)) + " GOD: " + String(curveDelta < 0));
//sign for rad (roll of ship / gondula relative to track ring transform)
let sig = 1;
if (this.playerShip.angleToTrackMod >= 0) {
sig = 1;
} else {
sig = -1;
}
//get player rotation on track - a pi/8 offset for the 16 segments of the collision circles
let rad = (this.playerShip.angleToTrack * -1 + 1) * sig * (Math.PI * 0.5) - 0.39269;
//console.log(rad)
this.ui.txtLower.setText("AMT: " + String(this.playerShip.curveAmt.toFixed(4)) + " DEL: " + String(curveDelta.toFixed(4)) + " RAD: " + String(rad));
//push all obstacles in range to lit array with their 0-15 range of roll
if (this.scene.quartJustChanged === true) {
let lit = [];
for (let o of this.trackBuilder.obstacles) {
if (o.data.id < this.playerShip.splineId + 99 && o.data.id >= this.playerShip.splineId && o.data.ignoreRadar === false) {
let dist = Math.floor(((o.data.id - this.playerShip.splineId) / 100) * 6);
if (dist > 5) {
dist -= 6;
}
if (dist < 0) {
dist += 6;
}
//todo: add rolls inbetween obstacle and player to the calculation
let diff = rad - (o.data.roll === undefined ? o.data.angle : o.data.angle + o.data.roll);
let toSeg = Math.floor((diff + Math.PI) / (Math.PI / 8));
//add offset and additional blockers
if (toSeg > 15) {
toSeg -= 16;
}
if (toSeg < 0) {
toSeg += 16;
}
//console.log(toSeg)
lit.push({ obstacle: o, diff: diff, seg: toSeg, dist: dist });
}
}
for (let q of this.ui.dangerCirclets) {
for (let s of q) {
s.alpha = 0;
}
}
for (let l of lit) {
//console.log(l.seg, l.dist)
if (l.seg >= 0 && l.seg < 16 && l.dist >= 0 && l.dist <= 5) {
let tos = [];
tos.push(l.seg);
tos[0] += l.obstacle.data.collisionRadar.offset;
for (let a of l.obstacle.data.collisionRadar.additionals) {
tos.push(tos[0] + a);
}
for (let t of tos) {
let tCorrected = t;
if (tCorrected > 15) {
tCorrected -= 16;
}
if (tCorrected < 0) {
tCorrected += 16;
}
this.ui.dangerCirclets[tCorrected][l.dist].alpha = 1;
}
//let s = this.ui.dangerCirclets[l.seg][l.dist];
//s.alpha = 1;
}
}
}
this.ui.pitchLimit.y = this.ui.pitchPosY + 64 - 32 * this.playerShip.curveAmt - 32 * this.playerShip.pitch.current;
//ship sound
if (this.state !== this.states.pause) {
if (this.scene.soundManager.engineSound.howlGroup.playing() === false) {
this.scene.soundManager.playSound(this.scene.soundManager.engineSound);
//this.scene.soundManager.playSound(this.scene.soundManager.engineRotorSound);
} else {
this.scene.soundManager.engineSound.howlGroup.rate(0.1 + 0.9 * Math.min(1, this.playerShip.speed / this.playerShip.speedMax));
//this.scene.soundManager.engineRotorSound.howlGroup.rate(0.1 + (0.9 * Math.min(1, (this.playerShip.speed + this.playerShip.speedBonus) / (this.playerShip.speedMax + this.playerShip.speedBonus))));
}
if (this.playerShip.scraping === true && this.finishedRace === false) {
if (this.scene.soundManager.scrapeSound.howlGroup.playing() === false) {
this.scene.soundManager.playSound(this.scene.soundManager.scrapeSound);
}
} else {
this.scene.soundManager.stopSound(this.scene.soundManager.scrapeSound);
}
if (this.playerShip.temp >= 900 && this.finishedRace === false) {
if (this.scene.soundManager.heatWarningSound.howlGroup.playing() === false) {
this.scene.soundManager.playSound(this.scene.soundManager.heatWarningSound);
}
} else {
this.scene.soundManager.stopSound(this.scene.soundManager.heatWarningSound);
}
}
//move camera
this.moveCamera();
/* INFO keep an eye out for this if its buggy when not used also the function nthat hides it
if(this.finishedRace === false){
this.ui.txtBestLapTime.alpha = 1;
this.ui.txtLastLapTime.alpha = 1;
this.ui.txtLapTime.alpha = 1;
this.ui.txtDelta.alpha = 1;
this.ui.txtHelper.alpha = 1;
}
*/
}
updateCanyon() {
//console.log(this.playerShip.splineId - this.aiShips[0].splineId); - points = behind
if (this.raceModeData.playerIsHunter === true) {
let playerBehind = true;
let amt = this.playerShip.splineId - this.aiShips[0].splineId;
if (this.aiShips[0].crossedFinish === false) {
amt -= this.trackBuilder.spline.length;
}
if (this.playerShip.lapTimes.length === this.aiShips[0].lapTimes.length) {
if (amt > 0) {
playerBehind = false;
}
amt += 40;
if (this.playerShip.slipstreaming === true) {
amt *= 1.5;
}
if (playerBehind === false) {
amt *= 2;
}
} else {
amt = 0;
}
if (amt < 0) {
amt = 0;
}
amt = Math.floor(amt);
this.raceModeData.points.overall += amt;
this.raceModeData.points.rounds[0] += amt;
this.ui.txtBestLapTime.setText("");
this.ui.txtLastLapTime.setText(`DLT: ${amt}`);
this.ui.txtLapTime.setText(`PTS: ${this.raceModeData.points.overall}`);
} else {
let playerBehind = false;
let amt = this.aiShips[0].splineId - this.playerShip.splineId;
if (this.playerShip.crossedFinish === false) {
amt -= this.trackBuilder.spline.length;
}
if (this.playerShip.lapTimes.length === this.aiShips[0].lapTimes.length) {
if (amt > 0) {
playerBehind = true;
}
amt += 40;
if (this.aiShips[0].slipstreaming === true) {
amt *= 1.5;
}
if (playerBehind === true) {
amt *= 2;
}
} else {
amt = 0;
}
if (amt < 0) {
amt = 0;
}
amt = Math.floor(amt);
this.raceModeData.points.overall -= amt;
this.raceModeData.points.rounds[1] += amt;
this.ui.txtBestLapTime.setText("");
this.ui.txtLastLapTime.setText(`DLT: ${amt}`);
this.ui.txtLapTime.setText(`PTS: ${this.raceModeData.points.overall}`);
}
if (this.aiShips[0].splineId - this.playerShip.splineId > 44) {
this.aiShips[0].speedMax *= 0.9;
} else {
this.aiShips[0].speedMax = 16;
}
}
startNewCanyon() {
this.ui.txtBestLapTime.setText(`POT: ${this.raceModeData.points.overall}`);
if (this.playerShip.lapTimes.length >= this.maxLaps) {
this.finishedRace = true;
}
if (this.finishedRace === false) {
//pause and show mid result, result screen will soft restart the race for second round
this.state = this.states.pause;
this.scene.soundManager.stopSound(this.scene.soundManager.engineSound);
//this.scene.soundManager.stopSound(this.scene.soundManager.engineRotorSound);
this.scene.soundManager.stopSound(this.scene.soundManager.scrapeSound);
this.scene.soundManager.stopSound(this.scene.soundManager.heatWarningSound);
this.ui.hide();
//show mid results
this.scene.player.hideUI();
this.scene.player.setMode(PLAYERMODE.INTERACT);
this.scene.player.panel = new PanelEndOfCanyon(this.scene, this, this.state);
}
if (this.finishedRace === true && this.scene.player.panel === null) {
//end for real now
this.playerShip.autopilot = true;
this.ui.hide();
//show end results
this.scene.player.hideUI();
this.scene.player.setMode(PLAYERMODE.INTERACT);
this.scene.player.panel = new PanelEndOfCanyon(this.scene, this, this.state);
//if is demo?
if (this.raceModeData.points.overall > 0) {
//you won the race
flagManager.setFlag("wonDemoRace", "true");
}
flagManager.setFlag("demoProgress", "3");
}
}
startNewLap() {
this.ui.txtLastLapTime.setText("LST: " + timeToLapTime(this.playerShip.elapsedTime));
let newRecord = false;
let finalLap = false;
if (this.playerShip.lapTimes.length + 1 === this.maxLaps) {
finalLap = true;
}
if (this.playerShip.lapTimes.length >= this.maxLaps) {
this.finishedRace = true;
}
let r = this.playerShip.lapTimes[this.playerShip.fastestLap];
let lapNo = this.playerShip.fastestLap + 1;
this.ui.txtBestLapTime.setText("BST: " + timeToLapTime(r.time) + " [L" + lapNo + "]");
if (this.playerShip.fastestLap !== this.playerShip.last.fastestLap) {
newRecord = true;
}
//make the correct sound (new record, finallap, knockedout etc)
if (newRecord === true && finalLap === false) {
this.scene.soundManager.playSpecificSound(this.scene.soundManager.raceAnnouncer, 0);
}
if (finalLap === true) {
this.scene.soundManager.playSpecificSound(this.scene.soundManager.raceAnnouncer, 5);
}
//
if (this.finishedRace === true && this.scene.player.panel === null) {
this.playerShip.autopilot = true;
this.ui.hide();
//show end results
this.scene.player.hideUI();
this.scene.player.setMode(PLAYERMODE.INTERACT);
this.scene.player.panel = new PanelEndOfRace(this.scene, this, this.state);
if (this.raceMode === this.raceModes.canyon) {
if (this.playerShip.position === 0) {
//you won the race
flagManager.setFlag("wonDemoRace", "true");
}
flagManager.setFlag("demoProgress", "1");
}
//this.scene.paused = true;
//this.state = this.states.pause;
//this.scene.soundManager.stopSound(this.scene.soundManager.engineSound);
}
}
listenToSwitchCamera() {
if (INPUTS.btnY.justReleased) {
if (this.scene.editor.enabled === false) {
this.playerShip.camera += 1;
if (this.playerShip.camera >= 4) {
this.playerShip.camera = 0;
}
//hide ship if in pov cams
if (this.playerShip.camera === 1 || this.playerShip.camera === 2) {
if (this.playerShip.ship.flags.draw === true) {
this.playerShip.ship.flags.draw = false;
this.playerShip.ship.flags.drawn = false;
for (let q of this.playerShip.ship.quadData) {
q.clearQuads();
}
//this.playerShip.ship.depthMod = -100000;
}
} else {
if (this.playerShip.ship.flags.draw === false) {
this.playerShip.ship.flags.draw = true;
}
//this.playerShip.ship.depthMod = 48;
}
OPTIONS.config.preferredCam = this.playerShip.camera;
}
}
}
toggleDrawByViewDistance() {
let frontLimit = Math.min(60, this.trackBuilder.spline.length); //60
let rearLimit = Math.min(62, this.trackBuilder.spline.length - 1); //59
for (let i = 0; i < frontLimit; i++) {
let fsid = this.playerShip.splineId + i;
if (fsid >= this.trackBuilder.spline.length) {
fsid -= this.trackBuilder.spline.length;
}
if (this.trackBuilder.spline[fsid].model !== null) {
this.trackBuilder.spline[fsid].model.flags.draw = true;
}
if (this.trackBuilder.spline[this.playerShip.splineId].model !== null) {
this.trackBuilder.spline[this.playerShip.splineId].model.flags.draw = true;
}
}
for (let i = 0; i < rearLimit; i++) {
let rsid = this.playerShip.splineId - i;
if (rsid < 0) {
rsid += this.trackBuilder.spline.length;
}
if (i < rearLimit - 3) {
if (this.trackBuilder.spline[rsid].model !== null) {
this.trackBuilder.spline[rsid].model.flags.draw = true;
}
} else {
if (this.trackBuilder.spline[rsid].model !== null) {
this.trackBuilder.spline[rsid].model.flags.draw = false;
}
}
}
}
moveCamera() {
let gamepad = null;
gamepad = navigator.getGamepads()[Math.max(0, gamepadsConnected - 1)];
if (gamepad === undefined) {
gamepad = null;
}
//this.scene.cam.zoom = 800 - (this.playerShip.speed * 10);
if (this.playerShip.speed + 1 >= this.playerShip.speedMax) {
//todo: find better way to show speed when super fast and especially when slipstreaming and dodging closely
//this.scene.cam.fov = 2.5 + Math.min(2, 2 - (this.playerShip.speedMax - this.playerShip.speed));
if (this.scene.cam.fov < 3) {
this.scene.cam.fov += 0.1 * this.scene.dt;
this.scene.cam.fov = Math.min(3, this.scene.cam.fov);
} else {
this.scene.cam.fov -= 0.01 * this.scene.dt;
this.scene.cam.fov = Math.max(2.5, this.scene.cam.fov);
}
} else {
if (this.scene.cam.fov > 2.5) {
this.scene.cam.fov -= 0.1 * this.scene.dt;
this.scene.cam.fov = Math.max(2.5, this.scene.cam.fov);
}
}
switch (this.playerShip.camera) {
case this.playerShip.cameras.thirdPersonFollow:
this.scene.player.jumpToPosition(
{
x:
this.playerShip.shipAnchor.pos.x +
this.playerShip.shipAnchor.transform.forward.x * -160 +
this.playerShip.shipAnchor.transform.up.x * (48 - (this.playerShip.flightRadiusUpperLimit - this.playerShip.flightRadius)),
y:
this.playerShip.shipAnchor.pos.y +
this.playerShip.shipAnchor.transform.forward.y * -160 +
this.playerShip.shipAnchor.transform.up.y * (48 - (this.playerShip.flightRadiusUpperLimit - this.playerShip.flightRadius)),
z:
this.playerShip.shipAnchor.pos.z +
this.playerShip.shipAnchor.transform.forward.z * -160 +
this.playerShip.shipAnchor.transform.up.z * (48 - (this.playerShip.flightRadiusUpperLimit - this.playerShip.flightRadius)),
},
true,
);
/*this.scene.player.jumpToPosition({
x: this.playerShip.gondula.pos.x + (this.playerShip.shipAnchor.transform.forward.x * -128) + (this.playerShip.shipAnchor.transform.up.x * -64),
y: this.playerShip.gondula.pos.y + (this.playerShip.shipAnchor.transform.forward.y * -128) + (this.playerShip.shipAnchor.transform.up.y * -64),
z: this.playerShip.gondula.pos.z + (this.playerShip.shipAnchor.transform.forward.z * -128) + (this.playerShip.shipAnchor.transform.up.z * -64)
}, true);*/
break;
case this.playerShip.cameras.firstPersonCockpit: //todo: pin the camera better to cockpit and do smth about the ship model
this.scene.player.jumpToPosition(
{
x: this.playerShip.ship.pos.x + this.playerShip.ship.transform.forward.x * 16 + this.playerShip.ship.transform.up.x * 32,
y: this.playerShip.ship.pos.y + this.playerShip.ship.transform.forward.y * 16 + this.playerShip.ship.transform.up.y * 32,
z: this.playerShip.ship.pos.z + this.playerShip.ship.transform.forward.z * 16 + this.playerShip.ship.transform.up.z * 32,
},
true,
);
break;
case this.playerShip.cameras.firstPersonBumper:
this.scene.player.jumpToPosition(
{
x:
this.playerShip.gondula.pos.x +
this.playerShip.gondula.transform.forward.x * 72 +
this.playerShip.ship.transform.up.x * 8 +
this.playerShip.gondula.transform.up.x * -this.playerShip.flightRadius,
y:
this.playerShip.gondula.pos.y +
this.playerShip.gondula.transform.forward.y * 72 +
this.playerShip.ship.transform.up.y * 8 +
this.playerShip.gondula.transform.up.y * -this.playerShip.flightRadius,
z:
this.playerShip.gondula.pos.z +
this.playerShip.gondula.transform.forward.z * 72 +
this.playerShip.ship.transform.up.z * 8 +
this.playerShip.gondula.transform.up.z * -this.playerShip.flightRadius,
},
true,
);
break;
case this.playerShip.cameras.thirdPersonOrbit:
this.scene.player.jumpToPosition(
{
x: this.playerShip.shipAnchor.pos.x + this.scene.cam.transform.forward.x * -128 + this.playerShip.shipAnchor.transform.up.x * 32,
y: this.playerShip.shipAnchor.pos.y + this.scene.cam.transform.forward.y * -128 + this.playerShip.shipAnchor.transform.up.y * 32,
z: this.playerShip.shipAnchor.pos.z + this.scene.cam.transform.forward.z * -128 + this.playerShip.shipAnchor.transform.up.z * 32,
},
true,
);
break;
default:
this.scene.player.jumpToPosition(
{
x: this.playerShip.shipAnchor.pos.x + this.playerShip.shipAnchor.transform.forward.x * -128 + this.playerShip.shipAnchor.transform.up.x * 32,
y: this.playerShip.shipAnchor.pos.y + this.playerShip.shipAnchor.transform.forward.y * -128 + this.playerShip.shipAnchor.transform.up.y * 32,
z: this.playerShip.shipAnchor.pos.z + this.playerShip.shipAnchor.transform.forward.z * -128 + this.playerShip.shipAnchor.transform.up.z * 32,
},
true,
);
break;
}
/*
//old direct sometimes jittery but working method
this.scene.cam.transform.up.x = this.playerShip.shipAnchor.transform.up.x;
this.scene.cam.transform.up.y = this.playerShip.shipAnchor.transform.up.y;
this.scene.cam.transform.up.z = this.playerShip.shipAnchor.transform.up.z;
this.scene.cam.transform.right.x = this.playerShip.shipAnchor.transform.right.x;
this.scene.cam.transform.right.y = this.playerShip.shipAnchor.transform.right.y;
this.scene.cam.transform.right.z = this.playerShip.shipAnchor.transform.right.z;
this.scene.cam.transform.forward.x = this.playerShip.shipAnchor.transform.forward.x;
this.scene.cam.transform.forward.y = this.playerShip.shipAnchor.transform.forward.y;
this.scene.cam.transform.forward.z = this.playerShip.shipAnchor.transform.forward.z;
//this.camOffset.dir.yaw += ((this.scene.player.dir.yaw - this.camOffset.dir.yaw) * 0.1);
//this.camOffset.dir.pitch += ((this.scene.player.dir.pitch - this.camOffset.dir.pitch) * 0.1);
this.camOffset.dir.yaw = this.scene.player.dir.yaw;
this.camOffset.dir.pitch = this.scene.player.dir.pitch;
this.scene.cam.rotateAroundAxis(this.playerShip.gondula.transform.toVectorArray(this.scene.cam.transform.up), this.camOffset.dir.yaw * -1);
this.scene.cam.rotateAroundAxis(this.playerShip.gondula.transform.toVectorArray(this.scene.cam.transform.right), this.camOffset.dir.pitch);
*/
//INFO IMPORTANT move camRig vorher und slerp cam to rig
//this coulod maybe work!! //todo: keep an eye on that - using .ship. instead of anchor seems cool but a bit too exagerated
this.camRig.transform.up.x = this.playerShip.ship.transform.up.x;
this.camRig.transform.up.y = this.playerShip.ship.transform.up.y;
this.camRig.transform.up.z = this.playerShip.ship.transform.up.z;
this.camRig.transform.right.x = this.playerShip.shipAnchor.transform.right.x;
this.camRig.transform.right.y = this.playerShip.shipAnchor.transform.right.y;
this.camRig.transform.right.z = this.playerShip.shipAnchor.transform.right.z;
this.camRig.transform.forward.x = this.playerShip.ship.transform.forward.x;
this.camRig.transform.forward.y = this.playerShip.ship.transform.forward.y;
this.camRig.transform.forward.z = this.playerShip.ship.transform.forward.z;
if (this.playerShip.camera === this.playerShip.cameras.thirdPersonOrbit) {
//todo: this should be only working when in specific camera and ui be hidden or reacting
//scene.hand.vel is never not 0 if mouse is locked (always when gamepad is connected)
/*if(this.scene.hand.vel.x !== 0){
this.camOffset.dir.yaw += ((this.scene.hand.vel.x) * this.scene.player.dir.spd.yaw);
}
if(this.scene.hand.vel.y !== 0){
this.camOffset.dir.pitch += ((this.scene.hand.vel.y) * this.scene.player.dir.spd.pitch);
}*/
this.camOffset.virtualMouse.delta.x = 0;
this.camOffset.virtualMouse.delta.y = 0;
//let velocity = {delta: {x: 0, y: 0}, lastPos: {x: 0, y: 0}}
if (this.scene.hand.useControllerMouse === false) {
this.camOffset.virtualMouse.pos.x = this.scene.hand.pos.x;
this.camOffset.virtualMouse.pos.y = this.scene.hand.pos.y;
this.camOffset.virtualMouse.delta.x = this.scene.hand.pos.x - this.camOffset.virtualMouse.lastPos.x;
this.camOffset.virtualMouse.delta.y = this.scene.hand.pos.y - this.camOffset.virtualMouse.lastPos.y;
this.camOffset.virtualMouse.lastPos.x = this.scene.hand.pos.x; //gets ignotred because of reset so velocity needs to be somethign in the cam rig or smth like that
this.camOffset.virtualMouse.lastPos.y = this.scene.hand.pos.y;
} else {
//gamepad
//console.log(INPUTS.stickRight.vertical)
if (gamepad !== null) {
//todo INFO + if options enabled gamepad control
//let sra = Math.abs(INPUTS.stickRight.vertical);
//let sla = Math.abs(INPUTS.stickLeft.vertical);
//this.keyInput.pitch = (sra > sla ? (INPUTS.stickRight.vertical * -1) : (INPUTS.stickLeft.vertical * -1));
this.camOffset.virtualMouse.delta.x = INPUTS.stickRight.horizontal * -1;
this.camOffset.virtualMouse.delta.y = INPUTS.stickRight.vertical * -1;
}
}
if (this.camOffset.virtualMouse.delta.x !== 0) {
this.camOffset.dir.yaw += this.camOffset.virtualMouse.delta.x * this.scene.player.dir.spd.yaw;
}
if (this.camOffset.virtualMouse.delta.y !== 0) {
this.camOffset.dir.pitch += this.camOffset.virtualMouse.delta.y * this.scene.player.dir.spd.pitch;
}
} else {
this.camOffset.dir.yaw = 0;
this.camOffset.dir.pitch = 0;
}
//try to look ahead of corner
if (this.playerShip.camera === this.playerShip.cameras.firstPersonBumper) {
this.camOffset.target.dir.pitch = this.playerShip.curveAmt * -0.5;
} else if (this.playerShip.camera === this.playerShip.cameras.thirdPersonFollow) {
this.camOffset.target.dir.pitch = this.playerShip.curveAmt * -0.25;
} else {
this.camOffset.target.dir.pitch = 0;
}
this.camOffset.dir.pitch += (this.camOffset.target.dir.pitch - this.camOffset.dir.pitch) * 0.1;
this.camOffset.dir.pitch = Math.max(-HALFPI, Math.min(HALFPI, this.camOffset.dir.pitch));
this.camRig.rotateAroundAxis(this.playerShip.gondula.transform.toVectorArray(this.camRig.transform.up), this.camOffset.dir.yaw);
this.camRig.rotateAroundAxis(this.playerShip.gondula.transform.toVectorArray(this.camRig.transform.right), this.camOffset.dir.pitch);
let rotFactor = 0.5;
let targetRot = [0, 0, 0, 0];
targetRot = gl_quat.rotationTo(
targetRot,
this.scene.cam.transform.toVectorArray(this.scene.cam.transform.right),
this.scene.cam.transform.toVectorArray(this.camRig.transform.right), //playerShip.ship for rotation with ship
);
let rot = [0, 0, 0, 0];
rot = gl_quat.slerp(rot, this.scene.cam.transform.rotationQuat, targetRot, rotFactor);
this.scene.cam.rotateByQuaternion(rot);
targetRot = [0, 0, 0, 0];
targetRot = gl_quat.rotationTo(
targetRot,
this.scene.cam.transform.toVectorArray(this.scene.cam.transform.up),
this.scene.cam.transform.toVectorArray(this.camRig.transform.up), //playerShip.ship for rotation with ship
);
rot = [0, 0, 0, 0];
rot = gl_quat.slerp(rot, this.scene.cam.transform.rotationQuat, targetRot, rotFactor);
this.scene.cam.rotateByQuaternion(rot);
targetRot = [0, 0, 0, 0];
targetRot = gl_quat.rotationTo(
targetRot,
this.scene.cam.transform.toVectorArray(this.scene.cam.transform.forward),
this.scene.cam.transform.toVectorArray(this.camRig.transform.forward), //playerShip.ship for rotation with ship
);
rot = [0, 0, 0, 0];
rot = gl_quat.slerp(rot, this.scene.cam.transform.rotationQuat, targetRot, rotFactor);
this.scene.cam.rotateByQuaternion(rot);
/*//todo: find a way to also move the camera after all the smooth to track rotation. Currently that does not work as intended...
//new method that tries to blend cam rig rotation with always rotating to ship anchor w/o overrides that tween back and forth to infinity and beyond
let rotFactor = 0.05;
let targetRot = [0, 0, 0, 0];
//let out = [0, 0, 0];
//out = gl_vec3.cross(out, this.scene.cam.transform.toVectorArray(this.scene.cam.transform.forward), this.scene.cam.transform.toVectorArray(this.camRig.transform.up)),
targetRot = gl_quat.rotationTo(targetRot,
this.scene.cam.transform.toVectorArray( this.scene.cam.transform.right),
//out,
this.scene.cam.transform.toVectorArray( this.playerShip.shipAnchor.transform.right) //playerShip.ship for rotation with ship
)
let rot = [0, 0, 0, 0];
rot = gl_quat.slerp(rot, this.scene.cam.transform.rotationQuat, targetRot, rotFactor);
this.scene.cam.rotateByQuaternion(rot);
targetRot = [0, 0, 0, 0];
//out = [0, 0, 0];
//out = gl_vec3.cross(out, this.scene.cam.transform.toVectorArray(this.scene.cam.transform.right), this.scene.cam.transform.toVectorArray(this.camRig.transform.forward)),
targetRot = gl_quat.rotationTo(targetRot,
this.scene.cam.transform.toVectorArray( this.scene.cam.transform.up),
//out,
this.scene.cam.transform.toVectorArray( this.playerShip.shipAnchor.transform.up) //playerShip.ship for rotation with ship
)
rot = [0, 0, 0, 0];
rot = gl_quat.slerp(rot, this.scene.cam.transform.rotationQuat, targetRot, rotFactor);
this.scene.cam.rotateByQuaternion(rot);
targetRot = [0, 0, 0, 0];
//out = [0, 0, 0];
//out = gl_vec3.cross(out, this.scene.cam.transform.toVectorArray(this.scene.cam.transform.up), this.scene.cam.transform.toVectorArray(this.camRig.transform.right)),
targetRot = gl_quat.rotationTo(targetRot,
this.scene.cam.transform.toVectorArray( this.scene.cam.transform.forward),
//out,
this.scene.cam.transform.toVectorArray( this.playerShip.shipAnchor.transform.forward) //playerShip.ship for rotation with ship
)
rot = [0, 0, 0, 0];
rot = gl_quat.slerp(rot, this.scene.cam.transform.rotationQuat, targetRot, rotFactor);
this.scene.cam.rotateByQuaternion(rot);
//this.camRig.transform.up.x = this.scene.cam.transform.up.x;
//this.camRig.transform.up.y = this.scene.cam.transform.up.y;
//this.camRig.transform.up.z = this.scene.cam.transform.up.z;
//this.camRig.transform.right.x = this.scene.cam.transform.right.x;
//this.camRig.transform.right.y = this.scene.cam.transform.right.y;
//this.camRig.transform.right.z = this.scene.cam.transform.right.z;
//this.camRig.transform.forward.x = this.scene.cam.transform.forward.x;
//this.camRig.transform.forward.y = this.scene.cam.transform.forward.y;
//this.camRig.transform.forward.z = this.scene.cam.transform.forward.z;
//this.camOffset.dir.yaw = this.scene.player.dir.yaw;
//this.camOffset.dir.pitch = this.scene.player.dir.pitch;
//this.camRig.rotateAroundAxis(this.playerShip.gondula.transform.toVectorArray(this.camRig.transform.up), this.camOffset.dir.yaw);
//this.camRig.rotateAroundAxis(this.playerShip.gondula.transform.toVectorArray(this.camRig.transform.right), this.camOffset.dir.pitch);
//this.scene.cam.rotateAroundAxis(this.playerShip.gondula.transform.toVectorArray(this.scene.cam.transform.up), this.camOffset.dir.yaw * -1);
//this.scene.cam.rotateAroundAxis(this.playerShip.gondula.transform.toVectorArray(this.scene.cam.transform.right), this.camOffset.dir.pitch);
*/
}
assessSituation() {
//let who = "";
let action = null;
if (this.situation.actions.win.who !== "") {
action = this.situation.actions.win;
let character = this.aiShips.filter(el => el.name === action.who)[0].character;
this.ui.addReaction("charSheetExpressions", character.reactions.cheer[Math.floor(Math.random() * character.reactions.cheer.length)], character);
} else if (this.situation.actions.loose.who !== "") {
action = this.situation.actions.loose;
let character = this.aiShips.filter(el => el.name === action.who)[0].character;
this.ui.addReaction("charSheetExpressions", character.reactions.angry[Math.floor(Math.random() * character.reactions.angry.length)], character);
} else if (this.situation.actions.hit.who !== "") {
action = this.situation.actions.hit;
let character = this.aiShips.filter(el => el.name === action.who)[0].character;
this.ui.addReaction("charSheetExpressions", character.reactions.hit[Math.floor(Math.random() * character.reactions.hit.length)], character);
} else if (this.situation.actions.gainPosition.who !== "") {
action = this.situation.actions.gainPosition;
let character = this.aiShips.filter(el => el.name === action.who)[0].character;
this.ui.addReaction("charSheetExpressions", character.reactions.angry[Math.floor(Math.random() * character.reactions.angry.length)], character);
} else if (this.situation.actions.loosePosition.who !== "") {
action = this.situation.actions.loosePosition;
let character = this.aiShips.filter(el => el.name === action.who)[0].character;
this.ui.addReaction("charSheetExpressions", character.reactions.haha[Math.floor(Math.random() * character.reactions.haha.length)], character);
} else if (this.situation.actions.slipstream.who !== "") {
action = this.situation.actions.slipstream;
let character = this.aiShips.filter(el => el.name === action.who)[0].character;
this.ui.addReaction("charSheetExpressions", character.reactions.thinking[Math.floor(Math.random() * character.reactions.thinking.length)], character);
} else if (this.situation.actions.slipstreamed.who !== "") {
action = this.situation.actions.slipstreamed;
let character = this.aiShips.filter(el => el.name === action.who)[0].character;
this.ui.addReaction("charSheetExpressions", character.reactions.taunt[Math.floor(Math.random() * character.reactions.taunt.length)], character);
} else if (this.situation.actions.mishap.who !== "") {
action = this.situation.actions.mishap;
let character = this.aiShips.filter(el => el.name === action.who)[0].character;
this.ui.addReaction("charSheetExpressions", character.reactions.haha[Math.floor(Math.random() * character.reactions.haha.length)], character);
}
/*
who = this.situation.actions.hit.who;
let actions = [
this.situation.actions.hit,
this.situation.actions.gainPosition,
this.situation.actions.loosePosition,
this.situation.actions.mishap,
this.situation.actions.slipstream,
this.situation.actions.slipstreamed,
this.situation.actions.win,
this.situation.actions.loose
]
actions = actions.sort((a, b) => { a.priority - b.priority });
console.log(actions[0].priority);
if (actions[0].priority > 0) {
who = actions[0].who;
if (who !== "") {
if (actions[0] == this.situation.actions.hit) {
console.log("hit someone")
let character = this.aiShips.filter(el => el.name === who)[0].character;
this.ui.addReaction("charSheetExpressions", character.reactions.hit[Math.floor(Math.random() * character.reactions.hit.length)]);
} else if (actions[0] == this.situation.actions.gainPosition) {
console.log("gained a position")
} else {
console.log(actions[0]);
}
}
}
*/
}
resetSituation() {
this.situation = {
actions: {
hit: { //player bumping into ai
who: "",
priority: 0,
time: 0
}, slipstream: { //player slipstreaming ai
who: "",
priority: 0,
time: 0
}, slipstreamed: { //ai slipstreaming behind player
who: "",
priority: 0,
time: 0
}, gainPosition: { //player overtakes ai
who: "",
priority: 0,
time: 0
}, loosePosition: { //ai overtakes player
who: "",
priority: 0,
time: 0
}, mishap: { //player crashes near ai
who: "",
priority: 0,
time: 0
}, win: { //ai wins
who: "",
priority: 0,
time: 0
}, loose: { //player wins / rival looses
who: "",
priority: 0,
time: 0
}
}
}
}
loadTrack(_track = 0, _pos = 7) {
this.graLoading.alpha = 1;
this.txtLoading.alpha = 1;
setTimeout(() => {
this.trackBuilder.loadTrack(_track);
if (this.raceMode === this.raceModes.canyon) {
if (this.raceModeData.playerIsHunter === true) {
this.playerShip.restartOnFromSplineId(1);
this.aiShips[0].restartOnFromSplineId((0 + 1) * 5 + 1, Math.PI * 0.25 * (0 + 1));
} else {
this.playerShip.restartOnFromSplineId((0 + 1) * 5 + 1, Math.PI * 0.25 * (0 + 1));
this.aiShips[0].restartOnFromSplineId(1);
}
} else {
//normal racing
this.playerShip.restartOnFromSplineId(1);
for (let [i, ai] of this.aiShips.entries()) {
ai.restartOnFromSplineId((i + 1) * 5 + 1, Math.PI * 0.25 * (i + 1));
}
}
/*
this.playerShip.splineId = 0;
let splg = this.trackBuilder.spline[this.playerShip.splineId];
this.playerShip.gondula.jumpToPosition({x: splg.x, y: splg.y, z: splg.z});
let targetRot = [0, 0, 0, 0];
targetRot = gl_quat.rotationTo(targetRot,
this.playerShip.gondula.transform.toVectorArray( this.playerShip.gondula.transform.forward),
[0, 0, 1]
)
this.playerShip.gondula.rotateByQuaternion(targetRot);
targetRot = [0, 0, 0, 0];
targetRot = gl_quat.rotationTo(targetRot,
this.playerShip.gondula.transform.toVectorArray( this.playerShip.gondula.transform.right),
[1, 0, 0]
)
this.playerShip.gondula.rotateByQuaternion(targetRot);
targetRot = [0, 0, 0, 0];
targetRot = gl_quat.rotationTo(targetRot,
this.playerShip.gondula.transform.toVectorArray( this.playerShip.gondula.transform.up),
[0, -1, 0]
)
this.playerShip.gondula.rotateByQuaternion(targetRot);
this.playerShip.speed = 0;
*/
this.graLoading.alpha = 0;
this.txtLoading.alpha = 0;
this.countdown.start = Date.now();
this.countdown.current = Date.now() - this.countdown.start;
this.countdown.step = 0;
this.countdown.go = false;
this.state = this.states.countDown;
}, 10);
}
updateTutorial() {
switch (this.tutorialStep) {
case 0:
this.playerShip.speed = 0;
this.playerShip.input.roll = 0;
this.aiShips[0].speed = 0;
this.aiShips[0].input.roll = 0;
break;
case 1: //just rolling and checking pitch HEAT ZONE
this.playerShip.speed = 0;
//this.playerShip.input.roll = 0;
this.playerShip.rollSpeedMax = 1;
this.playerShip.rollSpeedMin = -1;
this.aiShips[0].speed = 0;
this.aiShips[0].input.roll = 0;
this.aiShips[0].rollSpeedMax = 1;
this.aiShips[0].rollSpeedMin = -1;
//console.log(this.playerShip.distToPerfectPitch)
if (this.playerShip.distToPerfectPitch > 0 && this.playerShip.distToPerfectPitch < 32) {
this.tutorialHoldVar += this.scene.dt;
if (this.tutorialHoldVar >= this.tutorialHoldVarMax) {
this.cycleTutorial();
}
} else {
if (this.tutorialHoldVar > 0) {
this.tutorialHoldVar -= this.scene.dt;
}
}
//console.log(this.tutorialHoldVar)
break;
case 2:
this.playerShip.speed = 0;
this.playerShip.input.roll = 0;
this.aiShips[0].speed = 0;
this.aiShips[0].input.roll = 0;
break;
case 3:
if (this.aiShips[0].splineId - this.playerShip.splineId > 44) {
this.aiShips[0].speed = 0;
}
break;
case 4:
this.playerShip.speed = 0;
this.playerShip.input.roll = 0;
this.aiShips[0].speed = 0;
this.aiShips[0].input.roll = 0;
break;
case 5: //sllipstreaming
if (this.aiShips[0].splineId - this.playerShip.splineId > 44) {
this.aiShips[0].speed = 0;
}
if (this.aiShips[0].splineId - this.playerShip.splineId < -20) {
if (this.tutorialHoldVar > 10) {
//this.tutorialHoldVar += 4 * this.scene.dt;
//if (this.tutorialHoldVar >= this.tutorialHoldVarMax * 0.25) {
this.cycleTutorial();
//}
}
}
if (this.playerShip.slipstreaming === true) {
this.aiShips[0].speedMax = 14;
this.tutorialHoldVar += 1 * this.scene.dt;
if (this.tutorialHoldVar >= this.tutorialHoldVarMax) {
this.cycleTutorial();
}
} else {
this.aiShips[0].speedMax = 12;
if (this.tutorialHoldVar > 0) {
this.tutorialHoldVar -= 0.1 * this.scene.dt;
}
}
break;
case 6:
break;
case 7://free time trial
//catch up and wait mechanic
if (this.aiShips[0].splineId - this.playerShip.splineId > 44) {
this.aiShips[0].speedMax = 5;
} else if (this.aiShips[0].splineId - this.playerShip.splineId < -44) {
this.aiShips[0].speedMax = 18;
} else {
this.aiShips[0].speedMax = 16;
}
this.playerShip.temp *= 0.5;
if (this.playerShip.lapTimes.length >= 1) {
this.cycleTutorial();
}
break;
case 8:
break;
/*
case 99: //speedcheck
if (Math.floor(this.playerShip.speed * 10) >= 200) {
this.tutorialHoldVar += this.scene.dt;
if (this.playerShip.scraping === false && this.tutorialHoldVar > 300) {
this.cycleTutorial();
}
}
break;
case 5:
//this.playerShip.speed = 0;
//this.playerShip.input.roll = 0;
//this.aiShips[0].speed = 0;
//this.aiShips[0].input.roll = 0;
//this.aiShips[0].input.pitch = 0;
if (this.aiShips[0].splineId - this.playerShip.splineId > 44) {
this.aiShips[0].speed = 0;
}
if (this.playerShip.slipstreaming === true) {
this.tutorialHoldVar += 1 * this.scene.dt;
if (this.tutorialHoldVar >= this.tutorialHoldVarMax) {
this.cycleTutorial();
}
} else {
if (this.tutorialHoldVar > 0) {
this.tutorialHoldVar -= 0.1 * this.scene.dt;
}
}
break;
*/
/*
case 993://how to slipstream
if (this.aiShips[0].splineId - this.playerShip.splineId > 44) {
this.aiShips[0].speed = 0;
}
if (this.playerShip.position === 0 && this.aiShips[0].splineId - this.playerShip.splineId < -10 && this.playerShip.slipsteamTime > 30) {
this.cycleTutorial();
}
break;
case 5:
if (this.aiShips[0].splineId - this.playerShip.splineId > 44) {
this.aiShips[0].speed = 0;
}
if (this.playerShip.position === 1 && this.aiShips[0].splineId - this.playerShip.splineId > 20) {
this.cycleTutorial();
}
break;
*/
default:
console.log(`could not find step ${this.tutorialStep} in tutorial update`);
this.cycleTutorial();
break;
}
}
cycleTutorial() {
/*
0. look at your pitch
1. speedcheck to 200 for X seconds / keep in speedzone for X seconds
3. playground 1 / gather coins at shown ideal line (small but curve map with at least a hump not only a circle - 180 right, up down, 180 right straight)
(X. jump to start again) or at least let Roki show up in front of you
---maybe go back to hangar?
4. follow in slipstream for X seconds in same map that you played around
5. overtake (2 times?) throug slipstream
*/
this.tutorialStep += 1;
console.log(`tutorial step ${this.tutorialStep}`);
switch (this.tutorialStep) {
case 0: //how to accelerate
this.ui.txtProgress.setText("");
//start conversation
this.ui.hide();
this.scene.player.hideUI();
this.scene.player.setMode(PLAYERMODE.INTERACT);
this.scene.player.panel = new PanelRaceTutorial(this.scene, this, this.state, this.tutorialStep);
//this.scene.paused = true;
//this.state = this.states.pause;
this.playerShip.speedMax = 1;
this.playerShip.speed = 0;
this.playerShip.rollSpeedMax = 0.1;
this.playerShip.rollSpeedMin = -0.1;
this.playerShip.autopilot = true;
this.aiShips[0].speedMax = 1;
this.playerShip.speed = 0;
this.aiShips[0].rollSpeedMax = 0.1;
this.aiShips[0].rollSpeedMin = -0.1;
break;
case 1:
this.ui.txtProgress.setText("keep pitch indicator in the white HEAT ZONE");
this.playerShip.autopilot = false;
break;
case 2: //start collectathon 1 //how to slipstream
this.ui.txtProgress.setText("");
//start conversation
this.ui.hide();
this.scene.player.hideUI();
this.scene.player.setMode(PLAYERMODE.INTERACT);
this.scene.player.panel = new PanelRaceTutorial(this.scene, this, this.state, this.tutorialStep);
this.playerShip.speedMax = 1;
this.playerShip.rollSpeedMax = 0.1;
this.playerShip.rollSpeedMin = -0.1;
this.playerShip.autopilot = true;
this.aiShips[0].speedMax = 1;
this.aiShips[0].rollSpeedMax = 0.1;
this.aiShips[0].rollSpeedMin = -0.1;
this.trackBuilder.createObstacles(this.trackBuilder.currentTrackId, [
/*{sp: this.trackBuilder.spline[50], angle: Math.PI * 0.25, radius: 0, model: "modObstSteam", name: "steam 0"},
{sp: this.trackBuilder.spline[50], angle: Math.PI * 0.75, radius: 0, model: "modObstSteam", name: "steam 1"},
{sp: this.trackBuilder.spline[50], angle: Math.PI * -0.25, radius: 0, model: "modObstSteam", name: "steam 2"},
{sp: this.trackBuilder.spline[50], angle: Math.PI * -0.75, radius: 0, model: "modObstSteam", name: "steam 3"}*/
{ sp: this.trackBuilder.spline[0], angle: Math.PI * 0.5, radius: 100, model: "modRacingPickup", name: "token 0" },
{ sp: this.trackBuilder.spline[20], angle: Math.PI * 0.5, radius: 100, model: "modRacingPickup", name: "token 1" },
{ sp: this.trackBuilder.spline[40], angle: Math.PI * 0.5, radius: 100, model: "modRacingPickup", name: "token 2" },
{ sp: this.trackBuilder.spline[60], angle: Math.PI * 0.5, radius: 100, model: "modRacingPickup", name: "token 3" },
{ sp: this.trackBuilder.spline[80], angle: Math.PI * 0.5, radius: 100, model: "modRacingPickup", name: "token 4" },
{ sp: this.trackBuilder.spline[100], angle: Math.PI * 0.25, radius: 100, model: "modRacingPickup", name: "token 5" },
{ sp: this.trackBuilder.spline[120], angle: Math.PI * 0, radius: 100, model: "modRacingPickup", name: "token 6" },
{ sp: this.trackBuilder.spline[140], angle: Math.PI * -0.25, radius: 100, model: "modRacingPickup", name: "token 7" },
{ sp: this.trackBuilder.spline[160], angle: Math.PI * -0.5, radius: 100, model: "modRacingPickup", name: "token 10" },
{ sp: this.trackBuilder.spline[180], angle: Math.PI * -0.5, radius: 100, model: "modRacingPickup", name: "token 11" },
{ sp: this.trackBuilder.spline[200], angle: Math.PI * -0.5, radius: 100, model: "modRacingPickup", name: "token 12" },
{ sp: this.trackBuilder.spline[220], angle: Math.PI * -0.5, radius: 100, model: "modRacingPickup", name: "token 13" },
{ sp: this.trackBuilder.spline[240], angle: Math.PI * -0.5, radius: 100, model: "modRacingPickup", name: "token 14" },
{ sp: this.trackBuilder.spline[260], angle: Math.PI * -0.25, radius: 100, model: "modRacingPickup", name: "token 15" },
{ sp: this.trackBuilder.spline[280], angle: Math.PI * 0, radius: 100, model: "modRacingPickup", name: "token 16" },
{ sp: this.trackBuilder.spline[300], angle: Math.PI * 0.25, radius: 100, model: "modRacingPickup", name: "token 17" },
]);
this.tutorialHoldVar = 0;
this.tutorialHoldVarMax = 16;
for (let o of this.trackBuilder.obstacles) {
o.data.ignoreRadar = false;
o.trigger.isTrigger = true;
o.updateTrigger = () => {
if (o.trigger.other.name === "Player") {
this.scene.geometryController.destroyModelById(o.id);
this.scene.soundManager.playSound(this.scene.soundManager.computerStartSound);
this.tutorialHoldVar += 1;
this.ui.txtProgress.setText(`${this.tutorialHoldVar} of 16 token`);
o.data.ignoreRadar = true;
console.log(this.tutorialHoldVar);
if (this.tutorialHoldVar >= this.tutorialHoldVarMax) {
this.cycleTutorial();
}
}
};
}
break;
/*case 99:
this.playerShip.speedMax = 16;
this.playerShip.rollSpeedMax = 1;
this.playerShip.rollSpeedMin = -1;
this.playerShip.autopilot = false;
this.ui.show();
this.aiShips[0].speedMax = 16;
this.aiShips[0].rollSpeedMax = 1;
this.aiShips[0].rollSpeedMin = -1;
break;*/
case 3:
console.log("tutorial cycled to 3! free to race and collect the coins");
this.ui.txtProgress.setText(`${this.tutorialHoldVar} of 16 token`);
this.playerShip.speedMax = 12;
this.playerShip.rollSpeedMax = 1;
this.playerShip.rollSpeedMin = -1;
this.playerShip.autopilot = false;
this.ui.show();
this.aiShips[0].speedMax = 11;
this.aiShips[0].rollSpeedMax = 1;
this.aiShips[0].rollSpeedMin = -1;
break;
case 4:
this.ui.txtProgress.setText("");
console.log("tutorial for slipstream / overtake");
//start conversation
this.ui.hide();
this.scene.player.hideUI();
this.scene.player.setMode(PLAYERMODE.INTERACT);
this.scene.player.panel = new PanelRaceTutorial(this.scene, this, this.state, this.tutorialStep);
this.playerShip.speedMax = 1;
this.playerShip.rollSpeedMax = 0.1;
this.playerShip.rollSpeedMin = -0.1;
this.playerShip.autopilot = true;
this.aiShips[0].speedMax = 1;
this.aiShips[0].rollSpeedMax = 0.1;
this.aiShips[0].rollSpeedMin = -0.1;
break;
case 5:
console.log("go slipstreaming");
this.ui.txtProgress.setText("stay in Roki's SLIPSTREAM");
this.playerShip.speedMax = 14;
this.playerShip.rollSpeedMax = 1;
this.playerShip.rollSpeedMin = -1;
this.playerShip.autopilot = false;
this.playerShip.crashPoints = 0;
this.ui.show();
this.aiShips[0].speedMax = 13;
this.aiShips[0].rollSpeedMax = 1;
this.aiShips[0].rollSpeedMin = -1;
this.aiShips[0].pitch.max = 0.75;
this.aiShips[0].pitch.min = -0.75;
this.tutorialHoldVar = 0;
this.tutorialHoldVarMax = 1000;
this.startFromHangar = false;
this.params.startFromHangar = false;
this.loadTrack(9001);
//restart all ships
for (let ai of this.aiShips) {
ai.lapTimes = [];
ai.fastestLap = 0;
ai.last.fastestLap = 0;
}
this.playerShip.lapTimes = [];
this.playerShip.fastestLap = 0;
this.playerShip.last.fastestLap = 0;
this.playerShip.autopilot = false;
this.ui.show();
this.finishedRace = false;
this.maxLaps = 9999;
break;
case 6:
console.log("tutorial for end");
this.ui.txtProgress.setText("");
if (this.playerShip.crashPoints > 0) {
this.aiShips[0].ship.data.conversation.treePosition = 15;
}
if (this.aiShips[0].splineId - this.playerShip.splineId < -20) {
this.aiShips[0].ship.data.conversation.treePosition = 22;
if (this.playerShip.crashPoints > 0) {
this.aiShips[0].ship.data.conversation.treePosition = 21;
}
}
this.playerShip.crashPoints = 0;
//start conversation
this.ui.hide();
this.scene.player.hideUI();
this.scene.player.setMode(PLAYERMODE.INTERACT);
this.scene.player.panel = new PanelRaceTutorial(this.scene, this, this.state, this.tutorialStep);
this.playerShip.speedMax = 1;
this.playerShip.rollSpeedMax = 0.1;
this.playerShip.rollSpeedMin = -0.1;
this.playerShip.autopilot = true;
this.aiShips[0].speedMax = 1.5;
this.aiShips[0].rollSpeedMax = 0.1;
this.aiShips[0].rollSpeedMin = -0.1;
this.aiShips[0].pitch.max = 1;
this.aiShips[0].pitch.min = -1;
break;
case 7:
console.log("free time trial");
this.playerShip.speedMax = 16;
this.playerShip.rollSpeedMax = 1;
this.playerShip.rollSpeedMin = -1;
this.playerShip.autopilot = false;
this.playerShip.crashPoints = 0;
this.ui.show();
this.aiShips[0].speedMax = 16;
this.aiShips[0].rollSpeedMax = 1;
this.aiShips[0].rollSpeedMin = -1;
this.aiShips[0].pitch.max = 1;
this.aiShips[0].pitch.min = -1;
this.startFromHangar = false;
this.params.startFromHangar = false;
this.loadTrack(9002);
//restart all ships
for (let ai of this.aiShips) {
ai.lapTimes = [];
ai.fastestLap = 0;
ai.last.fastestLap = 0;
}
this.playerShip.lapTimes = [];
this.playerShip.fastestLap = 0;
this.playerShip.last.fastestLap = 0;
this.playerShip.autopilot = false;
this.ui.show();
this.finishedRace = false;
this.maxLaps = 99;
/*
console.log("tutorial end after slipstream");
//start conversation
this.ui.hide();
this.scene.player.hideUI();
this.scene.player.setMode(PLAYERMODE.INTERACT);
this.scene.player.panel = new PanelRaceTutorial(this.scene, this, this.state, this.tutorialStep);
this.playerShip.speedMax = 1;
this.playerShip.rollSpeedMax = 0.1;
this.playerShip.rollSpeedMin = -0.1;
this.playerShip.autopilot = true;
this.aiShips[0].speedMax = 1;
this.aiShips[0].rollSpeedMax = 0.1;
this.aiShips[0].rollSpeedMin = -0.1;
*/
break;
case 8:
//start conversation
this.ui.hide();
this.scene.player.hideUI();
this.scene.player.setMode(PLAYERMODE.INTERACT);
this.scene.player.panel = new PanelRaceTutorial(this.scene, this, this.state, this.tutorialStep);
this.playerShip.speedMax = 1;
this.playerShip.rollSpeedMax = 0.1;
this.playerShip.rollSpeedMin = -0.1;
this.playerShip.autopilot = true;
this.aiShips[0].speedMax = 1;
this.aiShips[0].rollSpeedMax = 0.1;
this.aiShips[0].rollSpeedMin = -0.1;
/*
this.playerShip.autopilot = true;
this.ui.hide();
//show end results
this.maxLaps = -1;
this.scene.player.hideUI();
this.scene.player.setMode(PLAYERMODE.INTERACT);
this.scene.player.panel = new PanelEndOfRace(this.scene, this, this.state);
if (this.raceMode === this.raceModes.tutorial) {
if (this.playerShip.position === 0) {
//you won the race
flagManager.setFlag("wonDemoRace", "true");
}
flagManager.setFlag("demoProgress", "1");
}
*/
break;
/*/
case 94://resolve slipstream
if (this.playerShip.crashPoints > 0) {
this.playerShip.crashPoints = 0;
this.aiShips[0].ship.data.conversation.treePosition = 8;
}
//start conversation
this.ui.hide();
this.scene.player.hideUI();
this.scene.player.setMode(PLAYERMODE.INTERACT);
this.scene.player.panel = new PanelRaceTutorial(this.scene, this, this.state, this.tutorialStep);
this.playerShip.speedMax = 1;
this.playerShip.rollSpeedMax = 0.1;
this.playerShip.rollSpeedMin = -0.1;
this.playerShip.autopilot = true;
this.aiShips[0].speedMax = 1;
this.aiShips[0].rollSpeedMax = 0.1;
this.aiShips[0].rollSpeedMin = -0.1;
break;
case 5://fall back to second
this.playerShip.speedMax = 10;
this.playerShip.rollSpeedMax = 1;
this.playerShip.rollSpeedMin = -1;
this.playerShip.autopilot = false;
this.ui.show();
this.aiShips[0].speedMax = 16;
this.aiShips[0].rollSpeedMax = 1;
this.aiShips[0].rollSpeedMin = -1;
break;
case 6://show extra controls and object avoid
if (this.playerShip.crashPoints > 0) {
this.playerShip.crashPoints = 0;
this.aiShips[0].ship.data.conversation.treePosition = 8;
}
//start conversation
this.ui.hide();
this.scene.player.hideUI();
this.scene.player.setMode(PLAYERMODE.INTERACT);
this.scene.player.panel = new PanelRaceTutorial(this.scene, this, this.state, this.tutorialStep);
this.playerShip.speedMax = 1;
this.playerShip.rollSpeedMax = 0.1;
this.playerShip.rollSpeedMin = -0.1;
this.playerShip.autopilot = true;
this.aiShips[0].speedMax = 1;
this.aiShips[0].rollSpeedMax = 0.1;
this.aiShips[0].rollSpeedMin = -0.1;
break;
case 7://fall back to second
this.playerShip.speedMax = 16;
this.playerShip.rollSpeedMax = 1;
this.playerShip.rollSpeedMin = -1;
this.playerShip.autopilot = false;
this.ui.show();
this.aiShips[0].speedMax = 18;
this.aiShips[0].rollSpeedMax = 1;
this.aiShips[0].rollSpeedMin = -1;
this.startFromHangar = false;
this.params.startFromHangar = false;
this.loadTrack(0);
//restart all ships
for (let ai of this.aiShips) {
ai.lapTimes = [];
ai.fastestLap = 0;
ai.last.fastestLap = 0;
}
this.playerShip.lapTimes = [];
this.playerShip.fastestLap = 0;
this.playerShip.last.fastestLap = 0;
this.playerShip.autopilot = false;
this.ui.show();
this.finishedRace = false;
this.maxLaps = 3;
break;*/
default:
console.log(`could not find tutorial step ${this.tutorialStep}`);
break;
}
}
createDefaultRing() {
//first Ring Test
let ring = this.scene.geometryController.loadModel("ring DEFAULT", "modDebugTile", { x: 0, y: 0, z: 0 });
ring.flags.draw = true;
let ringPts = [];
let r = 128;
let iter = 0;
for (let i = 0; i < Math.PI * 2; i += Math.PI / 8) {
let xx = Math.cos(i) * r;
let yy = Math.sin(i) * r;
ringPts.push({ x: xx, y: yy, z: 0 });
iter += 1;
}
//console.log(ringPts)
let texture = "sprDebugTexture";
for (let i = 0; i < ringPts.length - 1; i++) {
ring.addQuadFromData({
//this.scene, this.id, no, _q.type, pos, _q.points, _q.texture, _q.frame
type: "quad",
frame: texture,
texture: "atlasAll",
position: { x: 0, y: 0, z: 0 },
points: [
{
//hinten rechts
x: ringPts[i].x,
y: ringPts[i].y,
z: -this.trackBuilder.ringDeepness,
},
{
//hinten links
x: ringPts[i + 1].x,
y: ringPts[i + 1].y,
z: -this.trackBuilder.ringDeepness,
},
{
//vorne links
x: ringPts[i + 1].x,
y: ringPts[i + 1].y,
z: 0,
},
{
//vorne rechts
x: ringPts[i].x,
y: ringPts[i].y,
z: 0,
},
],
});
}
ring.addQuadFromData({
type: "quad",
frame: texture,
texture: "atlasAll",
position: { x: 0, y: 0, z: 0 },
points: [
{
x: ringPts[ringPts.length - 1].x,
y: ringPts[ringPts.length - 1].y,
z: -this.trackBuilder.ringDeepness,
},
{
x: ringPts[0].x,
y: ringPts[0].y,
z: -this.trackBuilder.ringDeepness,
},
{
x: ringPts[0].x,
y: ringPts[0].y,
z: 0,
},
{
x: ringPts[ringPts.length - 1].x,
y: ringPts[ringPts.length - 1].y,
z: 0,
},
],
});
//outer Ring
ringPts = [];
iter = 0;
r = 256;
for (let i = 0; i < Math.PI * 2; i += Math.PI / 8) {
let xx = Math.cos(i) * r;
let yy = Math.sin(i) * r;
ringPts.push({ x: xx, y: yy, z: 0 });
iter += 1;
}
texture = "sprDebugTexture";
for (let i = 0; i < ringPts.length - 1; i++) {
ring.addQuadFromData({
//this.scene, this.id, no, _q.type, pos, _q.points, _q.texture, _q.frame
type: "quad",
frame: texture,
texture: "atlasAll",
position: { x: 0, y: 0, z: 0 },
points: [
{
//hinten rechts
x: ringPts[i].x,
y: ringPts[i].y,
z: -this.trackBuilder.ringDeepness,
},
{
//hinten links
x: ringPts[i + 1].x,
y: ringPts[i + 1].y,
z: -this.trackBuilder.ringDeepness,
},
{
//vorne links
x: ringPts[i + 1].x,
y: ringPts[i + 1].y,
z: 0,
},
{
//vorne rechts
x: ringPts[i].x,
y: ringPts[i].y,
z: 0,
},
],
});
}
ring.addQuadFromData({
type: "quad",
frame: texture,
texture: "atlasAll",
position: { x: 0, y: 0, z: 0 },
points: [
{
x: ringPts[ringPts.length - 1].x,
y: ringPts[ringPts.length - 1].y,
z: -this.trackBuilder.ringDeepness,
},
{
x: ringPts[0].x,
y: ringPts[0].y,
z: -this.trackBuilder.ringDeepness,
},
{
x: ringPts[0].x,
y: ringPts[0].y,
z: 0,
},
{
x: ringPts[ringPts.length - 1].x,
y: ringPts[ringPts.length - 1].y,
z: 0,
},
],
});
/*
ring.addQuadFromData({
type: "collisionQuad",
position: { x: 0, y: 0, z: 0 },
points: [
{//hinten rechts
x: 128,
y: 128,
z: -this.trackBuilder.ringDeepness
},{//hinten links
x: -128,
y: 128,
z: -this.trackBuilder.ringDeepness
},{//vorne links
x: -128,
y: 128,
z: 0
},{//vorne rechts
x: 128,
y: 128,
z: 0
}
]
});
*/
//ring.deleteQuad(ring.quadData[0])
return ring;
}
destroy() {
this.ui.destroy();
this.trackBuilder.clearTrack();
this.playerShip.destroy();
for (let ai of this.aiShips) {
ai.destroy();
}
}
}