Port HotbarWidget to C.

This commit is contained in:
UnknownShadow200 2017-10-17 19:31:46 +11:00
parent 08c9173bae
commit 0c51e70380
16 changed files with 216 additions and 45 deletions

View File

@ -11,6 +11,7 @@
#include "ExtMath.h"
#include "Platform.h"
#include "Funcs.h"
#include "Utils.h"
GfxResourceID borders_sidesVb = -1, borders_edgesVb = -1;
GfxResourceID borders_edgeTexId, borders_sideTexId;
@ -70,7 +71,7 @@ void BordersRenderer_MakeTexture(GfxResourceID* texId, TextureLoc* lastTexLoc, B
}
void BordersRenderer_CalculateRects(Int32 extent) {
extent = Math_AdjViewDist(extent);
extent = Utils_AdjViewDist(extent);
borders_rects[0] = Rectangle2D_Make(-extent, -extent, extent + World_Width + extent, extent);
borders_rects[1] = Rectangle2D_Make(-extent, World_Length, extent + World_Width + extent, extent);

View File

@ -13,6 +13,7 @@
#include "Vectors.h"
#include "World.h"
#include "Builder.h"
#include "Utils.h"
void ChunkInfo_Reset(ChunkInfo* chunk, Int32 x, Int32 y, Int32 z) {
chunk->CentreX = (UInt16)(x + 8);
@ -163,7 +164,7 @@ void ChunkUpdater_OnNewMapLoaded(void) {
Int32 ChunkUpdater_AdjustViewDist(Real32 dist) {
if (dist < CHUNK_SIZE) dist = CHUNK_SIZE;
Int32 viewDist = Math_AdjViewDist(dist);
Int32 viewDist = Utils_AdjViewDist(dist);
return (viewDist + 24) * (viewDist + 24);
}

View File

@ -226,6 +226,7 @@
<ClInclude Include="GameStructs.h" />
<ClInclude Include="TerrainAtlas.h" />
<ClInclude Include="TreeGen.h" />
<ClInclude Include="Utils.h" />
<ClInclude Include="WeatherRenderer.h" />
<ClInclude Include="PackedCol.h" />
<ClInclude Include="Funcs.h" />
@ -305,6 +306,7 @@
<ClCompile Include="TerrainAtlas.c" />
<ClCompile Include="Texture.c" />
<ClCompile Include="TreeGen.c" />
<ClCompile Include="Utils.c" />
<ClCompile Include="Vectors.c" />
<ClCompile Include="VertexStructs.c" />
<ClCompile Include="WeatherRenderer.c" />

View File

@ -365,7 +365,10 @@
</ClInclude>
<ClInclude Include="Input.h">
<Filter>Header Files\Platform</Filter>
</ClInclude>
</ClInclude>
<ClInclude Include="Utils.h">
<Filter>Header Files\Utils</Filter>
</ClInclude>
</ItemGroup>
<ItemGroup>
<ClCompile Include="Noise.c">
@ -562,6 +565,9 @@
</ClCompile>
<ClCompile Include="Input.c">
<Filter>Source Files\Platform</Filter>
</ClCompile>
</ClCompile>
<ClCompile Include="Utils.c">
<Filter>Source Files\Utils</Filter>
</ClCompile>
</ItemGroup>
</Project>

View File

@ -10,6 +10,7 @@
#include "Platform.h"
#include "SkyboxRenderer.h"
#include "Events.h"
#include "Utils.h"
GfxResourceID env_cloudsVb = -1, env_skyVb = -1, env_cloudsTex = -1;
GfxResourceID env_cloudVertices, env_skyVertices;
@ -197,7 +198,7 @@ void EnvRenderer_DrawCloudsY(Int32 x1, Int32 z1, Int32 x2, Int32 z2, Int32 y, In
}
void EnvRenderer_RebuildClouds(Int32 extent, Int32 axisSize) {
extent = Math_AdjViewDist(extent);
extent = Utils_AdjViewDist(extent);
Int32 x1 = -extent, x2 = World_Width + extent;
Int32 z1 = -extent, z2 = World_Length + extent;
env_cloudVertices = Math_CountVertices(x2 - x1, z2 - z1, axisSize);
@ -216,7 +217,7 @@ void EnvRenderer_RebuildClouds(Int32 extent, Int32 axisSize) {
}
void EnvRenderer_RebuildSky(Int32 extent, Int32 axisSize) {
extent = Math_AdjViewDist(extent);
extent = Utils_AdjViewDist(extent);
Int32 x1 = -extent, x2 = World_Width + extent;
Int32 z1 = -extent, z2 = World_Length + extent;
env_skyVertices = Math_CountVertices(x2 - x1, z2 - z1, axisSize);

View File

@ -50,13 +50,9 @@ Int32 Math_NextPowOf2(Int32 value);
/* Returns whether the given value is a power of 2. */
bool Math_IsPowOf2(Int32 value);
Int32 Math_AccumulateWheelDelta(Real32* accmulator, Real32 delta);
/* Returns the number of vertices needed to subdivide a quad. */
#define Math_CountVertices(axis1Len, axis2Len, axisSize) (Math_CeilDiv(axis1Len, axisSize) * Math_CeilDiv(axis2Len, axisSize) * 4)
#define Math_AdjViewDist(value) ((Int32)(1.4142135f * (value)))
#define Math_Clamp(value, min, max)\
value = value < (min) ? (min) : value;\
value = value > (max) ? (max) : value;

View File

@ -116,7 +116,7 @@ Key KeyBind_Defaults[KeyBind_Count] = {
Key_Unknown, Key_Unknown, Key_F6, Key_AltLeft,
Key_F8, Key_G,
};
const UInt8** KeyBind_Names[KeyBind_Count] = {
const UInt8* KeyBind_Names[KeyBind_Count] = {
"Forward", "Back", "Left", "Right",
"Jump", "Respawn", "SetSpawn", "Chat",
"Inventory", "ToggleFog", "SendChat", "PauseOrExit",
@ -130,6 +130,7 @@ const UInt8** KeyBind_Names[KeyBind_Count] = {
Key KeyBind_Get(KeyBind binding) { return KeyBind_Keys[binding]; }
Key KeyBind_GetDefault(KeyBind binding) { return KeyBind_Defaults[binding]; }
bool KeyBind_GetPressed(KeyBind binding) { return Key_States[KeyBind_Keys[binding]]; }
#define KeyBind_MakeName(name) String_Clear(&name); String_AppendConst(&name, "key-"); String_AppendConst(&name, KeyBind_Names[i]);

View File

@ -139,6 +139,8 @@ typedef enum KeyBind_ {
Key KeyBind_Get(KeyBind binding);
/* Gets the default keyboard key that the given binding maps to. */
Key KeyBind_GetDefault(KeyBind binding);
/* Gets whether the keyboard key that the given maps to is currently pressed. */
bool KeyBind_GetPressed(KeyBind binding);
/* Sets the keyboard key that the given binding maps to. */
void KeyBind_Set(KeyBind binding, Key key);
/* Initalises and loads key bindings. */

View File

@ -8,6 +8,8 @@
Copyright 2014-2017 ClassicalSharp | Licensed under BSD-3
*/
/* Maximum number of vertices used to draw a block in isometric way. */
#define ISOMETRICDRAWER_MAXVERTICES 16
/* Sets up state for drawing a batch of isometric blocks. */
void IsometricDrawer_BeginBatch(VertexP3fT2fC4b* vertices, GfxResourceID vb);
/* Adds a block to the current batch. */

View File

@ -39,7 +39,7 @@ Int32 gl_compare[8] = { GL_ALWAYS, GL_NOTEQUAL, GL_NEVER, GL_LESS, GL_LEQUAL, GL
Int32 gl_fogModes[3] = { GL_LINEAR, GL_EXP, GL_EXP2 };
Int32 gl_matrixModes[3] = { GL_PROJECTION, GL_MODELVIEW, GL_TEXTURE };
void GL_CheckVboSupport() {
void GL_CheckVboSupport(void) {
String extensions = String_FromReadonly(glGetString(GL_EXTENSIONS));
String version = String_FromReadonly(glGetString(GL_VERSION));
Int32 major = (Int32)(version.buffer[0] - '0'); /* x.y. (and so forth) */

View File

@ -1,6 +1,7 @@
#include "Options.h"
#include "ExtMath.h"
#include "ErrorHandler.h"
#include "Utils.h"
UInt8 Options_KeysBuffer[String_BufferSize(26) * OPTIONS_COUNT];
UInt8 Options_ValuesBuffer[
@ -88,16 +89,9 @@ Real32 Options_GetFloat(const UInt8* key, Real32 min, Real32 max, Real32 defValu
}
UInt32 Options_GetEnum(const UInt8* key, UInt32 defValue, const UInt8** names, UInt32 namesCount) {
String str;
Real32 value;
String str;
if (!Options_TryGetValue(key, &str)) return defValue;
UInt32 i;
for (i = 0; i < namesCount; i++) {
String name = String_FromReadonly(names[i]);
if (String_CaselessEquals(&str, &name)) return i;
}
return defValue;
return Utils_ParseEnum(&str, defValue, names, namesCount);
}
void Options_Remove(Int32 i) {

19
src/Client/Utils.c Normal file
View File

@ -0,0 +1,19 @@
#include "Utils.h"
Int32 Utils_AccumulateWheelDelta(Real32* accmulator, Real32 delta) {
/* Some mice may use deltas of say (0.2, 0.2, 0.2, 0.2, 0.2) */
/* We must use rounding at final step, not at every intermediate step. */
*accmulator += delta;
Int32 steps = (Int32)*accmulator;
*accmulator -= steps;
return steps;
}
UInt32 Utils_ParseEnum(STRING_TRANSIENT String* text, UInt32 defValue, const UInt8** names, UInt32 namesCount) {
UInt32 i;
for (i = 0; i < namesCount; i++) {
String name = String_FromReadonly(names[i]);
if (String_CaselessEquals(text, &name)) return i;
}
return defValue;
}

11
src/Client/Utils.h Normal file
View File

@ -0,0 +1,11 @@
#ifndef CS_UTILS_H
#define CS_UTILS_H
#include "Typedefs.h"
#include "String.h"
Int32 Utils_AccumulateWheelDelta(Real32* accmulator, Real32 delta);
UInt32 Utils_ParseEnum(STRING_TRANSIENT String* text, UInt32 defValue, const UInt8** names, UInt32 namesCount);
#define Utils_AdjViewDist(value) ((Int32)(1.4142135f * (value)))
#endif

View File

@ -7,6 +7,8 @@
#include "Window.h"
#include "Inventory.h"
#include "IsometricDrawer.h"
#include "Utils.h"
#include "ModelCache.h"
void Widget_SetLocation(Widget* widget, Anchor horAnchor, Anchor verAnchor, Int32 xOffset, Int32 yOffset) {
widget->HorAnchor = horAnchor; widget->VerAnchor = verAnchor;
@ -254,7 +256,7 @@ bool ScrollbarWidget_HandlesMouseUp(GuiElement* elem, Int32 x, Int32 y, MouseBut
bool ScrollbarWidget_HandlesMouseScroll(GuiElement* elem, Real32 delta) {
ScrollbarWidget* widget = (ScrollbarWidget*)elem;
Int32 steps = Math_AccumulateWheelDelta(&widget->ScrollingAcc, delta);
Int32 steps = Utils_AccumulateWheelDelta(&widget->ScrollingAcc, delta);
widget->ScrollY -= steps;
ScrollbarWidget_ClampScrollY(widget);
return true;
@ -297,6 +299,152 @@ void ScrollbarWidget_ClampScrollY(ScrollbarWidget* widget) {
if (widget->ScrollY < 0) widget->ScrollY = 0;
}
void HotbarWidget_RenderHotbarOutline(HotbarWidget* widget) {
Widget* w = &widget->Base;
GfxResourceID texId = Game_UseClassicGui ? Gui_GuiClassicTex : Gui_GuiTex;
widget->BackTex.ID = texId;
Texture_Render(&widget->BackTex);
Int32 i = Inventory_SelectedIndex;
Int32 width = widget->ElemSize + widget->BorderSize;
Int32 x = (Int32)(w->X + widget->BarXOffset + width * i + widget->ElemSize / 2);
widget->SelTex.ID = texId;
widget->SelTex.X = (Int32)(x - widget->SelBlockSize / 2);
PackedCol white = PACKEDCOL_WHITE;
GfxCommon_Draw2DTexture(&widget->SelTex, white);
}
void HotbarWidget_RenderHotbarBlocks(HotbarWidget* widget) {
/* TODO: Should hotbar use its own VB? */
VertexP3fT2fC4b vertices[INVENTORY_BLOCKS_PER_HOTBAR * ISOMETRICDRAWER_MAXVERTICES];
IsometricDrawer_BeginBatch(vertices, ModelCache_Vb);
Widget* w = &widget->Base;
Int32 width = widget->ElemSize + widget->BorderSize;
UInt32 i;
for (i = 0; i < INVENTORY_BLOCKS_PER_HOTBAR; i++) {
BlockID block = Inventory_Get(i);
Int32 x = (Int32)(w->X + widget->BarXOffset + width * i + widget->ElemSize / 2);
Int32 y = (Int32)(w->Y + (w->Height - widget->BarHeight / 2));
Real32 scale = (widget->ElemSize * 13.5f / 16.0f) / 2.0f;
IsometricDrawer_DrawBatch(block, scale, x, y);
}
IsometricDrawer_EndBatch();
}
void HotbarWidget_RepositonBackgroundTexture(HotbarWidget* widget) {
Widget* w = &widget->Base;
TextureRec rec = TextureRec_FromPoints(0.0f, 0.0f, 182.0f / 256.0f, 22.0f / 256.0f);
widget->BackTex = Texture_FromRec(0, w->X, w->Y, w->Width, w->Height, rec);
}
void HotbarWidget_RepositionSelectionTexture(HotbarWidget* widget) {
Widget* w = &widget->Base;
Int32 hSize = (Int32)widget->SelBlockSize;
Real32 scale = Game_GetHotbarScale();
Int32 vSize = (Int32)(22.0f * scale);
Int32 y = w->Y + (w->Height - (Int32)(23.0f * scale));
TextureRec rec = TextureRec_FromPoints(0.0f, 22.0f / 256.0f, 24.0f / 256.0f, 22.0f / 256.0f);
widget->SelTex = Texture_FromRec(0, 0, y, hSize, vSize, rec);
}
void HotbarWidget_Reposition(Widget* elem) {
HotbarWidget* widget = (HotbarWidget*)elem;
Real32 scale = Game_GetHotbarScale();
widget->BarHeight = (Int32)(22 * scale);
elem->Width = (Int32)(182 * scale);
elem->Height = widget->BarHeight;
widget->SelBlockSize = (Real32)Math_Ceil(24.0f * scale);
widget->ElemSize = 16.0f * scale;
widget->BarXOffset = 3.1f * scale;
widget->BorderSize = 4.0f * scale;
elem->Reposition(elem);
HotbarWidget_RepositonBackgroundTexture(widget);
HotbarWidget_RepositionSelectionTexture(widget);
}
void HotbarWidget_Init(GuiElement* elem) {
Widget* widget = (Widget*)elem;
widget->Reposition(widget);
}
void HotbarWidget_Render(GuiElement* elem, Real64 delta) {
HotbarWidget* widget = (HotbarWidget*)elem;
HotbarWidget_RenderHotbarOutline(widget);
HotbarWidget_RenderHotbarBlocks(widget);
}
void HotbarWidget_Free(GuiElement* elem) { }
bool HotbarWidget_HandlesKeyDown(GuiElement* elem, Key key) {
if (key >= Key_1 && key <= Key_9) {
Int32 index = key - Key_1;
if (KeyBind_IsPressed(KeyBind_HotbarSwitching)) {
/* Pick from first to ninth row */
Inventory_SetOffset(index * INVENTORY_BLOCKS_PER_HOTBAR);
HotbarWidget* widget = (HotbarWidget*)elem;
widget->AltHandled = true;
} else {
Inventory_SetSelectedIndex(index);
}
return true;
}
return false;
}
bool HotbarWidget_HandlesKeyUp(GuiElement* elem, Key key) {
/* We need to handle these cases:
a) user presses alt then number
b) user presses alt
thus we only do case b) if case a) did not happen */
HotbarWidget* widget = (HotbarWidget*)elem;
if (key != KeyBind_Get(KeyBind_HotbarSwitching)) return false;
if (widget->AltHandled) { widget->AltHandled = false; return true; } /* handled already */
/* Alternate between first and second row */
Int32 index = Inventory_Offset == 0 ? 1 : 0;
Inventory_SetOffset(index * INVENTORY_BLOCKS_PER_HOTBAR);
return true;
}
bool HotbarWidget_HandlesMouseDown(GuiElement* elem, Int32 x, Int32 y, MouseButton btn) {
Widget* w = (Widget*)elem;
if (btn != MouseButton_Left || !Gui_Contains(w->X, w->Y, w->Width, w->Height, x, y)) return false;
InventoryScreen screen = game.Gui.ActiveScreen as InventoryScreen;
if (screen == null) return false;
HotbarWidget* widget = (HotbarWidget*)elem;
Int32 width = (Int32)(widget->ElemSize * widget->BorderSize);
Int32 height = Math_Ceil(widget->BarHeight);
UInt32 i;
for (i = 0; i < INVENTORY_BLOCKS_PER_HOTBAR; i++) {
Int32 winX = (Int32)(w->X + width * i);
Int32 winY = (Int32)(w->Y + (w->Height - height));
if (Gui_Contains(winX, winY, width, height, x, y)) {
Inventory_SetSelectedIndex(i);
return true;
}
}
return false;
}
void HotbarWidget_Create(HotbarWidget* widget) {
Widget_Init(&widget->Base);
widget->Base.HorAnchor = ANCHOR_CENTRE;
widget->Base.VerAnchor = ANCHOR_BOTTOM_OR_RIGHT;
}
Int32 Table_X(TableWidget* widget) { return widget->Base.X - 5 - 10; }
Int32 Table_Y(TableWidget* widget) { return widget->Base.Y - 5 - 30; }
Int32 Table_Width(TableWidget* widget) {
@ -313,7 +461,7 @@ PackedCol Table_TopCol = PACKEDCOL_CONST( 34, 34, 34, 168);
PackedCol Table_BottomCol = PACKEDCOL_CONST( 57, 57, 104, 202);
PackedCol Table_TopSelCol = PACKEDCOL_CONST(255, 255, 255, 142);
PackedCol Table_BottomSelCol = PACKEDCOL_CONST(255, 255, 255, 192);
#define TABLE_MAX_VERTICES (8 * 10 * (4 * 4))
#define TABLE_MAX_VERTICES (8 * 10 * ISOMETRICDRAWER_MAXVERTICES)
bool TableWidget_GetCoords(TableWidget* widget, Int32 i, Int32* winX, Int32* winY) {
Int32 x = i % widget->ElementsPerRow, y = i / widget->ElementsPerRow;
@ -373,20 +521,6 @@ void TableWidget_UpdatePos(TableWidget* widget) {
TableWidget_UpdateDescTexPos(widget);
}
void TableWidget_UpdateDescTexPos(TableWidget* widget) {
widget->DescTex.X = widget->Base.X + widget->Base.Width / 2 - widget->DescTex.Width / 2;
widget->DescTex.Y = widget->Base.Y - widget->DescTex.Height - 5;
}
void TableWidget_UpdatePos(TableWidget* widget) {
Int32 rowsDisplayed = min(TABLE_MAX_ROWS_DISPLAYED, widget->ElementsCount);
widget->Base.Width = widget->BlockSize * widget->ElementsPerRow;
widget->Base.Height = widget->BlockSize * rowsDisplayed;
widget->Base.X = Game_Width / 2 - widget->Base.Width / 2;
widget->Base.Y = Game_Height / 2 - widget->Base.Height / 2;
TableWidget_UpdateDescTexPos(widget);
}
#define TABLE_NAME_LEN 128
void TableWidget_RecreateDescTex(TableWidget* widget) {
if (widget->SelectedIndex == widget->LastCreatedIndex) return;
@ -402,7 +536,7 @@ void TableWidget_RecreateDescTex(TableWidget* widget) {
TableWidget_MakeBlockDesc(&desc, block);
DrawTextArgs args;
DrawTextArgs_Make(&args, &desc, font, true);
DrawTextArgs_Make(&args, &desc, widget->Font, true);
widget->DescTex = Drawer2D_MakeTextTexture(&args, 0, 0);
TableWidget_UpdateDescTexPos(widget);
}
@ -664,4 +798,4 @@ void TableWidget_OnInventoryChanged(TableWidget* widget) {
widget->Scroll.ScrollY = widget->SelectedIndex / widget->ElementsPerRow;
ScrollbarWidget_ClampScrollY(&widget->Scroll);
TableWidget_RecreateDescTex(widget);
}
}

View File

@ -92,11 +92,12 @@ typedef struct SpecialInputTab_ {
Int32 ItemsPerRow;
Int32 CharsPerItem;
} SpecialInputTab;
void SpecialInputTab_Init(String title, Int32 itemsPerRow, Int32 charsPerItem, String contents);
void SpecialInputTab_Init(SpecialInputTab* tab, STRING_REF String title,
Int32 itemsPerRow, Int32 charsPerItem, STRING_REF String contents);
typedef struct SpecialInputWidget_ {
Widget Base;
Texture texture;
Texture Tex;
void* Font;
SpecialInputAppendFunc AppendFunc;
Size2D ElementSize;
@ -181,7 +182,7 @@ typedef struct TextGroupWidget_ {
void TextGroupWidget_Create(TextGroupWidget* widget, Int32 linesCount, void* font, void* underlineFont);
void TextGroupWidget_SetUsePlaceHolder(TextGroupWidget* widget, Int32 index, bool placeHolder);
void TextGroupWidget_PushUpAndReplaceLast(TextGroupWidget* widget, STRING_TRANSIENT String* text);
Int32 TextGroupWidget_GetUsedHeight();
Int32 TextGroupWidget_GetUsedHeight(TextGroupWidget* widget);
void TextGroupWidget_GetSelected(TextGroupWidget* widget, String* dstText, Int32 mouseX, Int32 mouseY);
void TextGroupWidget_SetText(TextGroupWidget* widget, int index, String* text);
void TextGroupWidget_SetText(TextGroupWidget* widget, Int32 index, String* text);
#endif

View File

@ -109,7 +109,7 @@ Key Window_MapKey(WPARAM key) {
return Key_F1 + (key - VK_F1);
}
if (key >= '0' && key <= '9') {
return Key_Number0 + (key - '0');
return Key_0 + (key - '0');
}
if (key >= 'A' && key <= 'Z') {
return Key_A + (key - 'A');
@ -659,7 +659,7 @@ Point2D Window_PointToScreen(Point2D p) {
}
MSG msg;
void Window_ProcessEvents() {
void Window_ProcessEvents(void) {
while (PeekMessageA(&msg, NULL, 0, 0, 1)) {
TranslateMessage(&msg);
DispatchMessageA(&msg);