git-svn-id: http://svn2.nishi.boats/svn/milsko/trunk@491 b9cfdab3-6d41-4d17-bbe4-086880011989
This commit is contained in:
NishiOwO
2025-10-24 19:32:24 +00:00
parent 453fb8702d
commit 6a83a184d1
10 changed files with 172 additions and 23 deletions

View File

@@ -14,7 +14,8 @@ else()
endif()
option(CLASSIC "Use classic theme" OFF)
option(USE_STB_IMAGE "Use stb_image" ON)
option(USE_STB_TRUETYPE "Use stb_truetype" ON)
option(USE_STB_TRUETYPE "Use stb_truetype" OFF)
option(USE_FREETYPE2 "Use FreeType 2" ON)
file(
GLOB
@@ -76,6 +77,20 @@ if(USE_STB_TRUETYPE)
)
endif()
if(USE_FREETYPE2)
target_compile_definitions(
Mw
PRIVATE
USE_FREETYPE2
)
find_package(PkgConfig)
pkg_check_modules(FT2 REQUIRED freetype2)
list(APPEND INCLUDE_DIRS ${FT2_INCLUDE_DIRS})
list(APPEND LIBRARY_DIRS ${FT2_LIBRARY_DIRS})
list(APPEND LIBRARIES ${FT2_LIBRARIES})
endif()
target_include_directories(
Mw
PRIVATE

View File

@@ -5,9 +5,13 @@ PREFIX = /usr/local
ifeq ($(TARGET),)
TARGET = $(shell uname -s)
endif
ifneq ($(TARGET),$(shell uname -s))
CROSS = 1
endif
USE_STB_IMAGE = 1
USE_STB_TRUETYPE = 1
USE_STB_TRUETYPE = 0
USE_FREETYPE2 = 1
CC = $(GCC)gcc
@@ -139,6 +143,15 @@ else
include external/deps.mk
endif
ifeq ($(USE_FREETYPE2),1)
L_CFLAGS += -DUSE_FREETYPE2
ifneq ($(CROSS),1)
L_CFLAGS += $(shell pkg-config --cflags freetype2)
L_LIBS += $(shell pkg-config --libs freetype2)
endif
endif
ifeq ($(USE_STB_TRUETYPE),1)
L_CFLAGS += -DUSE_STB_TRUETYPE
endif

View File

@@ -9,6 +9,11 @@ list(REMOVE_ITEM EXAMPLES_SOURCES ${CMAKE_SOURCE_DIR}/examples/harvard.c)
foreach(PATH IN LISTS EXAMPLES_SOURCES)
get_filename_component(TARGET ${PATH} NAME_WE)
add_executable(${TARGET} ${PATH})
target_include_directories(
${TARGET}
PRIVATE
${CMAKE_SOURCE_DIR}/include
)
target_link_libraries(
${TARGET}
PRIVATE

View File

@@ -8,6 +8,11 @@ file(
foreach(PATH IN LISTS EXAMPLES_BASIC_SOURCES)
get_filename_component(TARGET ${PATH} NAME_WE)
add_executable(${TARGET} ${PATH})
target_include_directories(
${TARGET}
PRIVATE
${CMAKE_SOURCE_DIR}/include
)
target_link_libraries(
${TARGET}
PRIVATE

View File

@@ -1,7 +1,6 @@
/* $Id$ */
#include <Mw/Milsko.h>
#include <stdint.h>
MwWidget vp;
#define WIN_SIZE 512

View File

@@ -434,7 +434,7 @@ static void inherit_integer(MwWidget handle, const char* key, int default_value)
MwSetInteger(handle, key, default_value);
}
#ifdef USE_STB_TRUETYPE
#if defined(USE_STB_TRUETYPE) || defined(USE_FREETYPE2)
static void set_font(MwWidget handle) {
void* f;
MwWidget h = handle;
@@ -474,7 +474,7 @@ void MwSetDefault(MwWidget handle) {
#else
inherit_integer(handle, MwNmodernLook, 1);
#endif
#ifdef USE_STB_TRUETYPE
#if defined(USE_STB_TRUETYPE) || defined(USE_FREETYPE2)
set_font(handle);
set_boldfont(handle);
#endif

View File

@@ -1,7 +1,7 @@
/* $Id$ */
#include <Mw/Milsko.h>
#ifdef USE_STB_TRUETYPE
#if defined(USE_STB_TRUETYPE) || defined(USE_FREETYPE2)
unsigned char MwBoldTTFData[] = {
0x00, 0x01, 0x00, 0x00, 0x00, 0x11, 0x01, 0x00, 0x00, 0x04, 0x00, 0x10,
0x46, 0x46, 0x54, 0x4d, 0xab, 0xe1, 0x51, 0x39, 0x00, 0x00, 0x56, 0x68,

View File

@@ -1,7 +1,18 @@
/* $Id$ */
#include <Mw/Milsko.h>
#ifdef USE_STB_TRUETYPE
#if defined(USE_FREETYPE2)
#include <ft2build.h>
#include FT_FREETYPE_H
typedef struct ttf {
FT_Library library;
FT_Face face;
void* data;
} ttf_t;
#define TTF
#elif defined(USE_STB_TRUETYPE)
#include "../../external/stb_truetype.h"
typedef struct ttf {
@@ -11,6 +22,8 @@ typedef struct ttf {
int ascent;
int descent;
} ttf_t;
#define TTF
#endif
#define FontWidth 7
@@ -80,10 +93,9 @@ static void bitmap_MwDrawText(MwWidget handle, MwPoint* point, const char* text,
free(px);
}
#ifdef USE_STB_TRUETYPE
#if defined(USE_STB_TRUETYPE)
static int ttf_MwDrawText(MwWidget handle, MwPoint* point, const char* text, int bold, int align, MwLLColor color) {
ttf_t* ttf = MwGetVoid(handle, bold ? MwNboldFont : MwNfont);
MwLLColor base;
unsigned char* px;
int tw, th;
MwRect r;
@@ -92,8 +104,6 @@ static int ttf_MwDrawText(MwWidget handle, MwPoint* point, const char* text, int
int x = 0;
if(ttf == NULL) return 1;
base = MwParseColor(handle, MwGetText(handle, MwNbackground));
tw = MwTextWidth(handle, text);
th = MwTextHeight(handle, text);
px = malloc(tw * th * 4);
@@ -149,12 +159,10 @@ static int ttf_MwDrawText(MwWidget handle, MwPoint* point, const char* text, int
MwLLDestroyPixmap(p);
free(px);
MwLLFreeColor(base);
return 0;
}
int ttf_MwTextWidth(MwWidget handle, const char* text) {
static int ttf_MwTextWidth(MwWidget handle, const char* text) {
ttf_t* ttf = MwGetVoid(handle, MwNfont);
int ax, lsb;
int tw = 0;
@@ -172,26 +180,108 @@ int ttf_MwTextWidth(MwWidget handle, const char* text) {
return tw;
}
int ttf_MwTextHeight(MwWidget handle, int count) {
static int ttf_MwTextHeight(MwWidget handle, int count) {
ttf_t* ttf = MwGetVoid(handle, MwNfont);
if(ttf == NULL) return -1;
return (ttf->ascent - ttf->descent) * ttf->scale * count;
}
#elif defined(USE_FREETYPE2)
static int ttf_MwDrawText(MwWidget handle, MwPoint* point, const char* text, int bold, int align, MwLLColor color) {
ttf_t* ttf = MwGetVoid(handle, bold ? MwNboldFont : MwNfont);
int tw, th;
unsigned char* px;
MwLLPixmap p;
MwRect r;
int x = 0;
if(ttf == NULL) return 1;
tw = MwTextWidth(handle, text);
th = MwTextHeight(handle, text);
px = malloc(tw * th * 4);
memset(px, 0, tw * th * 4);
while(text[0] != 0) {
int c;
FT_Bitmap* bmp;
int cy, cx;
text += MwUTF8ToUTF32(text, &c);
FT_Load_Char(ttf->face, c, FT_LOAD_RENDER);
bmp = &ttf->face->glyph->bitmap;
for(cy = 0; cy < bmp->rows; cy++) {
for(cx = 0; cx < bmp->width; cx++) {
int ox = x + cx + ttf->face->glyph->bitmap_left;
int oy = th - ttf->face->glyph->bitmap_top + cy + (ttf->face->descender * 14 / ttf->face->units_per_EM);
unsigned char* opx = &px[(oy * tw + ox) * 4];
opx[0] = color->red;
opx[1] = color->green;
opx[2] = color->blue;
opx[3] = bmp->buffer[cy * bmp->pitch + cx];
}
}
x += ttf->face->glyph->metrics.horiAdvance / 64;
}
p = MwLoadRaw(handle, px, tw, th);
r.x = point->x;
r.y = point->y - th / 2;
r.width = tw;
r.height = th;
if(align == MwALIGNMENT_CENTER) {
r.x -= tw / 2;
} else if(align == MwALIGNMENT_END) {
r.x -= tw;
}
MwLLDrawPixmap(handle->lowlevel, &r, p);
MwLLDestroyPixmap(p);
free(px);
return 0;
}
static int ttf_MwTextWidth(MwWidget handle, const char* text) {
ttf_t* ttf = MwGetVoid(handle, MwNfont);
int tw = 0;
if(ttf == NULL) return -1;
while(text[0] != 0) {
int c;
text += MwUTF8ToUTF32(text, &c);
FT_Load_Char(ttf->face, c, FT_LOAD_RENDER);
tw += ttf->face->glyph->metrics.horiAdvance / 64;
}
return tw;
}
static int ttf_MwTextHeight(MwWidget handle, int count) {
ttf_t* ttf = MwGetVoid(handle, MwNfont);
if(ttf == NULL) return -1;
return (ttf->face->height * 14 / ttf->face->units_per_EM) * count;
}
#endif
void MwDrawText(MwWidget handle, MwPoint* point, const char* text, int bold, int align, MwLLColor color) {
#ifdef USE_STB_TRUETYPE
#ifdef TTF
if(ttf_MwDrawText(handle, point, text, bold, align, color))
#endif
bitmap_MwDrawText(handle, point, text, bold, align, color);
}
int MwTextWidth(MwWidget handle, const char* text) {
/* TODO: check newline */
#ifdef TTF
int st;
/* TODO: check newline */
#ifdef USE_STB_TRUETYPE
if((st = ttf_MwTextWidth(handle, text)) != -1) return st;
#else
(void)handle;
@@ -203,7 +293,9 @@ int MwTextWidth(MwWidget handle, const char* text) {
int MwTextHeight(MwWidget handle, const char* text) {
int c = 1;
int i = 0;
#ifdef TTF
int st;
#endif
(void)handle;
(void)text;
@@ -214,14 +306,24 @@ int MwTextHeight(MwWidget handle, const char* text) {
if(out == '\n') c++;
}
#ifdef USE_STB_TRUETYPE
#ifdef TTF
if((st = ttf_MwTextHeight(handle, c)) != -1) return st;
#endif
return FontHeight * c;
}
void* MwFontLoad(unsigned char* data, unsigned int size) {
#ifdef USE_STB_TRUETYPE
#if defined(USE_FREETYPE2)
ttf_t* ttf = malloc(sizeof(*ttf));
ttf->data = malloc(size);
memcpy(ttf->data, data, size);
FT_Init_FreeType(&ttf->library);
FT_New_Memory_Face(ttf->library, ttf->data, size, 0, &ttf->face);
FT_Set_Pixel_Sizes(ttf->face, 0, 14);
return ttf;
#elif defined(USE_STB_TRUETYPE)
ttf_t* ttf = malloc(sizeof(*ttf));
ttf->data = malloc(size);
memcpy(ttf->data, data, size);
@@ -232,12 +334,22 @@ void* MwFontLoad(unsigned char* data, unsigned int size) {
return ttf;
#else
(void)data;
(void)size;
return NULL;
#endif
}
void MwFontFree(void* handle) {
#ifdef USE_STB_TRUETYPE
#if defined(USE_FREETYPE2)
ttf_t* ttf = handle;
FT_Done_Face(ttf->face);
FT_Done_FreeType(ttf->library);
free(ttf->data);
free(ttf);
#elif defined(USE_STB_TRUETYPE)
ttf_t* ttf = handle;
free(ttf->data);

View File

@@ -1,7 +1,7 @@
/* $Id$ */
#include <Mw/Milsko.h>
#ifdef USE_STB_TRUETYPE
#if defined(USE_STB_TRUETYPE) || defined(USE_FREETYPE2)
unsigned char MwTTFData[] = {
0x00, 0x01, 0x00, 0x00, 0x00, 0x11, 0x01, 0x00, 0x00, 0x04, 0x00, 0x10,
0x46, 0x46, 0x54, 0x4d, 0xab, 0xe1, 0x51, 0x56, 0x00, 0x00, 0x55, 0xe8,

View File

@@ -5,7 +5,7 @@ for out in src/text/ttf.c src/text/boldttf.c; do
echo '/* $Id$ */' > $out
echo '#include <Mw/Milsko.h>' >> $out
echo '' >> $out
echo '#ifdef USE_STB_TRUETYPE' >> $out
echo '#if defined(USE_STB_TRUETYPE) || defined(USE_FREETYPE2)' >> $out
done
xxd -n MwTTFData -i resource/IBMPlexMono.ttf | sed s/_len/Size/ >> src/text/ttf.c
xxd -n MwBoldTTFData -i resource/IBMPlexMono-Bold.ttf | sed s/_len/Size/ >> src/text/boldttf.c