2021-04-10 14:08:20 +02:00
|
|
|
using System;
|
|
|
|
|
using System.Collections.Generic;
|
|
|
|
|
using System.Text;
|
|
|
|
|
using Microsoft.Xna.Framework;
|
|
|
|
|
using Microsoft.Xna.Framework.Input;
|
|
|
|
|
using SynthySound;
|
|
|
|
|
using System.Linq;
|
|
|
|
|
using EvilSatellites.Objects;
|
2021-04-11 02:01:24 +02:00
|
|
|
using DavyKager;
|
2021-04-11 14:12:55 +02:00
|
|
|
using EvilSatellites.Quadtree;
|
2021-04-10 14:08:20 +02:00
|
|
|
|
|
|
|
|
namespace EvilSatellites.Screens
|
|
|
|
|
{
|
|
|
|
|
public class GameScreen : IScreen
|
|
|
|
|
{
|
|
|
|
|
public ScreenManager Manager { get; set; }
|
|
|
|
|
public ScreenState State { get; set; }
|
2021-04-11 17:09:57 +02:00
|
|
|
private InputManager Input = new InputManager();
|
2021-04-10 14:08:20 +02:00
|
|
|
public List<IGameObject> Objects = new List<IGameObject>();
|
2021-04-11 18:42:22 +02:00
|
|
|
public List<IGameObject> Removable = new List<IGameObject>();
|
|
|
|
|
public List<IGameObject> Addable = new List<IGameObject>();
|
2021-04-24 02:47:17 +02:00
|
|
|
private Quadtree<IGameObject> objtree = new Quadtree<IGameObject>(new Vector3(50000, 50000, 50000), 10, 20);
|
2021-04-10 14:08:20 +02:00
|
|
|
private float Theta = 0;
|
2021-04-11 02:01:24 +02:00
|
|
|
private Player _player;
|
2021-04-11 17:09:57 +02:00
|
|
|
private Radar ObjectRadar;
|
2021-04-19 19:49:13 +02:00
|
|
|
private SatelliteSpawner Spawner;
|
2021-04-23 20:28:06 +02:00
|
|
|
private bool GameOver = false;
|
2021-04-10 14:08:20 +02:00
|
|
|
public void Activate()
|
|
|
|
|
{
|
|
|
|
|
State = ScreenState.Active;
|
|
|
|
|
Player player = new Player(this);
|
|
|
|
|
Objects.Add(player);
|
2021-04-11 02:01:24 +02:00
|
|
|
_player = player;
|
2021-04-11 17:09:57 +02:00
|
|
|
ObjectRadar = new Radar(_player, this);
|
2021-04-19 19:49:13 +02:00
|
|
|
Spawner = new SatelliteSpawner(this);
|
|
|
|
|
Spawner.Spawn();
|
2021-04-23 20:28:06 +02:00
|
|
|
GameStats.Reset();
|
|
|
|
|
Manager.Music.Play("game1");
|
2021-04-24 18:47:51 +02:00
|
|
|
Manager.Computer.Play("GameStart");
|
2021-04-10 14:08:20 +02:00
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public void Deactivate()
|
|
|
|
|
{
|
|
|
|
|
State = ScreenState.Hidden;
|
|
|
|
|
return;
|
|
|
|
|
}
|
2021-04-11 02:01:24 +02:00
|
|
|
|
2021-04-10 14:08:20 +02:00
|
|
|
public void Update(GameTime gameTime)
|
|
|
|
|
{
|
2021-04-23 20:28:06 +02:00
|
|
|
if (GameOver == true)
|
|
|
|
|
{
|
|
|
|
|
foreach (var obj in Objects)
|
|
|
|
|
{
|
|
|
|
|
obj.Destroy();
|
|
|
|
|
}
|
|
|
|
|
ObjectRadar.Destroy();
|
|
|
|
|
Spawner.Destroy();
|
|
|
|
|
// TODO: figure out why cleanup doesn't work
|
2021-04-24 18:47:51 +02:00
|
|
|
Manager.Sound.Cleanup();
|
2021-04-23 20:28:06 +02:00
|
|
|
HandleGameOver(gameTime);
|
|
|
|
|
|
|
|
|
|
}
|
2021-04-11 18:42:22 +02:00
|
|
|
foreach (var obj in Removable)
|
|
|
|
|
{
|
|
|
|
|
Objects.Remove(obj);
|
|
|
|
|
}
|
|
|
|
|
if (Addable.Count > 0)
|
|
|
|
|
{
|
|
|
|
|
foreach (var obj in Addable)
|
|
|
|
|
{
|
|
|
|
|
Objects.Add(obj);
|
|
|
|
|
}
|
|
|
|
|
Addable.Clear();
|
|
|
|
|
}
|
|
|
|
|
Removable.Clear();
|
2021-04-11 14:12:55 +02:00
|
|
|
objtree.Clear();
|
2021-04-11 18:42:22 +02:00
|
|
|
foreach (var obj in Objects)
|
2021-04-10 14:08:20 +02:00
|
|
|
{
|
|
|
|
|
obj.Update(gameTime);
|
2021-04-11 18:42:22 +02:00
|
|
|
objtree.Add(obj);
|
2021-04-10 14:08:20 +02:00
|
|
|
if (obj.Type == ObjectType.Player)
|
|
|
|
|
{
|
2021-04-19 15:41:37 +02:00
|
|
|
Manager.Sound.ListenerPosition = new System.Numerics.Vector3(obj.Position.X+obj.Dimensions.X/2, obj.Position.Y+obj.Dimensions.Y/2, obj.Position.Z+obj.Dimensions.Z/2);
|
2021-04-10 14:08:20 +02:00
|
|
|
Manager.Sound.ListenerOrientationForward = System.Numerics.Vector3.Normalize(new System.Numerics.Vector3(obj.Rotation.Forward.X, obj.Rotation.Forward.Y, obj.Rotation.Forward.Z));
|
|
|
|
|
Manager.Sound.ListenerOrientationUpwards = System.Numerics.Vector3.Normalize(new System.Numerics.Vector3(obj.Rotation.Up.X, obj.Rotation.Up.Y, obj.Rotation.Up.Z));
|
|
|
|
|
}
|
2021-04-11 18:42:22 +02:00
|
|
|
if (obj.ShouldDestroy)
|
|
|
|
|
{
|
|
|
|
|
Removable.Add(obj);
|
|
|
|
|
}
|
2021-04-10 14:08:20 +02:00
|
|
|
}
|
2021-04-11 17:09:57 +02:00
|
|
|
UpdateRadar();
|
2021-04-11 14:12:55 +02:00
|
|
|
CheckCollisions();
|
2021-04-24 14:34:15 +02:00
|
|
|
Spawner.Update(gameTime);
|
2021-04-10 14:08:20 +02:00
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
2021-04-11 17:09:57 +02:00
|
|
|
private void UpdateRadar()
|
|
|
|
|
{
|
2021-04-11 18:42:22 +02:00
|
|
|
var candidates = objtree.Find(_player.Position, new Vector3(1000, 1000, 1000));
|
2021-04-19 19:49:13 +02:00
|
|
|
ObjectRadar.Update(Objects);
|
2021-04-11 17:09:57 +02:00
|
|
|
}
|
|
|
|
|
|
2021-04-10 14:08:20 +02:00
|
|
|
public void HandleInput(GameTime gameTime, KeyboardState inputs)
|
|
|
|
|
{
|
2021-04-11 17:09:57 +02:00
|
|
|
Input.Update();
|
2021-04-11 14:12:55 +02:00
|
|
|
Vector3 move = new Vector3(0, 0, 0);
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsPressed(Keys.W) || Input.IsPressed(Buttons.LeftThumbstickUp))
|
2021-04-11 02:01:24 +02:00
|
|
|
{
|
2021-04-11 20:43:29 +02:00
|
|
|
move.Z = -_player.Acceleration.Z;
|
2021-04-11 14:12:55 +02:00
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsPressed(Keys.S) || Input.IsPressed(Buttons.LeftThumbstickDown))
|
2021-04-11 14:12:55 +02:00
|
|
|
{
|
2021-04-11 20:43:29 +02:00
|
|
|
move.Z = _player.Acceleration.Z;
|
2021-04-11 14:12:55 +02:00
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsPressed(Keys.A) || Input.IsPressed(Buttons.LeftThumbstickLeft))
|
2021-04-11 14:12:55 +02:00
|
|
|
{
|
2021-04-11 20:43:29 +02:00
|
|
|
move.X = -_player.Acceleration.X;
|
2021-04-11 14:12:55 +02:00
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsPressed(Keys.D) || Input.IsPressed(Buttons.LeftThumbstickRight))
|
2021-04-11 14:12:55 +02:00
|
|
|
{
|
2021-04-11 20:43:29 +02:00
|
|
|
move.X = _player.Acceleration.X;
|
2021-04-11 02:01:24 +02:00
|
|
|
}
|
2021-04-19 17:22:14 +02:00
|
|
|
if (Input.IsJustPressed(Keys.A) || Input.IsJustPressed(Keys.S) || Input.IsJustPressed(Keys.D) || Input.IsJustPressed(Keys.W))
|
|
|
|
|
{
|
|
|
|
|
_player.PlayTap();
|
|
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustPressed(Keys.Left) || Input.IsJustPressed(Buttons.RightThumbstickLeft))
|
2021-04-11 02:01:24 +02:00
|
|
|
{
|
2021-04-18 22:35:49 +02:00
|
|
|
_player.StartTurning(-1, gameTime);
|
2021-04-11 02:01:24 +02:00
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustPressed(Keys.Right) || Input.IsJustPressed(Buttons.RightThumbstickRight))
|
2021-04-11 02:01:24 +02:00
|
|
|
{
|
2021-04-18 22:35:49 +02:00
|
|
|
_player.StartTurning(1, gameTime);
|
2021-04-11 02:01:24 +02:00
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustReleased(Keys.Left) || Input.IsJustReleased(Keys.Right) || Input.IsJustReleased(Buttons.RightThumbstickLeft) || Input.IsJustReleased(Buttons.RightThumbstickRight))
|
2021-04-11 02:01:24 +02:00
|
|
|
{
|
2021-04-18 22:35:49 +02:00
|
|
|
_player.StopTurning();
|
2021-04-11 02:01:24 +02:00
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustPressed(Keys.Up) || Input.IsJustPressed(Buttons.RightThumbstickUp))
|
2021-04-11 02:01:24 +02:00
|
|
|
{
|
2021-04-18 22:35:49 +02:00
|
|
|
_player.StartElevating(-1, gameTime);
|
|
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustPressed(Keys.Down) || Input.IsJustPressed(Buttons.RightThumbstickDown))
|
2021-04-18 22:35:49 +02:00
|
|
|
{
|
|
|
|
|
_player.StartElevating(1, gameTime);
|
|
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustReleased(Keys.Up) || Input.IsJustReleased(Keys.Down) || Input.IsJustReleased(Buttons.RightThumbstickUp) || Input.IsJustReleased(Buttons.RightThumbstickDown))
|
2021-04-18 22:35:49 +02:00
|
|
|
{
|
|
|
|
|
_player.StopElevating();
|
2021-04-11 02:01:24 +02:00
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustPressed(Keys.V) || Input.IsJustPressed(Buttons.LeftTrigger))
|
2021-04-19 15:41:37 +02:00
|
|
|
{
|
|
|
|
|
_player.StartVacuuming(gameTime);
|
|
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustReleased(Keys.V) || Input.IsJustReleased(Buttons.LeftTrigger))
|
2021-04-19 15:41:37 +02:00
|
|
|
{
|
|
|
|
|
_player.StopVacuuming();
|
|
|
|
|
}
|
2021-04-11 14:12:55 +02:00
|
|
|
_player.Accelerate(move);
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustPressed(Keys.Space) || Input.IsJustPressed(Buttons.RightTrigger))
|
2021-04-11 17:09:57 +02:00
|
|
|
{
|
|
|
|
|
_player.CurrentWeapon.Shoot(gameTime);
|
2021-04-19 17:22:14 +02:00
|
|
|
_player.PlayTap();
|
2021-04-11 17:09:57 +02:00
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustReleased(Keys.Space) || Input.IsJustReleased(Buttons.RightTrigger))
|
2021-04-11 17:09:57 +02:00
|
|
|
{
|
|
|
|
|
_player.CurrentWeapon.Stop();
|
|
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustPressed(Keys.R) || Input.IsJustPressed(Buttons.LeftShoulder))
|
2021-04-11 17:09:57 +02:00
|
|
|
{
|
2021-04-19 17:22:14 +02:00
|
|
|
_player.PlayTap();
|
2021-04-11 17:09:57 +02:00
|
|
|
if (ObjectRadar.Active)
|
|
|
|
|
{
|
|
|
|
|
ObjectRadar.Stop();
|
|
|
|
|
} else
|
|
|
|
|
{
|
|
|
|
|
ObjectRadar.Start();
|
|
|
|
|
}
|
|
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustPressed(Keys.T) || Input.IsJustPressed(Buttons.RightShoulder))
|
2021-04-11 18:42:22 +02:00
|
|
|
{
|
2021-04-19 17:22:14 +02:00
|
|
|
_player.PlayTap();
|
2021-04-19 15:41:37 +02:00
|
|
|
if (ObjectRadar.Filter == ObjectType.Satellite)
|
|
|
|
|
{
|
|
|
|
|
ObjectRadar.SetObjectType(ObjectType.Debris);
|
|
|
|
|
Tolk.Output("Debris");
|
|
|
|
|
} else
|
|
|
|
|
{
|
|
|
|
|
ObjectRadar.SetObjectType(ObjectType.Satellite);
|
|
|
|
|
Tolk.Output("Satellites");
|
|
|
|
|
}
|
2021-04-11 18:42:22 +02:00
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustPressed(Keys.H) || Input.IsJustPressed(Buttons.B))
|
2021-04-19 23:37:40 +02:00
|
|
|
{
|
|
|
|
|
_player.PlayTap();
|
2021-04-21 18:39:33 +02:00
|
|
|
Tolk.Output(Math.Round(_player.Health).ToString() + " health", true);
|
2021-04-19 23:37:40 +02:00
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustPressed(Keys.X) || Input.IsJustPressed(Buttons.A))
|
2021-04-19 23:37:40 +02:00
|
|
|
{
|
|
|
|
|
_player.PlayTap();
|
|
|
|
|
Tolk.Output(_player.CurrentWeapon.RemainingAmmo.ToString() + " rounds", true);
|
|
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustPressed(Keys.Y) || Input.IsJustPressed(Buttons.X))
|
2021-04-20 16:26:38 +02:00
|
|
|
{
|
|
|
|
|
_player.PlayTap();
|
2021-04-21 18:39:33 +02:00
|
|
|
if (ObjectRadar.Target != null)
|
|
|
|
|
{
|
|
|
|
|
Tolk.Output(Math.Round(Vector3.Distance(_player.Position, ObjectRadar.Target.Position)).ToString() + " units", true);
|
|
|
|
|
var radarYaw = (float)System.Math.Atan2(ObjectRadar.RadarOrientation.M13, ObjectRadar.RadarOrientation.M33);
|
|
|
|
|
var radarPitch = (float)System.Math.Asin(-ObjectRadar.RadarOrientation.M23);
|
|
|
|
|
var playerYaw = (float)System.Math.Atan2(_player.Rotation.M13, _player.Rotation.M33);
|
|
|
|
|
var playerPitch = (float)System.Math.Asin(-_player.Rotation.M23);
|
|
|
|
|
var totalYaw = MathHelper.ToDegrees(MathHelper.WrapAngle(radarYaw - playerYaw + MathHelper.Pi));
|
|
|
|
|
var totalPitch = MathHelper.ToDegrees(MathHelper.WrapAngle(radarPitch - playerPitch));
|
|
|
|
|
Tolk.Output(Math.Round(totalYaw).ToString() + " horizontal, " + Math.Round(totalPitch).ToString() + " vertical");
|
|
|
|
|
}
|
2021-04-20 16:26:38 +02:00
|
|
|
}
|
2021-04-19 19:49:13 +02:00
|
|
|
if (Input.IsJustPressed(Keys.O))
|
|
|
|
|
{
|
|
|
|
|
DavyKager.Tolk.Output(Objects.Count.ToString());
|
|
|
|
|
}
|
2021-04-23 21:08:37 +02:00
|
|
|
if (Input.IsJustPressed(Keys.PageUp))
|
|
|
|
|
{
|
|
|
|
|
Manager.Music.Volume = Manager.Music.Volume + 0.05f;
|
|
|
|
|
}
|
|
|
|
|
if (Input.IsJustPressed(Keys.PageDown))
|
|
|
|
|
{
|
|
|
|
|
Manager.Music.Volume = Manager.Music.Volume - 0.05f;
|
|
|
|
|
}
|
2021-04-24 02:47:17 +02:00
|
|
|
if (Input.IsJustPressed(Keys.Escape) || Input.IsJustPressed(Buttons.Start))
|
2021-04-23 21:08:37 +02:00
|
|
|
{
|
|
|
|
|
EndGame();
|
|
|
|
|
}
|
2021-04-10 14:08:20 +02:00
|
|
|
}
|
|
|
|
|
|
2021-04-11 14:12:55 +02:00
|
|
|
private void CheckCollisions()
|
|
|
|
|
{
|
|
|
|
|
foreach (var obj in Objects)
|
|
|
|
|
{
|
2021-04-11 18:42:22 +02:00
|
|
|
if (!obj.Active) continue;
|
2021-04-11 14:12:55 +02:00
|
|
|
var candidates = objtree.Find(obj.Position, obj.Dimensions);
|
|
|
|
|
foreach (var target in candidates)
|
|
|
|
|
{
|
2021-04-11 18:42:22 +02:00
|
|
|
if (obj == target || !target.Active) continue;
|
2021-04-11 14:12:55 +02:00
|
|
|
if (Intersects(obj, target))
|
|
|
|
|
{
|
|
|
|
|
obj.OnCollision(target);
|
|
|
|
|
target.OnCollision(obj);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public bool Intersects(IGameObject obj1, IGameObject obj2)
|
|
|
|
|
{
|
|
|
|
|
return (obj1.Position.X <= (obj2.Position.X + obj2.Dimensions.X) && (obj1.Position.X + obj1.Dimensions.X) >= obj2.Position.X) && (obj1.Position.Y <= (obj2.Position.Y + obj2.Dimensions.Y) && (obj1.Position.Y + obj1.Dimensions.Y) >= obj2.Position.Y) && (obj1.Position.Z <= (obj2.Position.Z + obj2.Dimensions.Z) && (obj1.Position.Z + obj1.Dimensions.Z) >= obj2.Position.Z);
|
|
|
|
|
}
|
2021-04-11 18:42:22 +02:00
|
|
|
|
|
|
|
|
public void AddObject(IGameObject obj)
|
|
|
|
|
{
|
|
|
|
|
Addable.Add(obj);
|
|
|
|
|
}
|
2021-04-19 20:23:23 +02:00
|
|
|
|
|
|
|
|
public Player GetPlayer()
|
|
|
|
|
{
|
|
|
|
|
return _player;
|
|
|
|
|
}
|
2021-04-23 20:28:06 +02:00
|
|
|
|
|
|
|
|
public void HandleGameOver(GameTime time)
|
|
|
|
|
{
|
|
|
|
|
GameStats.TotalPlayTime = time.TotalGameTime.TotalSeconds;
|
|
|
|
|
Manager.RemoveScreen(this);
|
|
|
|
|
Manager.AddScreen(new StatsScreen());
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public void EndGame()
|
|
|
|
|
{
|
|
|
|
|
GameOver = true;
|
2021-04-24 18:47:51 +02:00
|
|
|
Manager.Computer.Play("GameOver");
|
2021-04-23 20:28:06 +02:00
|
|
|
}
|
2021-04-10 14:08:20 +02:00
|
|
|
}
|
|
|
|
|
}
|