Загрузка / отображение актива шрифта - PullRequest
0 голосов
/ 19 октября 2019

Я пытаюсь загрузить шрифт (arial) из файла .ttf и с помощью библиотеки STB TrueType: https://github.com/nothings/stb/blob/master/stb_truetype.h и отобразить его на экране.

Я полагаю, что используюAPI библиотеки корректно отображался, когда я тестировал его, загружая только одну битовую карту с кодовой точкой, но теперь у меня есть глобальный буфер, в котором я храню 52 битовых карты с кодовой точкой (алфавит в нижнем и верхнем регистре), и для его проверки я выбираюслучайные символы для отображения на экране. Это выглядит странно. Пример (должен быть только 1 заглавная буква 'Q'):

Should just be 1 capital 'Q'

Я думаю, может быть, я неправильно понимаю или неправильно использую то, как память распределяется?

Вот соответствующий код:

(В файле слоя платформы win32)

struct character_bitmap
{
    unsigned char* memory;
    int width;
    int height;
};

struct font_buffer
{
    character_bitmap* memory;
    float size;
};

static font_buffer font_bitmaps;

void test_load_arial(float size)
{
    if (font_bitmaps.memory)
    {
        // VirtualFree(font_bitmaps.memory, 0, MEM_RELEASE);
        free(font_bitmaps.memory);
    }

    unsigned char* ttf_buffer = (unsigned char*)malloc(1 << 25);
    stbtt_fontinfo font;

    fread(ttf_buffer, 1, 1 << 25, fopen("c:/windows/fonts/arialbd.ttf", "rb"));
    stbtt_InitFont(&font, (unsigned char*)ttf_buffer, stbtt_GetFontOffsetForIndex((unsigned char*)ttf_buffer, 0));

    int char_bitmap_width = (int)size;
    int char_bitmap_height = (int)size;

    unsigned int character_memory_size = (char_bitmap_width * char_bitmap_height) * 4;
    int font_memory_size = character_memory_size * 52;

    // font_bitmaps.memory = (character_bitmap*)VirtualAlloc(0, font_memory_size, MEM_COMMIT, PAGE_READWRITE);
    font_bitmaps.memory = (character_bitmap*)malloc(font_memory_size);

    char alphabet[53] = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ";
    character_bitmap* current_character = font_bitmaps.memory;
    for (int i = 0; i < 52; i++)
    {
        current_character->width = char_bitmap_width;
        current_character->height = char_bitmap_height;

        current_character->memory = stbtt_GetCodepointBitmap(&font, 0, stbtt_ScaleForPixelHeight(&font, 128.0f), alphabet[i],
                                                 &char_bitmap_width, &char_bitmap_height, 0, 0);
        current_character++;
    }
}

(В другом файле, внутри основного обновления и функции рендеринга, которая вызывается каждый кадрЯ называю эту функцию)

void test_render_text(offscreen_buffer* buffer, font_buffer* font_bitmaps)
{
    int width = font_bitmaps->memory[0].width;
    int height = font_bitmaps->memory[0].height;

    unsigned char* dest_row = (unsigned char*)buffer->memory + ((buffer->width / 2) * buffer->bytes_per_pixel) + ((buffer->height / 2) * buffer->pitch);
    unsigned char* source = font_bitmaps->memory[42].memory;
    for (int y = 0; y < height; y++)
    {
        unsigned int* dest_pixel = (unsigned int*)dest_row;

        for (int x = 0; x < width; x++)
        {
            unsigned char alpha = *source;
            *dest_pixel = ((alpha << 24)
                          | (alpha << 16)
                          | (alpha << 8)
                          | (alpha << 0));

            dest_pixel++;
            source++;
        }

        dest_row += buffer->pitch;
    }
}
...