[draw] End CFF paths with a line-to

Issue a line-to command when start and end point of a path isn't same, matches freetype also.
This commit is contained in:
Ebrahim Byagowi 2020-02-23 22:46:26 +03:30
parent a46ba770ab
commit 86bd5a0ba1
3 changed files with 77 additions and 14 deletions

View File

@ -355,18 +355,26 @@ struct cff1_path_param_t
funcs = funcs_;
user_data = user_data_;
delta = delta_;
path_start_x = 0;
path_start_y = 0;
path_last_x = 0;
path_last_y = 0;
}
~cff1_path_param_t () { end_path (); }
void start_path () { path_open = true; }
void end_path () { if (path_open) funcs->close_path (user_data); path_open = false; }
void start_path ()
{
path_open = true;
}
bool is_path_open () const { return path_open; }
void move_to (const point_t &p)
{
point_t point = p;
if (delta) point.move (*delta);
funcs->move_to (font->em_scalef_x (point.x.to_real ()), font->em_scalef_y (point.y.to_real ()),
path_last_x = path_start_x = point.x.to_real ();
path_last_y = path_start_y = point.y.to_real ();
funcs->move_to (font->em_scalef_x (path_start_x), font->em_scalef_y (path_start_y),
user_data);
}
@ -376,6 +384,8 @@ struct cff1_path_param_t
if (delta) point.move (*delta);
funcs->line_to (font->em_scalef_x (point.x.to_real ()), font->em_scalef_y (point.y.to_real ()),
user_data);
path_last_x = point.x.to_real ();
path_last_y = point.y.to_real ();
}
void cubic_to (const point_t &p1, const point_t &p2, const point_t &p3)
@ -391,8 +401,27 @@ struct cff1_path_param_t
font->em_scalef_x (point2.x.to_real ()), font->em_scalef_y (point2.y.to_real ()),
font->em_scalef_x (point3.x.to_real ()), font->em_scalef_y (point3.y.to_real ()),
user_data);
path_last_x = point3.x.to_real ();
path_last_y = point3.y.to_real ();
}
void end_path ()
{
if (path_open)
{
if ((path_start_x != path_last_x) || (path_start_y != path_last_y))
funcs->line_to (font->em_scalef_x (path_start_x), font->em_scalef_y (path_start_y), user_data);
funcs->close_path (user_data);
}
path_open = false;
}
double path_start_x;
double path_start_y;
double path_last_x;
double path_last_y;
bool path_open;
hb_font_t *font;
const hb_draw_funcs_t *funcs;

View File

@ -151,16 +151,24 @@ struct cff2_path_param_t
font = font_;
funcs = funcs_;
user_data = user_data_;
path_start_x = 0;
path_start_y = 0;
path_last_x = 0;
path_last_y = 0;
}
~cff2_path_param_t () { end_path (); }
void start_path () { path_open = true; }
void end_path () { if (path_open) funcs->close_path (user_data); path_open = false; }
void start_path ()
{
path_open = true;
}
bool is_path_open () const { return path_open; }
void move_to (const point_t &p)
{
funcs->move_to (font->em_scalef_x (p.x.to_real ()), font->em_scalef_y (p.y.to_real ()),
path_last_x = path_start_x = p.x.to_real ();
path_last_y = path_start_y = p.y.to_real ();
funcs->move_to (font->em_scalef_x (path_start_x), font->em_scalef_y (path_start_y),
user_data);
}
@ -168,6 +176,8 @@ struct cff2_path_param_t
{
funcs->line_to (font->em_scalef_x (p.x.to_real ()), font->em_scalef_y (p.y.to_real ()),
user_data);
path_last_x = p.x.to_real ();
path_last_y = p.y.to_real ();
}
void cubic_to (const point_t &p1, const point_t &p2, const point_t &p3)
@ -176,12 +186,34 @@ struct cff2_path_param_t
font->em_scalef_x (p2.x.to_real ()), font->em_scalef_y (p2.y.to_real ()),
font->em_scalef_x (p3.x.to_real ()), font->em_scalef_y (p3.y.to_real ()),
user_data);
path_last_x = p3.x.to_real ();
path_last_y = p3.y.to_real ();
}
bool path_open;
void end_path ()
{
if (path_open)
{
if ((path_start_x != path_last_x) || (path_start_y != path_last_y))
funcs->line_to (font->em_scalef_x (path_start_x), font->em_scalef_y (path_start_y), user_data);
funcs->close_path (user_data);
}
path_open = false;
}
double path_start_x;
double path_start_y;
double path_last_x;
double path_last_y;
bool path_open;
hb_font_t *font;
const hb_draw_funcs_t *funcs;
void *user_data;
point_t *delta;
const OT::cff2::accelerator_t *cff;
};
struct cff2_path_procs_path_t : path_procs_t<cff2_path_procs_path_t, cff2_cs_interp_env_t, cff2_path_param_t>

View File

@ -243,9 +243,10 @@ test_hb_draw_cff1 (void)
.consumed = 0
};
g_assert (hb_font_draw_glyph (font, 3, funcs, &user_data));
char expected[] = "M203,367C227,440 248,512 268,588L272,588C293,512 314,440 338,367L369,267L172,267Z"
"M3,0L88,0L151,200L390,200L452,0L541,0L319,656L225,656Z"
"M300,653L342,694L201,861L143,806Z";
puts (str);
char expected[] = "M203,367C227,440 248,512 268,588L272,588C293,512 314,440 338,367L369,267L172,267L203,367Z"
"M3,0L88,0L151,200L390,200L452,0L541,0L319,656L225,656L3,0Z"
"M300,653L342,694L201,861L143,806L300,653Z";
g_assert_cmpmem (str, user_data.consumed, expected, sizeof (expected) - 1);
hb_font_destroy (font);
@ -394,8 +395,9 @@ test_hb_draw_ttf_parser_tests (void)
user_data.consumed = 0;
g_assert (hb_font_draw_glyph (font, 1, funcs, &user_data));
char expected[] = "M82,0L164,0L164,486L82,486ZM124,586C156,586 181,608 181,639"
"C181,671 156,692 124,692C92,692 67,671 67,639C67,608 92,586 124,586Z";
char expected[] = "M82,0L164,0L164,486L82,486L82,0Z"
"M124,586C156,586 181,608 181,639C181,671 156,692 124,692"
"C92,692 67,671 67,639C67,608 92,586 124,586Z";
g_assert_cmpmem (str, user_data.consumed, expected, sizeof (expected) - 1);
hb_font_destroy (font);
@ -492,8 +494,8 @@ test_hb_draw_font_kit_glyphs_tests (void)
user_data.consumed = 0;
g_assert (hb_font_draw_glyph (font, 5, funcs, &user_data));
char expected[] = "M90,0L258,0C456,0 564,122 564,331C564,539 456,656 254,656L90,656ZM173,68"
"L173,588L248,588C401,588 478,496 478,331C478,165 401,68 248,68Z";
char expected[] = "M90,0L258,0C456,0 564,122 564,331C564,539 456,656 254,656L90,656L90,0Z"
"M173,68L173,588L248,588C401,588 478,496 478,331C478,165 401,68 248,68L173,68Z";
g_assert_cmpmem (str, user_data.consumed, expected, sizeof (expected) - 1);
hb_font_destroy (font);