Pong/Scripts/Managers/ScalingManager.cs
Fries 65ef70f583 the enemy can now see when the screen is adjusted.
the scaling manager now controls when the various objects are active so stuff won't be null because of stuff running too fast or slow.
2023-06-02 17:15:44 -07:00

139 lines
4.2 KiB
C#

using System;
using Pong.Scripts.Data;
using Pong.Scripts.Objects;
namespace Pong.Scripts.Managers;
public partial class ScalingManager : Node
{
private HFlowContainer _score;
private BasePaddle _paddle;
private Ball _ball;
private Enemy _enemy;
private Area2D _leftWall;
private Area2D _rightWall;
private StaticBody2D _topWall;
private StaticBody2D _bottomWall;
private Vector2I _gameResolution;
internal GameArea GameArea;
public event Action<Vector2> NewPaddlePosition;
public event Action<Vector2> NewEnemyPosition;
public event Action<Vector2> NewBallPosition;
public override void _EnterTree()
{
GetNodes();
GetTree().Root.SizeChanged += AdaptToGameResolution;
AdaptToGameResolution();
}
public override void _ExitTree()
{
GetTree().Root.SizeChanged -= AdaptToGameResolution;
}
/// <summary>
/// a method that gets all the nodes that the scaling manager will manage the position and scale of.
/// </summary>
private void GetNodes()
{
_score = GetNode<HFlowContainer>("../Score");
_paddle = GetNode<BasePaddle>("../Paddle");
_ball = GetNode<Ball>("../Ball");
_enemy = GetNode<Enemy>("../Enemy");
_leftWall = GetNode<Area2D>("../Walls/Left");
_rightWall = GetNode<Area2D>("../Walls/Right");
_topWall = GetNode<StaticBody2D>("../Walls/Top");
_bottomWall = GetNode<StaticBody2D>("../Walls/Bottom");
_paddle.ScalingManager = this;
_enemy.ScalingManager = this;
NewPaddlePosition += _paddle.SetNewPosition;
NewEnemyPosition += _enemy.SetNewPosition;
}
/// <summary>
/// adapt to the current resolution of the game.
/// </summary>
private void AdaptToGameResolution()
{
_paddle.Running = false;
_enemy.Running = false;
var normalizedPaddlePosition =
GameArea?.NormalizePosition(_paddle.Position) ?? new Vector2(0, 0.5);
var normalizedEnemyPosition = GameArea?.NormalizePosition(_enemy.Position) ?? new Vector2(1, 0.5);
var normalizedBallPosition = GameArea?.NormalizePosition(_ball.Position) ?? new Vector2(0, 0);
_gameResolution = DisplayServer.WindowGetSize();
GameArea = new GameArea(_gameResolution);
SetWallPosition();
SetScorePosition();
SetPaddlePosition(normalizedPaddlePosition);
SetEnemyPosition(normalizedEnemyPosition);
_paddle.Running = true;
_enemy.GenerateCollisions();
_enemy.Running = true;
_ball.FlickBall();
}
/// <summary>
/// set the position and scale of the walls according to the edge position.
/// </summary>
private void SetWallPosition()
{
var xSize = GameArea.X.ByWallSizeExtents;
var ySize = GameArea.Y.ByWallSizeExtents;
_leftWall.Position = new Vector2(-xSize, 0);
_rightWall.Position = new Vector2(xSize, 0);
_topWall.Position = new Vector2(0, -ySize);
_bottomWall.Position = new Vector2(0, ySize);
_leftWall.Scale = _leftWall.Scale with { Y = _gameResolution.Y };
_rightWall.Scale = _rightWall.Scale with { Y = _gameResolution.Y };
_topWall.Scale = _topWall.Scale with { X = _gameResolution.X - 60 };
_bottomWall.Scale = _bottomWall.Scale with { X = _gameResolution.X - 60 };
}
/// <summary>
/// set the position of the score ui. this has to be calculated with 0, 0 being the top left of the screen as
/// the UIs point starts from there instead of the point being in the middle of the screen.
/// </summary>
private void SetScorePosition()
{
_score.Position = new Vector2(-GameArea.X.ByWallSize, -GameArea.Y.ByWallSize);
_score.Size = new Vector2(_gameResolution.X - 60, _gameResolution.Y - 60);
}
/// <summary>
/// set the paddle position to a normalized position that gets globalized. the paddle gets the new position with an event.
/// </summary>
private void SetPaddlePosition(Vector2 normalizedPosition)
{
var newPaddlePos = GameArea.GlobalizePosition(normalizedPosition with { X = 0 }) + new Vector2(48, 0);
NewPaddlePosition?.Invoke(newPaddlePos);
}
private void SetEnemyPosition(Vector2 normalizedPosition)
{
var newEnemyPos = GameArea.GlobalizePosition(normalizedPosition with { X = 1 }) + new Vector2(-48, 0);
NewEnemyPosition?.Invoke(newEnemyPos);
}
private void SetBallPosition(Vector2 normalizedPosition)
{
var newBallPos = GameArea.GlobalizePosition(normalizedPosition);
NewBallPosition?.Invoke(newBallPos);
}
public static void SetNewPosition(ref Vector2 newPositionField)
{
}
}