#ifndef PKE_FONT_TYPE_HPP #define PKE_FONT_TYPE_HPP #include "asset-manager.hpp" #include "components.hpp" #include "pk.h" #include "vendor-glm-include.hpp" #define PKE_FONT_MAX_FONT_TYPES 64 TypeSafeInt_H(FontTypeIndex, uint16_t, 0xFFFF); struct FontRenderHandle : pk_bkt_arr_handle {}; constexpr FontRenderHandle FontRenderHandle_MAX = FontRenderHandle{ pk_bkt_arr_handle_MAX_constexpr }; TypeSafeInt_H(FONT_GLYPH_CHAR_FLAG, uint8_t, 0xFF); TypeSafeInt_H(FONT_RENDER_FLAG, uint8_t, 0xFF); TypeSafeInt_H(FONT_RENDER_SURFACE_AREA_TYPE_FLAG, uint8_t, 0xFF); const FONT_GLYPH_CHAR_FLAG FONT_GLYPH_CHAR_FLAGS_NONE = FONT_GLYPH_CHAR_FLAG(0u); const FONT_GLYPH_CHAR_FLAG FONT_GLYPH_CHAR_FLAGS_CONTROL = FONT_GLYPH_CHAR_FLAG((1u << 0)); const FONT_GLYPH_CHAR_FLAG FONT_GLYPH_CHAR_FLAGS_WHITESPACE = FONT_GLYPH_CHAR_FLAG((1u << 1)); const FONT_GLYPH_CHAR_FLAG FONT_GLYPH_CHAR_FLAGS_ALIGN_ADVANCE = FONT_GLYPH_CHAR_FLAG((1u << 2)); const FONT_GLYPH_CHAR_FLAG FONT_GLYPH_CHAR_FLAGS_NEW_LINE = FONT_GLYPH_CHAR_FLAG((1u << 3)); const FONT_RENDER_FLAG FONT_RENDER_FLAG_NONE = FONT_RENDER_FLAG(0u << 0); const FONT_RENDER_FLAG FONT_RENDER_FLAG_VISIBILITY_INVISIBLE = FONT_RENDER_FLAG(1u << 0); const FONT_RENDER_SURFACE_AREA_TYPE_FLAG FONT_RENDER_SURFACE_AREA_TYPE_FLAGS_NONE = FONT_RENDER_SURFACE_AREA_TYPE_FLAG(0u); const FONT_RENDER_SURFACE_AREA_TYPE_FLAG FONT_RENDER_SURFACE_AREA_TYPE_FLAGS_CENTER_VERTICAL = FONT_RENDER_SURFACE_AREA_TYPE_FLAG((1u << 0)); const FONT_RENDER_SURFACE_AREA_TYPE_FLAG FONT_RENDER_SURFACE_AREA_TYPE_FLAGS_CENTER_HORIZONTAL = FONT_RENDER_SURFACE_AREA_TYPE_FLAG((1u << 1)); const FONT_RENDER_SURFACE_AREA_TYPE_FLAG FONT_RENDER_SURFACE_AREA_TYPE_FLAGS_CENTER_BOTH = FONT_RENDER_SURFACE_AREA_TYPE_FLAG((1u << 0) | (1u << 1)); struct FontTypeRender { FontTypeIndex index_ft; FontRenderHandle handle_fr; }; constexpr FontTypeRender FontTypeRender_MAX = { .index_ft = FontTypeIndex_MAX, .handle_fr = { pk_bkt_arr_handle_MAX }, }; struct FontGlyphChar { double advance; glm::vec2 sprite_region_min; glm::vec2 sprite_region_max; glm::dvec4 plane_bounds; uint32_t unicode; FONT_GLYPH_CHAR_FLAG flags; }; struct FontRenderSettings { glm::vec4 color_foreground = glm::vec4(0.4, 0.9, 0.5, 0.8); glm::vec4 color_background = glm::vec4(0.0, 0.0, 0.0, 0.0); float char_scale = 1.f; float line_height_scale = 1.f; float char_spacing_scale = 1.f; glm::ivec2 surface_area_size; glm::ivec2 surface_area_pos; FONT_RENDER_FLAG flags; FONT_RENDER_SURFACE_AREA_TYPE_FLAG surface_area_type_flags; }; struct FontRender : public Entity_Base { uint32_t *glyph_indices = nullptr; FontTypeIndex index_ft = FontTypeIndex{0}; FontRenderHandle fr_handle = FontRenderHandle_MAX; uint32_t n_glyphs = 0; uint32_t buffer_start_index = 0; FontRenderSettings settings{}; pk_cstr text{}; }; struct FontTypeMSDFSettings { float minimum_scale; float px_range; }; struct FontTypeSpacing { double geometry_scale; double em_size; double ascender_y; double descender_y; double line_height; double underline_y; double underline_thickness; }; struct FontType : public Entity_Base { pk_cstr title; AssetHandle fontTextureAssetHandle; AssetHandle glyphDetailsAssetHandle; FontGlyphChar *glyphs; glm::vec2 atlas_size; uint32_t n_glyphs; pk_bkt_arr_t renders; FontTypeIndex index_ft = FontTypeIndex{0}; struct FontTypeMSDFSettings msdf_settings; struct FontTypeSpacing spacing; struct FontTypeGraphics { VkDeviceMemory deviceMemoryVert = VK_NULL_HANDLE; VkDeviceMemory deviceMemoryTexture = VK_NULL_HANDLE; VkDeviceMemory deviceMemoryInst = VK_NULL_HANDLE; VkImage textureImage = VK_NULL_HANDLE; VkImageView textureImageView = VK_NULL_HANDLE; VkDescriptorPool vkDescriptorPool = VK_NULL_HANDLE; VkDescriptorSet vkDescriptorSet = VK_NULL_HANDLE; bool should_update_instance_buffer; } gr; struct FontTypeBindings { BufferBindingDetails bd_vertex; BufferBindingDetails bd_uv; BufferBindingDetails bd_atlas_size; BufferBindingDetails bd_index; BufferBindingDetails bd_instance; uint32_t index_count = 0; uint32_t instance_counter = 0; uint32_t instance_buffer_max_count = 0; } bindings; }; void FontType_Init(); void FontType_Teardown(); void FontType_Tick(double delta); void FontType_Serialize(std::ostream &stream, FontType *ft); void FontType_Deserialize(std::istream &stream); FontType* FontType_Get(FontTypeIndex idx); FontType* FontType_GetByTitle(const pk_cstr title); FontType* FontType_GetFonts(uint64_t &idx_unused); FontTypeIndex FontType_RegisterFont(pk_cstr title, AssetHandle fontTextureHandle, AssetHandle glyphsHandle, FontTypeMSDFSettings *msdf_settings, FontTypeSpacing *spacing); FontTypeRender FontType_AddStringRender(FontTypeIndex idx_ft, const pk_cstr &&str, FontRenderSettings *settings, Entity_Base *parent = nullptr, pk_uuid uuid = pk_uuid_zed); FontRender *FontType_GetFontRender(FontTypeRender frh); void FontType_UpdateStringRender(FontTypeRender frh, FontRenderSettings *settings); void FontType_UpdateStringRenderText(FontTypeRender frh, pk_cstr &&cstr); void FontType_RemoveStringRender(FontTypeRender frh); #endif /* PKE_FONT_TYPE_HPP */