Tune GlyphRunInfo

This commit is contained in:
Vincent Wei
2019-03-16 19:12:57 +08:00
parent 349f310148
commit d63fe9849b
3 changed files with 134 additions and 48 deletions
+43 -6
View File
@@ -12199,8 +12199,15 @@ MG_EXPORT int GUIAPI UChars2AChars(LOGFONT* logfont, const Uchar32* ucs,
/** @} end of glyph_render_flags */
#define GLYPH_ORIENTATION_UPRIGHT 0
#define GLYPH_ORIENTATION_SIDEWAYS 1
#define GLYPH_GRAVITY_NORTH 0
#define GLYPH_GRAVITY_EAST 1
#define GLYPH_GRAVITY_WEST 2
#define GLYPH_GRAVITY_SOUTH 3
#define GLYPH_ORIENTATION_UPRIGHT GLYPH_GRAVITY_NORTH
#define GLYPH_ORIENTATION_SIDEWAYS GLYPH_GRAVITY_EAST
#define GLYPH_ORIENTATION_SIDEWAYS_LEFT GLYPH_GRAVITY_WEST
#define GLYPH_ORIENTATION_INVERTED GLYPH_GRAVITY_SOUTH
#define GLYPH_HANGED_NONE 0
#define GLYPH_HANGED_START 1
@@ -12232,6 +12239,10 @@ typedef struct _GLYPHEXTINFO {
* the glyph is in the standard horizontal orientation.
* - GLYPH_ORIENTATION_SIDEWAYS\n
* the glyph rotates 90° clockwise from horizontal.
* - GLYPH_ORIENTATION_SIDEWAYS_LEFT\n
* the glyph rotates 90° counter-clockwise from horizontal.
* - GLYPH_ORIENTATION_INVERTED\n
* the glyph is in the inverted horizontal orientation.
*/
Uint8 orientation:2;
} GLYPHEXTINFO;
@@ -12262,6 +12273,10 @@ typedef struct _GLYPHPOS {
* the glyph is in the standard horizontal orientation.
* - GLYPH_ORIENTATION_SIDEWAYS\n
* the glyph rotates 90° clockwise from horizontal.
* - GLYPH_ORIENTATION_SIDEWAYS_LEFT\n
* the glyph rotates 90° counter-clockwise from horizontal.
* - GLYPH_ORIENTATION_INVERTED\n
* the glyph is in the inverted horizontal orientation.
*/
Uint8 orientation:2;
/**
@@ -12365,6 +12380,23 @@ MG_EXPORT int GUIAPI GetGlyphsExtentFromUChars(LOGFONT* logfont_upright,
struct _GLYPHRUNINFO;
typedef struct _GLYPHRUNINFO GLYPHRUNINFO;
/* same as HarfBuzz */
typedef enum {
GLYPH_RUN_DIR_INVALID = 0,
GLYPH_RUN_DIR_LTR = 4,
GLYPH_RUN_DIR_RTL,
GLYPH_RUN_DIR_TTB,
GLYPH_RUN_DIR_BTT
} GlyphRunDir;
typedef enum {
GLYPH_ORIENT_NORTH = GLYPH_GRAVITY_NORTH,
GLYPH_ORIENT_EAST = GLYPH_GRAVITY_EAST,
GLYPH_ORIENT_WEST = GLYPH_GRAVITY_WEST,
GLYPH_ORIENT_SOUTH = GLYPH_GRAVITY_SOUTH,
GLYPH_ORIENT_MIXED,
} GlyphOrient;
/**
* Split a Uchar32 paragraph string into text runs according to the
* scripts of characters.
@@ -12372,11 +12404,10 @@ typedef struct _GLYPHRUNINFO GLYPHRUNINFO;
* This function also calculates the embedding levels and the
* breaking opportunities of the string.
*/
MG_EXPORT GLYPHRUNINFO* GUIAPI CreateGlyphRunInfo(
MG_EXPORT GLYPHRUNINFO* GUIAPI CreateGlyphRunInfo(Uchar32* ucs, int nr_ucs,
const char* lang_tag, const char* script_tag,
Uchar32* ucs, int nr_ucs, ParagraphDir base_dir,
Uint8 ctr, Uint8 wbr, Uint8 lbp,
LOGFONT* logfont, RGBCOLOR color);
GlyphRunDir run_dir, GlyphOrient glyph_orient, ParagraphDir base_dir,
Uint8 ctr, Uint8 wbr, Uint8 lbp, LOGFONT* logfont, RGBCOLOR color);
/**
* Set font of part characters. Please call this function before
@@ -12410,6 +12441,12 @@ MG_EXPORT BOOL GUIAPI ResetColorInGlyphRuns(GLYPHRUNINFO* run_info,
MG_EXPORT BOOL GUIAPI ResetBreaksInGlyphRuns(GLYPHRUNINFO* run_info,
Uint8 ctr, Uint8 wbr, Uint8 lbp);
/**
* Reset the direction and orientation of glyph runs.
*/
MG_EXPORT BOOL GUIAPI ResetDirectionInGlyphRuns(GLYPHRUNINFO* run_info,
GlyphRunDir run_dir, GlyphOrient glyph_orient);
/**
* Destroy the glyph run info object. It also frees all data allocated
* for shapping and layouting the glyphs.
+73 -16
View File
@@ -66,11 +66,10 @@ static BOOL init_glyph_runs(GLYPHRUNINFO* runinfo)
return FALSE;
}
GLYPHRUNINFO* GUIAPI CreateGlyphRunInfo(
GLYPHRUNINFO* GUIAPI CreateGlyphRunInfo(Uchar32* ucs, int nr_ucs,
const char* lang_tag, const char* script_tag,
Uchar32* ucs, int nr_ucs, ParagraphDir base_dir,
Uint8 ctr, Uint8 wbr, Uint8 lbp,
LOGFONT* logfont, RGBCOLOR color)
GlyphRunDir run_dir, GlyphOrient glyph_orient, ParagraphDir base_dir,
Uint8 ctr, Uint8 wbr, Uint8 lbp, LOGFONT* logfont, RGBCOLOR color)
{
BOOL ok = FALSE;
@@ -151,12 +150,16 @@ GLYPHRUNINFO* GUIAPI CreateGlyphRunInfo(
runinfo->run_head.lf = logfont;
runinfo->run_head.gs = NULL;
runinfo->run_head.nr_gs = 0;
runinfo->run_head.lt = lang_tag;
runinfo->run_head.st = script_type;
runinfo->run_head.dir = base_dir;
runinfo->run_head.si = 0;
runinfo->run_head.nr_ucs = nr_ucs;
runinfo->run_head.lt = lang_tag;
runinfo->run_head.st = script_type;
runinfo->run_head.level = BIDI_DIR_TO_LEVEL(base_dir);
runinfo->run_head.dir = run_dir;
runinfo->run_head.ort = glyph_orient;
// make the embedding levels of the bidi marks to be -1.
level_or = 0, level_and = 1;
j = 0;
@@ -206,8 +209,19 @@ out:
}
BOOL GUIAPI SetPartFontInGlyphRuns(GLYPHRUNINFO* runinfo,
int start_index, int length, LOGFONT* logfont)
int start_index, int length, LOGFONT* logfont)
{
if (runinfo == NULL)
return FALSE;
// can not change font after shaped the glyphs
if (runinfo->se.engine != NULL)
return FALSE;
// can not change font for empty runs
if (list_empty(&runinfo->run_head.list))
return FALSE;
return FALSE;
}
@@ -228,7 +242,7 @@ RGBCOLOR __mg_glyphruns_get_color(const GLYPHRUNINFO* runinfo, int index)
}
BOOL GUIAPI SetPartColorInGlyphRuns(GLYPHRUNINFO* runinfo,
int start_index, int length, RGBCOLOR color)
int start_index, int length, RGBCOLOR color)
{
UCHARCOLORMAP* color_entry = NULL;
@@ -263,12 +277,12 @@ BOOL GUIAPI ResetFontInGlyphRuns(GLYPHRUNINFO* runinfo, LOGFONT* logfont)
while (!list_empty(&runinfo->run_head.list)) {
GLYPHRUN* run = (GLYPHRUN*)runinfo->run_head.list.prev;
list_del(runinfo->run_head.list.prev);
runinfo->se.cb_destroy_glyphs(runinfo->se.shaping_engine, run->gs);
runinfo->se.destroy_glyphs(runinfo->se.engine, run->gs);
free(run);
}
if (runinfo->se.shaping_engine) {
runinfo->se.cb_destroy_engine(runinfo->se.shaping_engine);
if (runinfo->se.engine) {
runinfo->se.destroy_engine(runinfo->se.engine);
}
if (runinfo->l2g) {
@@ -286,6 +300,49 @@ BOOL GUIAPI ResetFontInGlyphRuns(GLYPHRUNINFO* runinfo, LOGFONT* logfont)
return init_glyph_runs(runinfo);
}
static void set_run_dir(GLYPHRUNINFO* runinfo, GLYPHRUN* run,
GlyphRunDir run_dir, GlyphOrient glyph_orient)
{
}
BOOL GUIAPI ResetDirectionInGlyphRuns(GLYPHRUNINFO* runinfo,
GlyphRunDir run_dir, GlyphOrient glyph_orient)
{
struct list_head *i;
if (runinfo == NULL)
return FALSE;
runinfo->run_head.dir = run_dir;
runinfo->run_head.ort = glyph_orient;
list_for_each(i, &runinfo->run_head.list) {
GLYPHRUN* run = (GLYPHRUN*)i;
if (runinfo->se.engine && run->gs) {
runinfo->se.destroy_glyphs(runinfo->se.engine, run->gs);
}
set_run_dir(runinfo, run, run_dir, glyph_orient);
}
if (runinfo->l2g) {
free(runinfo->l2g);
runinfo->l2g = NULL;
}
if (runinfo->ges) {
free(runinfo->ges);
runinfo->ges = NULL;
}
if (runinfo->se.engine) {
runinfo->se.destroy_engine(runinfo->se.engine);
runinfo->se.engine = NULL;
}
return TRUE;
}
BOOL GUIAPI ResetColorInGlyphRuns(GLYPHRUNINFO* runinfo, RGBCOLOR color)
{
if (runinfo == NULL)
@@ -312,7 +369,7 @@ BOOL GUIAPI ResetBreaksInGlyphRuns(GLYPHRUNINFO* runinfo,
runinfo->bos = NULL;
}
// Calculate the breaking opportunities
// Re-calculate the breaking opportunities
if (UStrGetBreaks(runinfo->run_head.st, ctr, wbr, lbp,
runinfo->ucs, runinfo->run_head.nr_ucs, &runinfo->bos) == 0) {
_DBG_PRINTF("%s: failed to get breaking opportunities.\n");
@@ -336,12 +393,12 @@ BOOL GUIAPI DestroyGlyphRunInfo(GLYPHRUNINFO* runinfo)
while (!list_empty(&runinfo->run_head.list)) {
GLYPHRUN* run = (GLYPHRUN*)runinfo->run_head.list.prev;
list_del(runinfo->run_head.list.prev);
runinfo->se.cb_destroy_glyphs(runinfo->se.shaping_engine, run->gs);
runinfo->se.destroy_glyphs(runinfo->se.engine, run->gs);
free(run);
}
if (runinfo->se.shaping_engine) {
runinfo->se.cb_destroy_engine(runinfo->se.shaping_engine);
if (runinfo->se.engine) {
runinfo->se.destroy_engine(runinfo->se.engine);
}
if (runinfo->l2g) free(runinfo->l2g);
+18 -26
View File
@@ -43,55 +43,47 @@
#include "list.h"
typedef Glyph32 (*CB_GET_GLYPH_INFO) (void* shaping_engine,
typedef Glyph32 (*CB_GET_GLYPH_INFO) (void* engine,
void* glyph_infos, int index, int* cluster);
typedef BOOL (*CB_DESTROY_GLYPHS) (void* shaping_engine, void* glyph_infos);
typedef BOOL (*CB_DESTROY_GLYPHS) (void* engine, void* glyph_infos);
typedef BOOL (*CB_DESTROY_ENGINE) (void* shaping_engine);
typedef BOOL (*CB_DESTROY_ENGINE) (void* engine);
typedef struct _SHAPPINGENGINE {
/* The pointer to the shaping engine */
void* shaping_engine;
void* engine;
/* the callback reverse the glyphs */
CB_REVERSE_ARRAY cb_reverse_glyphs;
CB_REVERSE_ARRAY reverse_glyphs;
/* The callback returns the glyph value and cluster
from a void glyph information */
CB_GET_GLYPH_INFO cb_get_glyph_info;
CB_GET_GLYPH_INFO get_glyph_info;
/* the callback destroy the shaped glyph info */
CB_DESTROY_GLYPHS cb_destroy_glyphs;
CB_DESTROY_GLYPHS destroy_glyphs;
/* the callback destroy the shapping engine instance */
CB_DESTROY_ENGINE cb_destroy_engine;
CB_DESTROY_ENGINE destroy_engine;
} SHAPPINGENGINE;
/* same as HarfBuzz */
typedef enum {
GR_DIRECTION_INVALID = 0,
GR_DIRECTION_LTR = 4,
GR_DIRECTION_RTL,
GR_DIRECTION_TTB,
GR_DIRECTION_BTT
} GlyphRunDir;
typedef struct _GLYPHRUN {
struct list_head list;
LOGFONT* lf; // The logfont for this run.
LOGFONT* lf; // the logfont for this run.
const char* lt; // language tag
void* gs; // the shaped glyph information
int nr_gs; // the number of shaped glyphs
int si; // start index in the Unicode string
int nr_ucs; // the number of Unicode characters
int si; // start index
int nr_ucs; // the number of characters
ScriptType st; // script type
GlyphRunDir dir; // The direction
Uint8 all_even;
Uint8 all_odd;
Uint32 st:8; // script type
Uint32 level:8; // the bidi level
Uint32 dir:4; // the run direction
Uint32 ort:2; // the glyph orientation
Uint32 all_even:1; // flag indicating all level is even
Uint8 all_odd:1; // flag indicating all level is odd
} GLYPHRUN;
// NOTE: we arrange the fields carefully to avoid wasting space when