Compare commits

...

9 Commits

Author SHA1 Message Date
Junior Rantila
7555613133
Merge 9e13524b52 into 9d659e8abd 2025-01-21 16:50:11 +00:00
Nic Barker
9d659e8abd [Examples/Raylib] Restore deleted font
Some checks failed
CMake on multiple platforms / build (Release, cl, cl, windows-latest) (push) Has been cancelled
CMake on multiple platforms / build (Release, clang, clang++, ubuntu-latest) (push) Has been cancelled
CMake on multiple platforms / build (Release, gcc, g++, ubuntu-latest) (push) Has been cancelled
2025-01-21 21:28:38 +13:00
Nic Barker
ec2b3b35ff [Renderers/Raylib] Early return 0 rather than segfault when Raylib fonts fail to load 2025-01-21 21:26:57 +13:00
Nic Barker
5f7176cdcc Fix quick start in README to include error handler 2025-01-21 21:17:24 +13:00
Nic Barker
ebeef93c34 [Documentation] Include CLAY_ID_LOCAL in README.md 2025-01-21 21:11:49 +13:00
Nic Barker
9b2d585499 Update odin and wasm bindings 2025-01-21 19:14:22 +13:00
Nic Barker
81589ad29b [Core] Fix layout bug in SIZING_PERCENT 2025-01-21 19:11:33 +13:00
Nic Barker
16f894bb4d Fix incorrect use of corner radius 2025-01-21 18:32:33 +13:00
Timothy Hoyt
9f07f5aac8
fixed video demo padding (#205) 2025-01-21 18:31:48 +13:00
10 changed files with 75 additions and 23 deletions

View File

@ -28,17 +28,31 @@ _An example GUI application built with clay_
#include "clay.h" #include "clay.h"
``` ```
2. Ask clay for how much static memory it needs using [Clay_MinMemorySize()](#clay_minmemorysize), create an Arena for it to use with [Clay_CreateArenaWithCapacityAndMemory(size, void *memory)](#clay_createarenawithcapacityandmemory), and initialize it with [Clay_Initialize(arena, dimensions)](#clay_initialize). 2. Ask clay for how much static memory it needs using [Clay_MinMemorySize()](#clay_minmemorysize), create an Arena for it to use with [Clay_CreateArenaWithCapacityAndMemory(size, void *memory)](#clay_createarenawithcapacityandmemory).
```C ```C
// Note: malloc is only used here as an example, any allocator that provides // Note: malloc is only used here as an example, any allocator that provides
// a pointer to addressable memory of at least totalMemorySize will work // a pointer to addressable memory of at least totalMemorySize will work
uint64_t totalMemorySize = Clay_MinMemorySize(); uint64_t totalMemorySize = Clay_MinMemorySize();
Clay_Arena arena = Clay_CreateArenaWithCapacityAndMemory(totalMemorySize, malloc(totalMemorySize)); Clay_Arena arena = Clay_CreateArenaWithCapacityAndMemory(totalMemorySize, malloc(totalMemorySize));
Clay_Initialize(arena, (Clay_Dimensions) { screenWidth, screenHeight });
``` ```
3. Provide a `MeasureText(text, config)` function pointer with [Clay_SetMeasureTextFunction(function)](#clay_setmeasuretextfunction) so that clay can measure and wrap text. 3. Create an [ErrorHandler](#clay_errorhandler) for Clay to call when an internal error occurs, and initialize Clay with the Arena and handler by calling [Clay_Initialize(arena, dimensions, errorHandler)](#clay_initialize).
```C
void HandleClayErrors(Clay_ErrorData errorData) {
// See the Clay_ErrorData struct for more information
printf("%s", errorData.errorText.chars);
switch(errorData.errorType) {
// etc
}
}
// In your startup function
Clay_Initialize(arena, (Clay_Dimensions) { screenWidth, screenHeight }, (Clay_ErrorHandler) { HandleClayErrors });
```
4. Provide a `MeasureText(text, config)` function pointer with [Clay_SetMeasureTextFunction(function)](#clay_setmeasuretextfunction) so that clay can measure and wrap text.
```C ```C
// Example measure text function // Example measure text function
@ -811,6 +825,53 @@ An offset version of [CLAY_ID](#clay_id). Generates a [Clay_ElementId](#clay_ele
--- ---
### CLAY_ID_LOCAL()
**Usage**
`CLAY(CLAY_ID_LOCAL(char* idString)) {}`
**Lifecycle**
`Clay_BeginLayout()` -> `CLAY(` -> `CLAY_ID_LOCAL()` -> `)` -> `Clay_EndLayout()`
**Notes**
**CLAY_ID_LOCAL()** is used to generate and attach a [Clay_ElementId](#clay_elementid) to a layout element during declaration.
Unlike [CLAY_ID](#clay_id) which needs to be globally unique, a local ID is based on the ID of it's parent and only needs to be unique among its siblings.
As a result, local id is suitable for use in reusable components and loops.
**Examples**
```C
void RenderHeaderButton(ButtonData button) {
CLAY(
CLAY_ID_LOCAL("HeaderButton"),
CLAY_LAYOUT({ .layoutDirection = CLAY_TOP_TO_BOTTOM, .sizing = { .width = CLAY_SIZING_GROW(0) }, .padding = CLAY_PADDING_ALL(16), .childGap = 16) })
) {
// ...children
}
}
for (int i = 0; i < headerButtons.length; i++) {
RenderHeaderButton(headerButtons.items[i]);
}
```
---
---
### CLAY_IDI_LOCAL()
`Clay_ElementId CLAY_IDI_LOCAL(char *label, int index)`
An offset version of [CLAY_ID_LOCAL](#clay_local_id). Generates a [Clay_ElementId](#clay_elementid) string id from the provided `char *label`, combined with the `int index`. Used for generating ids for sequential elements (such as in a `for` loop) without having to construct dynamic strings at runtime.
---
### CLAY_LAYOUT ### CLAY_LAYOUT
**Usage** **Usage**

Binary file not shown.

Binary file not shown.

Binary file not shown.

9
clay.h
View File

@ -2257,12 +2257,6 @@ void Clay__SizeContainersAlongAxis(bool xAxis) {
*childSize = (parentSize - totalPaddingAndChildGaps) * childSizing.size.percent; *childSize = (parentSize - totalPaddingAndChildGaps) * childSizing.size.percent;
if (sizingAlongAxis) { if (sizingAlongAxis) {
innerContentSize += *childSize; innerContentSize += *childSize;
if (childOffset > 0) {
innerContentSize += parentChildGap; // For children after index 0, the childAxisOffset is the gap from the previous child
totalPaddingAndChildGaps += parentChildGap;
}
} else {
innerContentSize = CLAY__MAX(*childSize, innerContentSize);
} }
} }
} }
@ -2483,9 +2477,6 @@ void Clay__CalculateFinalLayout() {
// DFS node has been visited, this is on the way back up to the root // DFS node has been visited, this is on the way back up to the root
Clay_LayoutConfig *layoutConfig = currentElement->layoutConfig; Clay_LayoutConfig *layoutConfig = currentElement->layoutConfig;
if (layoutConfig->sizing.height.type == CLAY__SIZING_TYPE_PERCENT) {
continue;
}
if (layoutConfig->layoutDirection == CLAY_LEFT_TO_RIGHT) { if (layoutConfig->layoutDirection == CLAY_LEFT_TO_RIGHT) {
// Resize any parent containers that have grown in height along their non layout axis // Resize any parent containers that have grown in height along their non layout axis
for (int32_t j = 0; j < currentElement->childrenOrTextContent.children.length; ++j) { for (int32_t j = 0; j < currentElement->childrenOrTextContent.children.length; ++j) {

View File

@ -117,7 +117,7 @@ int main(void) {
Clay_RectangleElementConfig contentBackgroundConfig = { Clay_RectangleElementConfig contentBackgroundConfig = {
.color = { 90, 90, 90, 255 }, .color = { 90, 90, 90, 255 },
.cornerRadius = 8 .cornerRadius = CLAY_CORNER_RADIUS(8)
}; };
Clay_BeginLayout(); Clay_BeginLayout();
@ -141,7 +141,7 @@ int main(void) {
.height = CLAY_SIZING_FIXED(60), .height = CLAY_SIZING_FIXED(60),
.width = CLAY_SIZING_GROW(0) .width = CLAY_SIZING_GROW(0)
}, },
.padding = { 16 }, .padding = { 16, 16, 0, 0 },
.childGap = 16, .childGap = 16,
.childAlignment = { .childAlignment = {
.y = CLAY_ALIGN_Y_CENTER .y = CLAY_ALIGN_Y_CENTER
@ -151,10 +151,10 @@ int main(void) {
// Header buttons go here // Header buttons go here
CLAY( CLAY(
CLAY_ID("FileButton"), CLAY_ID("FileButton"),
CLAY_LAYOUT({ .padding = { 16, 8 }}), CLAY_LAYOUT({ .padding = { 16, 16, 8, 8 }}),
CLAY_RECTANGLE({ CLAY_RECTANGLE({
.color = { 140, 140, 140, 255 }, .color = { 140, 140, 140, 255 },
.cornerRadius = 5 .cornerRadius = CLAY_CORNER_RADIUS(5)
}) })
) { ) {
CLAY_TEXT(CLAY_STRING("File"), CLAY_TEXT_CONFIG({ CLAY_TEXT(CLAY_STRING("File"), CLAY_TEXT_CONFIG({
@ -177,7 +177,7 @@ int main(void) {
}, },
}), }),
CLAY_LAYOUT({ CLAY_LAYOUT({
.padding = {0, 8 } .padding = {0, 0, 8, 8 }
}) })
) { ) {
CLAY( CLAY(
@ -189,7 +189,7 @@ int main(void) {
}), }),
CLAY_RECTANGLE({ CLAY_RECTANGLE({
.color = { 40, 40, 40, 255 }, .color = { 40, 40, 40, 255 },
.cornerRadius = 8 .cornerRadius = CLAY_CORNER_RADIUS(8)
}) })
) { ) {
// Render dropdown items here // Render dropdown items here
@ -236,7 +236,7 @@ int main(void) {
CLAY_LAYOUT(sidebarButtonLayout), CLAY_LAYOUT(sidebarButtonLayout),
CLAY_RECTANGLE({ CLAY_RECTANGLE({
.color = { 120, 120, 120, 255 }, .color = { 120, 120, 120, 255 },
.cornerRadius = 8, .cornerRadius = CLAY_CORNER_RADIUS(8),
}) })
) { ) {
CLAY_TEXT(document.title, CLAY_TEXT_CONFIG({ CLAY_TEXT(document.title, CLAY_TEXT_CONFIG({
@ -252,7 +252,7 @@ int main(void) {
Clay_Hovered() Clay_Hovered()
? CLAY_RECTANGLE({ ? CLAY_RECTANGLE({
.color = { 120, 120, 120, 120 }, .color = { 120, 120, 120, 120 },
.cornerRadius = 8 .cornerRadius = CLAY_CORNER_RADIUS(8)
}) })
: 0 : 0
) { ) {

View File

@ -87,10 +87,8 @@ Ray GetScreenToWorldPointWithZDistance(Vector2 position, Camera camera, int scre
return ray; return ray;
} }
uint32_t measureCalls = 0;
static inline Clay_Dimensions Raylib_MeasureText(Clay_StringSlice text, Clay_TextElementConfig *config, uintptr_t userData) { static inline Clay_Dimensions Raylib_MeasureText(Clay_StringSlice text, Clay_TextElementConfig *config, uintptr_t userData) {
measureCalls++;
// Measure string size for Font // Measure string size for Font
Clay_Dimensions textSize = { 0 }; Clay_Dimensions textSize = { 0 };
@ -99,6 +97,9 @@ static inline Clay_Dimensions Raylib_MeasureText(Clay_StringSlice text, Clay_Tex
float textHeight = config->fontSize; float textHeight = config->fontSize;
Font fontToUse = Raylib_fonts[config->fontId].font; Font fontToUse = Raylib_fonts[config->fontId].font;
// Font failed to load, likely the fonts are in the wrong place relative to the execution dir
if (!fontToUse.glyphs) return textSize;
float scaleFactor = config->fontSize/(float)fontToUse.baseSize; float scaleFactor = config->fontSize/(float)fontToUse.baseSize;
for (int i = 0; i < text.length; ++i) for (int i = 0; i < text.length; ++i)
@ -129,7 +130,6 @@ void Clay_Raylib_Initialize(int width, int height, const char *title, unsigned i
void Clay_Raylib_Render(Clay_RenderCommandArray renderCommands) void Clay_Raylib_Render(Clay_RenderCommandArray renderCommands)
{ {
measureCalls = 0;
for (int j = 0; j < renderCommands.length; j++) for (int j = 0; j < renderCommands.length; j++)
{ {
Clay_RenderCommand *renderCommand = Clay_RenderCommandArray_Get(&renderCommands, j); Clay_RenderCommand *renderCommand = Clay_RenderCommandArray_Get(&renderCommands, j);