#version 450 #extension GL_EXT_buffer_reference : require struct String { vec2 pos; vec4 color; float size; uint offset; uint length; }; layout(std430, buffer_reference) readonly buffer StringList { String s[]; }; struct Glyph { vec2 pos; vec4 color; float size; uint code; }; layout(std430, buffer_reference) readonly buffer GlyphList { Glyph g[]; }; struct Rect { vec2 pos; vec2 size; vec4 color; }; layout(std430, buffer_reference) readonly buffer RectList { Rect r[]; }; layout(std430, buffer_reference) readonly buffer CodeList { uint c[]; }; struct DrawCommand { uint vertex_count; uint instance_count; uint fist_vertex; uint first_instance; }; struct DispatchCommand { uint x; uint y; uint z; }; layout(std430, buffer_reference) buffer UILayer { StringList strings; CodeList codes; RectList rects; GlyphList glyphs; DrawCommand draw_glyphs; DrawCommand draw_rects; DispatchCommand dispatch_strings; uint font_index; }; struct Symbol { int top; uint left; uint width; uint height; uint advance; }; layout(std430, buffer_reference) buffer SymbolList { Symbol s[]; }; struct Font { SymbolList symbols; uint num_symbols; uint width; uint height; }; layout(std430, buffer_reference) buffer FontList { Font f[]; }; layout(std430, buffer_reference) buffer UIContext { FontList fonts; mat4 screen; }; layout(std430, push_constant) uniform PushConstant { UIContext context; UILayer layer; } pc; layout(location = 0) out vec4 fragColor; layout(location = 1) out vec2 fragUV; layout(location = 2) out uint code; layout(location = 3) out uint font_index; const vec2 square[6] = { vec2(0.0, 0.0), vec2(1.0, 0.0), vec2(0.0, 1.0), vec2(1.0, 0.0), vec2(1.0, 1.0), vec2(0.0, 1.0), }; void main() { Glyph glyph = pc.layer.glyphs.g[gl_InstanceIndex]; Font font = pc.context.fonts.f[pc.layer.font_index]; Symbol symbol = font.symbols.s[glyph.code]; float fragU = square[gl_VertexIndex].x * symbol.width/font.width; float fragV = square[gl_VertexIndex].y * symbol.height/font.height; float x = (square[gl_VertexIndex].x * symbol.width + symbol.left) * glyph.size / font.width; float y = (square[gl_VertexIndex].y * symbol.height - symbol.top) * glyph.size / font.height; fragUV = vec2(fragU, fragV); fragColor = glyph.color; gl_Position = pc.context.screen * vec4(vec2(x, y) + glyph.pos, 0.0, 1.0); code = glyph.code; font_index = pc.layer.font_index; }