using System.Numerics;
using Robust.Client.Graphics;
using Robust.Shared.Serialization.TypeSerializers.Implementations.Custom;
namespace Content.Client.TextScreen;
///
/// A component for rendering text on a screen.
/// Can show scrolling text, timers, or other specific-use information (e.g. arrivals timer).
///
///
/// Pausing handled manually due to logic.
///
[RegisterComponent, Access(typeof(TextScreenSystem))]
public sealed partial class TextScreenVisualsComponent : Component
{
///
/// 1/32 - the size of a pixel in meters.
///
public const float PixelSize = 1f / EyeManager.PixelsPerMeter;
#region Appearance
///
/// The color of the text drawn.
///
///
/// 15,151,251 is the old SS13 color used on tgstation.
///
[DataField]
public Color Color = new(15, 151, 251);
///
/// The current color being drawn on the screen.
///
[ViewVariables]
public Color CurrentColor;
///
/// Offset for centering the text.
///
///
/// Values in pixels.
///
[DataField]
public Vector2 TextOffset = Vector2.Zero;
///
/// Vertical distance between the top pixel of each row.
///
[DataField]
public int RowOffset = 7;
///
/// The amount of characters this component can show per row.
///
///
/// Note that scrolling text can show one more than this.
///
[DataField]
public int RowLength = 5;
///
/// The longest that a message should take to cross the screen before wrapping around.
///
[DataField]
public TimeSpan MaxMessageScrollTime = TimeSpan.FromSeconds(5);
///
/// The longest that it should take to scroll one pixel on a screen.
///
[DataField]
public TimeSpan MaxPixelScrollTime = TimeSpan.FromMilliseconds(100);
///
/// The maximum number of characters to display per row.
///
[DataField]
public int MaxScrollingCharacters = 32;
///
/// When scrolling, a horizontal offset for the scrolling, in pixels.
///
///
/// Needed for finer adjustments of scroll bounds, along with
/// and
///
///
[DataField]
public int HorizontalScrollOffset;
///
/// When scrolling, the number of pixels that the leftmost letters should be invisible for.
/// Value should be between [0,CharWidth).
///
///
[DataField]
public int LeftInvisiblePixels;
///
/// When scrolling, the number of pixels that the rightmost letters should be invisible for.
/// Value should be between [0,CharWidth).
///
///
[DataField]
public int RightInvisiblePixels;
///
/// The layer for the outer frame of the text screen.
///
///
/// Will be registered on top of the other layers.
/// Should be at least 2 pixels thick on either side for the illusion to work.
///
[DataField]
public PrototypeLayerData? FrameState;
#endregion
#region Text State
///
/// If true, the screen is able to scroll its text.
///
[DataField]
public bool ScrollEnabled;
///
/// The list of row data for the text screens.
///
///
/// Each row needs its own entry. To declare a three row timer, the yaml could look like rowData: [{},{},{}].
///
[DataField]
public TextScreenRow[] RowData = { new(), new() };
///
/// The text to display on the screen.
/// Each row delimited with a newline (\n) character.
///
[ViewVariables]
public string? TextToDisplay;
///
/// The time that the text was sent.
/// Used for scrolling.
///
[ViewVariables]
public TimeSpan TextTime;
///
/// If true, text to display has been updated and should redraw.
///
[ViewVariables]
public bool NewTextToDisplay;
#endregion
}
///
/// All information about a given row of text.
///
[DataDefinition, Serializable]
public partial struct TextScreenRow()
{
///
/// The time this row should next scroll the text by a pixel.
///
[DataField(customTypeSerializer: typeof(TimeOffsetSerializer))]
public TimeSpan NextScroll = TimeSpan.MaxValue;
///
/// The delay between each pixel scrolled on this screen.
///
[DataField]
public TimeSpan ScrollDelay = TimeSpan.MaxValue;
///
/// The current position of the row in the string, in pixels.
///
///
/// Increases monotonically, should be taken modulo the text length.
/// Each character is a fixed size (pixel width defined in ).
///
[DataField]
public int ScrollPosition;
///
/// A list with each of the row's sprite layers, with the key inside of it and the state it's currently on.
///
///
/// Currently not removed from the sprite when the component is removed.
///
[DataField]
public List<(string Key, string? State)> Layers = new();
///
/// The full text currently being drawn on the row. May not all fit on the screen at once.
///
[DataField]
public string Text = string.Empty;
}