/* * \brief Create and initialize a new drawing and return it */ ASS_Drawing *ass_drawing_new(void *fontconfig_priv, ASS_Font *font, ASS_Hinting hint, FT_Library lib) { ASS_Drawing *drawing; drawing = calloc(1, sizeof(*drawing)); drawing->text = calloc(1, DRAWING_INITIAL_SIZE); drawing->size = DRAWING_INITIAL_SIZE; drawing->ftlibrary = lib; if (font) { drawing->library = font->library; drawing_make_glyph(drawing, fontconfig_priv, font, hint); } drawing->scale_x = 1.; drawing->scale_y = 1.; drawing->max_contours = GLYPH_INITIAL_CONTOURS; drawing->max_points = GLYPH_INITIAL_POINTS; return drawing; }
/* * \brief Convert token list to outline. Calls the line and curve evaluators. */ FT_OutlineGlyph *ass_drawing_parse(ASS_Drawing *drawing, int raw_mode) { int started = 0; ASS_DrawingToken *token; FT_Vector pen = {0, 0}; if (drawing->font) drawing_make_glyph(drawing, drawing->fontconfig_priv, drawing->font); if (!drawing->glyph) return NULL; drawing->tokens = drawing_tokenize(drawing->text); drawing_prepare(drawing); token = drawing->tokens; while (token) { // Draw something according to current command switch (token->type) { case TOKEN_MOVE_NC: pen = token->point; translate_point(drawing, &pen); token = token->next; break; case TOKEN_MOVE: pen = token->point; translate_point(drawing, &pen); if (started) { drawing_close_shape(drawing); started = 0; } token = token->next; break; case TOKEN_LINE: { FT_Vector to; to = token->point; translate_point(drawing, &to); if (!started) drawing_add_point(drawing, &pen); drawing_add_point(drawing, &to); started = 1; token = token->next; break; } case TOKEN_CUBIC_BEZIER: if (token_check_values(token, 3, TOKEN_CUBIC_BEZIER) && token->prev) { drawing_evaluate_curve(drawing, token->prev, 0, started); token = token->next; token = token->next; token = token->next; started = 1; } else token = token->next; break; case TOKEN_B_SPLINE: if (token_check_values(token, 3, TOKEN_B_SPLINE) && token->prev) { drawing_evaluate_curve(drawing, token->prev, 1, started); token = token->next; started = 1; } else token = token->next; break; default: token = token->next; break; } } drawing_finish(drawing, raw_mode); drawing_free_tokens(drawing->tokens); return &drawing->glyph; }