diff --git a/README.md b/README.md index 4f9709be..c0e2f4a7 100644 --- a/README.md +++ b/README.md @@ -5,7 +5,7 @@ NanoVG is small antialiased vector graphics rendering library for OpenGL. It has ## Screenshot -![screenshot of some text rendered witht the sample program](/example/screenshot-01.png?raw=true) +![screenshot of some text rendered with the sample program](/example/screenshot-01.png?raw=true) Usage ===== diff --git a/src/fontstash.h b/src/fontstash.h index 9df68b31..698e406d 100644 --- a/src/fontstash.h +++ b/src/fontstash.h @@ -102,8 +102,8 @@ int fonsExpandAtlas(FONScontext* s, int width, int height); int fonsResetAtlas(FONScontext* stash, int width, int height); // Add fonts -int fonsAddFont(FONScontext* s, const char* name, const char* path); -int fonsAddFontMem(FONScontext* s, const char* name, unsigned char* data, int ndata, int freeData); +int fonsAddFont(FONScontext* s, const char* name, const char* path, int faceIdx); +int fonsAddFontMem(FONScontext* s, const char* name, unsigned char* data, int ndata, int faceIdx, int freeData); int fonsGetFontByName(FONScontext* s, const char* name); // State handling @@ -175,13 +175,13 @@ int fons__tt_done(FONScontext *context) return ftError == 0; } -int fons__tt_loadFont(FONScontext *context, FONSttFontImpl *font, unsigned char *data, int dataSize) +int fons__tt_loadFont(FONScontext *context, FONSttFontImpl *font, unsigned char *data, int dataSize, int faceIdx) { FT_Error ftError; FONS_NOTUSED(context); //font->font.userdata = stash; - ftError = FT_New_Memory_Face(ftLibrary, (const FT_Byte*)data, dataSize, 0, &font->font); + ftError = FT_New_Memory_Face(ftLibrary, (const FT_Byte*)data, dataSize, faceIdx, &font->font); return ftError == 0; } @@ -278,13 +278,18 @@ int fons__tt_done(FONScontext *context) return 1; } -int fons__tt_loadFont(FONScontext *context, FONSttFontImpl *font, unsigned char *data, int dataSize) +int fons__tt_loadFont(FONScontext *context, FONSttFontImpl *font, unsigned char *data, int dataSize, int faceIdx) { int stbError; FONS_NOTUSED(dataSize); + int offset = stbtt_GetFontOffsetForIndex(data, faceIdx); + + if (offset < 0) + return 0; + font->font.userdata = context; - stbError = stbtt_InitFont(&font->font, data, 0); + stbError = stbtt_InitFont(&font->font, data, offset); return stbError; } @@ -413,7 +418,7 @@ struct FONSstate typedef struct FONSstate FONSstate; struct FONSatlasNode { - short x, y, width; + short x, y, width; }; typedef struct FONSatlasNode FONSatlasNode; @@ -504,11 +509,11 @@ static unsigned int fons__decutf8(unsigned int* state, unsigned int* codep, unsi 12,12,12,12,12,12,12,24,12,12,12,12, 12,24,12,12,12,12,12,12,12,24,12,12, 12,12,12,12,12,12,12,36,12,36,12,12, 12,36,12,12,12,12,12,36,12,36,12,12, 12,36,12,12,12,12,12,12,12,12,12,12, - }; + }; unsigned int type = utf8d[byte]; - *codep = (*state != FONS_UTF8_ACCEPT) ? + *codep = (*state != FONS_UTF8_ACCEPT) ? (byte & 0x3fu) | (*codep << 6) : (0xff >> type) & (byte); @@ -890,7 +895,7 @@ static int fons__allocFont(FONScontext* stash) return FONS_INVALID; } -int fonsAddFont(FONScontext* stash, const char* name, const char* path) +int fonsAddFont(FONScontext* stash, const char* name, const char* path, int faceIdx) { FILE* fp = 0; int dataSize = 0; @@ -910,7 +915,7 @@ int fonsAddFont(FONScontext* stash, const char* name, const char* path) fp = 0; if (readed != dataSize) goto error; - return fonsAddFontMem(stash, name, data, dataSize, 1); + return fonsAddFontMem(stash, name, data, dataSize, faceIdx, 1); error: if (data) free(data); @@ -918,7 +923,7 @@ int fonsAddFont(FONScontext* stash, const char* name, const char* path) return FONS_INVALID; } -int fonsAddFontMem(FONScontext* stash, const char* name, unsigned char* data, int dataSize, int freeData) +int fonsAddFontMem(FONScontext* stash, const char* name, unsigned char* data, int dataSize, int faceIdx, int freeData) { int i, ascent, descent, fh, lineGap; FONSfont* font; @@ -943,7 +948,7 @@ int fonsAddFontMem(FONScontext* stash, const char* name, unsigned char* data, in // Init font stash->nscratch = 0; - if (!fons__tt_loadFont(stash, &font->font, data, dataSize)) goto error; + if (!fons__tt_loadFont(stash, &font->font, data, dataSize, faceIdx)) goto error; // Store normalized line height. The real line height is got // by multiplying the lineh by font size. diff --git a/src/nanovg.c b/src/nanovg.c index a28804fb..29eb67b1 100644 --- a/src/nanovg.c +++ b/src/nanovg.c @@ -337,7 +337,7 @@ NVGcontext* nvgCreateInternal(NVGparams* params) NVGparams* nvgInternalParams(NVGcontext* ctx) { - return &ctx->params; + return &ctx->params; } void nvgDeleteInternal(NVGcontext* ctx) @@ -1989,13 +1989,13 @@ void nvgBezierTo(NVGcontext* ctx, float c1x, float c1y, float c2x, float c2y, fl void nvgQuadTo(NVGcontext* ctx, float cx, float cy, float x, float y) { - float x0 = ctx->commandx; - float y0 = ctx->commandy; - float vals[] = { NVG_BEZIERTO, - x0 + 2.0f/3.0f*(cx - x0), y0 + 2.0f/3.0f*(cy - y0), - x + 2.0f/3.0f*(cx - x), y + 2.0f/3.0f*(cy - y), - x, y }; - nvg__appendCommands(ctx, vals, NVG_COUNTOF(vals)); + float x0 = ctx->commandx; + float y0 = ctx->commandy; + float vals[] = { NVG_BEZIERTO, + x0 + 2.0f/3.0f*(cx - x0), y0 + 2.0f/3.0f*(cy - y0), + x + 2.0f/3.0f*(cx - x), y + 2.0f/3.0f*(cy - y), + x, y }; + nvg__appendCommands(ctx, vals, NVG_COUNTOF(vals)); } void nvgArcTo(NVGcontext* ctx, float x1, float y1, float x2, float y2, float radius) @@ -2289,12 +2289,22 @@ void nvgStroke(NVGcontext* ctx) // Add fonts int nvgCreateFont(NVGcontext* ctx, const char* name, const char* path) { - return fonsAddFont(ctx->fs, name, path); + return nvgCreateFontFace(ctx, name, path, 0); +} + +int nvgCreateFontFace(NVGcontext* ctx, const char* name, const char* path, int faceIdx) +{ + return fonsAddFont(ctx->fs, name, path, faceIdx); } int nvgCreateFontMem(NVGcontext* ctx, const char* name, unsigned char* data, int ndata, int freeData) { - return fonsAddFontMem(ctx->fs, name, data, ndata, freeData); + return nvgCreateFontFaceMem(ctx, name, data, ndata, 0, freeData); +} + +int nvgCreateFontFaceMem(NVGcontext* ctx, const char* name, unsigned char* data, int ndata, int faceIdx, int freeData) +{ + return fonsAddFontMem(ctx->fs, name, data, ndata, faceIdx, freeData); } int nvgFindFont(NVGcontext* ctx, const char* name) diff --git a/src/nanovg.h b/src/nanovg.h index 2255d6a6..7128f77b 100644 --- a/src/nanovg.h +++ b/src/nanovg.h @@ -136,7 +136,7 @@ struct NVGtextRow { typedef struct NVGtextRow NVGtextRow; enum NVGimageFlags { - NVG_IMAGE_GENERATE_MIPMAPS = 1<<0, // Generate mipmaps during creation of the image. + NVG_IMAGE_GENERATE_MIPMAPS = 1<<0, // Generate mipmaps during creation of the image. NVG_IMAGE_REPEATX = 1<<1, // Repeat image in X direction. NVG_IMAGE_REPEATY = 1<<2, // Repeat image in Y direction. NVG_IMAGE_FLIPY = 1<<3, // Flips (inverses) image in Y direction when rendered. @@ -546,10 +546,18 @@ void nvgStroke(NVGcontext* ctx); // Returns handle to the font. int nvgCreateFont(NVGcontext* ctx, const char* name, const char* filename); +// Creates font by loading it from the disk from specified file name, loading a specific face by index. +// Returns handle to the font. +int nvgCreateFontFace(NVGcontext* ctx, const char* name, const char* filename, int faceIdx); + // Creates font by loading it from the specified memory chunk. // Returns handle to the font. int nvgCreateFontMem(NVGcontext* ctx, const char* name, unsigned char* data, int ndata, int freeData); +// Creates font by loading it from the specified memory chunk, loading a specific face by index. +// Returns handle to the font. +int nvgCreateFontFaceMem(NVGcontext* ctx, const char* name, unsigned char* data, int ndata, int faceIdx, int freeData); + // Finds a loaded font of specified name, and returns handle to it, or -1 if the font is not found. int nvgFindFont(NVGcontext* ctx, const char* name);