mirror of
https://github.com/VincentWei/MiniGUI.git
synced 2026-09-24 09:14:09 +08:00
debug DrawShapedGlyph
This commit is contained in:
+12
-4
@@ -13025,8 +13025,6 @@ MG_EXPORT BOOL GUIAPI GetLayoutLineSize(LAYOUTLINE* line,
|
||||
*
|
||||
* \return The number of lines laid out.
|
||||
*
|
||||
* \sa CreateLayoutInfo, DestroyLayoutInfo, LayoutNextLine
|
||||
*
|
||||
* \note The position coordinates of the first line are
|
||||
* with respect to the top-left corner of the output rectangle
|
||||
* if the writing mode is GRF_WRITING_MODE_HORIZONTAL_TB or
|
||||
@@ -13035,6 +13033,8 @@ MG_EXPORT BOOL GUIAPI GetLayoutLineSize(LAYOUTLINE* line,
|
||||
* the top-right corner if the writing mode is
|
||||
* GRF_WRITING_MODE_VERTICAL_RL.
|
||||
*
|
||||
* \sa CreateLayoutInfo, DestroyLayoutInfo, LayoutNextLine
|
||||
*
|
||||
* Since 3.4.0
|
||||
*/
|
||||
MG_EXPORT int GUIAPI CalcLayoutBoundingRect(LAYOUTINFO* layout_info,
|
||||
@@ -13076,7 +13076,7 @@ MG_EXPORT BOOL DrawShapedGlyph(HDC hdc,
|
||||
|
||||
/**
|
||||
* \fn DrawLayoutLine(HDC hdc, const LAYOUTLINE* line,
|
||||
* int x, int y, RECT* bounding)
|
||||
* int x, int y)
|
||||
* \brief Draw a laid out line at the specific position.
|
||||
*
|
||||
* This function draws a laied out line at the specified position.
|
||||
@@ -13095,12 +13095,20 @@ MG_EXPORT BOOL DrawShapedGlyph(HDC hdc,
|
||||
*
|
||||
* \return The number of glyphs drawn.
|
||||
*
|
||||
* \note The position coordinates of the first line are
|
||||
* with respect to the top-left corner of the output rectangle
|
||||
* if the writing mode is GRF_WRITING_MODE_HORIZONTAL_TB or
|
||||
* GRF_WRITING_MODE_VERTICAL_LR, the bottom-left corner if
|
||||
* the writing mode is GRF_WRITING_MODE_HORIZONTAL_BT,
|
||||
* the top-right corner if the writing mode is
|
||||
* GRF_WRITING_MODE_VERTICAL_RL.
|
||||
*
|
||||
* \sa CreateLayoutInfo, DestroyLayoutInfo, LayoutNextLine
|
||||
*
|
||||
* Since 3.4.0
|
||||
*/
|
||||
MG_EXPORT int DrawLayoutLine(HDC hdc, const LAYOUTLINE* line,
|
||||
int* x, int* y, RECT* bounding);
|
||||
int x, int y);
|
||||
|
||||
#ifdef _MGDEVEL_MODE
|
||||
typedef struct _TextRun TEXTRUN;
|
||||
|
||||
+6
-1
@@ -993,7 +993,12 @@ DEVFONT* GUIAPI LoadDevFontFromFile(const char *devfont_name,
|
||||
|
||||
void GUIAPI DestroyDynamicDevFont (DEVFONT** devfont)
|
||||
{
|
||||
font_DelDevFont ((*devfont)->name);
|
||||
char font_name [LEN_UNIDEVFONT_NAME + 1];
|
||||
|
||||
memset(font_name, 0, LEN_UNIDEVFONT_NAME + 1);
|
||||
strncpy(font_name, (*devfont)->name, LEN_UNIDEVFONT_NAME);
|
||||
|
||||
font_DelDevFont (font_name);
|
||||
*devfont = NULL;
|
||||
}
|
||||
|
||||
|
||||
@@ -56,6 +56,7 @@
|
||||
#include "cursor.h"
|
||||
#include "drawtext.h"
|
||||
#include "glyph.h"
|
||||
#include "layoutinfo.h"
|
||||
|
||||
#ifdef _MGCHARSET_UNICODE
|
||||
|
||||
@@ -71,12 +72,9 @@ BOOL DrawShapedGlyph(HDC hdc, Glyph32 gv,
|
||||
render_data->uc_index);
|
||||
|
||||
if (glyph_pos->suppressed == 0 && glyph_pos->whitespace == 0) {
|
||||
Uint32 old_ta;
|
||||
PLOGFONT old_lf = NULL;
|
||||
gal_pixel fg_pixel, bg_pixel;
|
||||
|
||||
old_ta = SetTextAlign(hdc, TA_LEFT | TA_TOP | TA_UPDATECP);
|
||||
|
||||
old_lf = SelectFont(hdc, render_data->logfont);
|
||||
|
||||
fg_color = GetTextColorInTextRuns(render_data->truninfo,
|
||||
@@ -93,12 +91,11 @@ BOOL DrawShapedGlyph(HDC hdc, Glyph32 gv,
|
||||
SetBkMode(hdc, BM_TRANSPARENT);
|
||||
}
|
||||
|
||||
DrawGlyph(hdc, glyph_pos->x, glyph_pos->y, gv, NULL, NULL);
|
||||
DrawGlyph(hdc, glyph_pos->x + glyph_pos->x_off,
|
||||
glyph_pos->y + glyph_pos->y_off, gv, NULL, NULL);
|
||||
|
||||
if (old_lf)
|
||||
SelectFont(hdc, old_lf);
|
||||
|
||||
SetTextAlign(hdc, old_ta);
|
||||
}
|
||||
else if (glyph_pos->whitespace && bg_color) {
|
||||
// TODO: draw background for whitespace.
|
||||
@@ -107,10 +104,81 @@ BOOL DrawShapedGlyph(HDC hdc, Glyph32 gv,
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
int DrawLayoutLine(HDC hdc, const LAYOUTLINE* line,
|
||||
int* x, int* y, RECT* bounding)
|
||||
int DrawLayoutLine(HDC hdc, const LAYOUTLINE* line, int x, int y)
|
||||
{
|
||||
return 0;
|
||||
int n, log_x = 0, log_y = 0;
|
||||
struct list_head* i;
|
||||
const TEXTRUNSINFO* truninfo;
|
||||
const LAYOUTINFO* layout;
|
||||
Uint32 old_ta;
|
||||
PLOGFONT old_lf = NULL;
|
||||
|
||||
if (line == NULL)
|
||||
return 0;
|
||||
|
||||
layout = line->layout;
|
||||
truninfo = layout->truninfo;
|
||||
|
||||
if ((layout->rf & GRF_WRITING_MODE_MASK) ==
|
||||
GRF_WRITING_MODE_HORIZONTAL_BT)
|
||||
old_ta = SetTextAlign(hdc, TA_LEFT | TA_BOTTOM | TA_NOUPDATECP);
|
||||
else if ((layout->rf & GRF_WRITING_MODE_MASK) ==
|
||||
GRF_WRITING_MODE_VERTICAL_RL)
|
||||
old_ta = SetTextAlign(hdc, TA_RIGHT | TA_TOP | TA_NOUPDATECP);
|
||||
else
|
||||
old_ta = SetTextAlign(hdc, TA_LEFT | TA_TOP | TA_NOUPDATECP);
|
||||
old_lf = GetCurFont(hdc);
|
||||
|
||||
list_for_each(i, &line->gruns) {
|
||||
GlyphRun* run = (GlyphRun*)i;
|
||||
int j;
|
||||
|
||||
SelectFont(hdc, run->lrun->lf);
|
||||
for (j = 0; j < run->gstr->nr_glyphs; j++) {
|
||||
int dev_x, dev_y;
|
||||
|
||||
ShapedGlyph* gi = run->gstr->glyphs + j;
|
||||
int log_index = run->lrun->si + run->gstr->log_clusters[j];
|
||||
RGBCOLOR bg_color, fg_color;
|
||||
|
||||
// We might use an interator to optimize the color settings.
|
||||
fg_color = GetTextColorInTextRuns(truninfo, log_index);
|
||||
bg_color = GetBackgroundColorInTextRuns(truninfo, log_index);
|
||||
SetTextColor(hdc, DWORD2Pixel(hdc, fg_color));
|
||||
if (bg_color) {
|
||||
SetBkColor(hdc, DWORD2Pixel(hdc, bg_color));
|
||||
SetBkMode(hdc, BM_OPAQUE);
|
||||
}
|
||||
else {
|
||||
SetBkMode(hdc, BM_TRANSPARENT);
|
||||
}
|
||||
|
||||
if (run->lrun->dir == GLYPH_RUN_DIR_TTB ||
|
||||
run->lrun->dir == GLYPH_RUN_DIR_BTT) {
|
||||
dev_y = log_x + gi->x_off;
|
||||
dev_x = log_y + gi->y_off;
|
||||
}
|
||||
else {
|
||||
dev_x = log_x + gi->x_off;
|
||||
dev_y = log_y + gi->y_off;
|
||||
}
|
||||
|
||||
if ((run->lrun->flags & LAYOUTRUN_FLAG_NO_SHAPING) &&
|
||||
gi->width > 0 && bg_color) {
|
||||
// FIXME: draw background here
|
||||
}
|
||||
else {
|
||||
DrawGlyph(hdc, x + dev_x, y + dev_y, gi->gv, NULL, NULL);
|
||||
n++;
|
||||
}
|
||||
|
||||
log_x += gi->width;
|
||||
}
|
||||
}
|
||||
|
||||
SelectFont(hdc, old_lf);
|
||||
SetTextAlign(hdc, old_ta);
|
||||
return n;
|
||||
}
|
||||
|
||||
#if 0
|
||||
|
||||
+1
-1
@@ -2275,7 +2275,7 @@ int _font_get_glyph_advance (LOGFONT* logfont, DEVFONT* devfont,
|
||||
REAL_GLYPH(glyph_value), &tmp_x, &tmp_y);
|
||||
|
||||
if (!direction) {
|
||||
if (bbox) bbox->x -= (bold + ch_extra + adv_len);
|
||||
bbox_x -= (bold + ch_extra + adv_len);
|
||||
}
|
||||
|
||||
if (direction) {
|
||||
|
||||
@@ -53,6 +53,9 @@ int _font_get_glyph_advance (LOGFONT* logfont, DEVFONT* devfont,
|
||||
Glyph32 glyph_value, BOOL direction, int ch_extra,
|
||||
int x, int y, int* adv_x, int* adv_y, BBOX* bbox);
|
||||
|
||||
int _font_get_glyph_metrics(LOGFONT* logfont,
|
||||
Glyph32 gv, int* adv_x, int* adv_y, BBOX* bbox);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif /* __cplusplus */
|
||||
|
||||
@@ -186,7 +186,8 @@ static void resolve_layout_run_dir(const LAYOUTINFO* layout,
|
||||
break;
|
||||
}
|
||||
|
||||
if (LAYOUT_GRAVITY_IS_VERTICAL(layout->grv_base))
|
||||
if (LAYOUT_GRAVITY_IS_VERTICAL(layout->grv_base) &&
|
||||
lrun->ort == GLYPH_ORIENT_UPRIGHT)
|
||||
lrun->flags |= LAYOUTRUN_FLAG_CENTERED_BASELINE;
|
||||
}
|
||||
|
||||
|
||||
+11
-5
@@ -1754,11 +1754,17 @@ static int traverse_line_glyphs(const LAYOUTINFO* layout,
|
||||
|
||||
glyph_info = run->gstr->glyphs + j;
|
||||
|
||||
pos.x = line_adv;
|
||||
pos.y = 0;
|
||||
pos.x_off = glyph_info->x_off;
|
||||
pos.y_off = glyph_info->y_off;
|
||||
pos.advance = glyph_info->width;
|
||||
if (run->lrun->dir == GLYPH_RUN_DIR_TTB ||
|
||||
run->lrun->dir == GLYPH_RUN_DIR_BTT) {
|
||||
pos.x = glyph_info->x_off;
|
||||
pos.y = line_adv + glyph_info->y_off;
|
||||
pos.advance = glyph_info->height;
|
||||
}
|
||||
else {
|
||||
pos.x = line_adv + glyph_info->x_off;
|
||||
pos.y = glyph_info->y_off;
|
||||
pos.advance = glyph_info->width;
|
||||
}
|
||||
|
||||
pos.suppressed = 0;
|
||||
pos.whitespace = 0;
|
||||
|
||||
@@ -188,10 +188,23 @@ static BOOL shape_layout_run(SEInstance* inst,
|
||||
gs->glyphs[j].width = 0;
|
||||
}
|
||||
else {
|
||||
gs->glyphs[j].x_off = 0;
|
||||
gs->glyphs[j].y_off = 0;
|
||||
gs->glyphs[j].width
|
||||
= _font_get_glyph_log_width(run->lf, gv);
|
||||
if (run->flags & LAYOUTRUN_FLAG_CENTERED_BASELINE) {
|
||||
BBOX bbox;
|
||||
int width = _font_get_glyph_metrics(run->lf, gv,
|
||||
NULL, NULL, &bbox);
|
||||
|
||||
gs->glyphs[j].width = run->lf->size;
|
||||
gs->glyphs[j].height = width;
|
||||
gs->glyphs[j].x_off = (width - bbox.w) / 2;
|
||||
gs->glyphs[j].y_off = 0;
|
||||
}
|
||||
else {
|
||||
gs->glyphs[j].x_off = 0;
|
||||
gs->glyphs[j].y_off = 0;
|
||||
gs->glyphs[j].width
|
||||
= _font_get_glyph_log_width(run->lf, gv);
|
||||
gs->glyphs[j].height = run->lf->size;
|
||||
}
|
||||
}
|
||||
|
||||
gs->log_clusters[j] = i;
|
||||
@@ -203,16 +216,31 @@ static BOOL shape_layout_run(SEInstance* inst,
|
||||
gs->glyphs[j].gv = gv;
|
||||
gs->glyphs[j].is_cluster_start = 0;
|
||||
|
||||
gs->glyphs[j].x_off = 0;
|
||||
gs->glyphs[j].y_off = 0;
|
||||
gs->glyphs[j].width
|
||||
= _font_get_glyph_log_width(run->lf, gv);
|
||||
if (run->flags & LAYOUTRUN_FLAG_CENTERED_BASELINE) {
|
||||
BBOX bbox;
|
||||
int width = _font_get_glyph_metrics(run->lf, gv,
|
||||
NULL, NULL, &bbox);
|
||||
|
||||
gs->glyphs[j].width = run->lf->size;
|
||||
gs->glyphs[j].height = width;
|
||||
gs->glyphs[j].x_off = (width - bbox.w) / 2;
|
||||
gs->glyphs[j].y_off = 0;
|
||||
}
|
||||
else {
|
||||
gs->glyphs[j].x_off = 0;
|
||||
gs->glyphs[j].y_off = 0;
|
||||
gs->glyphs[j].width
|
||||
= _font_get_glyph_log_width(run->lf, gv);
|
||||
gs->glyphs[j].height = run->lf->size;
|
||||
}
|
||||
|
||||
gs->log_clusters[j] = i;
|
||||
j++;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
gs->nr_glyphs = j;
|
||||
|
||||
if (ar_props && ar_props != local_ar_props) {
|
||||
|
||||
@@ -143,7 +143,7 @@ static BOOL is_horizontal_only_script(Uchar32 uc)
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static int font_get_glyph_metrics(LOGFONT* logfont,
|
||||
int _font_get_glyph_metrics(LOGFONT* logfont,
|
||||
Glyph32 gv, int* adv_x, int* adv_y, BBOX* bbox)
|
||||
{
|
||||
int bold = 0;
|
||||
@@ -151,7 +151,7 @@ static int font_get_glyph_metrics(LOGFONT* logfont,
|
||||
int tmp_y = 0;
|
||||
int bbox_x = 0, bbox_y = 0;
|
||||
int bbox_w = 0, bbox_h = 0;
|
||||
int gbt;
|
||||
int gbt, width;;
|
||||
|
||||
DEVFONT* devfont = SELECT_DEVFONT_BY_GLYPH(logfont, gv);
|
||||
gbt = devfont->font_ops->get_glyph_bmptype (logfont, devfont)
|
||||
@@ -174,21 +174,22 @@ static int font_get_glyph_metrics(LOGFONT* logfont,
|
||||
bbox->h = bbox_h;
|
||||
}
|
||||
|
||||
devfont->font_ops->get_glyph_advance (logfont, devfont, REAL_GLYPH(gv),
|
||||
&tmp_x, &tmp_y);
|
||||
width = devfont->font_ops->get_glyph_advance (logfont, devfont,
|
||||
REAL_GLYPH(gv), &tmp_x, &tmp_y);
|
||||
|
||||
tmp_x += bold;
|
||||
if (gbt == DEVFONTGLYPHTYPE_MONOBMP) {
|
||||
if ((logfont->style & FS_RENDER_MASK) == FS_RENDER_GREY ||
|
||||
(logfont->style & FS_DECORATE_OUTLINE)) {
|
||||
tmp_x += 1;
|
||||
tmp_x++;
|
||||
width++;
|
||||
}
|
||||
}
|
||||
|
||||
if (adv_x) *adv_x = tmp_x;
|
||||
if (adv_y) *adv_y = tmp_y;
|
||||
|
||||
return 0;
|
||||
return width;
|
||||
}
|
||||
|
||||
static void normalize_glyph_metrics(LOGFONT* logfont,
|
||||
@@ -909,7 +910,7 @@ static int get_glyph_extent_info(MYGLYPHARGS* args, Glyph32 gv,
|
||||
}
|
||||
}
|
||||
|
||||
font_get_glyph_metrics(logfont, gv, &adv_x, &adv_y, &bbox);
|
||||
_font_get_glyph_metrics(logfont, gv, &adv_x, &adv_y, &bbox);
|
||||
normalize_glyph_metrics(logfont, args->rf, &bbox,
|
||||
&adv_x, &adv_y, &line_adv, &args->lw);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user