From bf6a05d314af6a8023df3ded64a9321652bb7afc Mon Sep 17 00:00:00 2001 From: UnknownShadow200 Date: Fri, 23 Mar 2018 18:27:07 +1100 Subject: [PATCH] More port of ChatScreen to C --- ClassicalSharp/2D/GuiElement.cs | 4 +- ClassicalSharp/2D/Screens/ChatScreen.cs | 10 +- ClassicalSharp/2D/Screens/ClickableScreen.cs | 2 +- .../2D/Screens/Menu/ClassicOptionsScreen.cs | 2 +- .../2D/Screens/Menu/MenuOptionsScreen.cs | 2 +- ClassicalSharp/2D/Screens/Menu/PauseScreen.cs | 2 +- .../2D/Screens/Overlays/TexIdsOverlay.cs | 2 +- ClassicalSharp/2D/Screens/StatusScreen.cs | 4 +- .../2D/Widgets/Chat/SpecialInputWidget.cs | 4 +- .../2D/Widgets/Chat/TextGroupWidget.cs | 2 +- ClassicalSharp/2D/Widgets/HotbarWidget.cs | 2 +- ClassicalSharp/2D/Widgets/PlayerListWidget.cs | 2 +- ClassicalSharp/2D/Widgets/Widget.cs | 4 +- ClassicalSharp/Map/World.cs | 11 +- ClassicalSharp/Utils/Utils.cs | 6 +- src/Client/Chat.c | 26 +- src/Client/Chat.h | 22 +- src/Client/Event.h | 6 +- src/Client/Gui.c | 8 +- src/Client/Gui.h | 6 +- src/Client/Random.c | 4 +- src/Client/Screens.c | 379 +++++++++--------- src/Client/Utils.c | 8 +- src/Client/Utils.h | 4 +- src/Client/Widgets.c | 18 +- src/Client/Widgets.h | 2 +- src/Client/WinWindow.c | 3 +- src/Client/Window.h | 44 +- 28 files changed, 281 insertions(+), 308 deletions(-) diff --git a/ClassicalSharp/2D/GuiElement.cs b/ClassicalSharp/2D/GuiElement.cs index d2fd22961..89c327160 100644 --- a/ClassicalSharp/2D/GuiElement.cs +++ b/ClassicalSharp/2D/GuiElement.cs @@ -42,8 +42,8 @@ namespace ClassicalSharp.Gui { public virtual bool HandlesMouseUp(int mouseX, int mouseY, MouseButton button) { return false; } protected static int CalcPos(Anchor anchor, int offset, int size, int axisLen) { - if (anchor == Anchor.LeftOrTop) return offset; - if (anchor == Anchor.BottomOrRight) return axisLen - size - offset; + if (anchor == Anchor.Min) return offset; + if (anchor == Anchor.Max) return axisLen - size - offset; return (axisLen - size) / 2 + offset; } diff --git a/ClassicalSharp/2D/Screens/ChatScreen.cs b/ClassicalSharp/2D/Screens/ChatScreen.cs index 17a37c5e9..2c32a3c79 100644 --- a/ClassicalSharp/2D/Screens/ChatScreen.cs +++ b/ClassicalSharp/2D/Screens/ChatScreen.cs @@ -49,27 +49,27 @@ namespace ClassicalSharp.Gui.Screens { void ConstructWidgets() { input = new ChatInputWidget(game, chatFont) - .SetLocation(Anchor.LeftOrTop, Anchor.BottomOrRight, 5, 5); + .SetLocation(Anchor.Min, Anchor.Max, 5, 5); altText = new SpecialInputWidget(game, chatFont, input); altText.Init(); UpdateAltTextY(); status = new TextGroupWidget(game, 5, chatFont, chatUrlFont) - .SetLocation(Anchor.BottomOrRight, Anchor.LeftOrTop, 0, 0); + .SetLocation(Anchor.Max, Anchor.Min, 0, 0); status.Init(); status.SetUsePlaceHolder(0, false); status.SetUsePlaceHolder(1, false); bottomRight = new TextGroupWidget(game, 3, chatFont, chatUrlFont) - .SetLocation(Anchor.BottomOrRight, Anchor.BottomOrRight, 0, hud.BottomOffset + 15); + .SetLocation(Anchor.Max, Anchor.Max, 0, hud.BottomOffset + 15); bottomRight.Init(); normalChat = new TextGroupWidget(game, chatLines, chatFont, chatUrlFont) - .SetLocation(Anchor.LeftOrTop, Anchor.BottomOrRight, 10, hud.BottomOffset + 15); + .SetLocation(Anchor.Min, Anchor.Max, 10, hud.BottomOffset + 15); normalChat.Init(); clientStatus = new TextGroupWidget(game, game.Chat.ClientStatus.Length, chatFont, chatUrlFont) - .SetLocation(Anchor.LeftOrTop, Anchor.BottomOrRight, 10, hud.BottomOffset + 15); + .SetLocation(Anchor.Min, Anchor.Max, 10, hud.BottomOffset + 15); clientStatus.Init(); announcement = TextWidget.Create(game ,null, announcementFont) diff --git a/ClassicalSharp/2D/Screens/ClickableScreen.cs b/ClassicalSharp/2D/Screens/ClickableScreen.cs index 897fe3f34..bb9e5ef68 100644 --- a/ClassicalSharp/2D/Screens/ClickableScreen.cs +++ b/ClassicalSharp/2D/Screens/ClickableScreen.cs @@ -66,7 +66,7 @@ namespace ClassicalSharp.Gui.Screens { protected ButtonWidget MakeBack(int width, string text, int y, Font font, SimpleClickHandler onClick) { return ButtonWidget.Create(game, width, text, font, LeftOnly(onClick)) - .SetLocation(Anchor.Centre, Anchor.BottomOrRight, 0, y); + .SetLocation(Anchor.Centre, Anchor.Max, 0, y); } protected static void SwitchOptions(Game g, Widget w) { g.Gui.SetNewScreen(new OptionsGroupScreen(g)); } diff --git a/ClassicalSharp/2D/Screens/Menu/ClassicOptionsScreen.cs b/ClassicalSharp/2D/Screens/Menu/ClassicOptionsScreen.cs index 15834ce79..b2f3b9490 100644 --- a/ClassicalSharp/2D/Screens/Menu/ClassicOptionsScreen.cs +++ b/ClassicalSharp/2D/Screens/Menu/ClassicOptionsScreen.cs @@ -34,7 +34,7 @@ namespace ClassicalSharp.Gui.Screens { !hacks ? null : MakeOpt(0, 60, "Hacks enabled", onClick, GetHacks, SetHacks), ButtonWidget.Create(game, 400, "Controls...", titleFont, LeftOnly(SwitchClassic)) - .SetLocation(Anchor.Centre, Anchor.BottomOrRight, 0, 95), + .SetLocation(Anchor.Centre, Anchor.Max, 0, 95), MakeBack(400, "Done", 25, titleFont, SwitchPause), null, null, }; diff --git a/ClassicalSharp/2D/Screens/Menu/MenuOptionsScreen.cs b/ClassicalSharp/2D/Screens/Menu/MenuOptionsScreen.cs index dc3025016..abae7c5da 100644 --- a/ClassicalSharp/2D/Screens/Menu/MenuOptionsScreen.cs +++ b/ClassicalSharp/2D/Screens/Menu/MenuOptionsScreen.cs @@ -149,7 +149,7 @@ namespace ClassicalSharp.Gui.Screens { void MakeExtendedHelp(string[] desc) { extendedHelp = new TextGroupWidget(game, desc.Length, regularFont, null) - .SetLocation(Anchor.LeftOrTop, Anchor.LeftOrTop, 0, 0); + .SetLocation(Anchor.Min, Anchor.Min, 0, 0); extendedHelp.Init(); for (int i = 0; i < desc.Length; i++) extendedHelp.SetText(i, desc[i]); diff --git a/ClassicalSharp/2D/Screens/Menu/PauseScreen.cs b/ClassicalSharp/2D/Screens/Menu/PauseScreen.cs index 88b95b776..4d8cdee60 100644 --- a/ClassicalSharp/2D/Screens/Menu/PauseScreen.cs +++ b/ClassicalSharp/2D/Screens/Menu/PauseScreen.cs @@ -46,7 +46,7 @@ namespace ClassicalSharp.Gui.Screens { // Other ButtonWidget.Create(game, 120, "Quit game", titleFont, LeftOnly(QuitGame)) - .SetLocation(Anchor.BottomOrRight, Anchor.BottomOrRight, 5, 5), + .SetLocation(Anchor.Max, Anchor.Max, 5, 5), MakeBack(true, titleFont, SwitchGame), }; } diff --git a/ClassicalSharp/2D/Screens/Overlays/TexIdsOverlay.cs b/ClassicalSharp/2D/Screens/Overlays/TexIdsOverlay.cs index 9629c1553..6f9249bac 100644 --- a/ClassicalSharp/2D/Screens/Overlays/TexIdsOverlay.cs +++ b/ClassicalSharp/2D/Screens/Overlays/TexIdsOverlay.cs @@ -126,7 +126,7 @@ namespace ClassicalSharp.Gui.Screens { DisposeWidgets(widgets); widgets = new Widget[1]; widgets[0] = TextWidget.Create(game, "Texture ID reference sheet", titleFont) - .SetLocation(Anchor.Centre, Anchor.LeftOrTop, 0, yOffset - 30); + .SetLocation(Anchor.Centre, Anchor.Min, 0, yOffset - 30); } } } \ No newline at end of file diff --git a/ClassicalSharp/2D/Screens/StatusScreen.cs b/ClassicalSharp/2D/Screens/StatusScreen.cs index ce40669d0..3d75f9280 100644 --- a/ClassicalSharp/2D/Screens/StatusScreen.cs +++ b/ClassicalSharp/2D/Screens/StatusScreen.cs @@ -90,7 +90,7 @@ namespace ClassicalSharp.Gui.Screens { protected override void ContextRecreated() { status = new TextWidget(game, font) - .SetLocation(Anchor.LeftOrTop, Anchor.LeftOrTop, 2, 2); + .SetLocation(Anchor.Min, Anchor.Min, 2, 2); status.ReducePadding = true; status.Init(); string msg = statusBuffer.Length > 0 ? statusBuffer.ToString() : "FPS: no data yet"; @@ -102,7 +102,7 @@ namespace ClassicalSharp.Gui.Screens { int yOffset = status.Height + posAtlas.tex.Height + 2; hackStates = new TextWidget(game, font) - .SetLocation(Anchor.LeftOrTop, Anchor.LeftOrTop, 2, yOffset); + .SetLocation(Anchor.Min, Anchor.Min, 2, yOffset); hackStates.ReducePadding = true; hackStates.Init(); UpdateHackState(); diff --git a/ClassicalSharp/2D/Widgets/Chat/SpecialInputWidget.cs b/ClassicalSharp/2D/Widgets/Chat/SpecialInputWidget.cs index 7c7be0f97..8be2a133e 100644 --- a/ClassicalSharp/2D/Widgets/Chat/SpecialInputWidget.cs +++ b/ClassicalSharp/2D/Widgets/Chat/SpecialInputWidget.cs @@ -10,8 +10,8 @@ namespace ClassicalSharp.Gui.Widgets { public sealed class SpecialInputWidget : Widget { public SpecialInputWidget(Game game, Font font, InputWidget input) : base(game) { - HorizontalAnchor = Anchor.LeftOrTop; - VerticalAnchor = Anchor.BottomOrRight; + HorizontalAnchor = Anchor.Min; + VerticalAnchor = Anchor.Max; this.font = font; this.input = input; Active = false; diff --git a/ClassicalSharp/2D/Widgets/Chat/TextGroupWidget.cs b/ClassicalSharp/2D/Widgets/Chat/TextGroupWidget.cs index 114ac9ae7..dfb6607f1 100644 --- a/ClassicalSharp/2D/Widgets/Chat/TextGroupWidget.cs +++ b/ClassicalSharp/2D/Widgets/Chat/TextGroupWidget.cs @@ -72,7 +72,7 @@ namespace ClassicalSharp.Gui.Widgets { int y = 0; int deltaY = newHeight - Textures[index].Height; - if (VerticalAnchor == Anchor.LeftOrTop) { + if (VerticalAnchor == Anchor.Min) { y = Y; for (int i = 0; i < index; i++) y += Textures[i].Height; diff --git a/ClassicalSharp/2D/Widgets/HotbarWidget.cs b/ClassicalSharp/2D/Widgets/HotbarWidget.cs index 068a7b524..3dbda0496 100644 --- a/ClassicalSharp/2D/Widgets/HotbarWidget.cs +++ b/ClassicalSharp/2D/Widgets/HotbarWidget.cs @@ -11,7 +11,7 @@ namespace ClassicalSharp.Gui.Widgets { public HotbarWidget(Game game) : base(game) { HorizontalAnchor = Anchor.Centre; - VerticalAnchor = Anchor.BottomOrRight; + VerticalAnchor = Anchor.Max; } Texture selTex, backTex; diff --git a/ClassicalSharp/2D/Widgets/PlayerListWidget.cs b/ClassicalSharp/2D/Widgets/PlayerListWidget.cs index d3c7650d4..1598637dd 100644 --- a/ClassicalSharp/2D/Widgets/PlayerListWidget.cs +++ b/ClassicalSharp/2D/Widgets/PlayerListWidget.cs @@ -41,7 +41,7 @@ namespace ClassicalSharp.Gui.Widgets { SortAndReposition(); overview = TextWidget.Create(game, "Connected players:", font) - .SetLocation(Anchor.Centre, Anchor.LeftOrTop, 0, 0); + .SetLocation(Anchor.Centre, Anchor.Min, 0, 0); game.EntityEvents.TabListEntryAdded += TabEntryAdded; game.EntityEvents.TabListEntryRemoved += TabEntryRemoved; game.EntityEvents.TabListEntryChanged += TabEntryChanged; diff --git a/ClassicalSharp/2D/Widgets/Widget.cs b/ClassicalSharp/2D/Widgets/Widget.cs index 1418fcc56..3a845d0a2 100644 --- a/ClassicalSharp/2D/Widgets/Widget.cs +++ b/ClassicalSharp/2D/Widgets/Widget.cs @@ -8,8 +8,8 @@ namespace ClassicalSharp.Gui.Widgets { public abstract class Widget : GuiElement { public Widget(Game game) : base(game) { - HorizontalAnchor = Anchor.LeftOrTop; - VerticalAnchor = Anchor.LeftOrTop; + HorizontalAnchor = Anchor.Min; + VerticalAnchor = Anchor.Min; } /// Whether this widget is currently being moused over. diff --git a/ClassicalSharp/Map/World.cs b/ClassicalSharp/Map/World.cs index 7ee90436b..429f1d0f9 100644 --- a/ClassicalSharp/Map/World.cs +++ b/ClassicalSharp/Map/World.cs @@ -59,14 +59,17 @@ namespace ClassicalSharp.Map { /// Sets the block at the given world coordinates without bounds checking. public void SetBlock(int x, int y, int z, BlockID blockId) { - blocks1[(y * Length + z) * Width + x] = (BlockRaw)blockId; + int i = (y * Length + z) * Width + x; + blocks1[i] = (BlockRaw)blockId; + if (blocks1 == blocks2) return; + blocks2[i] = (BlockRaw)(blockId >> 8); } /// Returns the block at the given world coordinates without bounds checking. public BlockID GetBlock(int x, int y, int z) { int i = (y * Length + z) * Width + x; #if USE16_BIT - return (BlockID)((blocks1[i] | (blocks2[i] << 8) & BlockInfo.MaxDefined); + return (BlockID)((blocks1[i] | (blocks2[i] << 8)) & BlockInfo.MaxDefined); #else return blocks1[i]; #endif @@ -76,7 +79,7 @@ namespace ClassicalSharp.Map { public BlockID GetBlock(Vector3I p) { int i = (p.Y * Length + p.Z) * Width + p.X; #if USE16_BIT - return (BlockID)((blocks1[i] | (blocks2[i] << 8) & BlockInfo.MaxDefined); + return (BlockID)((blocks1[i] | (blocks2[i] << 8)) & BlockInfo.MaxDefined); #else return blocks1[i]; #endif @@ -119,7 +122,7 @@ namespace ClassicalSharp.Map { int i = (y * Length + z) * Width + x; #if USE16_BIT - return (BlockID)((blocks1[i] | (blocks2[i] << 8) & BlockInfo.MaxDefined); + return (BlockID)((blocks1[i] | (blocks2[i] << 8)) & BlockInfo.MaxDefined); #else return blocks1[i]; #endif diff --git a/ClassicalSharp/Utils/Utils.cs b/ClassicalSharp/Utils/Utils.cs index 8c462df3d..3b54fbdcd 100644 --- a/ClassicalSharp/Utils/Utils.cs +++ b/ClassicalSharp/Utils/Utils.cs @@ -19,7 +19,11 @@ namespace ClassicalSharp { public delegate void Action(); // ################################################################ - public enum Anchor { LeftOrTop, Centre, BottomOrRight, } + public enum Anchor { + Min, // left or top + Centre, // middle + Max, // right or bottom + } public static partial class Utils { diff --git a/src/Client/Chat.c b/src/Client/Chat.c index 19b09a957..2095c9c16 100644 --- a/src/Client/Chat.c +++ b/src/Client/Chat.c @@ -117,19 +117,19 @@ void Chat_AppendLog(STRING_PURE String* text) { Stream_WriteLine(&Chat_LogStream, &str); } -void Chat_Add(STRING_PURE String* text) { Chat_AddOf(text, MESSAGE_TYPE_NORMAL); } +void Chat_Add(STRING_PURE String* text) { Chat_AddOf(text, MSG_TYPE_NORMAL); } void Chat_AddOf(STRING_PURE String* text, Int32 msgType) { - if (msgType == MESSAGE_TYPE_NORMAL) { + if (msgType == MSG_TYPE_NORMAL) { StringsBuffer_Add(&Chat_Log, text); Chat_AppendLog(text); - } else if (msgType >= MESSAGE_TYPE_STATUS_1 && msgType <= MESSAGE_TYPE_STATUS_3) { - ChatLine_Make(&Chat_Status[msgType - MESSAGE_TYPE_STATUS_1], text); - } else if (msgType >= MESSAGE_TYPE_BOTTOMRIGHT_1 && msgType <= MESSAGE_TYPE_BOTTOMRIGHT_3) { - ChatLine_Make(&Chat_BottomRight[msgType - MESSAGE_TYPE_BOTTOMRIGHT_1], text); - } else if (msgType == MESSAGE_TYPE_ANNOUNCEMENT) { + } else if (msgType >= MSG_TYPE_STATUS_1 && msgType <= MSG_TYPE_STATUS_3) { + ChatLine_Make(&Chat_Status[msgType - MSG_TYPE_STATUS_1], text); + } else if (msgType >= MSG_TYPE_BOTTOMRIGHT_1 && msgType <= MSG_TYPE_BOTTOMRIGHT_3) { + ChatLine_Make(&Chat_BottomRight[msgType - MSG_TYPE_BOTTOMRIGHT_1], text); + } else if (msgType == MSG_TYPE_ANNOUNCEMENT) { ChatLine_Make(&Chat_Announcement, text); - } else if (msgType >= MESSAGE_TYPE_CLIENTSTATUS_1 && msgType <= MESSAGE_TYPE_CLIENTSTATUS_3) { - ChatLine_Make(&Chat_ClientStatus[msgType - MESSAGE_TYPE_CLIENTSTATUS_1], text); + } else if (msgType >= MSG_TYPE_CLIENTSTATUS_1 && msgType <= MSG_TYPE_CLIENTSTATUS_3) { + ChatLine_Make(&Chat_ClientStatus[msgType - MSG_TYPE_CLIENTSTATUS_1], text); } Event_RaiseChat(&ChatEvents_ChatReceived, text, msgType); } @@ -427,18 +427,18 @@ void CuboidCommand_BlockChanged(void* obj, Vector3I coords, BlockID oldBlock, Bl String_AppendInt32(&msg, coords.Y); String_AppendConst(&msg, ", "); String_AppendInt32(&msg, coords.Z); String_AppendConst(&msg, "), place mark 2."); - Chat_AddOf(&msg, MESSAGE_TYPE_CLIENTSTATUS_3); + Chat_AddOf(&msg, MSG_TYPE_CLIENTSTATUS_3); } else { cuboid_mark2 = coords; CuboidCommand_DoCuboid(); - String empty = String_MakeNull(); Chat_AddOf(&empty, MESSAGE_TYPE_CLIENTSTATUS_3); + String empty = String_MakeNull(); Chat_AddOf(&empty, MSG_TYPE_CLIENTSTATUS_3); if (!cuboid_persist) { Event_UnregisterBlock(&UserEvents_BlockChanged, NULL, CuboidCommand_BlockChanged); } else { cuboid_mark1 = Vector3I_Create1(Int32_MaxValue); String msg = String_FromConst("&eCuboid: &fPlace or delete a block."); - Chat_AddOf(&msg, MESSAGE_TYPE_CLIENTSTATUS_3); + Chat_AddOf(&msg, MSG_TYPE_CLIENTSTATUS_3); } } } @@ -457,7 +457,7 @@ void CuboidCommand_Execute(STRING_PURE String* args, UInt32 argsCount) { } String msg = String_FromConst("&eCuboid: &fPlace or delete a block."); - Chat_AddOf(&msg, MESSAGE_TYPE_CLIENTSTATUS_3); + Chat_AddOf(&msg, MSG_TYPE_CLIENTSTATUS_3); Event_RegisterBlock(&UserEvents_BlockChanged, NULL, CuboidCommand_BlockChanged); } diff --git a/src/Client/Chat.h b/src/Client/Chat.h index 0742787eb..27d72b8d9 100644 --- a/src/Client/Chat.h +++ b/src/Client/Chat.h @@ -8,17 +8,17 @@ Copyright 2014-2017 ClassicalSharp | Licensed under BSD-3 */ -#define MESSAGE_TYPE_NORMAL 0 -#define MESSAGE_TYPE_STATUS_1 1 -#define MESSAGE_TYPE_STATUS_2 2 -#define MESSAGE_TYPE_STATUS_3 3 -#define MESSAGE_TYPE_BOTTOMRIGHT_1 11 -#define MESSAGE_TYPE_BOTTOMRIGHT_2 12 -#define MESSAGE_TYPE_BOTTOMRIGHT_3 13 -#define MESSAGE_TYPE_ANNOUNCEMENT 100 -#define MESSAGE_TYPE_CLIENTSTATUS_1 256 /* Cuboid messages*/ -#define MESSAGE_TYPE_CLIENTSTATUS_2 257 /* Clipboard invalid character */ -#define MESSAGE_TYPE_CLIENTSTATUS_3 258 /* Tab list matching names*/ +#define MSG_TYPE_NORMAL 0 +#define MSG_TYPE_STATUS_1 1 +#define MSG_TYPE_STATUS_2 2 +#define MSG_TYPE_STATUS_3 3 +#define MSG_TYPE_BOTTOMRIGHT_1 11 +#define MSG_TYPE_BOTTOMRIGHT_2 12 +#define MSG_TYPE_BOTTOMRIGHT_3 13 +#define MSG_TYPE_ANNOUNCEMENT 100 +#define MSG_TYPE_CLIENTSTATUS_1 256 /* Cuboid messages*/ +#define MSG_TYPE_CLIENTSTATUS_2 257 /* Clipboard invalid character */ +#define MSG_TYPE_CLIENTSTATUS_3 258 /* Tab list matching names*/ typedef struct ChatLine_ { UInt8 Buffer[String_BufferSize(STRING_SIZE)]; DateTime Received; } ChatLine; ChatLine Chat_Status[3], Chat_BottomRight[3], Chat_ClientStatus[3], Chat_Announcement; diff --git a/src/Client/Event.h b/src/Client/Event.h index 427ce0d38..df4d6dc5b 100644 --- a/src/Client/Event.h +++ b/src/Client/Event.h @@ -120,9 +120,9 @@ Event_Real32 WorldEvents_MapLoading; /* Portion of world is decompressed/gener Event_Void WorldEvents_MapLoaded; /* New world has finished loading, player can now interact with it. */ Event_Int32 WorldEvents_EnvVarChanged; /* World environment variable changed by player/CPE/WoM config. */ -Event_Void ChatEvents_FontChanged; /* User changes whether system chat font used, and when the bitmapped font texture changes. */ -Event_Chat ChatEvents_ChatReceived; /* Raised when the server or a client-side command sends a message */ - +Event_Void ChatEvents_FontChanged; /* User changes whether system chat font used, and when the bitmapped font texture changes. */ +Event_Chat ChatEvents_ChatReceived; /* Raised when the server or a client-side command sends a message */ +Event_Int32 ChatEvents_ColCodeChanged; /* Raised when a colour code changes */ Event_Void WindowEvents_Moved; /* Window is moved. */ Event_Void WindowEvents_Resized; /* Window is resized. */ diff --git a/src/Client/Gui.c b/src/Client/Gui.c index 8c24e5bd1..b5d68436c 100644 --- a/src/Client/Gui.c +++ b/src/Client/Gui.c @@ -57,16 +57,16 @@ void Widget_Init(Widget* widget) { widget->Base.HandlesMouseDown = NULL; widget->X = 0; widget->Y = 0; widget->Width = 0; widget->Height = 0; - widget->HorAnchor = ANCHOR_LEFT_OR_TOP; - widget->VerAnchor = ANCHOR_LEFT_OR_TOP; + widget->HorAnchor = ANCHOR_MIN; + widget->VerAnchor = ANCHOR_MIN; widget->XOffset = 0; widget->YOffset = 0; widget->Reposition = Widget_DoReposition; } Int32 Gui_CalcPos(UInt8 anchor, Int32 offset, Int32 size, Int32 axisLen) { - if (anchor == ANCHOR_LEFT_OR_TOP) return offset; - if (anchor == ANCHOR_BOTTOM_OR_RIGHT) return axisLen - size - offset; + if (anchor == ANCHOR_MIN) return offset; + if (anchor == ANCHOR_MAX) return axisLen - size - offset; return (axisLen - size) / 2 + offset; } diff --git a/src/Client/Gui.h b/src/Client/Gui.h index 7877854c6..35bf8d477 100644 --- a/src/Client/Gui.h +++ b/src/Client/Gui.h @@ -11,9 +11,9 @@ Copyright 2014-2017 ClassicalSharp | Licensed under BSD-3 */ -#define ANCHOR_LEFT_OR_TOP 0 -#define ANCHOR_CENTRE 1 -#define ANCHOR_BOTTOM_OR_RIGHT 2 +#define ANCHOR_MIN 0 /* Left or top */ +#define ANCHOR_CENTRE 1 /* Middle */ +#define ANCHOR_MAX 2 /* Bottom or right */ struct GuiElement_; typedef struct GuiElement_ { diff --git a/src/Client/Random.c b/src/Client/Random.c index 6e274d7b6..b5ef0bdd9 100644 --- a/src/Client/Random.c +++ b/src/Client/Random.c @@ -7,8 +7,8 @@ void Random_Init(Random* seed, Int32 seedInit) { Random_SetSeed(seed, seedInit); } void Random_InitFromCurrentTime(Random* rnd) { DateTime now = Platform_CurrentUTCTime(); - Int64 totalMS = DateTime_TotalMilliseconds(&now); - Random_Init(rnd, (Int32)totalMS); + Int64 totalMs = DateTime_TotalMs(&now); + Random_Init(rnd, (Int32)totalMs); } void Random_SetSeed(Random* seed, Int32 seedInit) { diff --git a/src/Client/Screens.c b/src/Client/Screens.c index 0662cab9e..152dfc63c 100644 --- a/src/Client/Screens.c +++ b/src/Client/Screens.c @@ -14,6 +14,8 @@ #include "MapGenerator.h" #include "ServerConnection.h" #include "Chat.h" +#include "ExtMath.h" +#include "Window.h" #define LeftOnly(func) { if (btn == MouseButton_Left) { func; } return true; } #define Widget_Init(widget) (widget)->Base.Base.Init(&((widget)->Base.Base)) @@ -129,7 +131,7 @@ void Screen_RenderWidgets(Widget** widgets, UInt32 widgetsCount, Real64 delta) { void Screen_MakeBack(ButtonWidget* widget, Int32 width, STRING_PURE String* text, Int32 y, FontDesc* font, Gui_MouseHandler onClick) { ButtonWidget_Create(widget, text, width, font, onClick); - Widget_SetLocation(&widget->Base, ANCHOR_CENTRE, ANCHOR_BOTTOM_OR_RIGHT, 0, y); + Widget_SetLocation(&widget->Base, ANCHOR_CENTRE, ANCHOR_MAX, 0, y); } void Screen_MakeDefaultBack(ButtonWidget* widget, bool toGame, FontDesc* font, Gui_MouseHandler onClick) { @@ -450,7 +452,7 @@ void StatusScreen_Update(StatusScreen* screen, Real64 delta) { } void StatusScreen_OnResize(Screen* screen) { } -void StatusScreen_ChatFontChanged(void* obj) { +void StatusScreen_FontChanged(void* obj) { StatusScreen* screen = (StatusScreen*)obj; GuiElement* elem = &screen->Base.Base; elem->Recreate(elem); @@ -467,7 +469,7 @@ void StatusScreen_ContextRecreated(void* obj) { StatusScreen* screen = (StatusScreen*)obj; TextWidget* status = &screen->Status; TextWidget_Make(status, &screen->Font); - Widget_SetLocation(&status->Base, ANCHOR_LEFT_OR_TOP, ANCHOR_LEFT_OR_TOP, 2, 2); + Widget_SetLocation(&status->Base, ANCHOR_MIN, ANCHOR_MIN, 2, 2); status->ReducePadding = true; Widget_Init(status); StatusScreen_Update(screen, 1.0); @@ -479,7 +481,7 @@ void StatusScreen_ContextRecreated(void* obj) { Int32 yOffset = status->Base.Height + screen->PosAtlas.Tex.Height + 2; TextWidget* hacks = &screen->HackStates; TextWidget_Make(hacks, &screen->Font); - Widget_SetLocation(&hacks->Base, ANCHOR_LEFT_OR_TOP, ANCHOR_LEFT_OR_TOP, 2, yOffset); + Widget_SetLocation(&hacks->Base, ANCHOR_MIN, ANCHOR_MIN, 2, yOffset); hacks->ReducePadding = true; Widget_Init(hacks); StatusScreen_UpdateHackState(screen); @@ -490,7 +492,7 @@ void StatusScreen_Init(GuiElement* elem) { Platform_MakeFont(&screen->Font, &Game_FontName, 16, FONT_STYLE_NORMAL); StatusScreen_ContextRecreated(screen); - Event_RegisterVoid(&ChatEvents_FontChanged, screen, StatusScreen_ChatFontChanged); + Event_RegisterVoid(&ChatEvents_FontChanged, screen, StatusScreen_FontChanged); Event_RegisterVoid(&GfxEvents_ContextLost, screen, StatusScreen_ContextLost); Event_RegisterVoid(&GfxEvents_ContextRecreated, screen, StatusScreen_ContextRecreated); } @@ -516,7 +518,7 @@ void StatusScreen_Free(GuiElement* elem) { Platform_FreeFont(&screen->Font); StatusScreen_ContextLost(screen); - Event_UnregisterVoid(&ChatEvents_FontChanged, screen, StatusScreen_ChatFontChanged); + Event_UnregisterVoid(&ChatEvents_FontChanged, screen, StatusScreen_FontChanged); Event_UnregisterVoid(&GfxEvents_ContextLost, screen, StatusScreen_ContextLost); Event_UnregisterVoid(&GfxEvents_ContextRecreated, screen, StatusScreen_ContextRecreated); } @@ -1041,10 +1043,10 @@ void HUDScreen_Init(GuiElement* elem) { void HUDScreen_Render(GuiElement* elem, Real64 delta) { HUDScreen* screen = (HUDScreen*)elem; - Screen* chat = screen->Chat; - if (Game_HideGui && chat->HandlesAllInput) { + ChatScreen* chat = (ChatScreen*)screen->Chat; + if (Game_HideGui && chat->Base.HandlesAllInput) { Gfx_SetTexturing(true); - chat.input.Render(delta); + Widget_Render(&chat->Input, delta); Gfx_SetTexturing(false); } if (Game_HideGui) return; @@ -1055,8 +1057,8 @@ void HUDScreen_Render(GuiElement* elem, Real64 delta) { HUDScreen_DrawCrosshairs(); Gfx_SetTexturing(false); } - if (chat->HandlesAllInput && !Game_PureClassic) { - chat.RenderBackground(); + if (chat->Base.HandlesAllInput && !Game_PureClassic) { + ChatScreen_RenderBackground(chat); } Gfx_SetTexturing(true); @@ -1121,51 +1123,56 @@ typedef struct ChatScreen_ { Int32 ChatIndex; SpecialInputWidget AltText; FontDesc ChatFont, ChatUrlFont, AnnouncementFont; - string chatInInputBuffer; /* needed for lost contexts, to restore chat typed in */ -} + UInt8 ChatInInputBuffer[INPUTWIDGET_MAX_LINES * INPUTWIDGET_LEN]; + String ChatInInput; /* needed for lost contexts, to restore chat typed in */ + Int32 inputOldHeight = -1; +} ChatScreen; void ChatScreen_Init(GuiElement* elem) { - int fontSize = (int)(8 * game.GuiChatScale); - Utils.Clamp(ref fontSize, 8, 60); - chatFont = new Font(game.FontName, fontSize); - chatUrlFont = new Font(game.FontName, fontSize, FontStyle.Underline); + ChatScreen* screen = (ChatScreen*)elem; - fontSize = (int)(16 * game.GuiChatScale); - Utils.Clamp(ref fontSize, 8, 60); - announcementFont = new Font(game.FontName, fontSize); - ContextRecreated(); + Int32 fontSize = (Int32)(8 * Game_GetChatScale()); + Math_Clamp(fontSize, 8, 60); + Platform_MakeFont(&screen->ChatFont, &Game_FontName, fontSize, FONT_STYLE_NORMAL); + Platform_MakeFont(&screen->ChatUrlFont, &Game_FontName, fontSize, FONT_STYLE_UNDERLINE); - game.Events.ChatReceived += ChatReceived; - game.Events.ChatFontChanged += ChatFontChanged; - game.Events.ColourCodeChanged += ColourCodeChanged; - game.Graphics.ContextLost += ContextLost; - game.Graphics.ContextRecreated += ContextRecreated; + fontSize = (Int32)(16 * Game_GetChatScale()); + Math_Clamp(fontSize, 8, 60); + Platform_MakeFont(&screen->AnnouncementFont, &Game_FontName, fontSize, FONT_STYLE_NORMAL); + ChatScreen_ContextRecreated(elem); + + Event_RegisterChat(&ChatEvents_ChatReceived, screen, ChatScreen_ChatReceived); + Event_RegisterVoid(&ChatEvents_FontChanged, screen, ChatScreen_FontChanged); + Event_RegisterInt32(&ChatEvents_ColCodeChanged, screen, ChatScreen_ColCodeChanged); + Event_RegisterVoid(&GfxEvents_ContextLost, screen, ChatScreen_ContextLost); + Event_RegisterVoid(&GfxEvents_ContextRecreated, screen, ChatScreen_ContextRecreated); } void ChatScreen_ConstructWidgets(ChatScreen* screen) { ChatInputWidget_Create(&screen->Input, &screen->ChatFont); - Widget_SetLocation(&screen->Input.Base, ANCHOR_LEFT_OR_TOP, ANCHOR_BOTTOM_OR_RIGHT, 5, 5); + Widget_SetLocation(&screen->Input.Base, ANCHOR_MIN, ANCHOR_MAX, 5, 5); + altText = new SpecialInputWidget(game, chatFont, input); altText.Init(); UpdateAltTextY(); - status = new TextGroupWidget(game, 5, chatFont, chatUrlFont) - .SetLocation(Anchor.BottomOrRight, Anchor.LeftOrTop, 0, 0); - status.Init(); + status = new TextGroupWidget(game, 5, chatFont, chatUrlFont); + Widget_SetLocation(&screen->Status.Base, ANCHOR_MAX, ANCHOR_MIN, 0, 0); + Widget_Init(&screen->Status); status.SetUsePlaceHolder(0, false); status.SetUsePlaceHolder(1, false); bottomRight = new TextGroupWidget(game, 3, chatFont, chatUrlFont) .SetLocation(Anchor.BottomOrRight, Anchor.BottomOrRight, 0, hud.BottomOffset + 15); - bottomRight.Init(); + Widget_Init(&screen->BottomRight); normalChat = new TextGroupWidget(game, chatLines, chatFont, chatUrlFont) .SetLocation(Anchor.LeftOrTop, Anchor.BottomOrRight, 10, hud.BottomOffset + 15); - normalChat.Init(); + Widget_Init(&screen->NormalChat); clientStatus = new TextGroupWidget(game, game.Chat.ClientStatus.Length, chatFont, chatUrlFont) .SetLocation(Anchor.LeftOrTop, Anchor.BottomOrRight, 10, hud.BottomOffset + 15); - clientStatus.Init(); + Widget_Init(&screen->ClientStatus); String empty = String_MakeNull(); TextWidget_Create(&screen->Announcement, &empty, &screen->AnnouncementFont); @@ -1173,7 +1180,6 @@ void ChatScreen_ConstructWidgets(ChatScreen* screen) { } void ChatScreen_SetInitialMessages(ChatScreen* screen) { - Chat chat = game.Chat; chatIndex = chat.Log.Count - Game_ChatLines; ResetChat(); status.SetText(2, chat.Status1.Text); @@ -1184,45 +1190,65 @@ void ChatScreen_SetInitialMessages(ChatScreen* screen) { bottomRight.SetText(1, chat.BottomRight2.Text); bottomRight.SetText(0, chat.BottomRight3.Text); announcement.SetText(chat.Announcement.Text); - for (int i = 0; i < chat.ClientStatus.Length; i++) { + + Int32 i; + for (i = 0; i < Array_NumElements(Chat_ClientStatus); i++) { clientStatus.SetText(i, chat.ClientStatus[i].Text); } - if (chatInInputBuffer != null) { + if (screen->ChatInInput.length > 0) { OpenTextInputBar(chatInInputBuffer); - chatInInputBuffer = null; + String_Clear(&screen->ChatInInput); } } void ChatScreen_Render(GuiElement* elem, Real64 delta) { - if (!Game_PureClassic) { - status.Render(delta); - } - bottomRight.Render(delta); + ChatScreen* screen = (ChatScreen*)elem; + if (!Game_PureClassic) { Widget_Render(&screen->Status, delta); } + Widget_Render(&screen->BottomRight, delta); CheckOtherStatuses(); UpdateChatYOffset(false); - RenderClientStatus(); - DateTime now = Platform_CurrentUTCTime(); - if (HandlesAllInput) { - normalChat.Render(delta); - } else { - RenderRecentChat(now, delta); - } - announcement.Render(delta); + Int32 i, y = clientStatus.Y + clientStatus.Height; + for (i = 0; i < clientStatus.Textures.Length; i++) { + Texture tex = clientStatus.Textures[i]; + if (tex.ID == NULL) continue; - if (HandlesAllInput) { - input.Render(delta); - if (altText.Active) { - altText.Render(delta); + y -= tex.Height; tex.Y = y; + Texture_Render(&tex); + } + + DateTime now = Platform_CurrentUTCTime(); + if (screen->Base.HandlesAllInput) { + Widget_Render(&screen->NormalChat, delta); + } else { + for (i = 0; i < normalChat.Textures.Length; i++) { + Texture tex = normalChat.Textures[i]; + Int32 logIdx = screen->ChatIndex + i; + if (tex.ID == NULL) continue; + if (logIdx < 0 || logIdx >= Chat_Log.Count) continue; + + DateTime received = game.Chat.Log[logIdx].Received; + if ((now - received).TotalSeconds <= 10) { + Texture_Render(&tex); + } } } - if (announcement.IsValid && (now - game.Chat.Announcement.Received).TotalSeconds > 5) - announcement.Dispose(); + Widget_Render(&screen->Announcement, delta); + if (screen->Base.HandlesAllInput) { + Widget_Render(&screen->Input, delta); + if (screen->AltText.Base.Active) { + Widget_Render(&screen->AltText, delta); + } + } + + if (screen->Announcement.Texture.ID != NULL && DateTime_MsBetween(&now, &Chat_Announcement.Received) > 5000) { + Widget_Free(&screen->Announcement); + } } -int lastDownloadStatus = int.MinValue; +Int32 lastDownloadStatus = int.MinValue; void ChatScreen_CheckOtherStatuses() { Request item = game.Downloader.CurrentItem; if (item == null || !(item.Identifier == "terrain" || item.Identifier == "texturePack")) { @@ -1231,7 +1257,7 @@ void ChatScreen_CheckOtherStatuses() { return; } - int progress = game.Downloader.CurrentItemProgress; + Int32 progress = game.Downloader.CurrentItemProgress; if (progress == lastDownloadStatus) return; lastDownloadStatus = progress; SetFetchStatus(progress); @@ -1253,51 +1279,23 @@ void ChatScreen_SetFetchStatus(Int32 progress) { status.SetText(1, &str); } -void ChatScreen_RenderRecentChat(DateTime now, double delta) { - for (int i = 0; i < normalChat.Textures.Length; i++) { - Texture texture = normalChat.Textures[i]; - int logIdx = chatIndex + i; +void ChatScreen_RenderBackground(ChatScreen* screen) { + Int32 minIndex = Math.Min(0, game.Chat.Log.Count - chatLines); + Int32 height = chatIndex == minIndex ? normalChat.GetUsedHeight() : normalChat.Height; - if (texture.ID == NULL) continue; - if (logIdx < 0 || logIdx >= Chat_Log.Count) continue; + Int32 y = normalChat.Y + normalChat.Height - height - 5; + Int32 x = normalChat.X - 5; + Int32 width = max(clientStatus.Width, normalChat.Width) + 10; - DateTime received = game.Chat.Log[logIdx].Received; - if ((now - received).TotalSeconds <= 10) { - texture.Render(game.Graphics); - } - } -} - -void ChatScreen_RenderClientStatus() { - int y = clientStatus.Y + clientStatus.Height; - for (int i = 0; i < clientStatus.Textures.Length; i++) { - Texture texture = clientStatus.Textures[i]; - if (texture.ID == NULL) continue; - - y -= texture.Height; - texture.Y = y; - Texture_Render(&texture); - } -} - -void ChatScreen_RenderBackground() { - int minIndex = Math.Min(0, game.Chat.Log.Count - chatLines); - int height = chatIndex == minIndex ? normalChat.GetUsedHeight() : normalChat.Height; - - int y = normalChat.Y + normalChat.Height - height - 5; - int x = normalChat.X - 5; - int width = Math.Max(clientStatus.Width, normalChat.Width) + 10; - - int boxHeight = height + clientStatus.GetUsedHeight(); + Int32 boxHeight = height + clientStatus.GetUsedHeight(); if (boxHeight > 0) { PackedCol backCol = PACKEDCOL_CONST(0, 0, 0, 127); game.Graphics.Draw2DQuad(x, y, width, boxHeight + 10, backCol); } } -int inputOldHeight = -1; -void ChatScreen_UpdateChatYOffset(bool force) { - int height = InputUsedHeight; +void ChatScreen_UpdateChatYOffset(ChatScreen* screen, bool force) { + Int32 height = InputUsedHeight; if (force || height != inputOldHeight) { clientStatus.YOffset = Math.Max(hud.BottomOffset + 15, height); clientStatus.Reposition(); @@ -1308,104 +1306,112 @@ void ChatScreen_UpdateChatYOffset(bool force) { } } -void ColourCodeChanged(void* obj, UInt8 code) { +void ChatScreen_ColCodeChanged(void* obj, Int32 code) { + ChatScreen* screen = (ChatScreen*)obj; if (Gfx_LostContext) return; - altText.UpdateColours(); - Recreate(normalChat, code); Recreate(status, code); - Recreate(bottomRight, code); Recreate(clientStatus, code); + SpecialInputWidget_UpdateCols(&screen->AltText); + ChatScreen_Recreate(normalChat, code); + ChatScreen_Recreate(status, code); + ChatScreen_Recreate(bottomRight, code); + ChatScreen_Recreate(clientStatus, code); input.Recreate(); } void ChatScreen_Recreate(TextGroupWidget* group, UInt8 code) { - for (int i = 0; i < group->LinesCount; i++) { - string line = group.lines[i]; - if (line == null) continue; + Int32 i, j; + for (i = 0; i < group->LinesCount; i++) { + String line = group.lines[i]; /* TODO: Can't use UNSAFE_GET here because SetText later*/ + if (line.length == 0) continue; - for (int j = 0; j < line.Length - 1; j++) { - if (line[j] == '&' && line[j + 1] == code) { - group.SetText(i, line); break; + for (j = 0; j < line.length - 1; j++) { + if (line.buffer[j] == '&' && line.buffer[j + 1] == code) { + TextGroupWidget_SetText(group, i, &line); + break; } } } } -void ChatScreen_ChatReceived(void* obj, UInt8 msgType) { - MessageType type = e.Type; +void ChatScreen_ChatReceived(void* obj, String* msg, UInt8 type) { if (Gfx_LostContext) return; + ChatScreen* screen = (ChatScreen*)obj; - if (type == MessageType.Normal) { - chatIndex++; + if (type == MSG_TYPE_NORMAL) { + screen->ChatIndex++; if (Game_ChatLines == 0) return; - List chat = game.Chat.Log; - normalChat.PushUpAndReplaceLast(chat[chatIndex + chatLines - 1].Text); - } else if (type >= MessageType.Status1 && type <= MessageType.Status3) { - status.SetText(2 + (int)(type - MessageType.Status1), e.Text); - } else if (type >= MessageType.BottomRight1 && type <= MessageType.BottomRight3) { - bottomRight.SetText(2 - (int)(type - MessageType.BottomRight1), e.Text); - } else if (type == MessageType.Announcement) { - announcement.SetText(e.Text); - } else if (type >= MessageType.ClientStatus1 && type <= MessageType.ClientStatus3) { - clientStatus.SetText((int)(type - MessageType.ClientStatus1), e.Text); - UpdateChatYOffset(true); + Int32 index = screen->ChatIndex + (Game_ChatLines - 1); + String msg = StringsBuffer_UNSAFE_Get(&Chat_Log, index); + normalChat.PushUpAndReplaceLast(&msg); + } else if (type >= MSG_TYPE_STATUS_1 && type <= MSG_TYPE_STATUS_3) { + status.SetText(2 + (type - MSG_TYPE_STATUS_1), msg); + } else if (type >= MSG_TYPE_BOTTOMRIGHT_1 && type <= MSG_TYPE_BOTTOMRIGHT_3) { + bottomRight.SetText(2 - (type - MSG_TYPE_BOTTOMRIGHT_1), msg); + } else if (type == MSG_TYPE_ANNOUNCEMENT) { + TextWidget_SetText(&screen->Announcement, msg); + } else if (type >= MSG_TYPE_CLIENTSTATUS_1 && type <= MSG_TYPE_CLIENTSTATUS_3) { + clientStatus.SetText((type - MSG_TYPE_CLIENTSTATUS_1), msg); + ChatScreen_UpdateChatYOffset(screen, true); } } -void ChatScreen_Dispose() { - ContextLost(); - chatFont.Dispose(); - chatUrlFont.Dispose(); - announcementFont.Dispose(); +void ChatScreen_Free(GuiElement* elem) { + ChatScreen* screen = (ChatScreen*)elem; + ChatScreen_ContextLost(elem); + Platform_FreeFont(&screen->ChatFont); + Platform_FreeFont(&screen->ChatUrlFont); + Platform_FreeFont(&screen->AnnouncementFont); - game.Events.ChatReceived -= ChatReceived; - game.Events.ChatFontChanged -= ChatFontChanged; - game.Events.ColourCodeChanged -= ColourCodeChanged; - game.Graphics.ContextLost -= ContextLost; - game.Graphics.ContextRecreated -= ContextRecreated; + Event_UnregisterChat(&ChatEvents_ChatReceived, screen, ChatScreen_ChatReceived); + Event_UnregisterVoid(&ChatEvents_FontChanged, screen, ChatScreen_FontChanged); + Event_UnregisterInt32(&ChatEvents_ColCodeChanged, screen, ChatScreen_ColCodeChanged); + Event_UnregisterVoid(&GfxEvents_ContextLost, screen, ChatScreen_ContextLost); + Event_UnregisterVoid(&GfxEvents_ContextRecreated, screen, ChatScreen_ContextRecreated); } -void ChatScreen_ContextLost() { - if (HandlesAllInput) { - chatInInputBuffer = input.Text.ToString(); - game.CursorVisible = false; - } else { - chatInInputBuffer = null; +void ChatScreen_ContextLost(void* obj) { + ChatScreen* screen = (ChatScreen*)obj; + String_Clear(&screen->ChatInInput); + if (screen->Base.HandlesAllInput) { + String_AppendString(&screen->ChatInInput, &screen->Input.Text); + Game_SetCursorVisible(false); } - normalChat.Dispose(); - input.Dispose(); - altText.Dispose(); - status.Dispose(); - bottomRight.Dispose(); - clientStatus.Dispose(); - announcement.Dispose(); + Widget_Free(&screen->NormalChat); + Widget_Free(&screen->Input); + Widget_Free(&screen->AltText); + Widget_Free(&screen->Status); + Widget_Free(&screen->BottomRight); + Widget_Free(&screen->ClientStatus); + Widget_Free(&screen->Announcement); } -void ChatScreen_ContextRecreated() { - ConstructWidgets(); - SetInitialMessages(); +void ChatScreen_ContextRecreated(void* obj) { + ChatScreen* screen = (ChatScreen*)obj; + ChatScreen_ConstructWidgets(screen); + ChatScreen_SetInitialMessages(screen); } -void ChatScreen_ChatFontChanged(void* obj) { - if (!game.Drawer2D.UseBitmappedChat) return; +void ChatScreen_FontChanged(void* obj) { + if (!Drawer2D_UseBitmappedChat) return; Recreate(); - UpdateChatYOffset(true); + ChatScreen_UpdateChatYOffset(true); } -void ChatScreen_OnResize(int width, int height) { +void ChatScreen_OnResize(void* obj) { bool active = altText != null && altText.Active; Recreate(); altText.SetActive(active); } -void ResetChat() { - normalChat.Dispose(); - List chat = game.Chat.Log; - - for (int i = chatIndex; i < chatIndex + chatLines; i++) { - if (i >= 0 && i < chat.Count) { - normalChat.PushUpAndReplaceLast(chat[i].Text); +void ResetChat(ChatScreen* screen) { + Widget_Free(&screen->NormalChat); + Int32 i; + for (i = screen->ChatIndex; i < screen->ChatIndex + Game_ChatLines; i++) { + if (i >= 0 && i < Chat_Log.Count) { + String msg = StringsBuffer_UNSAFE_Get(&Chat_Log, i); + normalChat.PushUpAndReplaceLast(&msg); } } } @@ -1440,7 +1446,7 @@ void ChatScreen_AppendTextToInput(string text) { bool ChatScreen_HandlesKeyDown(Key key) { suppressNextPress = false; - if (HandlesAllInput) { // text input bar + if (HandlesAllInput) { /* text input bar */ if (key == game.Mapping(KeyBind.SendChat) || key == Key_KeypadEnter || key == game.Mapping(KeyBind.PauseOrExit)) { SetHandlesAllInput(false); game.CursorVisible = false; @@ -1452,16 +1458,16 @@ bool ChatScreen_HandlesKeyDown(Key key) { input.EnterInput(); altText.SetActive(false); - // Do we need to move all chat down? - int resetIndex = game.Chat.Log.Count - chatLines; + /* Do we need to move all chat down? */ + Int32 resetIndex = game.Chat.Log.Count - chatLines; if (chatIndex != resetIndex) { chatIndex = ClampIndex(resetIndex); ResetChat(); } } else if (key == Key_PageUp) { - ScrollHistoryBy(-chatLines); + ScrollHistoryBy(-Game_ChatLines); } else if (key == Key_PageDown) { - ScrollHistoryBy(chatLines); + ScrollHistoryBy(+Game_ChatLines); } else { input.HandlesKeyDown(key); UpdateAltTextY(); @@ -1469,7 +1475,7 @@ bool ChatScreen_HandlesKeyDown(Key key) { return key < Key_F1 || key > Key_F35; } - if (key == game.Mapping(KeyBind.Chat)) { + if (key == KeyBind_Get(KeyBind_Chat)) { OpenTextInputBar(""); } else if (key == Key_Slash) { OpenTextInputBar("/"); @@ -1482,8 +1488,10 @@ bool ChatScreen_HandlesKeyDown(Key key) { bool ChatScreen_HandlesKeyUp(Key key) { if (!HandlesAllInput) return false; - if (game.Server.SupportsFullCP437 && key == game.Input.Keys[KeyBind.ExtInput]) { - if (game.window.Focused) altText.SetActive(!altText.Active); + if (ServerConnection_SupportsFullCP437 && key == KeyBind_Get(KeyBind_ExtInput)) { + if (Window_GetFocused()) { + altText.SetActive(!altText.Active); + } } return true; } @@ -1491,13 +1499,13 @@ bool ChatScreen_HandlesKeyUp(Key key) { float chatAcc; bool ChatScreen_HandlesMouseScroll(float delta) { if (!HandlesAllInput) return false; - int steps = Utils.AccumulateWheelDelta(ref chatAcc, delta); + Int32 steps = Utils.AccumulateWheelDelta(ref chatAcc, delta); ScrollHistoryBy(-steps); return true; } -bool ChatScreen_HandlesMouseDown(int mouseX, int mouseY, MouseButton button) { - if (!HandlesAllInput || game.HideGui) return false; +bool ChatScreen_HandlesMouseDown(Int32 mouseX, Int32 mouseY, MouseButton button) { + if (!HandlesAllInput || Game_HideGui) return false; if (!normalChat.Bounds.Contains(mouseX, mouseY)) { if (altText.Active && altText.Bounds.Contains(mouseX, mouseY)) { @@ -1509,14 +1517,15 @@ bool ChatScreen_HandlesMouseDown(int mouseX, int mouseY, MouseButton button) { return true; } - int height = normalChat.GetUsedHeight(); - int y = normalChat.Y + normalChat.Height - height; - if (GuiElement.Contains(normalChat.X, y, normalChat.Width, height, mouseX, mouseY)) + Int32 height = normalChat.GetUsedHeight(); + Int32 y = normalChat.Y + normalChat.Height - height; + if (Gui_Contains(normalChat.X, y, normalChat.Width, height, mouseX, mouseY)) { return HandlesChatClick(mouseX, mouseY); + } return false; } -bool ChatScreen_HandlesChatDown(int mouseX, int mouseY) { +bool ChatScreen_HandlesChatDown(Int32 mouseX, Int32 mouseY) { string text = normalChat.GetSelected(mouseX, mouseY); if (text == null) return false; string url = Utils.StripColours(text); @@ -1546,33 +1555,33 @@ void ChatScreen_AppendUrl(Overlay urlOverlay, bool always) { input.Append(urlOverlay.Metadata); } -int ChatScreen_ClampIndex(int index) { - int maxIndex = game.Chat.Log.Count - chatLines; - int minIndex = Math.Min(0, maxIndex); +Int32 ChatScreen_ClampIndex(Int32 index) { + Int32 maxIndex = game.Chat.Log.Count - chatLines; + Int32 minIndex = min(0, maxIndex); Utils.Clamp(ref index, minIndex, maxIndex); return index; } -void ChatScreen_ScrollHistoryBy(int delta) { - int newIndex = ClampIndex(chatIndex + delta); - if (newIndex == chatIndex) return; +void ChatScreen_ScrollHistoryBy(ChatScreen* screen, Int32 delta) { + Int32 newIndex = ChatScreen_ClampIndex(screen->ChatIndex + delta); + if (newIndex == screen->ChatIndex) return; - chatIndex = newIndex; + screen->ChatIndex = newIndex; ResetChat(); } -int ChatScreen_InputUsedHeight { - get{ return altText.Height == 0 ? input.Height + 20 : (game.Height - altText.Y + 5); } +Int32 ChatScreen_InputUsedHeight(ChatScreen* screen) { + return altText.Height == 0 ? input.Height + 20 : (game.Height - altText.Y + 5); } -void ChatScreen_UpdateAltTextY() { - int height = Math.Max(input.Height + input.YOffset, hud.BottomOffset); +void ChatScreen_UpdateAltTextY(ChatScreen* screen) { + Int32 height = Math.Max(input.Height + input.YOffset, hud.BottomOffset); height += input.YOffset; altText.texture.Y1 = game.Height - (height + altText.texture.Height); altText.Y = altText.texture.Y; } -void ChatScreen_SetHandlesAllInput(bool handles) { - HandlesAllInput = handles; - game.Gui.hudScreen.HandlesAllInput = handles; +void ChatScreen_SetHandlesAllInput(ChatScreen* screen, bool handles) { + screen->Base.HandlesAllInput = handles; + Gui_HUD->HandlesAllInput = handles; } \ No newline at end of file diff --git a/src/Client/Utils.c b/src/Client/Utils.c index f68a4d21e..053194c41 100644 --- a/src/Client/Utils.c +++ b/src/Client/Utils.c @@ -7,7 +7,7 @@ bool DateTime_IsLeapYear(Int32 year) { } UInt16 DateTime_TotalDays[13] = { 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334, 365 }; -Int64 DateTime_TotalMilliseconds(DateTime* time) { +Int64 DateTime_TotalMs(DateTime* time) { /* Days from before this year */ Int32 days = 365 * (time->Year - 1), i; /* Only need to check leap years for whether days need adding */ @@ -29,9 +29,9 @@ Int64 DateTime_TotalMilliseconds(DateTime* time) { return seconds * DATETIME_MILLISECS_PER_SECOND + time->Milli; } -Int64 DateTime_MillisecondsBetween(DateTime* start, DateTime* end) { - Int64 msStart = DateTime_TotalMilliseconds(start); - Int64 msEnd = DateTime_TotalMilliseconds(end); +Int64 DateTime_MsBetween(DateTime* start, DateTime* end) { + Int64 msStart = DateTime_TotalMs(start); + Int64 msEnd = DateTime_TotalMs(end); return msEnd - msStart; } diff --git a/src/Client/Utils.h b/src/Client/Utils.h index d7416a601..39a99e3c3 100644 --- a/src/Client/Utils.h +++ b/src/Client/Utils.h @@ -23,8 +23,8 @@ typedef struct DateTime_ { #define DATETIME_SECONDS_PER_HOUR (60 * 60) #define DATETIME_SECONDS_PER_DAY (60 * 60 * 24) -Int64 DateTime_TotalMilliseconds(DateTime* time); -Int64 DateTime_MillisecondsBetween(DateTime* start, DateTime* end); +Int64 DateTime_TotalMs(DateTime* time); +Int64 DateTime_MsBetween(DateTime* start, DateTime* end); UInt32 Utils_ParseEnum(STRING_PURE String* text, UInt32 defValue, const UInt8** names, UInt32 namesCount); bool Utils_IsValidInputChar(UInt8 c, bool supportsCP437); diff --git a/src/Client/Widgets.c b/src/Client/Widgets.c index 3ee08ca73..475d611b6 100644 --- a/src/Client/Widgets.c +++ b/src/Client/Widgets.c @@ -16,7 +16,7 @@ #include "Event.h" #include "Chat.h" -void Widget_SetLocation(Widget* widget, Anchor horAnchor, Anchor verAnchor, Int32 xOffset, Int32 yOffset) { +void Widget_SetLocation(Widget* widget, UInt8 horAnchor, UInt8 verAnchor, Int32 xOffset, Int32 yOffset) { widget->HorAnchor = horAnchor; widget->VerAnchor = verAnchor; widget->XOffset = xOffset; widget->YOffset = yOffset; widget->Reposition(widget); @@ -481,7 +481,7 @@ bool HotbarWidget_HandlesMouseScroll(GuiElement* elem, Real32 delta) { void HotbarWidget_Create(HotbarWidget* widget) { Widget_Init(&widget->Base); widget->Base.HorAnchor = ANCHOR_CENTRE; - widget->Base.VerAnchor = ANCHOR_BOTTOM_OR_RIGHT; + widget->Base.VerAnchor = ANCHOR_MAX; widget->Base.Base.Init = HotbarWidget_Init; widget->Base.Base.Render = HotbarWidget_Render; @@ -1083,7 +1083,7 @@ void SpecialInputWidget_SetActive(SpecialInputWidget* widget, bool active) { void SpecialInputWidget_Create(SpecialInputWidget* widget, FontDesc* font, SpecialInputAppendFunc appendFunc, void* appendObj) { Widget_Init(&widget->Base); - widget->Base.VerAnchor = ANCHOR_BOTTOM_OR_RIGHT; + widget->Base.VerAnchor = ANCHOR_MAX; widget->Font = *font; widget->AppendFunc = appendFunc; widget->AppendObj = appendObj; @@ -1853,8 +1853,8 @@ void ChatInputWidget_OnPressedEnter(GuiElement* elem) { widget->TypingLogPos = Chat_InputLog.Count; /* Index of newest entry + 1. */ String empty = String_MakeNull(); - Chat_AddOf(&empty, MESSAGE_TYPE_CLIENTSTATUS_2); - Chat_AddOf(&empty, MESSAGE_TYPE_CLIENTSTATUS_3); + Chat_AddOf(&empty, MSG_TYPE_CLIENTSTATUS_2); + Chat_AddOf(&empty, MSG_TYPE_CLIENTSTATUS_3); InputWidget_OnPressedEnter(elem); } @@ -1938,7 +1938,7 @@ void ChatInputWidget_TabKey(GuiElement* elem) { String part = String_UNSAFE_Substring(&input->Text, start, (end + 1) - start); String empty = String_MakeNull(); - Chat_AddOf(&empty, MESSAGE_TYPE_CLIENTSTATUS_3); + Chat_AddOf(&empty, MSG_TYPE_CLIENTSTATUS_3); EntityID matches[TABLIST_MAX_NAMES]; UInt32 i, matchesCount = 0; @@ -1976,7 +1976,7 @@ void ChatInputWidget_TabKey(GuiElement* elem) { String_AppendString(&str, &match); String_Append(&str, ' '); } - Chat_AddOf(&str, MESSAGE_TYPE_CLIENTSTATUS_3); + Chat_AddOf(&str, MSG_TYPE_CLIENTSTATUS_3); } } @@ -2320,7 +2320,7 @@ void PlayerListWidget_Init(GuiElement* elem) { String msg = String_FromConst("Connected players:"); TextWidget_Create(&widget->Overview, &msg, &widget->Font); - Widget_SetLocation(&widget->Overview.Base, ANCHOR_CENTRE, ANCHOR_LEFT_OR_TOP, 0, 0); + Widget_SetLocation(&widget->Overview.Base, ANCHOR_CENTRE, ANCHOR_MIN, 0, 0); Event_RegisterEntityID(&TabListEvents_Added, widget, PlayerListWidget_TabEntryAdded); Event_RegisterEntityID(&TabListEvents_Changed, widget, PlayerListWidget_TabEntryChanged); @@ -2413,7 +2413,7 @@ Int32 TextGroupWidget_CalcY(TextGroupWidget* widget, Int32 index, Int32 newHeigh Texture* textures = widget->Textures; Int32 deltaY = newHeight - textures[index].Height; - if (widget->Base.VerAnchor == ANCHOR_LEFT_OR_TOP) { + if (widget->Base.VerAnchor == ANCHOR_MIN) { y = widget->Base.Y; for (i = 0; i < index; i++) { y += textures[i].Height; diff --git a/src/Client/Widgets.h b/src/Client/Widgets.h index 5a16cd40c..dbbac6811 100644 --- a/src/Client/Widgets.h +++ b/src/Client/Widgets.h @@ -11,7 +11,7 @@ Copyright 2014-2017 ClassicalSharp | Licensed under BSD-3 */ -void Widget_SetLocation(Widget* widget, Anchor horAnchor, Anchor verAnchor, Int32 xOffset, Int32 yOffset); +void Widget_SetLocation(Widget* widget, UInt8 horAnchor, UInt8 verAnchor, Int32 xOffset, Int32 yOffset); typedef struct TextWidget_ { Widget Base; diff --git a/src/Client/WinWindow.c b/src/Client/WinWindow.c index 7ebf7c39a..b78a2ce8f 100644 --- a/src/Client/WinWindow.c +++ b/src/Client/WinWindow.c @@ -583,8 +583,7 @@ void Window_SetVisible(bool visible) { BringWindowToTop(win_Handle); SetForegroundWindow(win_Handle); } - } - else { + } else { ShowWindow(win_Handle, SW_HIDE); } } diff --git a/src/Client/Window.h b/src/Client/Window.h index 61c2deb27..a137a1923 100644 --- a/src/Client/Window.h +++ b/src/Client/Window.h @@ -35,98 +35,56 @@ OTHER DEALINGS IN THE SOFTWARE. */ -/* The window is in its normal state. */ #define WINDOW_STATE_NORMAL 0 -/* The window is minimized to the taskbar (also known as 'iconified'). */ #define WINDOW_STATE_MINIMISED 1 -/* The window covers the whole working area, which includes the desktop but not the taskbar and/or panels. */ #define WINDOW_STATE_MAXIMISED 2 -/* The window covers the whole screen, including all taskbars and/or panels. */ #define WINDOW_STATE_FULLSCREEN 3 -/* Creates a new window. */ void Window_Create(Int32 x, Int32 y, Int32 width, Int32 height, STRING_REF String* title, DisplayDevice* device); -/* Gets the current contents of the clipboard. */ void Window_GetClipboardText(STRING_TRANSIENT String* value); -/* Sets the current contents of the clipboard. */ void Window_SetClipboardText(STRING_PURE String* value); -/* TODO: IMPLEMENT THIS -/* Sets the icon of this window. */ -/*void Window_SetIcon(Bitmap* bmp); -*/ +/* TODO: IMPLEMENT THIS void Window_SetIcon(Bitmap* bmp); */ -/* Gets whether this window has input focus. */ bool Window_GetFocused(void); -/* Gets whether whether this window is visible. */ bool Window_GetVisible(void); -/* Sets whether this window is visible. */ void Window_SetVisible(bool visible); -/* Gets whether this window has been created and has not been destroyed. */ bool Window_GetExists(void); -/* Gets the handle of this window. */ void* Window_GetWindowHandle(void); -/* Gets the WindowState of this window. */ UInt8 Window_GetWindowState(void); -/* Sets the WindowState of this window. */ void Window_SetWindowState(UInt8 value); -/* Gets the external bounds of this window, in screen coordinates. -External bounds include title bar, borders and drawing area of the window. */ Rectangle2D Window_GetBounds(void); -/* Sets the external bounds of this window, in screen coordinates. */ void Window_SetBounds(Rectangle2D rect); -/* Returns the location of this window on the desktop. */ Point2D Window_GetLocation(void); -/* Sets the location of this window on the desktop. */ void Window_SetLocation(Point2D point); -/* Gets the external size of this window. */ Size2D Window_GetSize(void); -/* Sets the external size of this window. */ void Window_SetSize(Size2D size); -/* Gets the internal bounds of this window, in client coordinates. -Internal bounds include the drawing area of the window, but exclude the titlebar and window borders.*/ Rectangle2D Window_GetClientRectangle(void); -/* Sets the internal bounds of this window, in client coordinates. */ void Window_SetClientRectangle(Rectangle2D rect); -/* Gets the internal size of this window. */ Size2D Window_GetClientSize(void); -/* Sets the internal size of this window. */ void Window_SetClientSize(Size2D size); -/* Closes this window. */ void Window_Close(void); -/* Processes pending window events. */ void Window_ProcessEvents(void); /* Transforms the specified point from screen to client coordinates. */ Point2D Window_PointToClient(Point2D point); /* Transforms the specified point from client to screen coordinates. */ Point2D Window_PointToScreen(Point2D point); -/* Gets the cursor position in screen coordinates. */ Point2D Window_GetDesktopCursorPos(void); -/* Sets the cursor position in screen coordinates. */ void Window_SetDesktopCursorPos(Point2D point); -/* Gets whether the cursor is visible in the window. */ bool Window_GetCursorVisible(void); -/* Sets whether the cursor is visible in the window. */ void Window_SetCursorVisible(bool visible); #if !USE_DX -/* Initalises the OpenGL context, and makes it current. */ void GLContext_Init(GraphicsMode mode); -/* Updates OpenGL context on a window resize. */ void GLContext_Update(void); -/* Frees the OpenGL context. */ void GLContext_Free(void); #define GLContext_IsInvalidAddress(ptr) (ptr == (void*)0 || ptr == (void*)1 || ptr == (void*)-1 || ptr == (void*)2) -/* Retrieves the address of the given OpenGL function. */ void* GLContext_GetAddress(const UInt8* function); -/* Swaps the front and back buffer of the OpenGL context. */ void GLContext_SwapBuffers(void); -/* Gets whether the OpenGL context has VSync enabled. */ bool GLContext_GetVSync(void); -/* Sets whether the OpenGL context uses VSync. */ void GLContext_SetVSync(bool enabled); #endif #endif \ No newline at end of file