forked from minhngoc25a/freetype2
Compare commits
80 Commits
master
...
GSoC-2019-
Author | SHA1 | Date |
---|---|---|
Moazin Khatti | f943af6490 | |
Moazin Khatti | eb9a614011 | |
Moazin Khatti | 67c108bc9c | |
Moazin Khatti | b84ae3420a | |
Moazin Khatti | 3325b42e91 | |
Moazin Khatti | 561364002a | |
Moazin Khatti | 7d6ebe3a81 | |
Moazin Khatti | 4d24f52ead | |
Moazin Khatti | cb2e775408 | |
Moazin Khatti | 03f7b5a6b6 | |
Moazin Khatti | 253d2bad97 | |
Moazin Khatti | e54fbbf283 | |
Moazin Khatti | b6f04b03e4 | |
Moazin Khatti | 836c94e8d2 | |
Moazin Khatti | c492bf3f0a | |
Moazin Khatti | 3f6f939378 | |
Moazin Khatti | 2727bba550 | |
Moazin Khatti | cff4467f25 | |
Moazin Khatti | 22d7c8578f | |
Moazin Khatti | 5f5a56a0cc | |
Moazin Khatti | c21c2b0e70 | |
Moazin Khatti | b122db0953 | |
Moazin Khatti | 168a8f8fe0 | |
Moazin Khatti | 705320b72d | |
Moazin Khatti | fdb7d53ebf | |
Moazin Khatti | 74f80fba49 | |
Moazin Khatti | a227395912 | |
Moazin Khatti | dbcc809e7c | |
Moazin Khatti | 398801e2c0 | |
Moazin Khatti | 0e8e132bd7 | |
Moazin Khatti | d7f6f8b16d | |
Moazin Khatti | 2cef19641a | |
Moazin Khatti | faa495befc | |
Moazin Khatti | b85cc5ef0d | |
Moazin Khatti | 3479e03cdb | |
Moazin Khatti | ba9e6f9d41 | |
Moazin Khatti | 6962986cf3 | |
Moazin Khatti | 2d13c5127c | |
Moazin Khatti | bb1b25e560 | |
Moazin Khatti | 5e949729e3 | |
Moazin Khatti | f86fe242d4 | |
Moazin Khatti | 4025f1213e | |
Moazin Khatti | 246ac684e4 | |
Moazin Khatti | d86de4e9d4 | |
Moazin Khatti | 1541091e76 | |
Moazin Khatti | b6f2303338 | |
Moazin Khatti | 3b62e9dc9d | |
Moazin Khatti | c25304fa34 | |
Moazin Khatti | c6a6859ad9 | |
Moazin Khatti | bf1deae970 | |
Moazin Khatti | fbdd9f9ba3 | |
Moazin Khatti | cf44c0cbdd | |
Moazin Khatti | 1f74524929 | |
Moazin Khatti | de44a3fda8 | |
Moazin Khatti | e028be97b8 | |
Moazin Khatti | d8202166c0 | |
Moazin Khatti | e48cf716f8 | |
Moazin Khatti | 7275d6562f | |
Moazin Khatti | 22988063b0 | |
Moazin Khatti | 1073e4cf5c | |
Moazin Khatti | 6a39dd0b16 | |
Moazin Khatti | 1e6cfffcb2 | |
Moazin Khatti | 41d34c8118 | |
Moazin Khatti | d1a0615f00 | |
Moazin Khatti | 6bf9ade45c | |
Moazin Khatti | 61b1f0b73c | |
Moazin Khatti | 294a7ebee2 | |
Moazin Khatti | 0bf6444911 | |
Moazin Khatti | 877736d057 | |
Moazin Khatti | f8eae8a824 | |
Moazin Khatti | 479c76c867 | |
Moazin Khatti | 9a55001454 | |
Moazin Khatti | 4d59b8535e | |
Moazin Khatti | f1db18a464 | |
Moazin Khatti | db972c0568 | |
Moazin Khatti | b9734fd870 | |
Moazin Khatti | 82f8102da6 | |
Moazin Khatti | 9b7c3d1df9 | |
Moazin Khatti | 0729a65165 | |
Moazin Khatti | 311a253d4b |
|
@ -1,3 +1,4 @@
|
|||
config.mk
|
||||
objs/vc2010/
|
||||
build
|
||||
tags
|
||||
|
|
|
@ -130,8 +130,9 @@ ifdef DEVEL_DIR
|
|||
# We assume that all library dependencies for FreeType are fulfilled for a
|
||||
# development build, so we directly access the necessary include directory
|
||||
# information using `pkg-config'.
|
||||
INCLUDE_FLAGS += $(shell pkg-config --cflags libpng \
|
||||
harfbuzz )
|
||||
INCLUDE_FLAGS += $(shell pkg-config --cflags libpng \
|
||||
harfbuzz \
|
||||
librsvg-2.0 \)
|
||||
endif
|
||||
|
||||
|
||||
|
|
|
@ -542,7 +542,44 @@ if test x"$with_harfbuzz" = xyes -a "$have_harfbuzz" = no; then
|
|||
AC_MSG_ERROR([harfbuzz support requested but library not found])
|
||||
fi
|
||||
|
||||
# OT-SVG checks
|
||||
# Librsvg is the default for now!
|
||||
AC_ARG_WITH([svg],
|
||||
[AS_HELP_STRING([--with-svg=@<:@yes|no|auto|no-default@:>@],
|
||||
[support OpenType SVG fonts @<:@default=auto@:>@])],
|
||||
[], [with_svg=auto])
|
||||
|
||||
have_librsvg=no
|
||||
if test x"$with_svg" = xyes -o x"$with_svg" = xauto; then
|
||||
librsvg_pkg="librsvg-2.0 >= 2.40.0"
|
||||
have_librsvg_pkg=no
|
||||
|
||||
if test x"$LIBRSVG_CFLAGS" = x -a x"$LIBRSVG_LIBS" = x; then
|
||||
PKG_CHECK_EXISTS([$librsvg_pkg], [have_librsvg_pkg=yes])
|
||||
fi
|
||||
PKG_CHECK_MODULES([LIBRSVG], [$librsvg_pkg],
|
||||
[have_librsvg="yes (pkg-config)"], [:])
|
||||
|
||||
if test $have_librsvg_pkg = yes; then
|
||||
# we have librsvg pkg-config file
|
||||
librsvg_reqpriv="$librsvg_pkg"
|
||||
librsvg_libspriv=
|
||||
librsvg_libsstaticconf=`$PKG_CONFIG --static --libs "$librsvg_pkg"`
|
||||
else
|
||||
librsvg_reqpriv=
|
||||
|
||||
if test "$have_librsvg" != no; then
|
||||
# LIBRSVG_CFLAGS and LIBRSVG_LIBS are set by the user
|
||||
librsvg_libspriv="$LIBRSVG_LIBS"
|
||||
librsvg_libsstaticconf="$LIBRSVG_LIBS"
|
||||
have_librsvg="yes (LIBRSVG_CFLAGS and LIBRSVG_LIBS)"
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
|
||||
if test x"$with_svg" = xyes -a x"$have_librsvg" = xno; then
|
||||
AC_MSG_ERROR([SVG support requested but library not found])
|
||||
fi
|
||||
# check for librt
|
||||
#
|
||||
# We need `clock_gettime' for the `ftbench' demo program.
|
||||
|
@ -992,7 +1029,8 @@ fi
|
|||
REQUIRES_PRIVATE="$zlib_reqpriv, \
|
||||
$bzip2_reqpriv, \
|
||||
$libpng_reqpriv, \
|
||||
$harfbuzz_reqpriv"
|
||||
$harfbuzz_reqpriv, \
|
||||
$librsvg_reqpriv"
|
||||
# beautify
|
||||
REQUIRES_PRIVATE=`echo "$REQUIRES_PRIVATE" \
|
||||
| sed -e 's/^ *//' \
|
||||
|
@ -1007,7 +1045,8 @@ LIBS_PRIVATE="$zlib_libspriv \
|
|||
$bzip2_libspriv \
|
||||
$libpng_libspriv \
|
||||
$harfbuzz_libspriv \
|
||||
$ft2_extra_libs"
|
||||
$ft2_extra_libs \
|
||||
$librsvg_libspriv"
|
||||
# beautify
|
||||
LIBS_PRIVATE=`echo "$LIBS_PRIVATE" \
|
||||
| sed -e 's/^ *//' \
|
||||
|
@ -1019,7 +1058,9 @@ LIBSSTATIC_CONFIG="-lfreetype \
|
|||
$bzip2_libsstaticconf \
|
||||
$libpng_libsstaticconf \
|
||||
$harfbuzz_libsstaticconf \
|
||||
$ft2_extra_libs"
|
||||
$ft2_extra_libs \
|
||||
$librsvg_libsstaticconf"
|
||||
|
||||
# remove -L/usr/lib and -L/usr/lib64 since `freetype-config' adds them later
|
||||
# on if necessary; also beautify
|
||||
LIBSSTATIC_CONFIG=`echo "$LIBSSTATIC_CONFIG" \
|
||||
|
@ -1084,6 +1125,24 @@ else
|
|||
ftoption_unset FT_CONFIG_OPTION_USE_HARFBUZZ
|
||||
fi
|
||||
|
||||
if test "$with_svg" = no-default; then
|
||||
ftoption_set FT_CONFIG_OPTION_SVG
|
||||
ftoption_unset FT_CONFIG_OPTION_DEFAULT_SVG
|
||||
have_librsvg="no-default"
|
||||
elif test "$with_svg" = no; then
|
||||
ftoption_unset FT_CONFIG_OPTION_SVG
|
||||
ftoption_unset FT_CONFIG_OPTION_DEFAULT_SVG
|
||||
elif test "$with_svg" = auto -a "$have_librsvg" = no; then
|
||||
ftoption_unset FT_CONFIG_OPTION_SVG
|
||||
ftoption_unset FT_CONFIG_OPTION_DEFAULT_SVG
|
||||
else
|
||||
LIBRSVG_CFLAGS=$(echo $LIBRSVG_CFLAGS | sed -e 's/freetype2//g')
|
||||
CFLAGS="$CFLAGS $LIBRSVG_CFLAGS"
|
||||
LDFLAGS="$LDFLAGS $LIBRSVG_LIBS"
|
||||
ftoption_set FT_CONFIG_OPTION_SVG
|
||||
ftoption_set FT_CONFIG_OPTION_DEFAULT_SVG
|
||||
fi
|
||||
|
||||
AC_SUBST([CFLAGS])
|
||||
AC_SUBST([LDFLAGS])
|
||||
|
||||
|
@ -1129,6 +1188,7 @@ Library configuration:
|
|||
bzip2: $have_bzip2
|
||||
libpng: $have_libpng
|
||||
harfbuzz: $have_harfbuzz
|
||||
svg support: $have_librsvg
|
||||
])
|
||||
|
||||
# Warn if docwriter is not installed
|
||||
|
|
|
@ -493,6 +493,19 @@ FT_BEGIN_HEADER
|
|||
#undef FT_CONFIG_OPTION_USE_MODULE_ERRORS
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* OpenType SVG Glyph Support
|
||||
*
|
||||
* If `FT_CONFIG_OPTION_SVG` is set, OpenType SVG glyphs will be
|
||||
* supported.
|
||||
* If `FT_CONFIG_OPTION_DEFAULT_SVG` is also set, a default library will
|
||||
* also be integrated so no external hooks will be necessary.
|
||||
*/
|
||||
#define FT_CONFIG_OPTION_SVG
|
||||
#define FT_CONFIG_OPTION_DEFAULT_SVG
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* Error Strings
|
||||
|
|
|
@ -547,6 +547,19 @@
|
|||
#define FT_BITMAP_H <freetype/ftbitmap.h>
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @macro:
|
||||
* FT_OTSVG_H
|
||||
*
|
||||
* @description:
|
||||
* A macro used in `#include` statements to name the file containing the
|
||||
* API of OT-SVG support related things.
|
||||
*
|
||||
*/
|
||||
#define FT_OTSVG_H <freetype/otsvg.h>
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @macro:
|
||||
|
|
|
@ -414,7 +414,7 @@ FT_BEGIN_HEADER
|
|||
* them for certain configurations only.
|
||||
*/
|
||||
/* #define FT_DEBUG_LEVEL_ERROR */
|
||||
/* #define FT_DEBUG_LEVEL_TRACE */
|
||||
#define FT_DEBUG_LEVEL_TRACE
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
|
@ -473,7 +473,7 @@ FT_BEGIN_HEADER
|
|||
* Do not `#undef` this macro here since the build system might define it
|
||||
* for certain configurations only.
|
||||
*/
|
||||
/* #define FT_DEBUG_MEMORY */
|
||||
#define FT_DEBUG_MEMORY
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
|
@ -493,6 +493,19 @@ FT_BEGIN_HEADER
|
|||
#undef FT_CONFIG_OPTION_USE_MODULE_ERRORS
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* OpenType SVG Glyph Support
|
||||
*
|
||||
* If `FT_CONFIG_OPTION_SVG` is set, OpenType SVG glyphs will be
|
||||
* supported.
|
||||
* If `FT_CONFIG_OPTION_DEFAULT_SVG` is also set, a default library will
|
||||
* also be integrated so no external hooks will be necessary.
|
||||
*/
|
||||
#define FT_CONFIG_OPTION_SVG
|
||||
/* #define FT_CONFIG_OPTION_DEFAULT_SVG */
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* Error Strings
|
||||
|
|
|
@ -141,6 +141,7 @@ FT_BEGIN_HEADER
|
|||
* FT_FACE_FLAG_GLYPH_NAMES
|
||||
* FT_FACE_FLAG_EXTERNAL_STREAM
|
||||
* FT_FACE_FLAG_HINTER
|
||||
* FT_FACE_FLAG_SVG
|
||||
*
|
||||
* FT_HAS_HORIZONTAL
|
||||
* FT_HAS_VERTICAL
|
||||
|
@ -1206,6 +1207,9 @@ FT_BEGIN_HEADER
|
|||
* altered with @FT_Set_MM_Design_Coordinates,
|
||||
* @FT_Set_Var_Design_Coordinates, or @FT_Set_Var_Blend_Coordinates.
|
||||
* This flag is unset by a call to @FT_Set_Named_Instance.
|
||||
*
|
||||
* FT_FACE_FLAG_SVG ::
|
||||
* Set if the current face has an SVG table.
|
||||
*/
|
||||
#define FT_FACE_FLAG_SCALABLE ( 1L << 0 )
|
||||
#define FT_FACE_FLAG_FIXED_SIZES ( 1L << 1 )
|
||||
|
@ -1223,6 +1227,7 @@ FT_BEGIN_HEADER
|
|||
#define FT_FACE_FLAG_TRICKY ( 1L << 13 )
|
||||
#define FT_FACE_FLAG_COLOR ( 1L << 14 )
|
||||
#define FT_FACE_FLAG_VARIATION ( 1L << 15 )
|
||||
#define FT_FACE_FLAG_SVG ( 1L << 16 )
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
|
|
|
@ -619,6 +619,46 @@ FT_BEGIN_HEADER
|
|||
*/
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @property:
|
||||
* svg_hooks
|
||||
*
|
||||
* @description:
|
||||
* OT-SVG glyphs are rendererd with the use of some callback hooks to an
|
||||
* external SVG rendering library. OT-SVG glyphs support can be enabled
|
||||
* by compiling FreeType with `FT_CONFIG_OPTION_SVG`. The hooks can be
|
||||
* stored in an @SVG_RendererHooks structure, which is then passed as the
|
||||
* value of `svg_hooks` property. See the example. We also provide
|
||||
* default hooks which can be enabled by compiling with
|
||||
* `FT_CONFIG_OPTION_DEFAULT_SVG`. Then, nothing needs to be set from
|
||||
* the user side, unless the user wants to use some other library.
|
||||
*
|
||||
* @note:
|
||||
* This property can only be set via @FT_Property_Set.
|
||||
*
|
||||
* @example:
|
||||
* ```
|
||||
* FT_Library library;
|
||||
* SVG_RendererHooks hooks;
|
||||
*
|
||||
*
|
||||
* FT_Init_FreeType( &library );
|
||||
*
|
||||
* hooks.init_svg = (SVG_Lib_Init_Func)foo_port_init;
|
||||
* hooks.free_svg = (SVG_Lib_Free_Func)foo_port_free;
|
||||
* hooks.render_svg = (SVG_Lib_Render_Func)foo_port_render;
|
||||
* hooks.preset_slot = (SVG_Lib_Preset_Slot_Func)foo_port_preset_slot;
|
||||
*
|
||||
* FT_Property_Set( library, "ot-svg", "svg_hooks", &hooks );
|
||||
*
|
||||
* ```
|
||||
*
|
||||
* @since:
|
||||
* 2.11
|
||||
*/
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @enum:
|
||||
|
|
|
@ -101,6 +101,8 @@
|
|||
"too many hints" )
|
||||
FT_ERRORDEF_( Invalid_Pixel_Size, 0x17,
|
||||
"invalid pixel size" )
|
||||
FT_ERRORDEF_( Invalid_SVG_Document, 0x18,
|
||||
"invalid SVG document" )
|
||||
|
||||
/* handle errors */
|
||||
|
||||
|
@ -234,6 +236,8 @@
|
|||
"found FDEF or IDEF opcode in glyf bytecode" )
|
||||
FT_ERRORDEF_( Missing_Bitmap, 0x9D,
|
||||
"missing bitmap in strike" )
|
||||
FT_ERRORDEF_( Missing_SVG_Hooks, 0x9E,
|
||||
"hooks have not been set" )
|
||||
|
||||
/* CFF, CID, and Type 1 errors */
|
||||
|
||||
|
|
|
@ -223,6 +223,87 @@ FT_BEGIN_HEADER
|
|||
} FT_OutlineGlyphRec;
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @type:
|
||||
* FT_SvgGlyph
|
||||
*
|
||||
* @description:
|
||||
* A handle to an object used to model an SVG glyph image. This is a
|
||||
* sub-class of @FT_Glyph, and a pointer to @FT_SvgGlyphRec.
|
||||
*/
|
||||
typedef struct FT_SvgGlyphRec_* FT_SvgGlyph;
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @struct:
|
||||
* FT_SvgGlyphRec
|
||||
*
|
||||
* @description:
|
||||
* A structure used for OT-SVG glyph images. This really is a 'sub-class'
|
||||
* of @FT_GlyphRec.
|
||||
*
|
||||
* @fields:
|
||||
* root ::
|
||||
* The root @FT_GlyphRec fields.
|
||||
*
|
||||
* svg_document ::
|
||||
* A pointer to the SVG document.
|
||||
*
|
||||
* svg_document_length ::
|
||||
* The length of `svg_document`.
|
||||
*
|
||||
* glyph_index ::
|
||||
* The index of the glyph to be rendered.
|
||||
*
|
||||
* metrics ::
|
||||
* A metrics object storing the size information.
|
||||
*
|
||||
* units_per_EM ::
|
||||
* The size of the EM square.
|
||||
*
|
||||
* start_glyph_id ::
|
||||
* The first glyph ID in the glyph range is covered by this document.
|
||||
*
|
||||
* end_glyph_id ::
|
||||
* The last glyph ID in the glyph range is covered by this document.
|
||||
*
|
||||
* transform ::
|
||||
* A 2x2 transformation matrix to apply on the glyph while rendering it.
|
||||
*
|
||||
* delta ::
|
||||
* Translation to apply on the glyph while rendering.
|
||||
*
|
||||
* @note:
|
||||
* `metrics` and `units_per_EM` might look like repetitions since both
|
||||
* fields are stored in face objects. However, the Glyph Management API
|
||||
* requires an `FT_Glyph` to store all the information that completely
|
||||
* describes a glyph. Outline glyphs are themselves scaled thus they
|
||||
* don't need this information. However, SVG documents do. The field of
|
||||
* `units_per_EM` is needed because the SVG is to be scaled in case its
|
||||
* viewbox size differs from `units_per_EM`. For more info, refer to
|
||||
* the section _Coordinate Systems and Glyph Metrics_ of the OpenType
|
||||
* SVG specs. The `transform` and `delta` are stored here because for an
|
||||
* SVG document, there's no way to apply a transformation without parsing
|
||||
* it. Thus, we just store the transform and later the renderer can apply
|
||||
* it while rendering.
|
||||
*/
|
||||
typedef struct FT_SvgGlyphRec_
|
||||
{
|
||||
FT_GlyphRec root;
|
||||
FT_Byte* svg_document;
|
||||
FT_ULong svg_document_length;
|
||||
FT_UInt glyph_index;
|
||||
FT_Size_Metrics metrics;
|
||||
FT_UShort units_per_EM;
|
||||
FT_UShort start_glyph_id;
|
||||
FT_UShort end_glyph_id;
|
||||
FT_Matrix transform;
|
||||
FT_Vector delta;
|
||||
|
||||
} FT_SvgGlyphRec;
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @function:
|
||||
|
|
|
@ -732,6 +732,10 @@ FT_BEGIN_HEADER
|
|||
* contours. Some Type~1 fonts, like those in the Hershey family,
|
||||
* contain glyphs in this format. These are described as @FT_Outline,
|
||||
* but FreeType isn't currently capable of rendering them correctly.
|
||||
*
|
||||
* FT_GLYPH_FORMAT_SVG ::
|
||||
* The glyph is represented by an SVG documents in the SVG table.
|
||||
*
|
||||
*/
|
||||
typedef enum FT_Glyph_Format_
|
||||
{
|
||||
|
@ -740,7 +744,8 @@ FT_BEGIN_HEADER
|
|||
FT_IMAGE_TAG( FT_GLYPH_FORMAT_COMPOSITE, 'c', 'o', 'm', 'p' ),
|
||||
FT_IMAGE_TAG( FT_GLYPH_FORMAT_BITMAP, 'b', 'i', 't', 's' ),
|
||||
FT_IMAGE_TAG( FT_GLYPH_FORMAT_OUTLINE, 'o', 'u', 't', 'l' ),
|
||||
FT_IMAGE_TAG( FT_GLYPH_FORMAT_PLOTTER, 'p', 'l', 'o', 't' )
|
||||
FT_IMAGE_TAG( FT_GLYPH_FORMAT_PLOTTER, 'p', 'l', 'o', 't' ),
|
||||
FT_IMAGE_TAG( FT_GLYPH_FORMAT_SVG, 's', 'v', 'g', ' ' )
|
||||
|
||||
} FT_Glyph_Format;
|
||||
|
||||
|
@ -752,6 +757,7 @@ FT_BEGIN_HEADER
|
|||
#define ft_glyph_format_bitmap FT_GLYPH_FORMAT_BITMAP
|
||||
#define ft_glyph_format_outline FT_GLYPH_FORMAT_OUTLINE
|
||||
#define ft_glyph_format_plotter FT_GLYPH_FORMAT_PLOTTER
|
||||
#define ft_glyph_format_svg FT_GLYPH_FORMAT_SVG
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
|
|
|
@ -418,7 +418,8 @@ FT_BEGIN_HEADER
|
|||
* initializing the glyph slot.
|
||||
*/
|
||||
|
||||
#define FT_GLYPH_OWN_BITMAP 0x1U
|
||||
#define FT_GLYPH_OWN_BITMAP 0x1U
|
||||
#define FT_GLYPH_OWN_GZIP_SVG 0x2U
|
||||
|
||||
typedef struct FT_Slot_InternalRec_
|
||||
{
|
||||
|
@ -889,6 +890,10 @@ FT_BEGIN_HEADER
|
|||
* created. @FT_Reference_Library increments this counter, and
|
||||
* @FT_Done_Library only destroys a library if the counter is~1,
|
||||
* otherwise it simply decrements it.
|
||||
*
|
||||
* svg_renderer_state ::
|
||||
* A pointer to a state object that will have the state of the SVG
|
||||
* Renderer. This will be totally managed by the renderer.
|
||||
*/
|
||||
typedef struct FT_LibraryRec_
|
||||
{
|
||||
|
@ -916,6 +921,10 @@ FT_BEGIN_HEADER
|
|||
|
||||
FT_Int refcount;
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
void* svg_renderer_state;
|
||||
#endif
|
||||
|
||||
} FT_LibraryRec;
|
||||
|
||||
|
||||
|
|
|
@ -39,6 +39,7 @@ FT_TRACE_DEF( mm ) /* MM interface (ftmm.c) */
|
|||
FT_TRACE_DEF( psprops ) /* PS driver properties (ftpsprop.c) */
|
||||
FT_TRACE_DEF( raccess ) /* resource fork accessor (ftrfork.c) */
|
||||
FT_TRACE_DEF( raster ) /* monochrome rasterizer (ftraster.c) */
|
||||
FT_TRACE_DEF( otsvg ) /* ot-svg renderer (ftsvg.c) */
|
||||
FT_TRACE_DEF( smooth ) /* anti-aliasing raster (ftgrays.c) */
|
||||
FT_TRACE_DEF( synth ) /* bold/slant synthesizer (ftsynth.c) */
|
||||
|
||||
|
@ -53,6 +54,7 @@ FT_TRACE_DEF( ttbdf ) /* TrueType embedded BDF (ttbdf.c) */
|
|||
FT_TRACE_DEF( ttcmap ) /* charmap handler (ttcmap.c) */
|
||||
FT_TRACE_DEF( ttcolr ) /* glyph layer table (ttcolr.c) */
|
||||
FT_TRACE_DEF( ttcpal ) /* color palette table (ttcpal.c) */
|
||||
FT_TRACE_DEF( ttsvg ) /* ot-svg glyph table (ttsvg.c) */
|
||||
FT_TRACE_DEF( ttkern ) /* kerning handler (ttkern.c) */
|
||||
FT_TRACE_DEF( ttload ) /* basic TrueType tables (ttload.c) */
|
||||
FT_TRACE_DEF( ttmtx ) /* metrics-related tables (ttmtx.c) */
|
||||
|
|
|
@ -37,6 +37,7 @@
|
|||
#define FT_INTERNAL_SERVICE_H <freetype/internal/ftserv.h>
|
||||
#define FT_INTERNAL_RFORK_H <freetype/internal/ftrfork.h>
|
||||
#define FT_INTERNAL_VALIDATE_H <freetype/internal/ftvalid.h>
|
||||
#define FT_INTERNAL_SVG_INTERFACE_H <freetype/internal/svginterface.h>
|
||||
|
||||
#define FT_INTERNAL_TRUETYPE_TYPES_H <freetype/internal/tttypes.h>
|
||||
#define FT_INTERNAL_TYPE1_TYPES_H <freetype/internal/t1types.h>
|
||||
|
|
|
@ -312,6 +312,31 @@ FT_BEGIN_HEADER
|
|||
TT_SBit_MetricsRec *ametrics );
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @functype:
|
||||
* TT_Load_Svg_Doc_Func
|
||||
*
|
||||
* @description:
|
||||
* Scan the SVG document list to find the document containing the glyph
|
||||
* that has the id "glyph<glyph_index>".
|
||||
*
|
||||
* @input:
|
||||
* glyph ::
|
||||
* The glyph slot from which pointers to SVG document list will be
|
||||
* grabbed. The results will be stored back in the slot too.
|
||||
*
|
||||
* glyph_index ::
|
||||
* The index of the glyph that is to be looked up.
|
||||
*
|
||||
* @return:
|
||||
* FreeType error code. 0 means success.
|
||||
*/
|
||||
typedef FT_Error
|
||||
(*TT_Load_Svg_Doc_Func)( FT_GlyphSlot glyph,
|
||||
FT_UInt glyph_index );
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @functype:
|
||||
|
@ -778,6 +803,11 @@ FT_BEGIN_HEADER
|
|||
TT_Get_Name_Func get_name;
|
||||
TT_Get_Name_ID_Func get_name_id;
|
||||
|
||||
/* Open Type SVG Support */
|
||||
TT_Load_Table_Func load_svg;
|
||||
TT_Free_Table_Func free_svg;
|
||||
TT_Load_Svg_Doc_Func load_svg_doc;
|
||||
|
||||
} SFNT_Interface;
|
||||
|
||||
|
||||
|
@ -824,7 +854,10 @@ FT_BEGIN_HEADER
|
|||
colr_blend_, \
|
||||
get_metrics_, \
|
||||
get_name_, \
|
||||
get_name_id_ ) \
|
||||
get_name_id_, \
|
||||
load_svg_, \
|
||||
free_svg_, \
|
||||
load_svg_doc_ ) \
|
||||
static const SFNT_Interface class_ = \
|
||||
{ \
|
||||
goto_table_, \
|
||||
|
@ -864,7 +897,10 @@ FT_BEGIN_HEADER
|
|||
colr_blend_, \
|
||||
get_metrics_, \
|
||||
get_name_, \
|
||||
get_name_id_ \
|
||||
get_name_id_, \
|
||||
load_svg_, \
|
||||
free_svg_, \
|
||||
load_svg_doc_ \
|
||||
};
|
||||
|
||||
|
||||
|
|
|
@ -0,0 +1,43 @@
|
|||
/****************************************************************************
|
||||
*
|
||||
* svginterface.h
|
||||
*
|
||||
* Exposes the interface of ot-svg module
|
||||
*
|
||||
* Copyright (C) 1996-2019 by
|
||||
* David Turner, Robert Wilhelm, Werner Lemberg and Moazin Khatti.
|
||||
*
|
||||
* This file is part of the FreeType project, and may only be used,
|
||||
* modified, and distributed under the terms of the FreeType project
|
||||
* license, LICENSE.TXT. By continuing to use, modify, or distribute
|
||||
* this file you indicate that you have read the license and
|
||||
* understand and accept it fully.
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
#ifndef SVGINTERFACE_H
|
||||
#define SVGINTERFACE_H
|
||||
|
||||
#include <ft2build.h>
|
||||
#include FT_OTSVG_H
|
||||
|
||||
|
||||
FT_BEGIN_HEADER
|
||||
|
||||
typedef FT_Error
|
||||
(*Preset_Bitmap_Func)( FT_Module module,
|
||||
FT_GlyphSlot slot,
|
||||
FT_Bool cache );
|
||||
|
||||
typedef struct SVG_Interface_
|
||||
{
|
||||
Preset_Bitmap_Func preset_slot;
|
||||
|
||||
} SVG_Interface;
|
||||
|
||||
typedef SVG_Interface* SVG_Service;
|
||||
|
||||
FT_END_HEADER
|
||||
|
||||
#endif
|
|
@ -1645,6 +1645,9 @@ FT_BEGIN_HEADER
|
|||
void* cpal;
|
||||
void* colr;
|
||||
|
||||
/* OpenType SVG Glyph Support */
|
||||
void* svg;
|
||||
|
||||
} TT_FaceRec;
|
||||
|
||||
|
||||
|
|
|
@ -0,0 +1,232 @@
|
|||
/****************************************************************************
|
||||
*
|
||||
* otsvg.h
|
||||
*
|
||||
* Interface for OT-SVG support related things (specification).
|
||||
*
|
||||
* Copyright (C) 2004-2019 by
|
||||
* David Turner, Robert Wilhelm, Werner Lemberg and Moazin Khatti.
|
||||
*
|
||||
* This file is part of the FreeType project, and may only be used,
|
||||
* modified, and distributed under the terms of the FreeType project
|
||||
* license, LICENSE.TXT. By continuing to use, modify, or distribute
|
||||
* this file you indicate that you have read the license and
|
||||
* understand and accept it fully.
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
#ifndef FTSVG_RENDERER_H_
|
||||
#define FTSVG_RENDERER_H_
|
||||
|
||||
#include <ft2build.h>
|
||||
#include FT_FREETYPE_H
|
||||
|
||||
#ifdef FREETYPE_H
|
||||
#error "freetype.h of FreeType 1 has been loaded!"
|
||||
#error "Please fix the directory search order for header files"
|
||||
#error "so that freetype.h of FreeType 2 is found first."
|
||||
#endif
|
||||
|
||||
FT_BEGIN_HEADER
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @functype:
|
||||
* SVG_Lib_Init_Func
|
||||
*
|
||||
* @description:
|
||||
* A callback which is called when the first OT-SVG glyph is rendered in
|
||||
* the lifetime of an @FT_Library object. The callback should perform all
|
||||
* sorts of initializations that the SVG rendering library needs such as
|
||||
* allocating memory for `svg_renderer_state` of @FT_LibraryRec.
|
||||
*
|
||||
* @input:
|
||||
* library ::
|
||||
* An instance of @FT_Library. It's passed to give the callbacks access
|
||||
* to `svg_renderer_state` of @FT_LibraryRec.
|
||||
*
|
||||
* @return:
|
||||
* FreeType error code. 0 means success.
|
||||
*/
|
||||
typedef FT_Error
|
||||
(*SVG_Lib_Init_Func)( FT_Library library );
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @functype:
|
||||
* SVG_Lib_Free_Func
|
||||
*
|
||||
* @description:
|
||||
* A callback which is called when the `ot-svg` module is being freed.
|
||||
* It is only called only if the init hook was called earlier. So, if no
|
||||
* OT-SVG glyph is rendered, neither the init hook is called nor the free
|
||||
* hook.
|
||||
*
|
||||
* @input:
|
||||
* library ::
|
||||
* An instance of @FT_Library. It's passed to give the callbacks access
|
||||
* to `svg_renderer_state` of @FT_LibraryRec.
|
||||
*/
|
||||
typedef void
|
||||
(*SVG_Lib_Free_Func)( FT_Library library );
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @functype:
|
||||
* SVG_Lib_Render_Func
|
||||
*
|
||||
* @description:
|
||||
* A callback which is called to render an OT-SVG glyph. This callback
|
||||
* hook is called right after the preset hook has been called with
|
||||
* `cache` set to `TRUE`. The data necessary to render is available
|
||||
* through the handle @FT_SVG_Document which is set in `other` field of
|
||||
* @FT_GlyphSlotRec.
|
||||
*
|
||||
* @input:
|
||||
* slot ::
|
||||
* The slot to render.
|
||||
*
|
||||
* @return:
|
||||
* FreeType error code. 0 means success.
|
||||
*/
|
||||
typedef FT_Error
|
||||
(*SVG_Lib_Render_Func)( FT_GlyphSlot slot );
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @functype:
|
||||
* SVG_Lib_Preset_Slot_Func
|
||||
*
|
||||
* @description:
|
||||
* A callback which is called to preset the glyphslot. It is called from
|
||||
* two places.
|
||||
*
|
||||
* 1. When `FT_Load_Glyph` needs to preset the glyphslot.
|
||||
* 2. Right before the `ot-svg` module calls the render callback hook.
|
||||
*
|
||||
* When it is the former, the argument `cache` is set to `FALSE`. When it
|
||||
* is the latter, the argument `cache` is set to `TRUE`. This distinction
|
||||
* has been made because while presetting a glyphslot many calculations
|
||||
* are needed and later the render callback hook needs the same
|
||||
* calculations, thus, if `cache` is `TRUE`, the hook might _cache_ these
|
||||
* calculations in `svg_renderer_state` of @FT_LibraryRec.
|
||||
*
|
||||
* @input:
|
||||
* slot ::
|
||||
* The glyph slot which has the SVG document loaded.
|
||||
*
|
||||
* cache ::
|
||||
* See description.
|
||||
*
|
||||
* @return:
|
||||
* FreeType error code. 0 means success.
|
||||
*/
|
||||
typedef FT_Error
|
||||
(*SVG_Lib_Preset_Slot_Func)( FT_GlyphSlot slot, FT_Bool cache);
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @struct:
|
||||
* SVG_RendererHooks
|
||||
*
|
||||
* @description:
|
||||
* A structure that stores the four hooks needed to render OT-SVG glyphs
|
||||
* properly. The structure is publicly used to set the hooks via driver
|
||||
* properties.
|
||||
*
|
||||
* @fields:
|
||||
* init_svg ::
|
||||
* The initialization hook.
|
||||
*
|
||||
* free_svg ::
|
||||
* The cleanup hook.
|
||||
*
|
||||
* render_hook ::
|
||||
* The render hook.
|
||||
*
|
||||
* preset_slot ::
|
||||
* The preset hook.
|
||||
*/
|
||||
typedef struct SVG_RendererHooks_
|
||||
{
|
||||
SVG_Lib_Init_Func init_svg;
|
||||
SVG_Lib_Free_Func free_svg;
|
||||
SVG_Lib_Render_Func render_svg;
|
||||
|
||||
SVG_Lib_Preset_Slot_Func preset_slot;
|
||||
|
||||
} SVG_RendererHooks;
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @struct:
|
||||
* FT_SVG_DocumentRec_
|
||||
*
|
||||
* @description:
|
||||
* A structure that models one SVG document.
|
||||
*
|
||||
* @fields:
|
||||
* svg_document ::
|
||||
* A pointer to the SVG document.
|
||||
*
|
||||
* svg_document_length ::
|
||||
* The length of `svg_document`.
|
||||
*
|
||||
* metrics ::
|
||||
* A metrics object storing the size information.
|
||||
*
|
||||
* units_per_EM ::
|
||||
* The size of the EM square.
|
||||
*
|
||||
* start_glyph_id ::
|
||||
* The first glyph ID in the glyph range is covered by this document.
|
||||
*
|
||||
* end_glyph_id ::
|
||||
* The last glyph ID in the glyph range is covered by this document.
|
||||
*
|
||||
* transform ::
|
||||
* A 2x2 transformation matrix to apply on the glyph while rendering it.
|
||||
*
|
||||
* delta ::
|
||||
* Translation to apply on the glyph while rendering.
|
||||
*
|
||||
* @note:
|
||||
* `metrics` and `units_per_EM` might look like repetitions since both
|
||||
* fields are stored in face object, but they are not; When the slot is
|
||||
* passed down to a renderer, the renderer can only access the `metrics`
|
||||
* and `units_per_EM` by `slot->face`. However, when `FT_Glyph_To_Bitmap`
|
||||
* sets up a dummy object, it has no way to set a `face` object. Thus,
|
||||
* metrics information and units_per_EM (which is necessary for OT-SVG)
|
||||
* has to be stored separately.
|
||||
*/
|
||||
|
||||
typedef struct FT_SVG_DocumentRec_
|
||||
{
|
||||
FT_Byte* svg_document;
|
||||
FT_ULong svg_document_length;
|
||||
FT_Size_Metrics metrics;
|
||||
FT_UShort units_per_EM;
|
||||
FT_UShort start_glyph_id;
|
||||
FT_UShort end_glyph_id;
|
||||
FT_Matrix transform;
|
||||
FT_Vector delta;
|
||||
|
||||
} FT_SVG_DocumentRec;
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* @type:
|
||||
* FT_SVG_Document
|
||||
*
|
||||
* @description:
|
||||
* A handle to a FT_SVG_DocumentRec object.
|
||||
*/
|
||||
typedef struct FT_SVG_DocumentRec_* FT_SVG_Document;
|
||||
|
||||
FT_END_HEADER
|
||||
#endif
|
|
@ -96,6 +96,7 @@ FT_BEGIN_HEADER
|
|||
#define TTAG_sbix FT_MAKE_TAG( 's', 'b', 'i', 'x' )
|
||||
#define TTAG_sfnt FT_MAKE_TAG( 's', 'f', 'n', 't' )
|
||||
#define TTAG_SING FT_MAKE_TAG( 'S', 'I', 'N', 'G' )
|
||||
#define TTAG_SVG FT_MAKE_TAG( 'S', 'V', 'G', ' ' )
|
||||
#define TTAG_trak FT_MAKE_TAG( 't', 'r', 'a', 'k' )
|
||||
#define TTAG_true FT_MAKE_TAG( 't', 'r', 'u', 'e' )
|
||||
#define TTAG_ttc FT_MAKE_TAG( 't', 't', 'c', ' ' )
|
||||
|
|
|
@ -99,6 +99,9 @@ RASTER_MODULES += raster
|
|||
# Anti-aliasing rasterizer.
|
||||
RASTER_MODULES += smooth
|
||||
|
||||
# OT-SVG
|
||||
RASTER_MODULES += svg
|
||||
|
||||
|
||||
####
|
||||
#### auxiliary modules
|
||||
|
|
|
@ -35,6 +35,7 @@
|
|||
#include FT_OUTLINE_H
|
||||
#include FT_BITMAP_H
|
||||
#include FT_INTERNAL_OBJECTS_H
|
||||
#include FT_OTSVG_H
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
|
@ -275,6 +276,214 @@
|
|||
ft_outline_glyph_prepare /* FT_Glyph_PrepareFunc glyph_prepare */
|
||||
)
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
/*************************************************************************/
|
||||
/*************************************************************************/
|
||||
/**** ****/
|
||||
/**** FT_SvgGlyph support ****/
|
||||
/**** ****/
|
||||
/*************************************************************************/
|
||||
/*************************************************************************/
|
||||
|
||||
|
||||
FT_CALLBACK_DEF( FT_Error )
|
||||
ft_svg_glyph_init( FT_Glyph svg_glyph,
|
||||
FT_GlyphSlot slot )
|
||||
{
|
||||
FT_ULong doc_length;
|
||||
FT_SVG_Document document;
|
||||
FT_SvgGlyph glyph = (FT_SvgGlyph)svg_glyph;
|
||||
FT_Error error = FT_Err_Ok;
|
||||
FT_Memory memory = FT_GLYPH( glyph )->library->memory;
|
||||
|
||||
|
||||
if ( slot->format != FT_GLYPH_FORMAT_SVG )
|
||||
{
|
||||
error = FT_THROW( Invalid_Glyph_Format );
|
||||
goto Exit;
|
||||
}
|
||||
|
||||
if ( slot->other == NULL )
|
||||
{
|
||||
error = FT_THROW( Invalid_Slot_Handle );
|
||||
goto Exit;
|
||||
}
|
||||
|
||||
document = (FT_SVG_Document)slot->other;
|
||||
|
||||
if ( document->svg_document_length == 0 )
|
||||
{
|
||||
error = FT_THROW( Invalid_Slot_Handle );
|
||||
goto Exit;
|
||||
}
|
||||
|
||||
/* allocate a new document */
|
||||
doc_length = document->svg_document_length;
|
||||
glyph->svg_document = memory->alloc( memory, doc_length );
|
||||
glyph->svg_document_length = doc_length;
|
||||
glyph->glyph_index = slot->glyph_index;
|
||||
glyph->metrics = document->metrics;
|
||||
glyph->units_per_EM = document->units_per_EM;
|
||||
glyph->start_glyph_id = document->start_glyph_id;
|
||||
glyph->end_glyph_id = document->end_glyph_id;
|
||||
glyph->transform = document->transform;
|
||||
glyph->delta = document->delta;
|
||||
|
||||
/* copy the document into glyph */
|
||||
FT_MEM_COPY( glyph->svg_document, document->svg_document, doc_length );
|
||||
|
||||
Exit:
|
||||
return error;
|
||||
}
|
||||
|
||||
|
||||
FT_CALLBACK_DEF( void )
|
||||
ft_svg_glyph_done( FT_Glyph svg_glyph )
|
||||
{
|
||||
FT_SvgGlyph glyph = (FT_SvgGlyph)svg_glyph;
|
||||
FT_Memory memory = svg_glyph->library->memory;
|
||||
|
||||
|
||||
/* just free the memory */
|
||||
memory->free( memory, glyph->svg_document );
|
||||
}
|
||||
|
||||
FT_CALLBACK_DEF( FT_Error )
|
||||
ft_svg_glyph_copy( FT_Glyph svg_source,
|
||||
FT_Glyph svg_target )
|
||||
{
|
||||
FT_SvgGlyph source = (FT_SvgGlyph)svg_source;
|
||||
FT_SvgGlyph target = (FT_SvgGlyph)svg_target;
|
||||
FT_Error error = FT_Err_Ok;
|
||||
FT_Memory memory = FT_GLYPH( source )->library->memory;
|
||||
|
||||
|
||||
if ( svg_source->format != FT_GLYPH_FORMAT_SVG )
|
||||
{
|
||||
error = FT_THROW( Invalid_Glyph_Format );
|
||||
return error;
|
||||
}
|
||||
|
||||
if ( source->svg_document_length == 0 )
|
||||
{
|
||||
error = FT_THROW( Invalid_Slot_Handle );
|
||||
return error;
|
||||
}
|
||||
|
||||
|
||||
target->glyph_index = source->glyph_index;
|
||||
target->svg_document_length = source->svg_document_length;
|
||||
target->metrics = source->metrics;
|
||||
target->units_per_EM = source->units_per_EM;
|
||||
target->start_glyph_id = source->start_glyph_id;
|
||||
target->end_glyph_id = source->end_glyph_id;
|
||||
target->transform = source->transform;
|
||||
target->delta = source->delta;
|
||||
|
||||
/* allocate space for the svg document */
|
||||
target->svg_document = memory->alloc( memory,
|
||||
target->svg_document_length );
|
||||
|
||||
/* copy the stuff */
|
||||
FT_MEM_COPY( target->svg_document,
|
||||
source->svg_document,
|
||||
target->svg_document_length );
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
FT_CALLBACK_DEF( void )
|
||||
ft_svg_glyph_transform( FT_Glyph svg_glyph,
|
||||
const FT_Matrix* _matrix,
|
||||
const FT_Vector* _delta )
|
||||
{
|
||||
FT_SvgGlyph glyph = (FT_SvgGlyph)svg_glyph;
|
||||
FT_Matrix* matrix = (FT_Matrix*)_matrix;
|
||||
FT_Vector* delta = (FT_Vector*)_delta;
|
||||
FT_Matrix tmp_matrix;
|
||||
FT_Vector tmp_delta;
|
||||
FT_Matrix a, b;
|
||||
FT_Pos x, y;
|
||||
|
||||
|
||||
if ( !matrix )
|
||||
{
|
||||
tmp_matrix.xx = 0x10000;
|
||||
tmp_matrix.xy = 0;
|
||||
tmp_matrix.yx = 0;
|
||||
tmp_matrix.yy = 0x10000;
|
||||
matrix = &tmp_matrix;
|
||||
}
|
||||
|
||||
if ( !delta )
|
||||
{
|
||||
tmp_delta.x = 0;
|
||||
tmp_delta.y = 0;
|
||||
delta = &tmp_delta;
|
||||
}
|
||||
|
||||
a = glyph->transform;
|
||||
b = *matrix;
|
||||
FT_Matrix_Multiply( &b, &a );
|
||||
|
||||
x = ADD_LONG(ADD_LONG(
|
||||
FT_MulFix(matrix->xx, glyph->delta.x),
|
||||
FT_MulFix(matrix->xy, glyph->delta.y)),
|
||||
delta->x);
|
||||
y = ADD_LONG(ADD_LONG(
|
||||
FT_MulFix(matrix->yx, glyph->delta.x),
|
||||
FT_MulFix(matrix->yy, glyph->delta.y)),
|
||||
delta->y);
|
||||
glyph->delta.x = x;
|
||||
glyph->delta.y = y;
|
||||
|
||||
glyph->transform = a;
|
||||
}
|
||||
|
||||
FT_CALLBACK_DEF( FT_Error )
|
||||
ft_svg_glyph_prepare( FT_Glyph svg_glyph,
|
||||
FT_GlyphSlot slot )
|
||||
{
|
||||
FT_SvgGlyph glyph = (FT_SvgGlyph)svg_glyph;
|
||||
FT_Error error = FT_Err_Ok;
|
||||
FT_Memory memory = svg_glyph->library->memory;
|
||||
FT_SVG_Document document;
|
||||
|
||||
|
||||
if ( FT_NEW( document ) )
|
||||
return error;
|
||||
|
||||
document->svg_document = glyph->svg_document;
|
||||
document->svg_document_length = glyph->svg_document_length;
|
||||
document->metrics = glyph->metrics;
|
||||
document->units_per_EM = glyph->units_per_EM;
|
||||
document->start_glyph_id = glyph->start_glyph_id;
|
||||
document->end_glyph_id = glyph->end_glyph_id;
|
||||
document->transform = glyph->transform;
|
||||
document->delta = glyph->delta;
|
||||
|
||||
slot->format = FT_GLYPH_FORMAT_SVG;
|
||||
slot->glyph_index = glyph->glyph_index;
|
||||
slot->other = document;
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
FT_DEFINE_GLYPH(
|
||||
ft_svg_glyph_class,
|
||||
|
||||
sizeof ( FT_SvgGlyphRec ),
|
||||
FT_GLYPH_FORMAT_SVG,
|
||||
|
||||
ft_svg_glyph_init, /* FT_Glyph_InitFunc glyph_init */
|
||||
ft_svg_glyph_done, /* FT_Glyph_DoneFunc glyph_done */
|
||||
ft_svg_glyph_copy, /* FT_Glyph_CopyFunc glyph_copy */
|
||||
ft_svg_glyph_transform, /* FT_Glyph_TransformFunc glyph_transform */
|
||||
NULL, /* FT_Glyph_GetBBoxFunc glyph_bbox */
|
||||
ft_svg_glyph_prepare /* FT_Glyph_PrepareFunc glyph_prepare */
|
||||
)
|
||||
|
||||
#endif
|
||||
|
||||
/*************************************************************************/
|
||||
/*************************************************************************/
|
||||
|
@ -376,6 +585,12 @@
|
|||
else if ( format == FT_GLYPH_FORMAT_OUTLINE )
|
||||
clazz = &ft_outline_glyph_class;
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
/* if it is a SVG glyph */
|
||||
else if ( format == FT_GLYPH_FORMAT_SVG )
|
||||
clazz = &ft_svg_glyph_class;
|
||||
#endif
|
||||
|
||||
else
|
||||
{
|
||||
/* try to find a renderer that supports the glyph image format */
|
||||
|
@ -592,7 +807,16 @@
|
|||
/* prepare dummy slot for rendering */
|
||||
error = clazz->glyph_prepare( glyph, &dummy );
|
||||
if ( !error )
|
||||
{
|
||||
error = FT_Render_Glyph_Internal( glyph->library, &dummy, render_mode );
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
if ( clazz == &ft_svg_glyph_class )
|
||||
{
|
||||
FT_Memory memory = library->memory;
|
||||
FT_FREE( dummy.other );
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
#if 1
|
||||
if ( !destroy && origin )
|
||||
|
|
|
@ -28,6 +28,7 @@
|
|||
#include FT_INTERNAL_STREAM_H
|
||||
#include FT_INTERNAL_SFNT_H /* for SFNT_Load_Table_Func */
|
||||
#include FT_INTERNAL_POSTSCRIPT_AUX_H /* for PS_Driver */
|
||||
#include FT_INTERNAL_SVG_INTERFACE_H
|
||||
|
||||
#include FT_TRUETYPE_TABLES_H
|
||||
#include FT_TRUETYPE_TAGS_H
|
||||
|
@ -40,6 +41,7 @@
|
|||
#include FT_SERVICE_TT_CMAP_H
|
||||
#include FT_SERVICE_KERNING_H
|
||||
#include FT_SERVICE_TRUETYPE_ENGINE_H
|
||||
#include FT_OTSVG_H
|
||||
|
||||
#include FT_DRIVER_H
|
||||
|
||||
|
@ -317,6 +319,17 @@
|
|||
if ( !error && clazz->init_slot )
|
||||
error = clazz->init_slot( slot );
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
/* check if SVG table exists allocate the space in slot->other */
|
||||
if ( slot->face->face_flags & FT_FACE_FLAG_SVG )
|
||||
{
|
||||
FT_SVG_Document document;
|
||||
if ( FT_NEW( document ) )
|
||||
goto Exit;
|
||||
slot->other = document;
|
||||
}
|
||||
#endif
|
||||
|
||||
Exit:
|
||||
return error;
|
||||
}
|
||||
|
@ -351,6 +364,7 @@
|
|||
{
|
||||
FT_Outline* outline = &slot->outline;
|
||||
FT_Bitmap* bitmap = &slot->bitmap;
|
||||
FT_Module module;
|
||||
|
||||
FT_Pixel_Mode pixel_mode;
|
||||
|
||||
|
@ -362,7 +376,19 @@
|
|||
|
||||
|
||||
if ( slot->format != FT_GLYPH_FORMAT_OUTLINE )
|
||||
{
|
||||
if ( slot->format == FT_GLYPH_FORMAT_SVG )
|
||||
{
|
||||
SVG_Service svg_service;
|
||||
|
||||
module = FT_Get_Module(slot->library, "ot-svg" );
|
||||
svg_service = (SVG_Service)module->clazz->module_interface;
|
||||
return svg_service->preset_slot( module, slot, FALSE );
|
||||
}
|
||||
else
|
||||
return 1;
|
||||
return 1;
|
||||
}
|
||||
|
||||
if ( origin )
|
||||
{
|
||||
|
@ -551,7 +577,23 @@
|
|||
slot->subglyphs = NULL;
|
||||
slot->control_data = NULL;
|
||||
slot->control_len = 0;
|
||||
#ifndef FT_CONFIG_OPTION_SVG
|
||||
slot->other = NULL;
|
||||
#else
|
||||
if ( !( slot->face->face_flags & FT_FACE_FLAG_SVG ) )
|
||||
slot->other = NULL;
|
||||
else
|
||||
{
|
||||
if ( slot->internal->flags & FT_GLYPH_OWN_GZIP_SVG )
|
||||
{
|
||||
FT_Memory memory = slot->face->memory;
|
||||
FT_SVG_Document doc = (FT_SVG_Document)slot->other;
|
||||
FT_FREE( doc->svg_document );
|
||||
slot->internal->load_flags &= ~FT_GLYPH_OWN_GZIP_SVG;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
slot->format = FT_GLYPH_FORMAT_NONE;
|
||||
|
||||
slot->linearHoriAdvance = 0;
|
||||
|
@ -569,6 +611,20 @@
|
|||
FT_Memory memory = driver->root.memory;
|
||||
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
if ( slot->face->face_flags & FT_FACE_FLAG_SVG )
|
||||
{
|
||||
/* free memory in case svg was there */
|
||||
if ( slot->internal->flags & FT_GLYPH_OWN_GZIP_SVG )
|
||||
{
|
||||
FT_SVG_Document doc = (FT_SVG_Document)slot->other;
|
||||
FT_FREE( doc->svg_document );
|
||||
slot->internal->flags &= ~FT_GLYPH_OWN_GZIP_SVG;
|
||||
}
|
||||
FT_FREE( slot->other );
|
||||
}
|
||||
#endif
|
||||
|
||||
if ( clazz->done_slot )
|
||||
clazz->done_slot( slot );
|
||||
|
||||
|
@ -587,6 +643,7 @@
|
|||
|
||||
FT_FREE( slot->internal );
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
@ -4403,6 +4460,13 @@
|
|||
render->render = clazz->render_glyph;
|
||||
}
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
if ( clazz->glyph_format == FT_GLYPH_FORMAT_SVG )
|
||||
{
|
||||
render->render = clazz->render_glyph;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* add to list */
|
||||
node->data = module;
|
||||
FT_List_Add( &library->renderers, node );
|
||||
|
@ -4538,7 +4602,6 @@
|
|||
{
|
||||
case FT_GLYPH_FORMAT_BITMAP: /* already a bitmap, don't do anything */
|
||||
break;
|
||||
|
||||
default:
|
||||
if ( slot->internal->load_flags & FT_LOAD_COLOR )
|
||||
{
|
||||
|
@ -5546,5 +5609,4 @@
|
|||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/* END */
|
||||
|
|
|
@ -177,7 +177,8 @@
|
|||
if ( !error )
|
||||
{
|
||||
if ( face->glyph->format == FT_GLYPH_FORMAT_BITMAP ||
|
||||
face->glyph->format == FT_GLYPH_FORMAT_OUTLINE )
|
||||
face->glyph->format == FT_GLYPH_FORMAT_OUTLINE ||
|
||||
face->glyph->format == FT_GLYPH_FORMAT_SVG )
|
||||
{
|
||||
/* ok, copy it */
|
||||
FT_Glyph glyph;
|
||||
|
|
|
@ -347,6 +347,56 @@
|
|||
if ( load_flags & FT_LOAD_SBITS_ONLY )
|
||||
return FT_THROW( Invalid_Argument );
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
/* check for OT-SVG */
|
||||
if ( ( load_flags & FT_LOAD_COLOR ) &&
|
||||
( ((TT_Face)glyph->root.face)->svg ) )
|
||||
{
|
||||
SFNT_Service sfnt;
|
||||
FT_Short leftBearing;
|
||||
FT_Short topBearing;
|
||||
FT_UShort advanceX;
|
||||
FT_UShort advanceY;
|
||||
|
||||
|
||||
if ( ( size->root.metrics.x_ppem < 1 ||
|
||||
size->root.metrics.y_ppem < 1 ) )
|
||||
{
|
||||
error = FT_THROW( Invalid_Size_Handle );
|
||||
return error;
|
||||
}
|
||||
|
||||
FT_TRACE3(( "Attemping to load SVG glyph\n" ));
|
||||
sfnt = (SFNT_Service)((TT_Face)glyph->root.face)->sfnt;
|
||||
|
||||
error = sfnt->load_svg_doc( (FT_GlyphSlot)glyph, glyph_index );
|
||||
if( error == FT_Err_Ok )
|
||||
{
|
||||
FT_TRACE3(( "Successfully loaded SVG glyph\n" ));
|
||||
glyph->root.format = FT_GLYPH_FORMAT_SVG;
|
||||
sfnt->get_metrics( face,
|
||||
FALSE,
|
||||
glyph_index,
|
||||
&leftBearing,
|
||||
&advanceX );
|
||||
sfnt->get_metrics( face,
|
||||
TRUE,
|
||||
glyph_index,
|
||||
&topBearing,
|
||||
&advanceY );
|
||||
advanceX *= ((float)glyph->root.face->size->metrics.x_ppem)/
|
||||
((float)glyph->root.face->units_per_EM) * 64.0;
|
||||
advanceY *= ((float)glyph->root.face->size->metrics.y_ppem)/
|
||||
((float)glyph->root.face->units_per_EM) * 64.0;
|
||||
glyph->root.metrics.horiAdvance = advanceX;
|
||||
glyph->root.metrics.vertAdvance = advanceY;
|
||||
|
||||
return error;
|
||||
}
|
||||
FT_TRACE3(( "Failed to load SVG glyph\n" ));
|
||||
}
|
||||
#endif
|
||||
|
||||
/* if we have a CID subfont, use its matrix (which has already */
|
||||
/* been multiplied with the root matrix) */
|
||||
|
||||
|
|
|
@ -36,6 +36,7 @@ SFNT_DRV_SRC := $(SFNT_DIR)/pngshim.c \
|
|||
$(SFNT_DIR)/ttcmap.c \
|
||||
$(SFNT_DIR)/ttcolr.c \
|
||||
$(SFNT_DIR)/ttcpal.c \
|
||||
$(SFNT_DIR)/ttsvg.c \
|
||||
$(SFNT_DIR)/ttkern.c \
|
||||
$(SFNT_DIR)/ttload.c \
|
||||
$(SFNT_DIR)/ttmtx.c \
|
||||
|
|
|
@ -37,6 +37,10 @@
|
|||
#include "ttcpal.h"
|
||||
#endif
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
#include "ttsvg.h" /* OpenType SVG support */
|
||||
#endif
|
||||
|
||||
#ifdef TT_CONFIG_OPTION_POSTSCRIPT_NAMES
|
||||
#include "ttpost.h"
|
||||
#endif
|
||||
|
@ -1208,6 +1212,12 @@
|
|||
#define PUT_EMBEDDED_BITMAPS( a ) NULL
|
||||
#endif
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
#define PUT_SVG_SUPPORT( a ) a
|
||||
#else
|
||||
#define PUT_SVG_SUPPORT( a ) NULL
|
||||
#endif
|
||||
|
||||
#ifdef TT_CONFIG_OPTION_COLOR_LAYERS
|
||||
#define PUT_COLOR_LAYERS( a ) a
|
||||
#else
|
||||
|
@ -1294,7 +1304,14 @@
|
|||
tt_face_get_metrics, /* TT_Get_Metrics_Func get_metrics */
|
||||
|
||||
tt_face_get_name, /* TT_Get_Name_Func get_name */
|
||||
sfnt_get_name_id /* TT_Get_Name_ID_Func get_name_id */
|
||||
sfnt_get_name_id, /* TT_Get_Name_ID_Func get_name_id */
|
||||
|
||||
PUT_SVG_SUPPORT( tt_face_load_svg ),
|
||||
/* TT_Load_Table_Func load_svg */
|
||||
PUT_SVG_SUPPORT( tt_face_free_svg ),
|
||||
/* TT_Free_Table_Func free_svg */
|
||||
PUT_SVG_SUPPORT( tt_face_load_svg_doc )
|
||||
/* TT_Load_Svg_Doc_Func load_svg_doc */
|
||||
)
|
||||
|
||||
|
||||
|
|
|
@ -27,6 +27,7 @@
|
|||
#include "ttcmap.c"
|
||||
#include "ttcolr.c"
|
||||
#include "ttcpal.c"
|
||||
#include "ttsvg.c"
|
||||
|
||||
#include "ttkern.c"
|
||||
#include "ttload.c"
|
||||
|
|
|
@ -953,6 +953,12 @@
|
|||
LOAD_( colr );
|
||||
}
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
/* opentype svg glyph support */
|
||||
if ( sfnt->load_svg )
|
||||
LOAD_( svg );
|
||||
#endif
|
||||
|
||||
/* consider the pclt, kerning, and gasp tables as optional */
|
||||
LOAD_( pclt );
|
||||
LOAD_( gasp );
|
||||
|
@ -1372,6 +1378,11 @@
|
|||
sfnt->free_cpal( face );
|
||||
sfnt->free_colr( face );
|
||||
}
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
/* free svg data */
|
||||
if ( sfnt->free_svg )
|
||||
sfnt->free_svg( face );
|
||||
#endif
|
||||
}
|
||||
|
||||
#ifdef TT_CONFIG_OPTION_BDF
|
||||
|
|
|
@ -0,0 +1,349 @@
|
|||
/****************************************************************************
|
||||
*
|
||||
* ttsvg.c
|
||||
*
|
||||
* OpenType SVG Color (specification).
|
||||
*
|
||||
* Copyright (C) 2018-2019 by
|
||||
* David Turner, Robert Wilhelm, Werner Lemberg and Moazin Khatti.
|
||||
*
|
||||
* This file is part of the FreeType project, and may only be used,
|
||||
* modified, and distributed under the terms of the FreeType project
|
||||
* license, LICENSE.TXT. By continuing to use, modify, or distribute
|
||||
* this file you indicate that you have read the license and
|
||||
* understand and accept it fully.
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
/**************************************************************************
|
||||
*
|
||||
* `SVG' table specification:
|
||||
*
|
||||
* https://docs.microsoft.com/en-us/typography/opentype/spec/svg
|
||||
*
|
||||
*/
|
||||
|
||||
#include <ft2build.h>
|
||||
#include FT_INTERNAL_STREAM_H
|
||||
#include FT_INTERNAL_OBJECTS_H
|
||||
#include FT_INTERNAL_DEBUG_H
|
||||
#include FT_TRUETYPE_TAGS_H
|
||||
#include FT_GZIP_H
|
||||
#include FT_OTSVG_H
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
|
||||
#include "ttsvg.h"
|
||||
|
||||
|
||||
typedef struct Svg_
|
||||
{
|
||||
FT_UShort version; /* Table version (starting at 0) */
|
||||
FT_UShort num_entries; /* Number of SVG document records */
|
||||
/* Pointer to the starting of SVG Document List */
|
||||
FT_Byte* svg_doc_list;
|
||||
/* Memory that backs up SVG */
|
||||
void* table;
|
||||
FT_ULong table_size;
|
||||
|
||||
} Svg;
|
||||
|
||||
#undef FT_COMPONENT
|
||||
#define FT_COMPONENT ttsvg
|
||||
|
||||
FT_LOCAL_DEF( FT_Error )
|
||||
tt_face_load_svg( TT_Face face,
|
||||
FT_Stream stream )
|
||||
{
|
||||
FT_Error error;
|
||||
FT_Memory memory = face->root.memory;
|
||||
FT_ULong table_size;
|
||||
FT_Byte* table = NULL;
|
||||
FT_Byte* p = NULL;
|
||||
Svg* svg = NULL;
|
||||
FT_ULong offsetToSVGDocumentList;
|
||||
|
||||
|
||||
error = face->goto_table( face, TTAG_SVG, stream, &table_size );
|
||||
if( error )
|
||||
goto NoSVG;
|
||||
|
||||
if( FT_FRAME_EXTRACT( table_size, table ))
|
||||
goto NoSVG;
|
||||
|
||||
/* Allocate the memory for the Svg object */
|
||||
if( FT_NEW( svg ) )
|
||||
goto NoSVG;
|
||||
|
||||
p = table;
|
||||
svg->version = FT_NEXT_USHORT( p );
|
||||
offsetToSVGDocumentList = FT_NEXT_ULONG( p );
|
||||
|
||||
if( offsetToSVGDocumentList == 0 )
|
||||
goto InvalidTable;
|
||||
|
||||
svg->svg_doc_list = (FT_Byte*)( table + offsetToSVGDocumentList );
|
||||
|
||||
p = svg->svg_doc_list;
|
||||
svg->num_entries = FT_NEXT_USHORT( p );
|
||||
|
||||
FT_TRACE3(( "version: %d\n", svg->version ));
|
||||
FT_TRACE3(( "num entiries: %d\n", svg->num_entries ));
|
||||
|
||||
svg->table = table;
|
||||
svg->table_size = table_size;
|
||||
|
||||
face->svg = svg;
|
||||
|
||||
face->root.face_flags |= FT_FACE_FLAG_SVG;
|
||||
|
||||
return FT_Err_Ok;
|
||||
|
||||
InvalidTable:
|
||||
error = FT_THROW( Invalid_Table );
|
||||
|
||||
NoSVG:
|
||||
FT_FRAME_RELEASE( table );
|
||||
FT_FREE( svg );
|
||||
face->svg = NULL;
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
FT_LOCAL_DEF( void )
|
||||
tt_face_free_svg( TT_Face face )
|
||||
{
|
||||
FT_Memory memory = face->root.memory;
|
||||
FT_Stream stream = face->root.stream;
|
||||
Svg* svg = (Svg*) face->svg;
|
||||
|
||||
|
||||
if( svg )
|
||||
{
|
||||
FT_FRAME_RELEASE( svg->table );
|
||||
FT_FREE( svg );
|
||||
}
|
||||
}
|
||||
|
||||
typedef struct Svg_doc_
|
||||
{
|
||||
FT_UShort start_glyph_id;
|
||||
FT_UShort end_glyph_id;
|
||||
FT_ULong offset;
|
||||
FT_ULong length;
|
||||
|
||||
} Svg_doc;
|
||||
|
||||
static Svg_doc
|
||||
extract_svg_doc( FT_Byte* stream )
|
||||
{
|
||||
Svg_doc doc;
|
||||
|
||||
|
||||
doc.start_glyph_id = FT_NEXT_USHORT( stream );
|
||||
doc.end_glyph_id = FT_NEXT_USHORT( stream );
|
||||
doc.offset = FT_NEXT_ULONG( stream );
|
||||
doc.length = FT_NEXT_ULONG( stream );
|
||||
return doc;
|
||||
}
|
||||
|
||||
static FT_Int
|
||||
compare_svg_doc( Svg_doc doc,
|
||||
FT_UInt glyph_index )
|
||||
{
|
||||
if ( glyph_index < doc.start_glyph_id )
|
||||
return -1;
|
||||
else if ( glyph_index > doc.end_glyph_id )
|
||||
return 1;
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
|
||||
static FT_Error
|
||||
find_doc( FT_Byte* stream,
|
||||
FT_UShort num_entries,
|
||||
FT_UInt glyph_index,
|
||||
FT_ULong *doc_offset,
|
||||
FT_ULong *doc_length,
|
||||
FT_UShort *start_glyph,
|
||||
FT_UShort *end_glyph )
|
||||
{
|
||||
FT_Error error;
|
||||
Svg_doc start_doc;
|
||||
Svg_doc mid_doc;
|
||||
Svg_doc end_doc;
|
||||
|
||||
FT_Bool found = FALSE;
|
||||
FT_UInt i = 0;
|
||||
FT_UInt start_index = 0;
|
||||
FT_UInt end_index = num_entries - 1;
|
||||
FT_Int comp_res;
|
||||
|
||||
|
||||
/* search algo */
|
||||
if ( num_entries == 0 )
|
||||
{
|
||||
error = FT_THROW( Invalid_Table );
|
||||
return error;
|
||||
}
|
||||
|
||||
FT_TRACE6(( "--- binary search glyph id: %d ---\n", glyph_index ));
|
||||
|
||||
start_doc = extract_svg_doc( stream + start_index * 12 );
|
||||
end_doc = extract_svg_doc( stream + end_index * 12 );
|
||||
|
||||
FT_TRACE6(( "--- start glyph ---\n" ));
|
||||
FT_TRACE6(( "start_id: %d\n", start_doc.start_glyph_id ));
|
||||
FT_TRACE6(( "end_id: %d\n", start_doc.end_glyph_id ));
|
||||
FT_TRACE6(( "--- end glyph ---\n" ));
|
||||
FT_TRACE6(( "start_id: %d\n", end_doc.start_glyph_id ));
|
||||
FT_TRACE6(( "end_id: %d\n", end_doc.end_glyph_id ));
|
||||
if ( ( compare_svg_doc( start_doc, glyph_index ) == -1 ) ||
|
||||
( compare_svg_doc( end_doc, glyph_index ) == 1 ) )
|
||||
{
|
||||
error = FT_THROW( Invalid_Glyph_Index );
|
||||
return error;
|
||||
}
|
||||
|
||||
while ( start_index <= end_index )
|
||||
{
|
||||
i = ( start_index + end_index ) / 2;
|
||||
mid_doc = extract_svg_doc( stream + i * 12 );
|
||||
FT_TRACE6(( "--- current glyph ---\n" ));
|
||||
FT_TRACE6(( "start_id: %d\n", mid_doc.start_glyph_id ));
|
||||
FT_TRACE6(( "end_id: %d\n", mid_doc.end_glyph_id ));
|
||||
comp_res = compare_svg_doc( mid_doc, glyph_index );
|
||||
if ( comp_res == 1 )
|
||||
{
|
||||
start_index = i + 1;
|
||||
start_doc = extract_svg_doc( stream + start_index * 4 );
|
||||
FT_TRACE6(( "RIGHT\n" ));
|
||||
}
|
||||
else if ( comp_res == -1 )
|
||||
{
|
||||
end_index = i - 1;
|
||||
end_doc = extract_svg_doc( stream + end_index * 4 );
|
||||
FT_TRACE6(( "LEFT\n" ));
|
||||
}
|
||||
else
|
||||
{
|
||||
found = TRUE;
|
||||
FT_TRACE5(( "FOUND\n" ));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
FT_TRACE5(( "--- binary search end ---\n" ));
|
||||
/* search algo end */
|
||||
if ( found != TRUE )
|
||||
{
|
||||
FT_TRACE5(( "NOT FOUND\n" ));
|
||||
error = FT_THROW( Invalid_Glyph_Index );
|
||||
}
|
||||
else
|
||||
{
|
||||
*doc_offset = mid_doc.offset;
|
||||
*doc_length = mid_doc.length;
|
||||
*start_glyph = mid_doc.start_glyph_id;
|
||||
*end_glyph = mid_doc.end_glyph_id;
|
||||
|
||||
error = FT_Err_Ok;
|
||||
}
|
||||
return error;
|
||||
}
|
||||
|
||||
FT_LOCAL_DEF( FT_Error )
|
||||
tt_face_load_svg_doc( FT_GlyphSlot glyph,
|
||||
FT_UInt glyph_index )
|
||||
{
|
||||
FT_Byte* doc_list; /* Pointer to the Svg Document List */
|
||||
FT_UShort num_entries; /* Total no of entires in doc list */
|
||||
FT_ULong doc_offset;
|
||||
FT_ULong doc_length;
|
||||
FT_UShort start_glyph_id;
|
||||
FT_UShort end_glyph_id;
|
||||
FT_ULong uncomp_size;
|
||||
FT_Byte* uncomp_buffer;
|
||||
|
||||
FT_Error error = FT_Err_Ok;
|
||||
TT_Face face = (TT_Face)glyph->face;
|
||||
FT_Memory memory = face->root.memory;
|
||||
Svg* svg = face->svg;
|
||||
|
||||
FT_SVG_Document svg_document = glyph->other;
|
||||
|
||||
|
||||
FT_ASSERT( !( svg == NULL ) );
|
||||
|
||||
doc_list = svg->svg_doc_list;
|
||||
num_entries = FT_NEXT_USHORT( doc_list );
|
||||
|
||||
error = find_doc( doc_list, num_entries, glyph_index,
|
||||
&doc_offset, &doc_length,
|
||||
&start_glyph_id, &end_glyph_id );
|
||||
if ( error != FT_Err_Ok )
|
||||
goto Exit;
|
||||
|
||||
doc_list = svg->svg_doc_list; /* Reset to so we can use it again */
|
||||
doc_list = (FT_Byte*)( doc_list + doc_offset );
|
||||
|
||||
if( ( doc_list[0] == 0x1F ) && ( doc_list[1] == 0x8B )
|
||||
&& ( doc_list[2] == 0x08 ) )
|
||||
{
|
||||
/* get the size of the orignal document. This helps in alotting the
|
||||
* buffer to accomodate the uncompressed version. The last 4 bytes
|
||||
* of the compressed document are equal to orignal_size modulo 2^32.
|
||||
* Since SVG docs will be lesser in size then 2^32, we can use this
|
||||
* accurately. The four bytes are stored in little-endian format.
|
||||
*/
|
||||
FT_TRACE4(( "SVG document found is GZIP compressed\n" ));
|
||||
uncomp_size = (FT_ULong)doc_list[doc_length - 1] << 24 |
|
||||
(FT_ULong)doc_list[doc_length - 2] << 16 |
|
||||
(FT_ULong)doc_list[doc_length - 3] << 8 |
|
||||
(FT_ULong)doc_list[doc_length - 4];
|
||||
|
||||
uncomp_buffer = (FT_Byte*) memory->alloc( memory, uncomp_size );
|
||||
error = FT_Gzip_Uncompress( memory, uncomp_buffer, &uncomp_size,
|
||||
doc_list, doc_length );
|
||||
if ( error != FT_Err_Ok )
|
||||
{
|
||||
memory->free( memory, uncomp_buffer );
|
||||
error = FT_THROW( Invalid_Table );
|
||||
goto Exit;
|
||||
}
|
||||
glyph->internal->flags |= FT_GLYPH_OWN_GZIP_SVG;
|
||||
doc_list = uncomp_buffer;
|
||||
doc_length = uncomp_size;
|
||||
}
|
||||
|
||||
svg_document->svg_document = doc_list;
|
||||
svg_document->svg_document_length = doc_length;
|
||||
svg_document->metrics = glyph->face->size->metrics;
|
||||
svg_document->units_per_EM = glyph->face->units_per_EM;
|
||||
svg_document->start_glyph_id = start_glyph_id;
|
||||
svg_document->end_glyph_id = end_glyph_id;
|
||||
|
||||
svg_document->transform.xx = 0x10000;
|
||||
svg_document->transform.xy = 0;
|
||||
svg_document->transform.yx = 0;
|
||||
svg_document->transform.yy = 0x10000;
|
||||
svg_document->delta.x = 0;
|
||||
svg_document->delta.y = 0;
|
||||
|
||||
FT_TRACE5(( "start_glyph_id: %d\n", start_glyph_id ));
|
||||
FT_TRACE5(( "end_glyph_id: %d\n", end_glyph_id ));
|
||||
FT_TRACE5(( "svg_document:\n%.*s\n", doc_length, doc_list ));
|
||||
|
||||
glyph->other = svg_document;
|
||||
|
||||
Exit:
|
||||
return error;
|
||||
}
|
||||
|
||||
#else /* !FT_CONFIG_OPTION_SVG */
|
||||
|
||||
/* ANSI C doesn't like empty source files */
|
||||
typedef int _tt_svg_dummy;
|
||||
|
||||
#endif /* !FT_CONFIG_OPTION_SVG */
|
|
@ -0,0 +1,40 @@
|
|||
/****************************************************************************
|
||||
*
|
||||
* ttsvg.h
|
||||
*
|
||||
* OpenType SVG Color (specification).
|
||||
*
|
||||
* Copyright (C) 2018-2019 by
|
||||
* David Turner, Robert Wilhelm, Werner Lemberg and Moazin Khatti.
|
||||
*
|
||||
* This file is part of the FreeType project, and may only be used,
|
||||
* modified, and distributed under the terms of the FreeType project
|
||||
* license, LICENSE.TXT. By continuing to use, modify, or distribute
|
||||
* this file you indicate that you have read the license and
|
||||
* understand and accept it fully.
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef __TTSVG_H__
|
||||
#define __TTSVG_H__
|
||||
|
||||
#include <ft2build.h>
|
||||
#include FT_INTERNAL_TRUETYPE_TYPES_H
|
||||
|
||||
FT_BEGIN_HEADER
|
||||
|
||||
FT_LOCAL( FT_Error )
|
||||
tt_face_load_svg( TT_Face face,
|
||||
FT_Stream stream );
|
||||
|
||||
FT_LOCAL( void )
|
||||
tt_face_free_svg( TT_Face face );
|
||||
|
||||
FT_LOCAL( FT_Error )
|
||||
tt_face_load_svg_doc( FT_GlyphSlot glyph,
|
||||
FT_UInt glyph_index );
|
||||
|
||||
FT_END_HEADER
|
||||
|
||||
#endif /* __TTSVG_H__ */
|
||||
/* END */
|
|
@ -0,0 +1,302 @@
|
|||
/****************************************************************************
|
||||
*
|
||||
* ftsvg.c
|
||||
*
|
||||
* The FreeType svg renderer interface (body).
|
||||
*
|
||||
* Copyright (C) 1996-2019 by
|
||||
* David Turner, Robert Wilhelm, Werner Lemberg and Moazin Khatti.
|
||||
*
|
||||
* This file is part of the FreeType project, and may only be used,
|
||||
* modified, and distributed under the terms of the FreeType project
|
||||
* license, LICENSE.TXT. By continuing to use, modify, or distribute
|
||||
* this file you indicate that you have read the license and
|
||||
* understand and accept it fully.
|
||||
*
|
||||
*/
|
||||
|
||||
#include <ft2build.h>
|
||||
#include FT_INTERNAL_DEBUG_H
|
||||
#include FT_INTERNAL_SERVICE_H
|
||||
#include FT_SERVICE_PROPERTIES_H
|
||||
#include FT_OTSVG_H
|
||||
#include FT_INTERNAL_SVG_INTERFACE_H
|
||||
#include FT_BBOX_H
|
||||
|
||||
#include "ftsvg.h"
|
||||
#include "svgtypes.h"
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_DEFAULT_SVG
|
||||
#include "rsvg_port.h"
|
||||
#endif
|
||||
|
||||
#undef FT_COMPONENT
|
||||
#define FT_COMPONENT otsvg
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
|
||||
/* ft_svg_init */
|
||||
static FT_Error
|
||||
ft_svg_init( SVG_Renderer svg_module )
|
||||
{
|
||||
FT_Error error = FT_Err_Ok;
|
||||
|
||||
|
||||
svg_module->loaded = FALSE;
|
||||
#ifdef FT_CONFIG_OPTION_DEFAULT_SVG
|
||||
FT_TRACE3(( "ft_svg_init: Default hooks being set\n" ));
|
||||
svg_module->hooks.init_svg = (SVG_Lib_Init_Func)rsvg_port_init;
|
||||
svg_module->hooks.free_svg = (SVG_Lib_Free_Func)rsvg_port_free;
|
||||
svg_module->hooks.render_svg = (SVG_Lib_Render_Func)rsvg_port_render;
|
||||
svg_module->hooks.preset_slot = (SVG_Lib_Preset_Slot_Func)rsvg_port_preset_slot;
|
||||
svg_module->hooks_set = TRUE;
|
||||
#else
|
||||
FT_TRACE3(( "ft_svg_init: No default hooks set\n" ));
|
||||
svg_module->hooks_set = FALSE;
|
||||
#endif
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
static void
|
||||
ft_svg_done( SVG_Renderer svg_module )
|
||||
{
|
||||
FT_Library library = svg_module->root.root.library;
|
||||
|
||||
|
||||
if ( svg_module->loaded == TRUE &&
|
||||
svg_module->hooks_set == TRUE )
|
||||
svg_module->hooks.free_svg( library );
|
||||
svg_module->loaded = FALSE;
|
||||
}
|
||||
|
||||
static FT_Error
|
||||
ft_svg_preset_slot( FT_Module module,
|
||||
FT_GlyphSlot slot,
|
||||
FT_Bool cache )
|
||||
{
|
||||
SVG_Renderer svg_renderer = (SVG_Renderer)module;
|
||||
SVG_RendererHooks hooks = svg_renderer->hooks;
|
||||
|
||||
|
||||
if ( svg_renderer->hooks_set == FALSE )
|
||||
{
|
||||
FT_TRACE1(( "Hooks are NOT set. Can't render OT-SVG glyphs\n" ));
|
||||
return FT_THROW( Missing_SVG_Hooks );
|
||||
}
|
||||
|
||||
return hooks.preset_slot( slot, cache );
|
||||
}
|
||||
|
||||
static FT_Error
|
||||
ft_svg_render( FT_Renderer renderer,
|
||||
FT_GlyphSlot slot,
|
||||
FT_Render_Mode mode,
|
||||
const FT_Vector* origin )
|
||||
{
|
||||
SVG_Renderer svg_renderer = (SVG_Renderer)renderer;
|
||||
FT_Library library = renderer->root.library;
|
||||
FT_Memory memory = library->memory;
|
||||
FT_Error error;
|
||||
FT_ULong size_image_buffer;
|
||||
|
||||
SVG_RendererHooks hooks = svg_renderer->hooks;
|
||||
|
||||
|
||||
FT_UNUSED( mode );
|
||||
FT_UNUSED( origin );
|
||||
|
||||
if ( svg_renderer->hooks_set == FALSE )
|
||||
{
|
||||
FT_TRACE1(( "Hooks are NOT set. Can't render OT-SVG glyphs\n" ));
|
||||
return FT_THROW( Missing_SVG_Hooks );
|
||||
}
|
||||
|
||||
if ( svg_renderer->loaded == FALSE )
|
||||
{
|
||||
FT_TRACE3(( "ft_svg_render: first rendering, calling init hook\n" ));
|
||||
error = hooks.init_svg( library );
|
||||
svg_renderer->loaded = TRUE;
|
||||
}
|
||||
|
||||
ft_svg_preset_slot( (FT_Module)renderer, slot, TRUE);
|
||||
|
||||
size_image_buffer = slot->bitmap.pitch * slot->bitmap.rows;
|
||||
FT_MEM_ALLOC( slot->bitmap.buffer, size_image_buffer);
|
||||
if ( error )
|
||||
return error;
|
||||
|
||||
error = hooks.render_svg( slot );
|
||||
if ( error )
|
||||
FT_FREE( slot->bitmap.buffer );
|
||||
else
|
||||
slot->internal->flags |= FT_GLYPH_OWN_BITMAP;
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
static const SVG_Interface svg_interface = {
|
||||
(Preset_Bitmap_Func)ft_svg_preset_slot
|
||||
};
|
||||
|
||||
static FT_Error
|
||||
ft_svg_property_set( FT_Module module,
|
||||
const char* property_name,
|
||||
const void* value,
|
||||
FT_Bool value_is_string )
|
||||
{
|
||||
FT_Error error = FT_Err_Ok;
|
||||
SVG_Renderer renderer = (SVG_Renderer)module;
|
||||
|
||||
|
||||
if ( !ft_strcmp( property_name, "svg_hooks" ) )
|
||||
{
|
||||
SVG_RendererHooks* hooks;
|
||||
|
||||
|
||||
if ( value_is_string == TRUE )
|
||||
return FT_THROW( Invalid_Argument );
|
||||
|
||||
hooks = (SVG_RendererHooks*)value;
|
||||
renderer->hooks = *hooks;
|
||||
renderer->hooks_set = TRUE;
|
||||
}
|
||||
else
|
||||
error = FT_THROW( Missing_Property );
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
static FT_Error
|
||||
ft_svg_property_get( FT_Module module,
|
||||
const char* property_name,
|
||||
const void* value )
|
||||
{
|
||||
FT_Error error = FT_Err_Ok;
|
||||
SVG_Renderer renderer = (SVG_Renderer)module;
|
||||
|
||||
|
||||
if ( !ft_strcmp( property_name, "svg_hooks" ) )
|
||||
{
|
||||
SVG_RendererHooks* hooks = (SVG_RendererHooks*)value;
|
||||
*hooks = renderer->hooks;
|
||||
}
|
||||
else
|
||||
error = FT_THROW( Missing_Property );
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
FT_DEFINE_SERVICE_PROPERTIESREC(
|
||||
ft_svg_service_properties,
|
||||
|
||||
(FT_Properties_SetFunc)ft_svg_property_set, /* set_property */
|
||||
(FT_Properties_GetFunc)ft_svg_property_get /* get_property */
|
||||
)
|
||||
|
||||
FT_DEFINE_SERVICEDESCREC1(
|
||||
ft_svg_services,
|
||||
FT_SERVICE_ID_PROPERTIES, &ft_svg_service_properties )
|
||||
|
||||
|
||||
FT_CALLBACK_DEF( FT_Module_Interface )
|
||||
ft_svg_get_interface( FT_Module module,
|
||||
const char* ft_svg_interface )
|
||||
{
|
||||
FT_Module_Interface result;
|
||||
|
||||
|
||||
FT_UNUSED( module );
|
||||
|
||||
result = ft_service_list_lookup( ft_svg_services, ft_svg_interface );
|
||||
if ( result )
|
||||
return result;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static FT_Error
|
||||
ft_svg_transform( FT_Renderer renderer,
|
||||
FT_GlyphSlot slot,
|
||||
const FT_Matrix* _matrix,
|
||||
const FT_Vector* _delta )
|
||||
{
|
||||
FT_SVG_Document doc = (FT_SVG_Document)slot->other;
|
||||
FT_Matrix* matrix = (FT_Matrix*)_matrix;
|
||||
FT_Vector* delta = (FT_Vector*)_delta;
|
||||
FT_Matrix tmp_matrix;
|
||||
FT_Vector tmp_delta;
|
||||
FT_Matrix a, b;
|
||||
FT_Pos x, y;
|
||||
|
||||
|
||||
FT_UNUSED( renderer );
|
||||
|
||||
if ( !matrix )
|
||||
{
|
||||
tmp_matrix.xx = 0x10000;
|
||||
tmp_matrix.xy = 0;
|
||||
tmp_matrix.yx = 0;
|
||||
tmp_matrix.yy = 0x10000;
|
||||
matrix = &tmp_matrix;
|
||||
}
|
||||
|
||||
if ( !delta )
|
||||
{
|
||||
tmp_delta.x = 0;
|
||||
tmp_delta.y = 0;
|
||||
delta = &tmp_delta;
|
||||
}
|
||||
|
||||
a = doc->transform;
|
||||
b = *matrix;
|
||||
FT_Matrix_Multiply( &b, &a );
|
||||
|
||||
|
||||
x = ADD_LONG(ADD_LONG(
|
||||
FT_MulFix(matrix->xx, doc->delta.x),
|
||||
FT_MulFix(matrix->xy, doc->delta.y)),
|
||||
delta->x);
|
||||
y = ADD_LONG(ADD_LONG(
|
||||
FT_MulFix(matrix->yx, doc->delta.x),
|
||||
FT_MulFix(matrix->yy, doc->delta.y)),
|
||||
delta->y);
|
||||
|
||||
doc->delta.x = x;
|
||||
doc->delta.y = y;
|
||||
doc->transform = a;
|
||||
|
||||
return FT_Err_Ok;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
#define PUT_SVG_MODULE( a ) a
|
||||
#define SVG_GLYPH_FORMAT FT_GLYPH_FORMAT_SVG
|
||||
#else
|
||||
#define PUT_SVG_MODULE( a ) NULL
|
||||
#define SVG_GLYPH_FORMAT FT_GLYPH_FORMAT_NONE
|
||||
#endif
|
||||
|
||||
|
||||
FT_DEFINE_RENDERER(
|
||||
ft_svg_renderer_class,
|
||||
|
||||
FT_MODULE_RENDERER,
|
||||
sizeof( SVG_RendererRec ),
|
||||
|
||||
"ot-svg",
|
||||
0x10000L,
|
||||
0x20000L,
|
||||
(const void*)PUT_SVG_MODULE( &svg_interface ), /* module specific interface */
|
||||
(FT_Module_Constructor)PUT_SVG_MODULE( ft_svg_init ), /* module_init */
|
||||
(FT_Module_Destructor)PUT_SVG_MODULE( ft_svg_done ), /* module_done */
|
||||
PUT_SVG_MODULE( ft_svg_get_interface ), /* get_interface */
|
||||
SVG_GLYPH_FORMAT,
|
||||
(FT_Renderer_RenderFunc)PUT_SVG_MODULE( ft_svg_render ),
|
||||
(FT_Renderer_TransformFunc)PUT_SVG_MODULE( ft_svg_transform ),
|
||||
NULL,
|
||||
NULL,
|
||||
NULL
|
||||
)
|
|
@ -0,0 +1,33 @@
|
|||
/****************************************************************************
|
||||
*
|
||||
* ftsvg.h
|
||||
*
|
||||
* The FreeType svg renderer interface (specification).
|
||||
*
|
||||
* Copyright (C) 1996-2019 by
|
||||
* David Turner, Robert Wilhelm, Werner Lemberg and Moazin Khatti.
|
||||
*
|
||||
* This file is part of the FreeType project, and may only be used,
|
||||
* modified, and distributed under the terms of the FreeType project
|
||||
* license, LICENSE.TXT. By continuing to use, modify, or distribute
|
||||
* this file you indicate that you have read the license and
|
||||
* understand and accept it fully.
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef FTSVG_H_
|
||||
#define FTSVG_H_
|
||||
|
||||
#include <ft2build.h>
|
||||
#include FT_RENDER_H
|
||||
#include FT_INTERNAL_OBJECTS_H
|
||||
|
||||
FT_BEGIN_HEADER
|
||||
|
||||
FT_DECLARE_RENDERER( ft_svg_renderer_class )
|
||||
|
||||
FT_END_HEADER
|
||||
|
||||
#endif /* FTSVG_H_ */
|
||||
|
||||
/* END */
|
|
@ -0,0 +1,23 @@
|
|||
#
|
||||
# FreeType 2 svg renderer module definition
|
||||
#
|
||||
|
||||
|
||||
# Copyright (C) 1996-2019 by
|
||||
# David Turner, Robert Wilhelm, Werner Lemberg and Moazin Khatti.
|
||||
#
|
||||
# This file is part of the FreeType project, and may only be used, modified,
|
||||
# and distributed under the terms of the FreeType project license,
|
||||
# LICENSE.TXT. By continuing to use, modify, or distribute this file you
|
||||
# indicate that you have read the license and understand and accept it
|
||||
# fully.
|
||||
|
||||
|
||||
FTMODULE_H_COMMANDS += SVG_MODULE
|
||||
|
||||
define SVG_MODULE
|
||||
$(OPEN_DRIVER) FT_Renderer_Class, ft_svg_renderer_class $(CLOSE_DRIVER)
|
||||
$(ECHO_DRIVER)ot-svg $(ECHO_DRIVER_DESC)ot-svg glyph renderer module$(ECHO_DRIVER_DONE)
|
||||
endef
|
||||
|
||||
# EOF
|
|
@ -0,0 +1,71 @@
|
|||
#
|
||||
# FreeType 2 svg renderer module build rules
|
||||
#
|
||||
|
||||
|
||||
# Copyright (C) 1996-2019 by
|
||||
# David Turner, Robert Wilhelm, Werner Lemberg and Moazin Khatti.
|
||||
#
|
||||
# This file is part of the FreeType project, and may only be used, modified,
|
||||
# and distributed under the terms of the FreeType project license,
|
||||
# LICENSE.TXT. By continuing to use, modify, or distribute this file you
|
||||
# indicate that you have read the license and understand and accept it
|
||||
# fully.
|
||||
|
||||
|
||||
# svg renderer driver directory
|
||||
#
|
||||
SVG_DIR := $(SRC_DIR)/svg
|
||||
|
||||
# compilation flags for the driver
|
||||
#
|
||||
SVG_COMPILE := $(CC) $(ANSIFLAGS) \
|
||||
$I$(subst /,$(COMPILER_SEP),$(SVG_DIR)) \
|
||||
$(INCLUDE_FLAGS) \
|
||||
$(FT_CFLAGS)
|
||||
|
||||
# svg renderer sources (i.e., C files)
|
||||
#
|
||||
SVG_DRV_SRC := $(SVG_DIR)/ftsvg.c \
|
||||
$(SVG_DIR)/rsvg_port.c
|
||||
|
||||
|
||||
# svg renderer headers
|
||||
#
|
||||
SVG_DRV_H := $(SVG_DIR)/ftsvg.h \
|
||||
$(SVG_DIR)/svgtypes.h \
|
||||
$(SVG_DIR)/rsvg_port.h
|
||||
|
||||
|
||||
# svg renderer object(s)
|
||||
#
|
||||
# SVG_DRV_OBJ_M is used during `multi' builds.
|
||||
# SVG_DRV_OBJ_S is used during `single' builds.
|
||||
#
|
||||
SVG_DRV_OBJ_M := $(SVG_DRV_SRC:$(SVG_DIR)/%.c=$(OBJ_DIR)/%.$O)
|
||||
SVG_DRV_OBJ_S := $(OBJ_DIR)/svg.$O
|
||||
|
||||
# svg renderer source file for single build
|
||||
#
|
||||
SVG_DRV_SRC_S := $(SVG_DIR)/svg.c
|
||||
|
||||
|
||||
# svg renderer - single object
|
||||
#
|
||||
$(SVG_DRV_OBJ_S): $(SVG_DRV_SRC_S) $(SVG_DRV_SRC) \
|
||||
$(FREETYPE_H) $(SVG_DRV_H)
|
||||
$(SVG_COMPILE) $T$(subst /,$(COMPILER_SEP),$@ $(SVG_DRV_SRC_S))
|
||||
|
||||
|
||||
# svg renderer - multiple objects
|
||||
#
|
||||
$(OBJ_DIR)/%.$O: $(SVG_DIR)/%.c $(FREETYPE_H) $(SVG_DRV_H)
|
||||
$(SVG_COMPILE) $T$(subst /,$(COMPILER_SEP),$@ $<)
|
||||
|
||||
|
||||
# update main driver object lists
|
||||
#
|
||||
DRV_OBJS_S += $(SVG_DRV_OBJ_S)
|
||||
DRV_OBJS_M += $(SVG_DRV_OBJ_M)
|
||||
|
||||
# EOF
|
|
@ -0,0 +1,31 @@
|
|||
/****************************************************************************
|
||||
*
|
||||
* svg.c
|
||||
*
|
||||
* FreeType svg renderer module component (body only).
|
||||
*
|
||||
* Copyright (C) 1996-2019 by
|
||||
* David Turner, Robert Wilhelm, Werner Lemberg and Moazin Khatti.
|
||||
*
|
||||
* This file is part of the FreeType project, and may only be used,
|
||||
* modified, and distributed under the terms of the FreeType project
|
||||
* license, LICENSE.TXT. By continuing to use, modify, or distribute
|
||||
* this file you indicate that you have read the license and
|
||||
* understand and accept it fully.
|
||||
*
|
||||
*/
|
||||
|
||||
#define FT_MAKE_OPTION_SINGLE_OBJECT
|
||||
#include <ft2build.h>
|
||||
#include FT_FREETYPE_H
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_DEFAULT_SVG
|
||||
#include "rsvg_port.c"
|
||||
#endif
|
||||
|
||||
#include "svgtypes.h"
|
||||
#include "ftsvg.c"
|
||||
|
||||
|
||||
|
||||
/* END */
|
|
@ -0,0 +1,37 @@
|
|||
/****************************************************************************
|
||||
*
|
||||
* svgtypes.h
|
||||
*
|
||||
* The FreeType svg renderer internal types (specification).
|
||||
*
|
||||
* Copyright (C) 1996-2019 by
|
||||
* David Turner, Robert Wilhelm, Werner Lemberg and Moazin Khatti.
|
||||
*
|
||||
* This file is part of the FreeType project, and may only be used,
|
||||
* modified, and distributed under the terms of the FreeType project
|
||||
* license, LICENSE.TXT. By continuing to use, modify, or distribute
|
||||
* this file you indicate that you have read the license and
|
||||
* understand and accept it fully.
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef FTSVGTYPES_H
|
||||
#define FTSVGTYPES_H
|
||||
|
||||
#include <ft2build.h>
|
||||
#include FT_INTERNAL_OBJECTS_H
|
||||
#include FT_RENDER_H
|
||||
#include FT_OTSVG_H
|
||||
|
||||
typedef struct SVG_RendererRec_
|
||||
{
|
||||
FT_RendererRec root; /* This inherits FT_RendererRec */
|
||||
FT_Bool loaded;
|
||||
FT_Bool hooks_set;
|
||||
SVG_RendererHooks hooks; /* Holds out hooks to the outside library */
|
||||
|
||||
} SVG_RendererRec;
|
||||
|
||||
typedef struct SVG_RendererRec_* SVG_Renderer;
|
||||
|
||||
#endif
|
|
@ -2907,6 +2907,48 @@
|
|||
goto Exit;
|
||||
}
|
||||
|
||||
#ifdef FT_CONFIG_OPTION_SVG
|
||||
/* check for OT-SVG */
|
||||
if ( ( load_flags & FT_LOAD_COLOR ) && ( ((TT_Face)glyph->face)->svg ) )
|
||||
{
|
||||
SFNT_Service sfnt;
|
||||
FT_Short leftBearing;
|
||||
FT_Short topBearing;
|
||||
FT_UShort advanceX;
|
||||
FT_UShort advanceY;
|
||||
|
||||
|
||||
FT_TRACE3(( "Attemping to load SVG glyph\n" ));
|
||||
sfnt = (SFNT_Service)((TT_Face)glyph->face)->sfnt;
|
||||
|
||||
error = sfnt->load_svg_doc( glyph, glyph_index );
|
||||
if( error == FT_Err_Ok )
|
||||
{
|
||||
FT_TRACE3(( "Successfully loaded SVG glyph\n" ));
|
||||
glyph->format = FT_GLYPH_FORMAT_SVG;
|
||||
sfnt->get_metrics( (TT_Face)glyph->face,
|
||||
FALSE,
|
||||
glyph_index,
|
||||
&leftBearing,
|
||||
&advanceX );
|
||||
sfnt->get_metrics( (TT_Face)glyph->face,
|
||||
TRUE,
|
||||
glyph_index,
|
||||
&topBearing,
|
||||
&advanceY );
|
||||
advanceX *= ((float)glyph->face->size->metrics.x_ppem)/
|
||||
((float)glyph->face->units_per_EM) * 64.0;
|
||||
advanceY *= ((float)glyph->face->size->metrics.y_ppem)/
|
||||
((float)glyph->face->units_per_EM) * 64.0;
|
||||
glyph->metrics.horiAdvance = advanceX;
|
||||
glyph->metrics.vertAdvance = advanceY;
|
||||
|
||||
return error;
|
||||
}
|
||||
FT_TRACE3(( "Failed to load SVG glyph\n" ));
|
||||
}
|
||||
#endif
|
||||
|
||||
if ( load_flags & FT_LOAD_SBITS_ONLY )
|
||||
{
|
||||
error = FT_THROW( Invalid_Argument );
|
||||
|
|
Loading…
Reference in New Issue