commit b646474ac3b1a658a91df3bfcf8f4ee6f5fac747
parent c160525d2179d6cde61ab36c4d839f11588aa58e
Author: Kyle Milz <kyle@getaddrinfo.net>
Date: Mon, 14 Mar 2016 22:39:55 -0600
viewer: switch to using ftgl
- instead of hand rolling text generation use ftgl instead
Diffstat:
4 files changed, 89 insertions(+), 136 deletions(-)
diff --git a/viewer/Makefile b/viewer/Makefile
@@ -1,5 +1,5 @@
PROG = scv_viewer
-SRCS = viewer.cxx shader_utils.cxx text.cxx af_unix.cxx
+SRCS = viewer.cxx text.cxx af_unix.cxx
CXX = eg++
CXXFLAGS += -std=c++11
@@ -9,6 +9,6 @@ CXXFLAGS += -I/usr/X11R6/include/libdrm
CXXFLAGS += -I/usr/local/include
LDFLAGS += -L/usr/local/lib -L/usr/X11R6/lib
-LDADD += -lGL -lGLU -lGLEW -lfreetype -lz -lglut
+LDADD += -lGL -lGLU -lGLEW -lftgl -lz -lglut
.include <bsd.prog.mk>
diff --git a/viewer/text.cxx b/viewer/text.cxx
@@ -1,145 +1,93 @@
+#include <err.h>
+
#include <iostream>
#include <vector>
#include "text.h"
text::text(af_unix_nonblock *sock) :
- socket(sock)
+ socket(sock),
+ state(WRITE_REQUEST),
+ font(FTGLPixmapFont("DejaVuSansMono.ttf"))
{
- font_file_name = "DejaVuSansMono.ttf";
-
- /* Initialize the FreeType2 library */
- if (FT_Init_FreeType(&ft)) {
- std::cerr << "Could not init freetype library" << std::endl;
- exit(1);
- }
+ if (font.Error())
+ errx(1, "%s", "font error");
- /* Load a font */
- if (FT_New_Face(ft, font_file_name.c_str(), 0, &face)) {
- std::cerr << "Could not open font " << font_file_name << std::endl;
- exit(1);
- }
-
- g = face->glyph;
- glGenBuffers(1, &vbo);
+ font.FaceSize(72);
+ font.Render("Hello World!");
+ font.Render("Hello World!");
}
-/**
- * Render text using the currently loaded font and currently set font size.
- * Rendering starts at coordinates (x, y), z is always 0.
- * The pixel coordinates that the FreeType2 library uses are scaled by (sx, sy).
- */
void
-text::render_text(const char *text, float x, float y, float sx, float sy)
+text::draw()
{
- const char *p;
-
- /* Create a texture that will be used to hold one "glyph" */
- GLuint tex;
-
- glActiveTexture(GL_TEXTURE0);
- glGenTextures(1, &tex);
- glBindTexture(GL_TEXTURE_2D, tex);
- glUniform1i(text_shader.uniform_tex, 0);
-
- /* We require 1 byte alignment when uploading texture data */
- glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
-
- /* Clamping to edges is important to prevent artifacts when scaling */
- glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
- glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
-
- /* Linear filtering usually looks best for text */
- glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
- glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
-
- /* Set up the VBO for our vertex data */
- glEnableVertexAttribArray(text_shader.attribute_coord);
- glBindBuffer(GL_ARRAY_BUFFER, vbo);
- glVertexAttribPointer(text_shader.attribute_coord, 4, GL_FLOAT, GL_FALSE, 0, 0);
-
- /* Loop through all characters */
- for (p = text; *p; p++) {
- /* Try to load and render the character */
- if (FT_Load_Char(face, *p, FT_LOAD_RENDER))
- continue;
-
- /* Upload the "bitmap", which contains an 8-bit grayscale image, as an alpha texture */
- glTexImage2D(GL_TEXTURE_2D, 0, GL_ALPHA, g->bitmap.width, g->bitmap.rows, 0, GL_ALPHA, GL_UNSIGNED_BYTE, g->bitmap.buffer);
-
- /* Calculate the vertex and texture coordinates */
- float x2 = x + g->bitmap_left * sx;
- float y2 = -y - g->bitmap_top * sy;
- float w = g->bitmap.width * sx;
- float h = g->bitmap.rows * sy;
-
- point box[4] = {
- {x2, -y2, 0, 0},
- {x2 + w, -y2, 1, 0},
- {x2, -y2 - h, 0, 1},
- {x2 + w, -y2 - h, 1, 1},
- };
-
- /* Draw the character on the screen */
- glBufferData(GL_ARRAY_BUFFER, sizeof box, box, GL_DYNAMIC_DRAW);
- glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);
-
- /* Advance the cursor to the start of the next character */
- x += (g->advance.x >> 6) * sx;
- y += (g->advance.y >> 6) * sy;
- }
-
- glDisableVertexAttribArray(text_shader.attribute_coord);
- glDeleteTextures(1, &tex);
}
void
-text::draw()
+text::parse_buffer()
{
- float sx = 2.0 / glutGet(GLUT_WINDOW_WIDTH);
- float sy = 2.0 / glutGet(GLUT_WINDOW_HEIGHT);
-
- // glUseProgram(program);
- text_shader.use();
-
- GLfloat black[4] = { 0, 0, 0, 1 };
- GLfloat red[4] = { 1, 0, 0, 1 };
- GLfloat transparent_green[4] = { 0, 1, 0, 0.5 };
-
- /* Set font size to 48 pixels, color to black */
- FT_Set_Pixel_Sizes(face, 0, 48);
- glUniform4fv(text_shader.uniform_color, 1, black);
-
- /* Effects of alignment */
- render_text("The Quick Brown Fox Jumps Over The Lazy Dog", -1 + 8 * sx, 1 - 50 * sy, sx, sy);
- render_text("The Misaligned Fox Jumps Over The Lazy Dog", -1 + 8.5 * sx, 1 - 100.5 * sy, sx, sy);
-
- /* Scaling the texture versus changing the font size */
- render_text("The Small Texture Scaled Fox Jumps Over The Lazy Dog", -1 + 8 * sx, 1 - 175 * sy, sx * 0.5, sy * 0.5);
- FT_Set_Pixel_Sizes(face, 0, 24);
- render_text("The Small Font Sized Fox Jumps Over The Lazy Dog", -1 + 8 * sx, 1 - 200 * sy, sx, sy);
- FT_Set_Pixel_Sizes(face, 0, 48);
- render_text("The Tiny Texture Scaled Fox Jumps Over The Lazy Dog", -1 + 8 * sx, 1 - 235 * sy, sx * 0.25, sy * 0.25);
- FT_Set_Pixel_Sizes(face, 0, 12);
- render_text("The Tiny Font Sized Fox Jumps Over The Lazy Dog", -1 + 8 * sx, 1 - 250 * sy, sx, sy);
- FT_Set_Pixel_Sizes(face, 0, 48);
-
- /* Colors and transparency */
- render_text("The Solid Black Fox Jumps Over The Lazy Dog", -1 + 8 * sx, 1 - 430 * sy, sx, sy);
-
- glUniform4fv(text_shader.uniform_color, 1, red);
- render_text("The Solid Red Fox Jumps Over The Lazy Dog", -1 + 8 * sx, 1 - 330 * sy, sx, sy);
- render_text("The Solid Red Fox Jumps Over The Lazy Dog", -1 + 28 * sx, 1 - 450 * sy, sx, sy);
-
- glUniform4fv(text_shader.uniform_color, 1, transparent_green);
- render_text("The Transparent Green Fox Jumps Over The Lazy Dog", -1 + 8 * sx, 1 - 380 * sy, sx, sy);
- render_text("The Transparent Green Fox Jumps Over The Lazy Dog", -1 + 18 * sx, 1 - 440 * sy, sx, sy);
+ uint64_t off = 0;
+ /* Read 8 bytes from beginning */
+ uint64_t num_tus = buffer[off];
+ off += 8;
+
+ std::cerr << __func__ << ": num tus = " << num_tus << std::endl;
+
+ for (int i = 0; i < num_tus; i++) {
+ //file_name_sz = buffer[off];
+ off += 8;
+
+ // file_name =
+ }
}
void
text::idle()
{
- std::cerr << "text: idling" << std::endl;
- uint8_t zero = 0;
- socket->write_all(&zero, 1);
+ std::cerr << "text::idle() enter" << std::endl;
+ std::cerr << "text::idle() state = " << state << std::endl;
+
+ if (state == WRITE_REQUEST) {
+ uint8_t zero = 0;
+ if (socket->write_all(&zero, 1) == 1)
+ state = READ_HEADER;
+ else
+ errx(1, "%s", "write_all() failed");
+ }
+ if (state == READ_HEADER) {
+ msg_size = 0;
+ size_t n = socket->read_all((uint8_t *)&msg_size, 8);
+
+ if (n == 0)
+ return;
+ else if (n == 8)
+ state = READ_MSG;
+ else
+ errx(1, "%s %zu bytes", "read_all():", n);
+
+ std::cerr << "text::idle() msg size is " << msg_size << std::endl;
+
+ buffer = (uint8_t *)malloc(msg_size);
+ if (buffer == NULL)
+ err(1, "malloc");
+
+ bytes_left = msg_size;
+ bytes_read = 0;
+ }
+ if (state == READ_MSG) {
+ size_t n = socket->read_all(buffer + bytes_read, bytes_left);
+
+ std::cerr << "text::idle() READ_MSG read " << n << " bytes" << std::endl;
+
+ bytes_read += n;
+ bytes_left -= n;
+
+ if (bytes_left <= 0) {
+ //parse_buffer();
+ free(buffer);
+ state = WRITE_REQUEST;
+ std::cerr << "text::idle() got full message" << std::endl;
+ std::cerr << "text::idle() ==> resetting" << std::endl;
+ }
+ }
}
diff --git a/viewer/text.h b/viewer/text.h
@@ -4,11 +4,9 @@
#include <GL/glew.h>
#include <GL/freeglut.h>
-#include <ft2build.h>
-#include FT_FREETYPE_H
+#include <FTGL/ftgl.h>
#include "af_unix.h"
-#include "shader_utils.h"
#include "draw.h"
class text : public drawable {
@@ -17,15 +15,23 @@ public:
void draw();
void idle();
private:
- std::string font_file_name;
- FT_Library ft;
- FT_Face face;
- FT_GlyphSlot g;
- GLuint vbo;
- shader text_shader;
af_unix_nonblock *socket;
+ enum states {
+ WRITE_REQUEST,
+ READ_HEADER,
+ READ_MSG
+ };
+ enum states state;
+ uint64_t msg_size;
+ uint64_t bytes_left;
+ uint64_t bytes_read;
+ uint8_t *buffer;
+
void render_text(const char *, float x, float y, float sx, float sy);
+ void parse_buffer();
+
+ FTGLPixmapFont font;
};
#endif
diff --git a/viewer/viewer.cxx b/viewer/viewer.cxx
@@ -71,7 +71,7 @@ void
window::display(void)
{
/* White background */
- glClearColor(1, 1, 1, 1);
+ glClearColor(0, 0, 0, 1);
glClear(GL_COLOR_BUFFER_BIT);
/* Enable blending, necessary for our alpha texture */
@@ -92,7 +92,6 @@ window::idle(void)
temp_socket = socket.accept();
if (temp_socket)
drawables.push_back(new text(temp_socket));
- // socket.read();
for (auto &i : drawables)
i->idle();