mirror of
https://github.com/ClassiCube/ClassiCube.git
synced 2025-09-17 11:35:08 -04:00
Fix a bunch of stuff
This commit is contained in:
parent
20e9adbd24
commit
8a25708f6f
@ -13,6 +13,28 @@
|
|||||||
#include "Funcs.h"
|
#include "Funcs.h"
|
||||||
#include "Block.h"
|
#include "Block.h"
|
||||||
|
|
||||||
|
#define CHAT_LOGTIMES_DEF_ELEMS 256
|
||||||
|
#define CHAT_LOGTIMES_EXPAND_ELEMS 512
|
||||||
|
Int64 Chat_DefaultLogTimes[CHAT_LOGTIMES_DEF_ELEMS];
|
||||||
|
Int64* Chat_LogTimes = &Chat_DefaultLogTimes;
|
||||||
|
UInt32 Chat_LogTimesCount = CHAT_LOGTIMES_DEF_ELEMS, Chat_LogTimesUsed;
|
||||||
|
|
||||||
|
void Chat_GetLogTime(UInt32 index, Int64* timeMs) {
|
||||||
|
if (index >= Chat_LogTimesUsed) ErrorHandler_Fail("Tries to get time past LogTime end");
|
||||||
|
*timeMs = Chat_LogTimes[index];
|
||||||
|
}
|
||||||
|
|
||||||
|
void Chat_AppendLogTime(void) {
|
||||||
|
DateTime now = Platform_CurrentUTCTime();
|
||||||
|
UInt32 count = Chat_LogTimesUsed;
|
||||||
|
|
||||||
|
if (count == Chat_LogTimesCount) {
|
||||||
|
StringsBuffer_Resize(&Chat_LogTimes, &Chat_LogTimesCount, sizeof(Int64),
|
||||||
|
CHAT_LOGTIMES_DEF_ELEMS, CHAT_LOGTIMES_EXPAND_ELEMS);
|
||||||
|
}
|
||||||
|
Chat_LogTimes[Chat_LogTimesUsed++] = DateTime_TotalMs(&now);
|
||||||
|
}
|
||||||
|
|
||||||
void ChatLine_Make(ChatLine* line, STRING_TRANSIENT String* text) {
|
void ChatLine_Make(ChatLine* line, STRING_TRANSIENT String* text) {
|
||||||
String dst = String_InitAndClearArray(line->Buffer);
|
String dst = String_InitAndClearArray(line->Buffer);
|
||||||
String_AppendString(&dst, text);
|
String_AppendString(&dst, text);
|
||||||
@ -113,6 +135,7 @@ void Chat_AddOf(STRING_PURE String* text, Int32 msgType) {
|
|||||||
if (msgType == MSG_TYPE_NORMAL) {
|
if (msgType == MSG_TYPE_NORMAL) {
|
||||||
StringsBuffer_Add(&Chat_Log, text);
|
StringsBuffer_Add(&Chat_Log, text);
|
||||||
Chat_AppendLog(text);
|
Chat_AppendLog(text);
|
||||||
|
Chat_AppendLogTime();
|
||||||
} else if (msgType >= MSG_TYPE_STATUS_1 && msgType <= MSG_TYPE_STATUS_3) {
|
} else if (msgType >= MSG_TYPE_STATUS_1 && msgType <= MSG_TYPE_STATUS_3) {
|
||||||
ChatLine_Make(&Chat_Status[msgType - MSG_TYPE_STATUS_1], text);
|
ChatLine_Make(&Chat_Status[msgType - MSG_TYPE_STATUS_1], text);
|
||||||
} else if (msgType >= MSG_TYPE_BOTTOMRIGHT_1 && msgType <= MSG_TYPE_BOTTOMRIGHT_3) {
|
} else if (msgType >= MSG_TYPE_BOTTOMRIGHT_1 && msgType <= MSG_TYPE_BOTTOMRIGHT_3) {
|
||||||
@ -511,6 +534,7 @@ void Chat_Reset(void) {
|
|||||||
|
|
||||||
void Chat_Free(void) {
|
void Chat_Free(void) {
|
||||||
commands_count = 0;
|
commands_count = 0;
|
||||||
|
if (Chat_LogTimes != Chat_DefaultLogTimes) Platform_MemFree(Chat_LogTimes);
|
||||||
|
|
||||||
StringsBuffer_Free(&Chat_Log);
|
StringsBuffer_Free(&Chat_Log);
|
||||||
StringsBuffer_Free(&Chat_InputLog);
|
StringsBuffer_Free(&Chat_InputLog);
|
||||||
|
@ -22,6 +22,7 @@
|
|||||||
typedef struct ChatLine_ { UInt8 Buffer[String_BufferSize(STRING_SIZE)]; DateTime Received; } ChatLine;
|
typedef struct ChatLine_ { UInt8 Buffer[String_BufferSize(STRING_SIZE)]; DateTime Received; } ChatLine;
|
||||||
ChatLine Chat_Status[3], Chat_BottomRight[3], Chat_ClientStatus[3], Chat_Announcement;
|
ChatLine Chat_Status[3], Chat_BottomRight[3], Chat_ClientStatus[3], Chat_Announcement;
|
||||||
StringsBuffer Chat_Log, Chat_InputLog;
|
StringsBuffer Chat_Log, Chat_InputLog;
|
||||||
|
void Chat_GetLogTime(UInt32 index, Int64* timeMS);
|
||||||
|
|
||||||
IGameComponent Chat_MakeGameComponent(void);
|
IGameComponent Chat_MakeGameComponent(void);
|
||||||
void Chat_SetLogName(STRING_PURE String* name);
|
void Chat_SetLogName(STRING_PURE String* name);
|
||||||
|
@ -184,8 +184,7 @@ void Fcm_Load(Stream* stream) {
|
|||||||
#define NBT_TAG_COMPOUND 10
|
#define NBT_TAG_COMPOUND 10
|
||||||
#define NBT_TAG_INT32_ARRAY 11
|
#define NBT_TAG_INT32_ARRAY 11
|
||||||
|
|
||||||
/* supported utf8 codepoint can be up to 3 bytes big */
|
#define NBT_SMALL_SIZE STRING_SIZE
|
||||||
#define NBT_SMALL_SIZE (STRING_SIZE * 3)
|
|
||||||
struct NbtTag_;
|
struct NbtTag_;
|
||||||
typedef struct NbtTag_ {
|
typedef struct NbtTag_ {
|
||||||
struct NbtTag_* Parent;
|
struct NbtTag_* Parent;
|
||||||
@ -244,14 +243,23 @@ UInt8 NbtTag_U8_At(NbtTag* tag, Int32 i) {
|
|||||||
return tag->DataBig[i];
|
return tag->DataBig[i];
|
||||||
}
|
}
|
||||||
|
|
||||||
UInt32 Nbt_ReadString(Stream* stream, UInt8* buffer) {
|
UInt32 Nbt_ReadString(Stream* stream, UInt8* strBuffer) {
|
||||||
UInt16 nameLen = Stream_ReadUInt16_BE(stream);
|
UInt16 nameLen = Stream_ReadUInt16_BE(stream);
|
||||||
if (nameLen > NBT_SMALL_SIZE) ErrorHandler_Fail("NBT String too long");
|
if (nameLen > NBT_SMALL_SIZE * 4) ErrorHandler_Fail("NBT String too long");
|
||||||
|
UInt8 nameBuffer[NBT_SMALL_SIZE * 4];
|
||||||
|
Stream_Read(stream, nameBuffer, nameLen);
|
||||||
|
|
||||||
/* TODO: this is wrong, we need to UTF8 decode here*/
|
/* TODO: Check how slow reading strings this way is */
|
||||||
encoding.utf8.decode(buffer, nameLen);
|
Stream memStream;
|
||||||
Stream_Read(stream, buffer, nameLen);
|
Stream_ReadonlyMemory(&memStream, nameBuffer, nameLen, &stream->Name);
|
||||||
return nameLen;
|
UInt16 codepoint;
|
||||||
|
|
||||||
|
UInt32 i;
|
||||||
|
for (i = 0; i < NBT_SMALL_SIZE; i++) {
|
||||||
|
if (!Stream_ReadUtf8Char(&memStream, &codepoint)) break;
|
||||||
|
strBuffer[i] = Convert_UnicodeToCP437(codepoint);
|
||||||
|
}
|
||||||
|
return i;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Nbt_ReadTag(UInt8 typeId, bool readTagName, Stream* stream, NbtTag* parent) {
|
void Nbt_ReadTag(UInt8 typeId, bool readTagName, Stream* stream, NbtTag* parent) {
|
||||||
|
@ -18,6 +18,16 @@
|
|||||||
#include "Chat.h"
|
#include "Chat.h"
|
||||||
#include "Platform.h"
|
#include "Platform.h"
|
||||||
|
|
||||||
|
UInt8 Game_UsernameBuffer[String_BufferSize(STRING_SIZE)];
|
||||||
|
extern String Game_Username = String_FromEmptyArray(Game_UsernameBuffer);
|
||||||
|
UInt8 Game_MppassBuffer[String_BufferSize(STRING_SIZE)];
|
||||||
|
extern String Game_Mppass = String_FromEmptyArray(Game_MppassBuffer);
|
||||||
|
|
||||||
|
UInt8 Game_IPAddressBuffer[String_BufferSize(STRING_SIZE)];
|
||||||
|
extern String Game_IPAddress = String_FromEmptyArray(Game_IPAddressBuffer);
|
||||||
|
UInt8 Game_FontNameBuffer[String_BufferSize(STRING_SIZE)];
|
||||||
|
extern String Game_FontName = String_FromEmptyArray(Game_FontNameBuffer);
|
||||||
|
|
||||||
Int32 Game_GetWindowScale(void) {
|
Int32 Game_GetWindowScale(void) {
|
||||||
Real32 windowScale = min(Game_Width / 640.0f, Game_Height / 480.0f);
|
Real32 windowScale = min(Game_Width / 640.0f, Game_Height / 480.0f);
|
||||||
return 1 + (Int32)windowScale;
|
return 1 + (Int32)windowScale;
|
||||||
|
@ -20,9 +20,9 @@ PickedPos Game_CameraClipPos;
|
|||||||
GfxResourceID Game_DefaultIb;
|
GfxResourceID Game_DefaultIb;
|
||||||
|
|
||||||
bool Game_UseCPEBlocks;
|
bool Game_UseCPEBlocks;
|
||||||
String Game_Username;
|
extern String Game_Username;
|
||||||
String Game_Mppass;
|
extern String Game_Mppass;
|
||||||
String Game_IPAddress;
|
extern String Game_IPAddress;
|
||||||
Int32 Game_Port;
|
Int32 Game_Port;
|
||||||
Int32 Game_ViewDistance;
|
Int32 Game_ViewDistance;
|
||||||
Int32 Game_MaxViewDistance;
|
Int32 Game_MaxViewDistance;
|
||||||
@ -51,7 +51,7 @@ bool Game_SmoothLighting;
|
|||||||
bool Game_ChatLogging;
|
bool Game_ChatLogging;
|
||||||
bool Game_AutoRotate;
|
bool Game_AutoRotate;
|
||||||
bool Game_SmoothCamera;
|
bool Game_SmoothCamera;
|
||||||
String Game_FontName;
|
extern String Game_FontName;
|
||||||
Int32 Game_ChatLines;
|
Int32 Game_ChatLines;
|
||||||
bool Game_ClickableChat;
|
bool Game_ClickableChat;
|
||||||
bool Game_HideGui;
|
bool Game_HideGui;
|
||||||
|
@ -332,7 +332,8 @@ void InputHandler_MouseWheel(void* obj, Real32 delta) {
|
|||||||
if (!hotbar && Camera_Active->Zoom(delta)) return;
|
if (!hotbar && Camera_Active->Zoom(delta)) return;
|
||||||
if (InputHandler_DoFovZoom(delta) || !Inventory_CanChangeHeldBlock) return;
|
if (InputHandler_DoFovZoom(delta) || !Inventory_CanChangeHeldBlock) return;
|
||||||
|
|
||||||
Gui.hudScreen.hotbar.HandlesMouseScroll(delta);
|
Widget* hotbarW = HUDScreen_GetHotbar(Gui_HUD);
|
||||||
|
Elem_HandlesMouseScroll(hotbarW, delta);
|
||||||
}
|
}
|
||||||
|
|
||||||
void InputHandler_MouseMove(void* obj, Int32 xDelta, Int32 yDelta) {
|
void InputHandler_MouseMove(void* obj, Int32 xDelta, Int32 yDelta) {
|
||||||
|
@ -43,6 +43,10 @@ UInt32 Platform_FilePosition(void* file);
|
|||||||
UInt32 Platform_FileLength(void* file);
|
UInt32 Platform_FileLength(void* file);
|
||||||
|
|
||||||
void Platform_ThreadSleep(UInt32 milliseconds);
|
void Platform_ThreadSleep(UInt32 milliseconds);
|
||||||
|
typedef void Platform_ThreadFunc(void);
|
||||||
|
void* Platform_ThreadStart(Platform_ThreadFunc* func);
|
||||||
|
/* Frees handle to thread - NOT THE THREAD ITSELF */
|
||||||
|
void Platform_ThreadFreeHandle(void* handle);
|
||||||
|
|
||||||
void Platform_MakeFont(FontDesc* desc, STRING_PURE String* fontName, UInt16 size, UInt16 style);
|
void Platform_MakeFont(FontDesc* desc, STRING_PURE String* fontName, UInt16 size, UInt16 style);
|
||||||
void Platform_FreeFont(FontDesc* desc);
|
void Platform_FreeFont(FontDesc* desc);
|
||||||
|
@ -1093,16 +1093,16 @@ void ChatScreen_Render(GuiElement* elem, Real64 delta) {
|
|||||||
if (screen->HandlesAllInput) {
|
if (screen->HandlesAllInput) {
|
||||||
Elem_Render(&screen->Chat, delta);
|
Elem_Render(&screen->Chat, delta);
|
||||||
} else {
|
} else {
|
||||||
|
Int64 nowMS = DateTime_TotalMs(&now);
|
||||||
|
/* Only render recent chat */
|
||||||
for (i = 0; i < screen->Chat.LinesCount; i++) {
|
for (i = 0; i < screen->Chat.LinesCount; i++) {
|
||||||
Texture tex = screen->Chat.Textures[i];
|
Texture tex = screen->Chat.Textures[i];
|
||||||
Int32 logIdx = screen->ChatIndex + i;
|
Int32 logIdx = screen->ChatIndex + i;
|
||||||
if (tex.ID == NULL) continue;
|
if (tex.ID == NULL) continue;
|
||||||
if (logIdx < 0 || logIdx >= Chat_Log.Count) continue;
|
if (logIdx < 0 || logIdx >= Chat_Log.Count) continue;
|
||||||
|
|
||||||
DateTime received = game.Chat.Log[logIdx].Received;
|
Int64 received; Chat_GetLogTime(logIdx, &received);
|
||||||
if (DateTime_MsBetween(&received, &now) <= 10000) {
|
if ((nowMS - received) <= 10 * 1000) Texture_Render(&tex);
|
||||||
Texture_Render(&tex);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1114,7 +1114,7 @@ void ChatScreen_Render(GuiElement* elem, Real64 delta) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (screen->Announcement.Texture.ID != NULL && DateTime_MsBetween(&Chat_Announcement.Received, &now) > 5000) {
|
if (screen->Announcement.Texture.ID != NULL && DateTime_MsBetween(&Chat_Announcement.Received, &now) > 5 * 1000) {
|
||||||
Elem_Free(&screen->Announcement);
|
Elem_Free(&screen->Announcement);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1376,6 +1376,11 @@ void HUDScreen_AppendInput(Screen* hud, STRING_PURE String* text) {
|
|||||||
InputWidget_AppendString(&widget->Base, text);
|
InputWidget_AppendString(&widget->Base, text);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Widget* HUDScreen_GetHotbar(Screen* hud) {
|
||||||
|
HUDScreen* screen = (HUDScreen*)hud;
|
||||||
|
return &screen->Hotbar;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/*########################################################################################################################*
|
/*########################################################################################################################*
|
||||||
*----------------------------------------------------DisconnectScreen-----------------------------------------------------*
|
*----------------------------------------------------DisconnectScreen-----------------------------------------------------*
|
||||||
|
@ -13,13 +13,11 @@ Screen* LoadingScreen_MakeInstance(STRING_PURE String* title, STRING_PURE String
|
|||||||
Screen* GeneratingScreen_MakeInstance(void);
|
Screen* GeneratingScreen_MakeInstance(void);
|
||||||
Screen* HUDScreen_MakeInstance(void);
|
Screen* HUDScreen_MakeInstance(void);
|
||||||
IGameComponent HUDScreen_MakeComponent(void);
|
IGameComponent HUDScreen_MakeComponent(void);
|
||||||
void HUDScreen_OpenInput(Screen* hud, STRING_PURE String* text);
|
|
||||||
void HUDScreen_AppendInput(Screen* hud, STRING_PURE String* text);
|
|
||||||
Screen* DisconnectScreen_MakeInstance(STRING_PURE String* title, STRING_PURE String* message);
|
Screen* DisconnectScreen_MakeInstance(STRING_PURE String* title, STRING_PURE String* message);
|
||||||
|
|
||||||
Screen* OptionsGroupScreen_MakeInstance(void);
|
|
||||||
Screen* PauseScreen_MakeInstance(void);
|
|
||||||
|
|
||||||
/* Raw pointer to inventory screen. DO NOT USE THIS. Use InventoryScreen_MakeInstance() */
|
/* Raw pointer to inventory screen. DO NOT USE THIS. Use InventoryScreen_MakeInstance() */
|
||||||
extern Screen* InventoryScreen_UNSAFE_RawPointer;
|
extern Screen* InventoryScreen_UNSAFE_RawPointer;
|
||||||
|
void HUDScreen_OpenInput(Screen* hud, STRING_PURE String* text);
|
||||||
|
void HUDScreen_AppendInput(Screen* hud, STRING_PURE String* text);
|
||||||
|
Widget* HUDScreen_GetHotbar(Screen* hud);
|
||||||
#endif
|
#endif
|
@ -52,7 +52,15 @@ void ServerConnection_BeginGeneration(Int32 width, Int32 height, Int32 length, I
|
|||||||
|
|
||||||
Gui_SetNewScreen(GeneratingScreen_MakeInstance());
|
Gui_SetNewScreen(GeneratingScreen_MakeInstance());
|
||||||
Gen_Width = width; Gen_Height = height; Gen_Length = length; Gen_Seed = seed;
|
Gen_Width = width; Gen_Height = height; Gen_Length = length; Gen_Seed = seed;
|
||||||
gen.GenerateAsync();
|
|
||||||
|
void* threadHandle;
|
||||||
|
if (vanilla) {
|
||||||
|
threadHandle = Platform_ThreadStart(&NotchyGen_Generate);
|
||||||
|
} else {
|
||||||
|
threadHandle = Platform_ThreadStart(&FlatgrassGen_Generate);
|
||||||
|
}
|
||||||
|
/* don't leak thread handle here */
|
||||||
|
Platform_ThreadFreeHandle(threadHandle);
|
||||||
}
|
}
|
||||||
|
|
||||||
void ServerConnection_EndGeneration(void) {
|
void ServerConnection_EndGeneration(void) {
|
||||||
|
@ -236,45 +236,47 @@ void Stream_WriteUInt32_BE(Stream* stream, UInt32 value) {
|
|||||||
/*########################################################################################################################*
|
/*########################################################################################################################*
|
||||||
*--------------------------------------------------Read/Write strings-----------------------------------------------------*
|
*--------------------------------------------------Read/Write strings-----------------------------------------------------*
|
||||||
*#########################################################################################################################*/
|
*#########################################################################################################################*/
|
||||||
|
bool Stream_ReadUtf8Char(Stream* stream, UInt16* codepoint) {
|
||||||
|
UInt32 read = 0;
|
||||||
|
UInt8 header;
|
||||||
|
ReturnCode code = stream->Read(stream, &header, 1, &read);
|
||||||
|
|
||||||
|
if (read == 0) return false; /* end of stream */
|
||||||
|
if (!ErrorHandler_Check(code)) { Stream_Fail(stream, code, "reading utf8 from"); }
|
||||||
|
/* Header byte is just the raw codepoint (common case) */
|
||||||
|
if (header <= 0x7F) { *codepoint = header; return true; }
|
||||||
|
|
||||||
|
/* Header byte encodes variable number of following bytes */
|
||||||
|
/* The remaining bits of the header form first part of the character */
|
||||||
|
Int32 byteCount = 0, i;
|
||||||
|
for (i = 7; i >= 0; i--) {
|
||||||
|
if ((header & (1 << i)) != 0) {
|
||||||
|
byteCount++;
|
||||||
|
header &= (UInt8)~(1 << i);
|
||||||
|
} else {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
*codepoint = header;
|
||||||
|
for (i = 0; i < byteCount - 1; i++) {
|
||||||
|
*codepoint <<= 6;
|
||||||
|
/* Top two bits of each are always 10 */
|
||||||
|
*codepoint |= (UInt16)(Stream_ReadUInt8(stream) & 0x3F);
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
bool Stream_ReadLine(Stream* stream, STRING_TRANSIENT String* text) {
|
bool Stream_ReadLine(Stream* stream, STRING_TRANSIENT String* text) {
|
||||||
String_Clear(text);
|
String_Clear(text);
|
||||||
for (;;) {
|
for (;;) {
|
||||||
UInt32 byteCount = 0, read = 0;
|
UInt16 codepoint;
|
||||||
UInt8 header;
|
if (!Stream_ReadUtf8Char(stream, &codepoint)) return false;
|
||||||
|
|
||||||
ReturnCode code = stream->Read(stream, &header, 1, &read);
|
|
||||||
if (read == 0) return false; /* end of stream */
|
|
||||||
if (!ErrorHandler_Check(code)) { Stream_Fail(stream, code, "reading line from"); }
|
|
||||||
|
|
||||||
/* Header byte encodes variable number of following bytes */
|
|
||||||
/* The remaining bits of the header form first part of the character */
|
|
||||||
Int32 bit;
|
|
||||||
for (bit = 7; bit >= 0; bit--) {
|
|
||||||
if ((header & (1 << bit)) != 0) {
|
|
||||||
byteCount++;
|
|
||||||
header &= (UInt8)~(1 << bit);
|
|
||||||
} else {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
UInt16 codeword;
|
|
||||||
if (byteCount == 0) {
|
|
||||||
codeword = (UInt8)header;
|
|
||||||
} else {
|
|
||||||
codeword = header;
|
|
||||||
Int32 i;
|
|
||||||
for (i = 0; i < byteCount - 1; i++) {
|
|
||||||
codeword <<= 6;
|
|
||||||
/* Top two bits of each are always 10 */
|
|
||||||
codeword |= (UInt16)(Stream_ReadUInt8(stream) & 0x3F);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Handle \r\n or \n line endings */
|
/* Handle \r\n or \n line endings */
|
||||||
if (codeword == '\r') continue;
|
if (codepoint == '\r') continue;
|
||||||
if (codeword == '\n') return true;
|
if (codepoint == '\n') return true;
|
||||||
String_Append(text, Convert_UnicodeToCP437(codeword));
|
String_Append(text, Convert_UnicodeToCP437(codepoint));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -57,6 +57,8 @@ void Stream_WriteUInt32_LE(Stream* stream, UInt32 value);
|
|||||||
void Stream_WriteUInt32_BE(Stream* stream, UInt32 value);
|
void Stream_WriteUInt32_BE(Stream* stream, UInt32 value);
|
||||||
#define Stream_WriteInt32_BE(stream, value) Stream_WriteUInt32_BE(stream, (UInt32)(value))
|
#define Stream_WriteInt32_BE(stream, value) Stream_WriteUInt32_BE(stream, (UInt32)(value))
|
||||||
|
|
||||||
|
/* Reads a UTF8 encoded character from the given stream. Returns false if end of stream. */
|
||||||
|
bool Stream_ReadUtf8Char(Stream* stream, UInt16* codepoint);
|
||||||
/* Reads a line of UTF8 encoding text from the given stream. Returns false if end of stream. */
|
/* Reads a line of UTF8 encoding text from the given stream. Returns false if end of stream. */
|
||||||
bool Stream_ReadLine(Stream* stream, STRING_TRANSIENT String* text);
|
bool Stream_ReadLine(Stream* stream, STRING_TRANSIENT String* text);
|
||||||
/* Writes a line of UTF8 encoded text to the given stream. */
|
/* Writes a line of UTF8 encoded text to the given stream. */
|
||||||
|
@ -574,10 +574,10 @@ void StringsBuffer_Init(StringsBuffer* buffer) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void StringsBuffer_Free(StringsBuffer* buffer) {
|
void StringsBuffer_Free(StringsBuffer* buffer) {
|
||||||
if (buffer->TextBufferElems > STRINGSBUFFER_BUFFER_DEF_SIZE) {
|
if (buffer->TextBuffer != buffer->DefaultBuffer) {
|
||||||
Platform_MemFree(buffer->TextBuffer);
|
Platform_MemFree(buffer->TextBuffer);
|
||||||
}
|
}
|
||||||
if (buffer->FlagsBufferElems > STRINGSBUFFER_FLAGS_DEF_ELEMS) {
|
if (buffer->FlagsBuffer != buffer->DefaultFlags) {
|
||||||
Platform_MemFree(buffer->FlagsBuffer);
|
Platform_MemFree(buffer->FlagsBuffer);
|
||||||
}
|
}
|
||||||
StringsBuffer_UNSAFE_Reset(buffer);
|
StringsBuffer_UNSAFE_Reset(buffer);
|
||||||
@ -603,20 +603,23 @@ String StringsBuffer_UNSAFE_Get(StringsBuffer* buffer, UInt32 index) {
|
|||||||
return String_Init(&buffer->TextBuffer[offset], (UInt16)len, (UInt16)len);
|
return String_Init(&buffer->TextBuffer[offset], (UInt16)len, (UInt16)len);
|
||||||
}
|
}
|
||||||
|
|
||||||
void StringsBuffer_ResizeArray(void** buffer, UInt32 curSize, UInt32 newSize, bool reallocing) {
|
void StringsBuffer_Resize(void** buffer, UInt32* elems, UInt32 elemSize, UInt32 defElems, UInt32 expandElems) {
|
||||||
/* We use a statically allocated buffer initally, so can't realloc first time */
|
/* We use a statically allocated buffer initally, so can't realloc first time */
|
||||||
void* dst;
|
void* dst;
|
||||||
void* cur = *buffer;
|
void* cur = *buffer;
|
||||||
|
|
||||||
if (!reallocing) {
|
UInt32 curElems = *elems, newSize = (curElems + expandElems) * elemSize;
|
||||||
|
if (curElems <= defElems) {
|
||||||
dst = Platform_MemAlloc(newSize);
|
dst = Platform_MemAlloc(newSize);
|
||||||
if (dst == NULL) ErrorHandler_Fail("Failed allocating memory for StringsBuffer");
|
if (dst == NULL) ErrorHandler_Fail("Failed allocating memory for StringsBuffer");
|
||||||
Platform_MemCpy(dst, cur, curSize);
|
Platform_MemCpy(dst, cur, curElems * elemSize);
|
||||||
} else {
|
} else {
|
||||||
dst = Platform_MemRealloc(cur, newSize);
|
dst = Platform_MemRealloc(cur, newSize);
|
||||||
if (dst == NULL) ErrorHandler_Fail("Failed allocating memory for resizing StringsBuffer");
|
if (dst == NULL) ErrorHandler_Fail("Failed allocating memory for resizing StringsBuffer");
|
||||||
}
|
}
|
||||||
|
|
||||||
*buffer = dst;
|
*buffer = dst;
|
||||||
|
*elems = curElems + expandElems;
|
||||||
}
|
}
|
||||||
|
|
||||||
void StringsBuffer_Add(StringsBuffer* buffer, STRING_PURE String* text) {
|
void StringsBuffer_Add(StringsBuffer* buffer, STRING_PURE String* text) {
|
||||||
@ -625,11 +628,8 @@ void StringsBuffer_Add(StringsBuffer* buffer, STRING_PURE String* text) {
|
|||||||
if (buffer->FlagsBufferElems == 0) {
|
if (buffer->FlagsBufferElems == 0) {
|
||||||
ErrorHandler_Fail("StringsBuffer not properly initalised");
|
ErrorHandler_Fail("StringsBuffer not properly initalised");
|
||||||
}
|
}
|
||||||
|
StringsBuffer_Resize(&buffer->FlagsBuffer, &buffer->FlagsBufferElems, sizeof(UInt32),
|
||||||
UInt32 curElemSize = buffer->FlagsBufferElems * sizeof(UInt32);
|
STRINGSBUFFER_FLAGS_DEF_ELEMS, STRINGSBUFFER_FLAGS_EXPAND_ELEMS);
|
||||||
UInt32 newElemsSize = (buffer->FlagsBufferElems + STRINGSBUFFER_FLAGS_EXPAND_ELEMS) * sizeof(UInt32);
|
|
||||||
bool reallocingElems = buffer->FlagsBufferElems > STRINGSBUFFER_FLAGS_DEF_ELEMS;
|
|
||||||
StringsBuffer_ResizeArray(&buffer->FlagsBuffer, curElemSize, newElemsSize, reallocingElems);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (text->length > STRINGSBUFFER_LEN_MASK) {
|
if (text->length > STRINGSBUFFER_LEN_MASK) {
|
||||||
@ -638,10 +638,8 @@ void StringsBuffer_Add(StringsBuffer* buffer, STRING_PURE String* text) {
|
|||||||
|
|
||||||
UInt32 textOffset = buffer->UsedElems;
|
UInt32 textOffset = buffer->UsedElems;
|
||||||
if (textOffset + text->length >= buffer->TextBufferElems) {
|
if (textOffset + text->length >= buffer->TextBufferElems) {
|
||||||
UInt32 curTextSize = buffer->TextBufferElems;
|
StringsBuffer_Resize(&buffer->TextBuffer, &buffer->TextBufferElems, sizeof(UInt8),
|
||||||
UInt32 newTextSize = buffer->TextBufferElems + STRINGSBUFFER_BUFFER_EXPAND_SIZE;
|
STRINGSBUFFER_BUFFER_DEF_SIZE, STRINGSBUFFER_BUFFER_EXPAND_SIZE);
|
||||||
bool reallocingText = buffer->TextBufferElems > STRINGSBUFFER_BUFFER_DEF_SIZE;
|
|
||||||
StringsBuffer_ResizeArray(&buffer->FlagsBuffer, curTextSize, newTextSize, reallocingText);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (text->length > 0) {
|
if (text->length > 0) {
|
||||||
|
@ -114,6 +114,7 @@ void StringsBuffer_Free(StringsBuffer* buffer);
|
|||||||
void StringsBuffer_UNSAFE_Reset(StringsBuffer* buffer);
|
void StringsBuffer_UNSAFE_Reset(StringsBuffer* buffer);
|
||||||
void StringsBuffer_Get(StringsBuffer* buffer, UInt32 index, STRING_TRANSIENT String* text);
|
void StringsBuffer_Get(StringsBuffer* buffer, UInt32 index, STRING_TRANSIENT String* text);
|
||||||
STRING_REF String StringsBuffer_UNSAFE_Get(StringsBuffer* buffer, UInt32 index);
|
STRING_REF String StringsBuffer_UNSAFE_Get(StringsBuffer* buffer, UInt32 index);
|
||||||
|
void StringsBuffer_Resize(void** buffer, UInt32* elems, UInt32 elemSize, UInt32 defElems, UInt32 expandElems);
|
||||||
void StringsBuffer_Add(StringsBuffer* buffer, STRING_PURE String* text);
|
void StringsBuffer_Add(StringsBuffer* buffer, STRING_PURE String* text);
|
||||||
void StringsBuffer_Remove(StringsBuffer* buffer, UInt32 index);
|
void StringsBuffer_Remove(StringsBuffer* buffer, UInt32 index);
|
||||||
Int32 StringsBuffer_Compare(StringsBuffer* buffer, UInt32 idxA, UInt32 idxB);
|
Int32 StringsBuffer_Compare(StringsBuffer* buffer, UInt32 idxA, UInt32 idxB);
|
||||||
|
@ -228,6 +228,26 @@ void Platform_ThreadSleep(UInt32 milliseconds) {
|
|||||||
Sleep(milliseconds);
|
Sleep(milliseconds);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DWORD WINAPI Platform_ThreadStartCallback(LPVOID lpParam) {
|
||||||
|
Platform_ThreadFunc* func = (Platform_ThreadFunc*)lpParam;
|
||||||
|
(*func)();
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
void* Platform_ThreadStart(Platform_ThreadFunc* func) {
|
||||||
|
void* handle = CreateThread(NULL, 0, Platform_ThreadStartCallback, func, 0, NULL);
|
||||||
|
if (handle == NULL) {
|
||||||
|
ErrorHandler_FailWithCode(GetLastError(), "Creating thread");
|
||||||
|
}
|
||||||
|
return handle;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Platform_ThreadFreeHandle(void* handle) {
|
||||||
|
if (!CloseHandle((HANDLE)handle)) {
|
||||||
|
ErrorHandler_FailWithCode(GetLastError(), "Freeing thread handle");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void Platform_MakeFont(FontDesc* desc, STRING_PURE String* fontName, UInt16 size, UInt16 style) {
|
void Platform_MakeFont(FontDesc* desc, STRING_PURE String* fontName, UInt16 size, UInt16 style) {
|
||||||
desc->Size = size;
|
desc->Size = size;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user