recrownedgtk/RecrownedAthenaeum/UI/ScreenSystem/Screen.cs

206 lines
6.7 KiB
C#
Raw Normal View History

using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Graphics;
using RecrownedAthenaeum.Render;
using System.Collections.Generic;
namespace RecrownedAthenaeum.UI.ScreenSystem
{
2019-01-14 07:26:46 +00:00
/// <summary>
/// Represents one of the poosible states a screen can be in.
/// </summary>
public enum ScreenState {
/// <summary>
/// Screen is transitioning in.
/// </summary>
EnterTransition,
/// <summary>
/// Screen is transitioning out.
/// </summary>
ExitTransition,
/// <summary>
/// Screen is currently displayed normally without transition.
/// </summary>
Normal
}
2019-01-14 07:26:46 +00:00
/// <summary>
/// A screen represents a virtual system of management that controls an system of items to be displayed.
/// </summary>
public class Screen
{
2019-01-14 07:26:46 +00:00
/// <summary>
/// Transitions to apply.
/// </summary>
public readonly List<ITransition> Transitions;
2019-01-14 07:26:46 +00:00
/// <summary>
/// Whether or not to continue rendering this screen onto a buffer for the benefit of the next screen to use as a transition.
2019-01-14 07:26:46 +00:00
/// </summary>
public bool UseRenderTargetForExitTransition { get; private set; }
/// <summary>
/// The background color to be used to clear the screen.
/// </summary>
public Color BackgroundColor;
2019-01-14 07:26:46 +00:00
/// <summary>
/// The next screen to be displayed after exit transition finishes. May be null, leading to transition to previous screen or loading screen.
/// </summary>
public Screen NextScreen { get; set; }
2019-01-14 07:26:46 +00:00
/// <summary>
/// The current window dimensions.
2019-01-14 07:26:46 +00:00
/// </summary>
public int width, height;
2019-01-14 07:26:46 +00:00
/// <summary>
/// Current state of the screen.
/// </summary>
public ScreenState State { get; private set; }
/// <summary>
/// Creates a new screen.
/// </summary>
/// <param name="useEnterTransition">True to start in entering transition state.</param>
public Screen(bool useEnterTransition = false)
{
State = useEnterTransition ? ScreenState.EnterTransition : ScreenState.Normal;
Transitions = new List<ITransition>();
}
/// <summary>
/// Called when screen size is set.
/// </summary>
/// <param name="width">The width of the screen.</param>
/// <param name="height">The height of the screen.</param>
public virtual void ApplySize(int width, int height)
{
this.width = width;
this.height = height;
}
2019-01-14 05:23:03 +00:00
/// <summary>
/// Called to update the screen.
/// </summary>
/// <param name="gameTime">Game time information.</param>
public virtual void Update(GameTime gameTime)
{
}
2019-01-14 05:23:03 +00:00
/// <summary>
/// Called to draw this screen.
/// </summary>
/// <param name="spriteBatch">SpriteBatch to use.</param>
public virtual void Draw(ConsistentSpriteBatch spriteBatch)
{
foreach (ITransition transition in Transitions)
{
transition.DrawTransition(spriteBatch);
}
}
/// <summary>
2019-01-14 05:23:03 +00:00
/// Updates the transition based on the current state of the screen.
/// </summary>
/// <param name="delta">Time passed since last frame in seconds.</param>
2019-01-14 05:23:03 +00:00
/// <param name="waiting">If the this transition should wait.</param>
/// <returns>Only returns true if exit transition is complete. Returns false otherwise.</returns>
2019-01-14 05:23:03 +00:00
public bool UpdateTransition(double delta, bool waiting)
{
switch (State)
{
case ScreenState.EnterTransition:
2019-01-14 05:23:03 +00:00
EnteringTransition(delta, waiting);
break;
case ScreenState.ExitTransition:
2019-01-14 05:23:03 +00:00
return ExitingTransition(delta, waiting);
}
return false;
}
2019-01-14 05:23:03 +00:00
private void EnteringTransition(double delta, bool waiting)
{
bool complete = true;
for (int transitionID = 0; transitionID < Transitions.Count; transitionID++)
{
ITransition transition = Transitions[transitionID];
2019-01-14 07:26:46 +00:00
if (!transition.UpdateEnteringTransition(delta, waiting))
{
complete = false;
}
}
if (complete && State != ScreenState.ExitTransition)
{
State = ScreenState.Normal;
}
}
2019-01-14 05:23:03 +00:00
private bool ExitingTransition(double delta, bool waiting)
{
bool complete = true;
foreach (ITransition transition in Transitions)
{
2019-01-14 07:26:46 +00:00
if (!transition.UpdateExitingTransition(delta, waiting))
{
complete = false;
}
}
return complete;
}
/// <summary>
/// Called when the screen is shown.
/// </summary>
public virtual void Show()
{
foreach (ITransition transition in Transitions)
{
transition.InitiateTransition(new Rectangle(0, 0, width, height));
}
}
2019-01-14 05:23:03 +00:00
/// <summary>
/// Called when this screen is no longer the displayed screen.
/// </summary>
public virtual void Hide()
{
}
2019-01-14 05:23:03 +00:00
/// <summary>
/// Called whenever the status of assets changes from being loaded to unloaded or unloaded to loaded.
/// </summary>
/// <param name="state">True for loaded, false for unloaded.</param>
public virtual void AssetLoadStateChange(bool state)
{
}
2019-01-14 05:23:03 +00:00
/// <summary>
/// Call this to begin exit transition.
/// </summary>
/// <param name="UseRenderTargetForExitTransition">Whether or not to use a render target for the next screen to use.</param>
public void StartExitTransition(bool UseRenderTargetForExitTransition = false)
{
this.UseRenderTargetForExitTransition = UseRenderTargetForExitTransition;
State = ScreenState.ExitTransition;
}
2019-01-14 05:23:03 +00:00
/// <summary>
/// Called everytime the previous screen frame buffer updates. Used for transition purposes.
/// </summary>
/// <param name="previousScreenFrame">The previous screen's render buffer.</param>
public virtual void UpdatePreviousScreenFrame(RenderTarget2D previousScreenFrame)
{
foreach (ITransition transition in Transitions)
{
transition.UpdatePreviousScreenFrame(previousScreenFrame);
}
}
}
}