Как рассчитать оптимальные границы глифов в карте символов для рендеринга текста OpenGL
Для визуализации текста с помощью OpenGL я использую текстурированный четырехугольный подход, я рисую четырехугольник для каждого символа, который должен быть представлен. Я храню всю информацию о текстуре персонажа в одной текстуре и использую glScalef и glTranslatef в матрице текстуры, чтобы выбрать правильный символ в текстуре. Сначала я поместил в изображение только несколько символов, используемых для создания текстуры, и это сработало хорошо.
С тех пор мне нужно было отображать больше символов, например строчные буквы. Я попытался добавить больше символов, но теперь мой текст не выравнивается и становится меньше.
Есть ли правильный способ создания карт персонажей, или мой подход все неправильно?
Примечание: я использую шрифт в моно-стиле, поэтому размер шрифта не должен быть проблемой, однако я бы хотел добавить поддержку шрифтов с символами неравномерного размера.
РЕДАКТИРОВАТЬ: я использую буфер вершин для рисования, а не непосредственный режим.
РЕДАКТИРОВАТЬ 2: Текстура, содержащая карту символов имеет 9 строк, в каждой по 11 символов. Поскольку символы имеют одинаковый размер, я использую glscalef в матрице текстуры, чтобы 1/9 ширины текстуры и 1/11 высоты. VBO определяет квадраты (0,0),(1,0),(0,1),(1,1) и координаты текс (0,0),(1,0),(0,1),(1,1). Похоже, что несогласованность произошла из-за того, что мои преобразования не соответствуют точно каждому глифу. Как рассчитываются оптимальные границы для каждого глифа?
1 ответ
В надежде, что это может быть полезно для других. Оптимальные границы глифов можно рассчитать, сначала нормализуя смещения пикселей каждой буквы так, чтобы они были числами в диапазоне от 0 до 1. Ширина и высота также могут быть нормализованы для определения правильного ограничивающего прямоугольника. Если ширина и высота являются одинаковыми, как в монофонических шрифтах, статические значения ширины и высоты могут использоваться для вычисления границ глифа.
Сохранение массива значений положения пикселей для каждого глифа было бы утомительно вычислять вручную, поэтому лучше начинать первый глиф с первого пикселя карты символов и не оставлять интервалы между каждой буквой. Это облегчило бы вычисление нижних левых ультрафиолетовых координат с помощью циклов for.
void GetUVs(Vector2* us, Vector2* vs, float charWidth, float charHeight, int cols, int rows)
{
for (int x = 0; x < cols; x++)
{
for (int y = 0; y < rows; y++)
{
int index = x + cols * y;
us[index].x = x * charWidth;
vs[index].y = y * charHeight;
}
}
}
Остальные границы могут быть рассчитаны путем сложения ширины, высоты, ширины и высоты соответственно.