#version 330 core layout (location = 0) in vec2 begin; layout (location = 1) in int glyph; layout (location = 2) in float fontSize; layout (location = 3) in vec4 color; uniform samplerBuffer glyph_table; uniform mat4 projection; uniform sampler2D font; out vec4 frag_color; out vec2 frag_uv_position; const vec2 rectangle_vertices[4] = vec2[]( vec2(-1, -1), // bl vec2(-1, 1), // tl vec2( 1, -1), // br vec2( 1, 1) // tr ); const vec2 uv0_vertices[4] = vec2[]( vec2(1, 0), // bl vec2(1, 1), // tl vec2(0, 0), // br vec2(0, 1) // tr ); const vec2 uv1_vertices[4] = vec2[]( vec2(0, 1), vec2(0, 0), vec2(1, 1), vec2(1, 0) ); void main() { vec4 chunk1 = texelFetch(glyph_table, glyph * 2 + 0); vec4 chunk2 = texelFetch(glyph_table, glyph * 2 + 1); vec2 uv0 = chunk1.xy; vec2 uv1 = chunk1.zw; vec2 offset = chunk2.xy; vec2 dims = chunk2.zw; vec2 p0 = begin + offset*fontSize; vec2 p1 = begin + (offset + dims)*fontSize; vec2 dest_half_size = (p1 - p0) / 2; vec2 dest_center = (p1 + p0) / 2; vec2 dest_position = rectangle_vertices[gl_VertexID] * dest_half_size + dest_center; vec2 uv_position = uv0 * uv0_vertices[gl_VertexID] + uv1 * uv1_vertices[gl_VertexID]; gl_Position = projection * vec4(dest_position, 0, 1); frag_color = color; frag_uv_position = vec2(uv_position.x, uv_position.y); }