This commit is contained in:
ThatTanishqTak 2025-12-31 22:54:51 +01:00 committed by GitHub
commit 5aba1d8469
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
8 changed files with 1668 additions and 12 deletions

View file

@ -1,21 +1,73 @@
#include <iostream>
#include <cstdio>
#include <cstdlib>
#define WIN32_LEAN_AND_MEAN
#include <windows.h>
#include <wingdi.h>
#define CLAY_IMPLEMENTATION
#include "../../clay.h"
Clay_LayoutConfig layoutElement = Clay_LayoutConfig { .padding = {5} };
// Simple layout config with prefixed naming to match the MSVC-friendly style guide.
Clay_LayoutConfig s_LayoutElement = Clay_LayoutConfig{ .padding = {5} };
void HandleClayErrors(Clay_ErrorData errorData) {
// Win32-compatible font handle that can be reused by the text measuring callback.
static HFONT s_TextFont = static_cast<HFONT>(GetStockObject(DEFAULT_GUI_FONT));
// Bridge Clay's text measuring hook to GDI so layouts get accurate extents on Windows.
Clay_Dimensions HandleMeasureText(Clay_StringSlice text, Clay_TextElementConfig* config, void* userData)
{
(void)config; // Config is available for future font switching or styling.
HFONT* l_FontHandle = static_cast<HFONT*>(userData);
HFONT l_ResolvedFont = l_FontHandle != nullptr && *l_FontHandle != nullptr ? *l_FontHandle : s_TextFont;
HDC l_DeviceContext = GetDC(nullptr);
if (l_DeviceContext == nullptr)
{
return Clay_Dimensions{ 0, 0 };
}
HGDIOBJ l_PreviousFont = nullptr;
if (l_ResolvedFont != nullptr)
{
l_PreviousFont = SelectObject(l_DeviceContext, l_ResolvedFont);
}
SIZE l_TextSize{ 0, 0 };
int l_TextLength = static_cast<int>(text.length);
GetTextExtentPoint32A(l_DeviceContext, text.chars, l_TextLength, &l_TextSize);
if (l_PreviousFont != nullptr)
{
SelectObject(l_DeviceContext, l_PreviousFont);
}
ReleaseDC(nullptr, l_DeviceContext);
// Future improvement: swap GDI for DirectWrite or cache glyph metrics to avoid repeated calls.
return Clay_Dimensions{ static_cast<float>(l_TextSize.cx), static_cast<float>(l_TextSize.cy) };
}
void HandleClayErrors(Clay_ErrorData errorData)
{
printf("%s", errorData.errorText.chars);
}
int main(void) {
uint64_t totalMemorySize = Clay_MinMemorySize();
Clay_Arena clayMemory = Clay_CreateArenaWithCapacityAndMemory(totalMemorySize, (char *)malloc(totalMemorySize));
Clay_Initialize(clayMemory, Clay_Dimensions {1024,768}, Clay_ErrorHandler { HandleClayErrors });
int main(void)
{
uint64_t l_TotalMemorySize = Clay_MinMemorySize();
Clay_Arena l_ClayMemory = Clay_CreateArenaWithCapacityAndMemory(l_TotalMemorySize, static_cast<char*>(malloc(l_TotalMemorySize)));
// Initialize the Clay context and immediately provide a Windows-friendly text measure callback.
Clay_Initialize(l_ClayMemory, Clay_Dimensions{ 1024, 768 }, Clay_ErrorHandler{ HandleClayErrors });
Clay_SetMeasureTextFunction(HandleMeasureText, &s_TextFont);
// The measure function lets Clay compute text bounds before laying out widgets.
Clay_BeginLayout();
CLAY_AUTO_ID({ .layout = layoutElement, .backgroundColor = {255,255,255,0} }) {
CLAY_AUTO_ID({ .layout = s_LayoutElement, .backgroundColor = {255,255,255,0} })
{
CLAY_TEXT(CLAY_STRING(""), CLAY_TEXT_CONFIG({ .fontId = 0 }));
}
Clay_EndLayout();
return 0;
}
}

View file

@ -0,0 +1,56 @@
cmake_minimum_required(VERSION 3.27)
project(clay_examples_vulkan_demo LANGUAGES CXX)
set(CMAKE_CXX_STANDARD 20)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
include(FetchContent)
set(FETCHCONTENT_QUIET FALSE)
# GLFW is used only for window creation and Vulkan surface management in this demo.
# When other examples are enabled (e.g., raylib), GLFW may already be present via
# their dependencies. Guarding the population prevents duplicate target errors
# (CMP0002) while still reusing the existing GLFW target when available.
if(NOT TARGET glfw)
FetchContent_Declare(
glfw
GIT_REPOSITORY "https://github.com/glfw/glfw.git"
GIT_TAG "3.4"
GIT_PROGRESS TRUE
GIT_SHALLOW TRUE
)
FetchContent_MakeAvailable(glfw)
else()
message(STATUS "Reusing existing GLFW target for Vulkan demo")
endif()
find_package(Vulkan REQUIRED)
add_executable(clay_examples_vulkan_demo
main.cpp
)
target_include_directories(clay_examples_vulkan_demo PUBLIC
${CMAKE_CURRENT_SOURCE_DIR}
${CMAKE_CURRENT_SOURCE_DIR}/..
${CMAKE_CURRENT_SOURCE_DIR}/../..
)
target_link_libraries(clay_examples_vulkan_demo PRIVATE
glfw
Vulkan::Vulkan
)
if(MSVC)
# Keep MSVC warnings visible while allowing the demo to compile cleanly.
target_compile_options(clay_examples_vulkan_demo PRIVATE /W4)
else()
target_compile_options(clay_examples_vulkan_demo PRIVATE -Wall -Wextra)
endif()
# Allow Visual Studio users to copy sample resources (fonts, textures) beside the executable later.
add_custom_target(clay_examples_vulkan_demo_copy_resources ALL
COMMAND ${CMAKE_COMMAND} -E make_directory ${CMAKE_CURRENT_BINARY_DIR}/resources
COMMENT "Prepare resource directory for future font/texture assets"
)
add_dependencies(clay_examples_vulkan_demo clay_examples_vulkan_demo_copy_resources)

View file

@ -0,0 +1,28 @@
# Clay Vulkan Demo
This Visual Studio 2022 friendly sample shows how to pair Clay's layout engine with a Vulkan swapchain. It uses GLFW for the Win32 surface and stitches Clay render commands through the Vulkan renderer adapter.
## Build prerequisites
- [Vulkan SDK](https://vulkan.lunarg.com/doc/sdk) installed and the `VULKAN_SDK` environment variable set.
- Visual Studio 2022 with CMake and the MSVC toolset.
- Git submodules are not required because GLFW is fetched automatically through CMake's `FetchContent`.
## Configure and build (Visual Studio 2022)
1. Open a **Developer PowerShell for VS 2022** so the compiler environment variables are available.
2. Generate a build directory:
```pwsh
cmake -S examples/vulkan-demo -B build/vulkan-demo -G "Visual Studio 17 2022" -A x64
```
3. Build the executable:
```pwsh
cmake --build build/vulkan-demo --config Debug
```
4. Run the demo from the build tree (the app opens a GLFW window):
```pwsh
build/vulkan-demo/Debug/clay_examples_vulkan_demo.exe
```
## Notes and future work
- The code is intentionally verbose and commented with links to the Vulkan SDK reference and the ImGui wiki for font atlas/descriptor sharing advice.
- Swapchain, render pass, and command buffer setup are present, but pipeline configuration uses placeholders so you can wire your own shaders.
- TODOs remain for dynamic descriptor management and richer font handling; these are natural next steps after the basic window + swapchain bring-up.

File diff suppressed because it is too large Load diff