mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-10-08 19:04:45 +00:00
Bug 1483566 - Update Graphite2 to version 1.3.12. r=jfkthame
Differential Revision: https://phabricator.services.mozilla.com/D3426 --HG-- extra : moz-landing-system : lando
This commit is contained in:
parent
203aa92dca
commit
9966e32859
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, you may use this library under the terms of the Mozilla
|
||||
|
18
gfx/graphite2/ChangeLog
Executable file → Normal file
18
gfx/graphite2/ChangeLog
Executable file → Normal file
@ -1,3 +1,21 @@
|
||||
1.3.12
|
||||
. Graphite no longer does dumb rendering for fonts with no smarts
|
||||
. Segment caching code removed. Anything attempting to use the segment cache gets given a regular face instead
|
||||
. Add libfuzzer support
|
||||
. Builds now require C++11
|
||||
. Improvements to Windows 64 bit builds
|
||||
. Support different versions of python including 32 bit and python 3
|
||||
. Various minor bug fixes
|
||||
|
||||
1.3.11
|
||||
. Fixes due to security review
|
||||
. Minor collision avoidance fixes
|
||||
. Fix LZ4 decompressor against high compression
|
||||
|
||||
1.3.10
|
||||
. Address floating point build parameters to give consistent positioning results across platforms
|
||||
. Various bug fixes
|
||||
|
||||
1.3.9
|
||||
. Add Collision COLL_ISSPACE to allow for visible spaces in collision avoidance
|
||||
. Add segment and pass direction information to tracing output
|
||||
|
@ -1,11 +1,10 @@
|
||||
# Graphite engine
|
||||
|
||||
## Project CI status
|
||||
Linux -- Intel 64bit:[![Build Status](http://build.palaso.org/app/rest/builds/buildType:bt124/statusIcon)](http://build.palaso.org/viewType.html?buildTypeId=bt124&guest=1)
|
||||
Intel 32bit:[![Build Status](http://build.palaso.org/app/rest/builds/buildType:bt123/statusIcon)](http://build.palaso.org/viewType.html?buildTypeId=bt123&guest=1)
|
||||
ARM 32bit:[![Build Status](http://build.palaso.org/app/rest/builds/buildType:Graphite_Linux32bitArm/statusIcon)](http://build.palaso.org/viewType.html?buildTypeId=Graphite_Linux32bitArm&guest=1)
|
||||
|
||||
Windows -- Intel 64bit:[![Build Status](http://build.palaso.org/app/rest/builds/buildType:Graphite_Windows64bitProduction/statusIcon)](http://build.palaso.org/viewType.html?buildTypeId=Graphite_Windows64bitProduction&guest=1)
|
||||
## Project CI status
|
||||
| OS | Intel 64 bit | Intel 32 bit | Arm 32 bit |
|
||||
|---------|:------------:|:------------:|:----------:|
|
||||
| Linux | [![Build Status](http://build.palaso.org/app/rest/builds/buildType:bt124/statusIcon)](http://build.palaso.org/viewType.html?buildTypeId=bt124&guest=1) | [![Build Status](http://build.palaso.org/app/rest/builds/buildType:bt123/statusIcon)](http://build.palaso.org/viewType.html?buildTypeId=bt123&guest=1) | [![Build Status](http://build.palaso.org/app/rest/builds/buildType:Graphite_Linux32bitArm/statusIcon)](http://build.palaso.org/viewType.html?buildTypeId=Graphite_Linux32bitArm&guest=1) |
|
||||
| Windows | [![Build Status](http://build.palaso.org/app/rest/builds/buildType:Graphite_Windows64bitProduction/statusIcon)](http://build.palaso.org/viewType.html?buildTypeId=Graphite_Windows64bitProduction&guest=1) | [![Build Status](http://build.palaso.org/app/rest/builds/buildType:bt91/statusIcon)](http://build.palaso.org/viewType.html?buildTypeId=bt91&guest=1)| |
|
||||
|
||||
## What is Graphite?
|
||||
|
||||
|
@ -1,7 +1,3 @@
|
||||
This directory contains the Graphite2 library release 1.3.11 from
|
||||
https://github.com/silnrsi/graphite/releases/download/1.3.11/graphite2-minimal-1.3.11.tgz
|
||||
This directory contains the Graphite2 library release 1.3.12 from
|
||||
https://github.com/silnrsi/graphite/releases/download/1.3.12/graphite2-minimal-1.3.12.tgz
|
||||
See ./gfx/graphite2/moz-gr-update.sh for update procedure.
|
||||
|
||||
Note (2018-03-10):
|
||||
Cherry-picked 6e24eb7edbd0872b46441d7397e8b87cccfede73 from upstream to fix memory leak
|
||||
as noted in bug https://bugzilla.mozilla.org/show_bug.cgi?id=1443095.
|
@ -30,7 +30,7 @@
|
||||
|
||||
#define GR2_VERSION_MAJOR 1
|
||||
#define GR2_VERSION_MINOR 3
|
||||
#define GR2_VERSION_BUGFIX 11
|
||||
#define GR2_VERSION_BUGFIX 12
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C"
|
||||
@ -51,12 +51,12 @@ GR2_API void gr_engine_version(int *nMajor, int *nMinor, int *nBugFix);
|
||||
* The Face Options allow the application to require that certain tables are
|
||||
* read during face construction. This may be of concern if the appFaceHandle
|
||||
* used in the gr_get_table_fn may change.
|
||||
* The values can be combined
|
||||
* The values can be combined
|
||||
*/
|
||||
enum gr_face_options {
|
||||
/** No preload, no cmap caching, fail if the graphite tables are invalid */
|
||||
gr_face_default = 0,
|
||||
/** Dumb rendering will be enabled if the graphite tables are invalid */
|
||||
/** Dumb rendering will be enabled if the graphite tables are invalid. @deprecated Since 1.311 */
|
||||
gr_face_dumbRendering = 1,
|
||||
/** preload glyphs at construction time */
|
||||
gr_face_preloadGlyphs = 2,
|
||||
@ -113,7 +113,7 @@ struct gr_face_ops
|
||||
gr_get_table_fn get_table;
|
||||
/** is a pointer to a function to notify the client the a table can be released.
|
||||
* This can be NULL to signify that the client does not wish to do any release handling. */
|
||||
gr_release_table_fn release_table;
|
||||
gr_release_table_fn release_table;
|
||||
};
|
||||
typedef struct gr_face_ops gr_face_ops;
|
||||
|
||||
@ -130,8 +130,8 @@ typedef struct gr_face_ops gr_face_ops;
|
||||
*/
|
||||
GR2_API gr_face* gr_make_face_with_ops(const void* appFaceHandle/*non-NULL*/, const gr_face_ops *face_ops, unsigned int faceOptions);
|
||||
|
||||
/** Create a gr_face object given application information and a getTable function. This function is deprecated as of v1.2.0 in
|
||||
* favour of gr_make_face_with_ops.
|
||||
/** @deprecated Since v1.2.0 in favour of gr_make_face_with_ops.
|
||||
* Create a gr_face object given application information and a getTable function.
|
||||
*
|
||||
* @return gr_face or NULL if the font fails to load for some reason.
|
||||
* @param appFaceHandle This is application specific information that is passed
|
||||
@ -140,22 +140,25 @@ GR2_API gr_face* gr_make_face_with_ops(const void* appFaceHandle/*non-NULL*/, co
|
||||
* @param getTable Callback function to get table data.
|
||||
* @param faceOptions Bitfield describing various options. See enum gr_face_options for details.
|
||||
*/
|
||||
GR2_API gr_face* gr_make_face(const void* appFaceHandle/*non-NULL*/, gr_get_table_fn getTable, unsigned int faceOptions);
|
||||
GR2_DEPRECATED_API gr_face* gr_make_face(const void* appFaceHandle/*non-NULL*/, gr_get_table_fn getTable, unsigned int faceOptions);
|
||||
|
||||
//#ifndef GRAPHITE2_NSEGCACHE
|
||||
/** Create a gr_face object given application information, with subsegmental caching support
|
||||
/** @deprecated Since 1.3.7 this function is now an alias for gr_make_face_with_ops().
|
||||
*
|
||||
* Create a gr_face object given application information, with subsegmental caching support
|
||||
*
|
||||
* @return gr_face or NULL if the font fails to load.
|
||||
* @param appFaceHandle is a pointer to application specific information that is passed to getTable.
|
||||
* This may not be NULL and must stay alive as long as the gr_face is alive.
|
||||
* @param face_ops Pointer to face specific callback structure for table management. Must stay
|
||||
* alive for the duration of the call only.
|
||||
* @param segCacheMaxSize How large the segment cache is.
|
||||
* @param segCacheMaxSize Unused.
|
||||
* @param faceOptions Bitfield of values from enum gr_face_options
|
||||
*/
|
||||
GR2_API gr_face* gr_make_face_with_seg_cache_and_ops(const void* appFaceHandle, const gr_face_ops *face_ops, unsigned int segCacheMaxSize, unsigned int faceOptions);
|
||||
GR2_DEPRECATED_API gr_face* gr_make_face_with_seg_cache_and_ops(const void* appFaceHandle, const gr_face_ops *face_ops, unsigned int segCacheMaxSize, unsigned int faceOptions);
|
||||
|
||||
/** Create a gr_face object given application information, with subsegmental caching support.
|
||||
/** @deprecated Since 1.3.7 this function is now an alias for gr_make_face().
|
||||
*
|
||||
* Create a gr_face object given application information, with subsegmental caching support.
|
||||
* This function is deprecated as of v1.2.0 in favour of gr_make_face_with_seg_cache_and_ops.
|
||||
*
|
||||
* @return gr_face or NULL if the font fails to load.
|
||||
@ -165,8 +168,7 @@ GR2_API gr_face* gr_make_face_with_seg_cache_and_ops(const void* appFaceHandle,
|
||||
* @param segCacheMaxSize How large the segment cache is.
|
||||
* @param faceOptions Bitfield of values from enum gr_face_options
|
||||
*/
|
||||
GR2_API gr_face* gr_make_face_with_seg_cache(const void* appFaceHandle, gr_get_table_fn getTable, unsigned int segCacheMaxSize, unsigned int faceOptions);
|
||||
//#endif
|
||||
GR2_DEPRECATED_API gr_face* gr_make_face_with_seg_cache(const void* appFaceHandle, gr_get_table_fn getTable, unsigned int segCacheMaxSize, unsigned int faceOptions);
|
||||
|
||||
/** Convert a tag in a string into a gr_uint32
|
||||
*
|
||||
@ -243,16 +245,16 @@ GR2_API int gr_face_is_char_supported(const gr_face *pFace, gr_uint32 usv, gr_ui
|
||||
*/
|
||||
GR2_API gr_face* gr_make_file_face(const char *filename, unsigned int faceOptions);
|
||||
|
||||
//#ifndef GRAPHITE2_NSEGCACHE
|
||||
/** Create gr_face from a font file, with subsegment caching support.
|
||||
/** @deprecated Since 1.3.7. This function is now an alias for gr_make_file_face().
|
||||
*
|
||||
* Create gr_face from a font file, with subsegment caching support.
|
||||
*
|
||||
* @return gr_face that accesses a font file directly. Returns NULL on failure.
|
||||
* @param filename Full path and filename to font file
|
||||
* @param segCacheMaxSize Specifies how big to make the cache in segments.
|
||||
* @param faceOptions Bitfield from enum gr_face_options to control face options.
|
||||
*/
|
||||
GR2_API gr_face* gr_make_file_face_with_seg_cache(const char *filename, unsigned int segCacheMaxSize, unsigned int faceOptions);
|
||||
//#endif
|
||||
GR2_DEPRECATED_API gr_face* gr_make_file_face_with_seg_cache(const char *filename, unsigned int segCacheMaxSize, unsigned int faceOptions);
|
||||
#endif // !GRAPHITE2_NFILEFACE
|
||||
|
||||
/** Create a font from a face
|
||||
@ -347,7 +349,7 @@ GR2_API gr_uint16 gr_fref_n_values(const gr_feature_ref* pfeatureref);
|
||||
* @param pfeatureref gr_feature_ref of the feature of interest
|
||||
* @param settingno Index up to the return value of gr_fref_n_values() of the value
|
||||
*/
|
||||
GR2_API gr_int16 gr_fref_value(const gr_feature_ref* pfeatureref, gr_uint16 settingno);
|
||||
GR2_API gr_int16 gr_fref_value(const gr_feature_ref* pfeatureref, gr_uint16 settingno);
|
||||
|
||||
/** Returns a string of the UI name of a feature
|
||||
*
|
||||
@ -385,4 +387,3 @@ GR2_API void gr_featureval_destroy(gr_feature_val *pfeatures);
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
|
@ -42,7 +42,7 @@ typedef enum {
|
||||
GRLOG_SEGMENT = 0x02,
|
||||
GRLOG_PASS = 0x04,
|
||||
GRLOG_CACHE = 0x08,
|
||||
|
||||
|
||||
GRLOG_OPCODE = 0x80,
|
||||
GRLOG_ALL = 0xFF
|
||||
} GrLogMask;
|
||||
|
@ -62,63 +62,63 @@ enum gr_justFlags {
|
||||
/** Used for looking up slot attributes. Most are already available in other functions **/
|
||||
enum gr_attrCode {
|
||||
/// adjusted glyph advance in x direction in design units
|
||||
gr_slatAdvX = 0,
|
||||
gr_slatAdvX = 0,
|
||||
/// adjusted glyph advance in y direction (usually 0) in design units
|
||||
gr_slatAdvY,
|
||||
gr_slatAdvY,
|
||||
/// returns 0. Deprecated.
|
||||
gr_slatAttTo,
|
||||
gr_slatAttTo,
|
||||
/// This slot attaches to its parent at the given design units in the x direction
|
||||
gr_slatAttX,
|
||||
gr_slatAttX,
|
||||
/// This slot attaches to its parent at the given design units in the y direction
|
||||
gr_slatAttY,
|
||||
gr_slatAttY,
|
||||
/// This slot attaches to its parent at the given glyph point (not implemented)
|
||||
gr_slatAttGpt,
|
||||
gr_slatAttGpt,
|
||||
/// x-direction adjustment from the given glyph point (not implemented)
|
||||
gr_slatAttXOff,
|
||||
gr_slatAttXOff,
|
||||
/// y-direction adjustment from the given glyph point (not implemented)
|
||||
gr_slatAttYOff,
|
||||
gr_slatAttYOff,
|
||||
/// Where on this glyph should align with the attachment point on the parent glyph in the x-direction.
|
||||
gr_slatAttWithX,
|
||||
gr_slatAttWithX,
|
||||
/// Where on this glyph should align with the attachment point on the parent glyph in the y-direction
|
||||
gr_slatAttWithY,
|
||||
gr_slatAttWithY,
|
||||
/// Which glyph point on this glyph should align with the attachment point on the parent glyph (not implemented).
|
||||
gr_slatWithGpt,
|
||||
gr_slatWithGpt,
|
||||
/// Adjustment to gr_slatWithGpt in x-direction (not implemented)
|
||||
gr_slatAttWithXOff,
|
||||
gr_slatAttWithXOff,
|
||||
/// Adjustment to gr_slatWithGpt in y-direction (not implemented)
|
||||
gr_slatAttWithYOff,
|
||||
gr_slatAttWithYOff,
|
||||
/// Attach at given nesting level (not implemented)
|
||||
gr_slatAttLevel,
|
||||
gr_slatAttLevel,
|
||||
/// Line break breakweight for this glyph
|
||||
gr_slatBreak,
|
||||
gr_slatBreak,
|
||||
/// Ligature component reference (not implemented)
|
||||
gr_slatCompRef,
|
||||
gr_slatCompRef,
|
||||
/// bidi directionality of this glyph (not implemented)
|
||||
gr_slatDir,
|
||||
gr_slatDir,
|
||||
/// Whether insertion is allowed before this glyph
|
||||
gr_slatInsert,
|
||||
/// Final positioned position of this glyph relative to its parent in x-direction in pixels
|
||||
gr_slatPosX,
|
||||
gr_slatPosX,
|
||||
/// Final positioned position of this glyph relative to its parent in y-direction in pixels
|
||||
gr_slatPosY,
|
||||
gr_slatPosY,
|
||||
/// Amount to shift glyph by in x-direction design units
|
||||
gr_slatShiftX,
|
||||
gr_slatShiftX,
|
||||
/// Amount to shift glyph by in y-direction design units
|
||||
gr_slatShiftY,
|
||||
gr_slatShiftY,
|
||||
/// attribute user1
|
||||
gr_slatUserDefnV1,
|
||||
gr_slatUserDefnV1,
|
||||
/// not implemented
|
||||
gr_slatMeasureSol,
|
||||
gr_slatMeasureSol,
|
||||
/// not implemented
|
||||
gr_slatMeasureEol,
|
||||
gr_slatMeasureEol,
|
||||
/// Amount this slot can stretch (not implemented)
|
||||
gr_slatJStretch,
|
||||
gr_slatJStretch,
|
||||
/// Amount this slot can shrink (not implemented)
|
||||
gr_slatJShrink,
|
||||
gr_slatJShrink,
|
||||
/// Granularity by which this slot can stretch or shrink (not implemented)
|
||||
gr_slatJStep,
|
||||
gr_slatJStep,
|
||||
/// Justification weight for this glyph (not implemented)
|
||||
gr_slatJWeight,
|
||||
gr_slatJWeight,
|
||||
/// Amount this slot mush shrink or stretch in design units
|
||||
gr_slatJWidth = 29,
|
||||
/// SubSegment split point
|
||||
@ -159,11 +159,11 @@ enum gr_attrCode {
|
||||
gr_slatSeqBelowWt,
|
||||
gr_slatSeqValignHt,
|
||||
gr_slatSeqValignWt,
|
||||
|
||||
|
||||
/// not implemented
|
||||
gr_slatMax,
|
||||
gr_slatMax,
|
||||
/// not implemented
|
||||
gr_slatNoEffect = gr_slatMax + 1
|
||||
gr_slatNoEffect = gr_slatMax + 1
|
||||
};
|
||||
|
||||
enum gr_bidirtl {
|
||||
@ -182,13 +182,13 @@ typedef struct gr_segment gr_segment;
|
||||
typedef struct gr_slot gr_slot;
|
||||
|
||||
/** Returns Unicode character for a charinfo.
|
||||
*
|
||||
*
|
||||
* @param p Pointer to charinfo to return information on.
|
||||
*/
|
||||
GR2_API unsigned int gr_cinfo_unicode_char(const gr_char_info* p/*not NULL*/);
|
||||
|
||||
/** Returns breakweight for a charinfo.
|
||||
*
|
||||
*
|
||||
* @return Breakweight is a number between -50 and 50 indicating the cost of a
|
||||
* break before or after this character. If the value < 0, the absolute value
|
||||
* is this character's contribution to the overall breakweight before it. If the value
|
||||
|
@ -40,33 +40,40 @@ enum gr_encform {
|
||||
gr_utf8 = 1/*sizeof(uint8)*/, gr_utf16 = 2/*sizeof(uint16)*/, gr_utf32 = 4/*sizeof(uint32)*/
|
||||
};
|
||||
|
||||
// Definitions for library publicly exported symbols
|
||||
#if defined _WIN32 || defined __CYGWIN__
|
||||
#if defined GRAPHITE2_STATIC
|
||||
#define GR2_API
|
||||
#elif defined GRAPHITE2_EXPORTING
|
||||
#if defined __GNUC__
|
||||
#define GR2_API __attribute__((dllexport))
|
||||
#else
|
||||
#define GR2_API __declspec(dllexport)
|
||||
#endif
|
||||
#else
|
||||
#if defined __GNUC__
|
||||
#define GR2_API __attribute__((dllimport))
|
||||
#else
|
||||
#define GR2_API __declspec(dllimport)
|
||||
#endif
|
||||
#endif
|
||||
#define GR2_LOCAL
|
||||
#elif __GNUC__ >= 4
|
||||
#if defined GRAPHITE2_STATIC
|
||||
#define GR2_API __attribute__ ((visibility("hidden")))
|
||||
#else
|
||||
#define GR2_API __attribute__ ((visibility("default")))
|
||||
#endif
|
||||
#define GR2_LOCAL __attribute__ ((visibility("hidden")))
|
||||
#else
|
||||
#define GR2_API
|
||||
#define GR2_LOCAL
|
||||
|
||||
// Define API function declspec/attributes and how each supported compiler or OS
|
||||
// allows us to specify them.
|
||||
#if defined __GNUC__
|
||||
#define _gr2_and ,
|
||||
#define _gr2_tag_fn(a) __attribute__((a))
|
||||
#define _gr2_deprecated_flag deprecated
|
||||
#define _gr2_export_flag visibility("default")
|
||||
#define _gr2_import_flag visibility("default")
|
||||
#define _gr2_static_flag visibility("hidden")
|
||||
#endif
|
||||
|
||||
#if defined _WIN32 || defined __CYGWIN__
|
||||
#if defined __GNUC__ // These three will be redefined for Windows
|
||||
#undef _gr2_export_flag
|
||||
#undef _gr2_import_flag
|
||||
#undef _gr2_static_flag
|
||||
#else // How MSVC sepcifies function level attributes adn deprecation
|
||||
#define _gr2_and
|
||||
#define _gr2_tag_fn(a) __declspec(a)
|
||||
#define _gr2_deprecated_flag deprecated
|
||||
#endif
|
||||
#define _gr2_export_flag dllexport
|
||||
#define _gr2_import_flag dllimport
|
||||
#define _gr2_static_flag
|
||||
#endif
|
||||
|
||||
#if defined GRAPHITE2_STATIC
|
||||
#define GR2_API _gr2_tag_fn(_gr2_static_flag)
|
||||
#define GR2_DEPRECATED_API _gr2_tag_fn(_gr2_deprecated_flag _gr2_and _gr2_static_flag)
|
||||
#elif defined GRAPHITE2_EXPORTING
|
||||
#define GR2_API _gr2_tag_fn(_gr2_export_flag)
|
||||
#define GR2_DEPRECATED_API _gr2_tag_fn(_gr2_deprecated_flag _gr2_and _gr2_export_flag)
|
||||
#else
|
||||
#define GR2_API _gr2_tag_fn(_gr2_import_flag)
|
||||
#define GR2_DEPRECATED_API _gr2_tag_fn(_gr2_deprecated_flag _gr2_and _gr2_import_flag)
|
||||
#endif
|
||||
|
2
gfx/graphite2/moz-gr-update.sh
Normal file → Executable file
2
gfx/graphite2/moz-gr-update.sh
Normal file → Executable file
@ -22,7 +22,7 @@ fi
|
||||
TARBALL="https://github.com/silnrsi/graphite/releases/download/$RELEASE/graphite2-minimal-$RELEASE.tgz"
|
||||
|
||||
foo=`basename $0`
|
||||
TMPFILE=`mktemp -t ${foo}` || exit 1
|
||||
TMPFILE=`mktemp -t ${foo}.XXX` || exit 1
|
||||
|
||||
curl -L "$TARBALL" -o "$TMPFILE"
|
||||
tar -x -z -C gfx/graphite2/ --strip-components 1 -f "$TMPFILE" || exit 1
|
||||
|
@ -15,8 +15,8 @@
|
||||
#
|
||||
# You should also have received a copy of the GNU Lesser General Public
|
||||
# License along with this library in the file named "LICENSE".
|
||||
# If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
# Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
# If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
# Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
# internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
CMAKE_MINIMUM_REQUIRED(VERSION 2.8.0 FATAL_ERROR)
|
||||
@ -25,7 +25,7 @@ cmake_policy(SET CMP0012 NEW)
|
||||
INCLUDE(CheckCXXSourceCompiles)
|
||||
|
||||
set(GRAPHITE_API_CURRENT 3)
|
||||
set(GRAPHITE_API_REVISION 0)
|
||||
set(GRAPHITE_API_REVISION 2)
|
||||
set(GRAPHITE_API_AGE 1)
|
||||
set(GRAPHITE_VERSION ${GRAPHITE_API_CURRENT}.${GRAPHITE_API_REVISION}.${GRAPHITE_API_AGE})
|
||||
set(GRAPHITE_SO_VERSION ${GRAPHITE_API_CURRENT})
|
||||
@ -34,12 +34,6 @@ include(TestBigEndian)
|
||||
|
||||
include_directories(${PROJECT_SOURCE_DIR})
|
||||
|
||||
set(SEGCACHE SegCache.cpp SegCacheEntry.cpp SegCacheStore.cpp)
|
||||
if (GRAPHITE2_NSEGCACHE)
|
||||
add_definitions(-DGRAPHITE2_NSEGCACHE)
|
||||
set(SEGCACHE)
|
||||
endif (GRAPHITE2_NSEGCACHE)
|
||||
|
||||
set(FILEFACE FileFace.cpp)
|
||||
if (GRAPHITE2_NFILEFACE)
|
||||
add_definitions(-DGRAPHITE2_NFILEFACE)
|
||||
@ -60,14 +54,14 @@ if (NOT BUILD_SHARED_LIBS)
|
||||
add_definitions(-DGRAPHITE2_STATIC)
|
||||
endif (NOT BUILD_SHARED_LIBS)
|
||||
|
||||
set(GRAPHITE_HEADERS
|
||||
set(GRAPHITE_HEADERS
|
||||
../include/graphite2/Font.h
|
||||
../include/graphite2/Segment.h
|
||||
../include/graphite2/Types.h
|
||||
../include/graphite2/Log.h
|
||||
)
|
||||
|
||||
file(GLOB PRIVATE_HEADERS inc/*.h)
|
||||
file(GLOB PRIVATE_HEADERS inc/*.h)
|
||||
|
||||
add_library(graphite2
|
||||
${GRAPHITE2_VM_TYPE}_machine.cpp
|
||||
@ -78,7 +72,6 @@ add_library(graphite2
|
||||
gr_logging.cpp
|
||||
gr_segment.cpp
|
||||
gr_slot.cpp
|
||||
CachedFace.cpp
|
||||
CmapCache.cpp
|
||||
Code.cpp
|
||||
Collider.cpp
|
||||
@ -100,7 +93,6 @@ add_library(graphite2
|
||||
TtfUtil.cpp
|
||||
UtfCodec.cpp
|
||||
${FILEFACE}
|
||||
${SEGCACHE}
|
||||
${TRACING})
|
||||
|
||||
set_target_properties(graphite2 PROPERTIES PUBLIC_HEADER "${GRAPHITE_HEADERS}"
|
||||
@ -123,21 +115,21 @@ if (${CMAKE_SYSTEM_NAME} STREQUAL "Linux")
|
||||
endif (CMAKE_COMPILER_IS_GNUCXX)
|
||||
message(STATUS "Compiler ID is: ${CMAKE_CXX_COMPILER_ID}")
|
||||
if (${CMAKE_CXX_COMPILER_ID} STREQUAL "Clang")
|
||||
add_definitions(-Wimplicit-fallthrough)
|
||||
add_definitions(-Wimplicit-fallthrough -Wshorten-64-to-32)
|
||||
endif (${CMAKE_CXX_COMPILER_ID} STREQUAL "Clang")
|
||||
if (${CMAKE_CXX_COMPILER} MATCHES ".*mingw.*")
|
||||
target_link_libraries(graphite2 kernel32 msvcr90 mingw32 gcc user32)
|
||||
else (${CMAKE_CXX_COMPILER} MATCHES ".*mingw.*")
|
||||
if (GRAPHITE2_ASAN)
|
||||
if (GRAPHITE2_SANITIZERS)
|
||||
target_link_libraries(graphite2 c gcc_s)
|
||||
else (GRAPHITE2_ASAN)
|
||||
else ()
|
||||
target_link_libraries(graphite2 c gcc)
|
||||
endif (GRAPHITE2_ASAN)
|
||||
include(Graphite)
|
||||
if (BUILD_SHARED_LIBS)
|
||||
nolib_test(stdc++ $<TARGET_SONAME_FILE:graphite2>)
|
||||
endif (BUILD_SHARED_LIBS)
|
||||
endif ()
|
||||
endif (${CMAKE_CXX_COMPILER} MATCHES ".*mingw.*")
|
||||
include(Graphite)
|
||||
if (BUILD_SHARED_LIBS)
|
||||
nolib_test(stdc++ $<TARGET_SONAME_FILE:graphite2>)
|
||||
endif ()
|
||||
set(CMAKE_CXX_IMPLICIT_LINK_LIBRARIES "")
|
||||
CREATE_LIBTOOL_FILE(graphite2 "/lib${LIB_SUFFIX}")
|
||||
endif (${CMAKE_SYSTEM_NAME} STREQUAL "Linux")
|
||||
@ -155,7 +147,7 @@ if (${CMAKE_SYSTEM_NAME} STREQUAL "Darwin")
|
||||
endif (${CMAKE_SYSTEM_NAME} STREQUAL "Darwin")
|
||||
|
||||
if (${CMAKE_SYSTEM_NAME} STREQUAL "Windows")
|
||||
set_target_properties(graphite2 PROPERTIES
|
||||
set_target_properties(graphite2 PROPERTIES
|
||||
COMPILE_DEFINITIONS "_SCL_SECURE_NO_WARNINGS;_CRT_SECURE_NO_WARNINGS;UNICODE;GRAPHITE2_EXPORTING")
|
||||
endif (${CMAKE_SYSTEM_NAME} STREQUAL "Windows")
|
||||
|
||||
|
@ -1,127 +0,0 @@
|
||||
/* GRAPHITE2 LICENSING
|
||||
|
||||
Copyright 2010, SIL International
|
||||
All rights reserved.
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published
|
||||
by the Free Software Foundation; either version 2.1 of License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
Lesser General Public License for more details.
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
Mozilla Public License (http://mozilla.org/MPL) or the GNU General Public
|
||||
License, as published by the Free Software Foundation, either version 2
|
||||
of the License or (at your option) any later version.
|
||||
*/
|
||||
|
||||
#ifndef GRAPHITE2_NSEGCACHE
|
||||
|
||||
#include <graphite2/Segment.h>
|
||||
#include "inc/CachedFace.h"
|
||||
#include "inc/SegCacheStore.h"
|
||||
|
||||
|
||||
using namespace graphite2;
|
||||
|
||||
CachedFace::CachedFace(const void* appFaceHandle/*non-NULL*/, const gr_face_ops & ops)
|
||||
: Face(appFaceHandle, ops), m_cacheStore(0)
|
||||
{
|
||||
}
|
||||
|
||||
CachedFace::~CachedFace()
|
||||
{
|
||||
delete m_cacheStore;
|
||||
}
|
||||
|
||||
bool CachedFace::setupCache(unsigned int cacheSize)
|
||||
{
|
||||
m_cacheStore = new SegCacheStore(*this, m_numSilf, cacheSize);
|
||||
return bool(m_cacheStore);
|
||||
}
|
||||
|
||||
|
||||
bool CachedFace::runGraphite(Segment *seg, const Silf *pSilf) const
|
||||
{
|
||||
assert(pSilf);
|
||||
pSilf->runGraphite(seg, 0, pSilf->substitutionPass());
|
||||
|
||||
unsigned int silfIndex = 0;
|
||||
for (; silfIndex < m_numSilf && &(m_silfs[silfIndex]) != pSilf; ++silfIndex);
|
||||
if (silfIndex == m_numSilf) return false;
|
||||
SegCache * const segCache = m_cacheStore->getOrCreate(silfIndex, seg->getFeatures(0));
|
||||
if (!segCache)
|
||||
return false;
|
||||
|
||||
assert(m_cacheStore);
|
||||
// find where the segment can be broken
|
||||
Slot * subSegStartSlot = seg->first();
|
||||
Slot * subSegEndSlot = subSegStartSlot;
|
||||
uint16 cmapGlyphs[eMaxSpliceSize];
|
||||
int subSegStart = 0;
|
||||
for (unsigned int i = 0; i < seg->charInfoCount() && subSegEndSlot; ++i)
|
||||
{
|
||||
const unsigned int length = i - subSegStart + 1;
|
||||
if (length < eMaxSpliceSize && subSegEndSlot->gid() < m_cacheStore->maxCmapGid())
|
||||
cmapGlyphs[length-1] = subSegEndSlot->gid();
|
||||
else return false;
|
||||
const bool spaceOnly = m_cacheStore->isSpaceGlyph(subSegEndSlot->gid());
|
||||
// at this stage the character to slot mapping is still 1 to 1
|
||||
const int breakWeight = seg->charinfo(i)->breakWeight(),
|
||||
nextBreakWeight = (i + 1 < seg->charInfoCount())?
|
||||
seg->charinfo(i+1)->breakWeight() : 0;
|
||||
const uint8 f = seg->charinfo(i)->flags();
|
||||
if (((spaceOnly
|
||||
|| (breakWeight > 0 && breakWeight <= gr_breakWord)
|
||||
|| i + 1 == seg->charInfoCount()
|
||||
|| ((nextBreakWeight < 0 && nextBreakWeight >= gr_breakBeforeWord)
|
||||
|| (subSegEndSlot->next() && m_cacheStore->isSpaceGlyph(subSegEndSlot->next()->gid()))))
|
||||
&& f != 1)
|
||||
|| f == 2)
|
||||
{
|
||||
// record the next slot before any splicing
|
||||
Slot * nextSlot = subSegEndSlot->next();
|
||||
// spaces should be left untouched by graphite rules in any sane font
|
||||
if (!spaceOnly)
|
||||
{
|
||||
// found a break position, check for a cache of the sub sequence
|
||||
const SegCacheEntry * entry = segCache->find(cmapGlyphs, length);
|
||||
// TODO disable cache for words at start/end of line with contextuals
|
||||
if (!entry)
|
||||
{
|
||||
SegmentScopeState scopeState = seg->setScope(subSegStartSlot, subSegEndSlot, length);
|
||||
pSilf->runGraphite(seg, pSilf->substitutionPass(), pSilf->numPasses());
|
||||
if (length < eMaxSpliceSize)
|
||||
{
|
||||
seg->associateChars(subSegStart, length);
|
||||
segCache->cache(m_cacheStore, cmapGlyphs, length, seg, subSegStart);
|
||||
}
|
||||
seg->removeScope(scopeState);
|
||||
}
|
||||
else
|
||||
seg->splice(subSegStart, length, subSegStartSlot, subSegEndSlot,
|
||||
entry->first(), entry->glyphLength());
|
||||
}
|
||||
subSegStartSlot = subSegEndSlot = nextSlot;
|
||||
subSegStart = i + 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
subSegEndSlot = subSegEndSlot->next();
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -24,7 +24,7 @@ Mozilla Public License (http://mozilla.org/MPL) or the GNU General Public
|
||||
License, as published by the Free Software Foundation, either version 2
|
||||
of the License or (at your option) any later version.
|
||||
*/
|
||||
// This class represents loaded graphite stack machine code. It performs
|
||||
// This class represents loaded graphite stack machine code. It performs
|
||||
// basic sanity checks, on the incoming code to prevent more obvious problems
|
||||
// from crashing graphite.
|
||||
// Author: Tim Eves
|
||||
@ -67,7 +67,7 @@ inline bool is_return(const instr i) {
|
||||
struct context
|
||||
{
|
||||
context(uint8 ref=0) : codeRef(ref) {flags.changed=false; flags.referenced=false;}
|
||||
struct {
|
||||
struct {
|
||||
uint8 changed:1,
|
||||
referenced:1;
|
||||
} flags;
|
||||
@ -82,14 +82,14 @@ class Machine::Code::decoder
|
||||
public:
|
||||
struct limits;
|
||||
static const int NUMCONTEXTS = 256;
|
||||
|
||||
|
||||
decoder(limits & lims, Code &code, enum passtype pt) throw();
|
||||
|
||||
|
||||
bool load(const byte * bc_begin, const byte * bc_end);
|
||||
void apply_analysis(instr * const code, instr * code_end);
|
||||
byte max_ref() { return _max_ref; }
|
||||
int out_index() const { return _out_index; }
|
||||
|
||||
|
||||
private:
|
||||
void set_ref(int index) throw();
|
||||
void set_noref(int index) throw();
|
||||
@ -102,7 +102,7 @@ private:
|
||||
bool test_context() const throw();
|
||||
bool test_ref(int8 index) const throw();
|
||||
void failure(const status_t s) const throw() { _code.failure(s); }
|
||||
|
||||
|
||||
Code & _code;
|
||||
int _out_index;
|
||||
uint16 _out_length;
|
||||
@ -128,18 +128,18 @@ struct Machine::Code::decoder::limits
|
||||
features;
|
||||
const byte attrid[gr_slatMax];
|
||||
};
|
||||
|
||||
|
||||
inline Machine::Code::decoder::decoder(limits & lims, Code &code, enum passtype pt) throw()
|
||||
: _code(code),
|
||||
_out_index(code._constraint ? 0 : lims.pre_context),
|
||||
_out_length(code._constraint ? 1 : lims.rule_length),
|
||||
_out_index(code._constraint ? 0 : lims.pre_context),
|
||||
_out_length(code._constraint ? 1 : lims.rule_length),
|
||||
_instr(code._code), _data(code._data), _max(lims), _passtype(pt),
|
||||
_stack_depth(0),
|
||||
_in_ctxt_item(false),
|
||||
_slotref(0),
|
||||
_max_ref(0)
|
||||
{ }
|
||||
|
||||
|
||||
|
||||
|
||||
Machine::Code::Code(bool is_constraint, const byte * bytecode_begin, const byte * const bytecode_end,
|
||||
@ -159,38 +159,38 @@ Machine::Code::Code(bool is_constraint, const byte * bytecode_begin, const byte
|
||||
}
|
||||
assert(bytecode_end > bytecode_begin);
|
||||
const opcode_t * op_to_fn = Machine::getOpcodeTable();
|
||||
|
||||
|
||||
// Allocate code and data target buffers, these sizes are a worst case
|
||||
// estimate. Once we know their real sizes the we'll shrink them.
|
||||
if (_out) _code = reinterpret_cast<instr *>(*_out);
|
||||
else _code = static_cast<instr *>(malloc(estimateCodeDataOut(bytecode_end-bytecode_begin, 1, is_constraint ? 0 : rule_length)));
|
||||
_data = reinterpret_cast<byte *>(_code + (bytecode_end - bytecode_begin));
|
||||
|
||||
|
||||
if (!_code || !_data) {
|
||||
failure(alloc_failed);
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
decoder::limits lims = {
|
||||
bytecode_end,
|
||||
pre_context,
|
||||
rule_length,
|
||||
silf.numClasses(),
|
||||
face.glyphs().numAttrs(),
|
||||
face.numFeatures(),
|
||||
{1,1,1,1,1,1,1,1,
|
||||
face.numFeatures(),
|
||||
{1,1,1,1,1,1,1,1,
|
||||
1,1,1,1,1,1,1,255,
|
||||
1,1,1,1,1,1,1,1,
|
||||
1,1,1,1,1,1,0,0,
|
||||
0,0,0,0,0,0,0,0,
|
||||
0,0,0,0,0,0,0,0,
|
||||
1,1,1,1,1,1,1,1,
|
||||
1,1,1,1,1,1,0,0,
|
||||
0,0,0,0,0,0,0,0,
|
||||
0,0,0,0,0,0,0,0,
|
||||
0,0,0,0,0,0,0, silf.numUser()}
|
||||
};
|
||||
|
||||
|
||||
decoder dec(lims, *this, pt);
|
||||
if(!dec.load(bytecode_begin, bytecode_end))
|
||||
return;
|
||||
|
||||
|
||||
// Is this an empty program?
|
||||
if (_instr_count == 0)
|
||||
{
|
||||
@ -198,7 +198,7 @@ Machine::Code::Code(bool is_constraint, const byte * bytecode_begin, const byte
|
||||
::new (this) Code();
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
// When we reach the end check we've terminated it correctly
|
||||
if (!is_return(_code[_instr_count-1])) {
|
||||
failure(missing_return);
|
||||
@ -208,9 +208,9 @@ Machine::Code::Code(bool is_constraint, const byte * bytecode_begin, const byte
|
||||
assert((_constraint && immutable()) || !_constraint);
|
||||
dec.apply_analysis(_code, _code + _instr_count);
|
||||
_max_ref = dec.max_ref();
|
||||
|
||||
|
||||
// Now we know exactly how much code and data the program really needs
|
||||
// realloc the buffers to exactly the right size so we don't waste any
|
||||
// realloc the buffers to exactly the right size so we don't waste any
|
||||
// memory.
|
||||
assert((bytecode_end - bytecode_begin) >= ptrdiff_t(_instr_count));
|
||||
assert((bytecode_end - bytecode_begin) >= ptrdiff_t(_data_size));
|
||||
@ -255,13 +255,13 @@ bool Machine::Code::decoder::load(const byte * bc, const byte * bc_end)
|
||||
const opcode opc = fetch_opcode(bc++);
|
||||
if (opc == vm::MAX_OPCODE)
|
||||
return false;
|
||||
|
||||
|
||||
analyse_opcode(opc, reinterpret_cast<const int8 *>(bc));
|
||||
|
||||
|
||||
if (!emit_opcode(opc, bc))
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
return bool(_code);
|
||||
}
|
||||
|
||||
@ -275,7 +275,7 @@ opcode Machine::Code::decoder::fetch_opcode(const byte * bc)
|
||||
// Do some basic sanity checks based on what we know about the opcode
|
||||
if (!validate_opcode(opc, bc)) return MAX_OPCODE;
|
||||
|
||||
// And check it's arguments as far as possible
|
||||
// And check its arguments as far as possible
|
||||
switch (opcode(opc))
|
||||
{
|
||||
case NOP :
|
||||
@ -509,7 +509,7 @@ void Machine::Code::decoder::analyse_opcode(const opcode opc, const int8 * arg)
|
||||
case NEXT :
|
||||
case COPY_NEXT :
|
||||
++_slotref;
|
||||
_contexts[_slotref] = context(_code._instr_count+1);
|
||||
_contexts[_slotref] = context(uint8(_code._instr_count+1));
|
||||
// if (_analysis.slotref > _analysis.max_ref) _analysis.max_ref = _analysis.slotref;
|
||||
break;
|
||||
case INSERT :
|
||||
@ -517,7 +517,7 @@ void Machine::Code::decoder::analyse_opcode(const opcode opc, const int8 * arg)
|
||||
_code._modify = true;
|
||||
break;
|
||||
case PUT_SUBS_8BIT_OBS : // slotref on 1st parameter
|
||||
case PUT_SUBS :
|
||||
case PUT_SUBS :
|
||||
_code._modify = true;
|
||||
set_changed(0);
|
||||
GR_FALLTHROUGH;
|
||||
@ -559,7 +559,7 @@ bool Machine::Code::decoder::emit_opcode(opcode opc, const byte * & bc)
|
||||
const size_t param_sz = op.param_sz == VARARGS ? bc[0] + 1 : op.param_sz;
|
||||
|
||||
// Add this instruction
|
||||
*_instr++ = op.impl[_code._constraint];
|
||||
*_instr++ = op.impl[_code._constraint];
|
||||
++_code._instr_count;
|
||||
|
||||
// Grab the parameters
|
||||
@ -569,8 +569,8 @@ bool Machine::Code::decoder::emit_opcode(opcode opc, const byte * & bc)
|
||||
_data += param_sz;
|
||||
_code._data_size += param_sz;
|
||||
}
|
||||
|
||||
// recursively decode a context item so we can split the skip into
|
||||
|
||||
// recursively decode a context item so we can split the skip into
|
||||
// instruction and data portions.
|
||||
if (opc == CNTXT_ITEM)
|
||||
{
|
||||
@ -589,8 +589,8 @@ bool Machine::Code::decoder::emit_opcode(opcode opc, const byte * & bc)
|
||||
if (load(bc, bc + instr_skip))
|
||||
{
|
||||
bc += instr_skip;
|
||||
data_skip = instr_skip - (_code._instr_count - ctxt_start);
|
||||
instr_skip = _code._instr_count - ctxt_start;
|
||||
data_skip = instr_skip - byte(_code._instr_count - ctxt_start);
|
||||
instr_skip = byte(_code._instr_count - ctxt_start);
|
||||
_max.bytecode = curr_end;
|
||||
|
||||
_out_length = 1;
|
||||
@ -605,7 +605,7 @@ bool Machine::Code::decoder::emit_opcode(opcode opc, const byte * & bc)
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
return bool(_code);
|
||||
}
|
||||
|
||||
@ -620,15 +620,15 @@ void Machine::Code::decoder::apply_analysis(instr * const code, instr * code_end
|
||||
for (const context * c = _contexts, * const ce = c + _slotref; c < ce; ++c)
|
||||
{
|
||||
if (!c->flags.referenced || !c->flags.changed) continue;
|
||||
|
||||
instr * const tip = code + c->codeRef + tempcount;
|
||||
|
||||
instr * const tip = code + c->codeRef + tempcount;
|
||||
memmove(tip+1, tip, (code_end - tip) * sizeof(instr));
|
||||
*tip = temp_copy;
|
||||
++code_end;
|
||||
++tempcount;
|
||||
_code._delete = true;
|
||||
}
|
||||
|
||||
|
||||
_code._instr_count = code_end - code;
|
||||
}
|
||||
|
||||
@ -695,7 +695,7 @@ bool Machine::Code::decoder::test_context() const throw()
|
||||
return true;
|
||||
}
|
||||
|
||||
inline
|
||||
inline
|
||||
void Machine::Code::failure(const status_t s) throw() {
|
||||
release_buffers();
|
||||
_status = s;
|
||||
@ -750,4 +750,3 @@ int32 Machine::Code::run(Machine & m, slotref * & map) const
|
||||
|
||||
return m.run(_code, _data, map);
|
||||
}
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -37,7 +37,7 @@ of the License or (at your option) any later version.
|
||||
|
||||
#define ISQRT2 0.707106781f
|
||||
|
||||
// Possible rounding error for subbox boundaries: 0.016 = 1/64 = 1/256 * 4
|
||||
// Possible rounding error for subbox boundaries: 0.016 = 1/64 = 1/256 * 4
|
||||
// (values in font range from 0..256)
|
||||
// #define SUBBOX_RND_ERR 0.016
|
||||
|
||||
@ -118,7 +118,7 @@ bool ShiftCollider::initSlot(Segment *seg, Slot *aSlot, const Rect &limit, float
|
||||
|
||||
_margin = margin;
|
||||
_marginWt = marginWeight;
|
||||
|
||||
|
||||
SlotCollision *c = seg->collisionInfo(aSlot);
|
||||
_seqClass = c->seqClass();
|
||||
_seqProxClass = c->seqProxClass();
|
||||
@ -166,7 +166,7 @@ void ShiftCollider::addBox_slope(bool isx, const Rect &box, const BBox &bb, cons
|
||||
_ranges[axis].weighted<XY>(box.bl.y - c, box.tr.y - c, weight, a, 0, 0, org.x,
|
||||
m * (a * a + sqr((minright ? box.tr.x : box.bl.x) - 0.5f * (bb.xi + bb.xa))), false);
|
||||
else
|
||||
_ranges[axis].weighted<XY>(box.bl.y - c, box.tr.y - c, weight, a, m,
|
||||
_ranges[axis].weighted<XY>(box.bl.y - c, box.tr.y - c, weight, a, m,
|
||||
(minright ? box.tr.y : box.bl.y) - c, a, 0, false);
|
||||
}
|
||||
break;
|
||||
@ -230,7 +230,7 @@ inline void ShiftCollider::removeBox(const Rect &box, const BBox &bb, const Slan
|
||||
}
|
||||
break;
|
||||
case 2 :
|
||||
if (box.bl.x - box.tr.y < org.x - org.y + sb.da && box.tr.x - box.bl.y > org.x - org.y + sb.di
|
||||
if (box.bl.x - box.tr.y < org.x - org.y + sb.da && box.tr.x - box.bl.y > org.x - org.y + sb.di
|
||||
&& box.width() > 0 && box.height() > 0)
|
||||
{
|
||||
float di = org.x - org.y + sb.di;
|
||||
@ -242,7 +242,7 @@ inline void ShiftCollider::removeBox(const Rect &box, const BBox &bb, const Slan
|
||||
}
|
||||
break;
|
||||
case 3 :
|
||||
if (box.bl.x + box.bl.y < org.x + org.y + sb.sa && box.tr.x + box.tr.y > org.x + org.y + sb.si
|
||||
if (box.bl.x + box.bl.y < org.x + org.y + sb.sa && box.tr.x + box.tr.y > org.x + org.y + sb.si
|
||||
&& box.width() > 0 && box.height() > 0)
|
||||
{
|
||||
float si = org.x + org.y + sb.si;
|
||||
@ -285,7 +285,7 @@ bool ShiftCollider::mergeSlot(Segment *seg, Slot *slot, const SlotCollision *csl
|
||||
// SlotCollision * cslot = seg->collisionInfo(slot);
|
||||
int orderFlags = 0;
|
||||
bool sameClass = _seqProxClass == 0 && cslot->seqClass() == _seqClass;
|
||||
if (sameCluster && _seqClass
|
||||
if (sameCluster && _seqClass
|
||||
&& (sameClass || (_seqProxClass != 0 && cslot->seqClass() == _seqProxClass)))
|
||||
// Force the target glyph to be in the specified direction from the slot we're testing.
|
||||
orderFlags = _seqOrder;
|
||||
@ -378,7 +378,7 @@ bool ShiftCollider::mergeSlot(Segment *seg, Slot *slot, const SlotCollision *csl
|
||||
default :
|
||||
continue;
|
||||
}
|
||||
|
||||
|
||||
#if !defined GRAPHITE2_NTRACING
|
||||
if (dbgout)
|
||||
dbgout->setenv(1, reinterpret_cast<void *>(-1));
|
||||
@ -400,7 +400,7 @@ bool ShiftCollider::mergeSlot(Segment *seg, Slot *slot, const SlotCollision *csl
|
||||
float r1Xedge = cslot->seqAboveXoff() + 0.5f * (bb.xi + bb.xa) + sx;
|
||||
float r3Xedge = cslot->seqBelowXlim() + bb.xa + sx + 0.5f * (tbb.xa - tbb.xi);
|
||||
float r2Yedge = 0.5f * (bb.yi + bb.ya) + sy;
|
||||
|
||||
|
||||
// DBGTAG(1x) means the regions are up and right
|
||||
// region 1
|
||||
DBGTAG(11)
|
||||
@ -452,7 +452,7 @@ bool ShiftCollider::mergeSlot(Segment *seg, Slot *slot, const SlotCollision *csl
|
||||
}
|
||||
case SlotCollision::SEQ_ORDER_NOABOVE : // enforce neighboring glyph being above
|
||||
DBGTAG(31);
|
||||
removeBox(Rect(Position(bb.xi - tbb.xa + sx, sy + bb.ya),
|
||||
removeBox(Rect(Position(bb.xi - tbb.xa + sx, sy + bb.ya),
|
||||
Position(bb.xa - tbb.xi + sx, ypinf)), tbb, tsb, org, i);
|
||||
break;
|
||||
case SlotCollision::SEQ_ORDER_NOBELOW : // enforce neighboring glyph being below
|
||||
@ -569,7 +569,7 @@ bool ShiftCollider::mergeSlot(Segment *seg, Slot *slot, const SlotCollision *csl
|
||||
}
|
||||
hasCol |= isCol;
|
||||
return res;
|
||||
|
||||
|
||||
} // end of ShiftCollider::mergeSlot
|
||||
|
||||
|
||||
@ -666,7 +666,7 @@ void ShiftCollider::outputJsonDbg(json * const dbgout, Segment *seg, int axis)
|
||||
{
|
||||
*dbgout << json::flat << json::array << _ranges[iAxis].position();
|
||||
for (Zones::const_iterator s = _ranges[iAxis].begin(), e = _ranges[iAxis].end(); s != e; ++s)
|
||||
*dbgout << json::flat << json::array
|
||||
*dbgout << json::flat << json::array
|
||||
<< Position(s->x, s->xm) << s->sm << s->smx << s->c
|
||||
<< json::close;
|
||||
*dbgout << json::close;
|
||||
@ -703,7 +703,7 @@ void ShiftCollider::outputJsonDbgEndSlot(GR_MAYBE_UNUSED json * const dbgout,
|
||||
}
|
||||
|
||||
void ShiftCollider::outputJsonDbgOneVector(json * const dbgout, Segment *seg, int axis,
|
||||
float tleft, float bestCost, float bestVal)
|
||||
float tleft, float bestCost, float bestVal)
|
||||
{
|
||||
const char * label;
|
||||
switch (axis)
|
||||
@ -718,9 +718,9 @@ void ShiftCollider::outputJsonDbgOneVector(json * const dbgout, Segment *seg, in
|
||||
*dbgout << json::object // vector
|
||||
<< "direction" << label
|
||||
<< "targetMin" << tleft;
|
||||
|
||||
|
||||
outputJsonDbgRemovals(dbgout, axis, seg);
|
||||
|
||||
|
||||
*dbgout << "ranges";
|
||||
outputJsonDbg(dbgout, seg, axis);
|
||||
|
||||
@ -756,7 +756,7 @@ static float localmin(float al, float au, float bl, float bu, float x)
|
||||
if (bl > al)
|
||||
{ if (bu > au) return bl > x ? bl : x; }
|
||||
else if (au > bu) return al > x ? al : x;
|
||||
return x;
|
||||
return x;
|
||||
}
|
||||
|
||||
// Return the given edge of the glyph at height y, taking any slant box into account.
|
||||
@ -835,7 +835,7 @@ bool KernCollider::initSlot(Segment *seg, Slot *aSlot, const Rect &limit, float
|
||||
|
||||
_limit = limit;
|
||||
_offsetPrev = offsetPrev; // kern from a previous pass
|
||||
|
||||
|
||||
// Calculate the height of the glyph and how many horizontal slices to use.
|
||||
if (_maxy >= 1e37f)
|
||||
{
|
||||
@ -877,7 +877,7 @@ bool KernCollider::initSlot(Segment *seg, Slot *aSlot, const Rect &limit, float
|
||||
}
|
||||
goto done;
|
||||
}
|
||||
numSlices = _edges.size();
|
||||
numSlices = int(_edges.size());
|
||||
|
||||
#if !defined GRAPHITE2_NTRACING
|
||||
// Debugging
|
||||
@ -887,7 +887,7 @@ bool KernCollider::initSlot(Segment *seg, Slot *aSlot, const Rect &limit, float
|
||||
_nearEdges.clear();
|
||||
_nearEdges.insert(_nearEdges.begin(), numSlices, (dir & 1) ? -1e38f : +1e38f);
|
||||
#endif
|
||||
|
||||
|
||||
// Determine the trailing edge of each slice (ie, left edge for a RTL glyph).
|
||||
for (s = base; s; s = s->nextInCluster(s))
|
||||
{
|
||||
@ -997,7 +997,7 @@ bool KernCollider::mergeSlot(Segment *seg, Slot *slot, const Position &currShift
|
||||
if (collides && !nooverlap)
|
||||
_hit = true;
|
||||
return collides | nooverlap; // note that true is not a necessarily reliable value
|
||||
|
||||
|
||||
} // end of KernCollider::mergeSlot
|
||||
|
||||
|
||||
@ -1027,19 +1027,19 @@ Position KernCollider::resolve(GR_MAYBE_UNUSED Segment *seg, GR_MAYBE_UNUSED Slo
|
||||
<< "slantBox" << seg->getFace()->glyphs().slant(_target->gid())
|
||||
<< "fix" << "kern"
|
||||
<< json::close; // target object
|
||||
|
||||
|
||||
*dbgout << "slices" << json::array;
|
||||
for (int is = 0; is < (int)_edges.size(); is++)
|
||||
{
|
||||
*dbgout << json::flat << json::object
|
||||
<< "i" << is
|
||||
*dbgout << json::flat << json::object
|
||||
<< "i" << is
|
||||
<< "targetEdge" << _edges[is]
|
||||
<< "neighbor" << objectid(dslot(seg, _slotNear[is]))
|
||||
<< "nearEdge" << _nearEdges[is]
|
||||
<< "nearEdge" << _nearEdges[is]
|
||||
<< json::close;
|
||||
}
|
||||
*dbgout << json::close; // slices array
|
||||
|
||||
|
||||
*dbgout
|
||||
<< "xbound" << _xbound
|
||||
<< "minGap" << _mingap
|
||||
@ -1051,7 +1051,7 @@ Position KernCollider::resolve(GR_MAYBE_UNUSED Segment *seg, GR_MAYBE_UNUSED Slo
|
||||
#endif
|
||||
|
||||
return Position(result, 0.);
|
||||
|
||||
|
||||
} // end of KernCollider::resolve
|
||||
|
||||
void KernCollider::shift(const Position &mv, int dir)
|
||||
@ -1072,7 +1072,7 @@ SlotCollision::SlotCollision(Segment *seg, Slot *slot)
|
||||
void SlotCollision::initFromSlot(Segment *seg, Slot *slot)
|
||||
{
|
||||
// Initialize slot attributes from glyph attributes.
|
||||
// The order here must match the order in the grcompiler code,
|
||||
// The order here must match the order in the grcompiler code,
|
||||
// GrcSymbolTable::AssignInternalGlyphAttrIDs.
|
||||
uint16 gid = slot->gid();
|
||||
uint16 aCol = seg->silf()->aCollision(); // flags attr ID
|
||||
@ -1094,7 +1094,7 @@ void SlotCollision::initFromSlot(Segment *seg, Slot *slot)
|
||||
_seqBelowXlim = p[aCol+12];
|
||||
_seqBelowWt = p[aCol+13];
|
||||
_seqValignHt = p[aCol+14];
|
||||
_seqValignWt = p[aCol+15];
|
||||
_seqValignWt = p[aCol+15];
|
||||
|
||||
// These attributes do not have corresponding glyph attribute:
|
||||
_exclGlyph = 0;
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -47,7 +47,7 @@ bool read_sequence(u8 const * &src, u8 const * const end, u8 const * &literal,
|
||||
u32 & literal_len, u32 & match_len, u32 & match_dist)
|
||||
{
|
||||
u8 const token = *src++;
|
||||
|
||||
|
||||
literal_len = read_literal(src, end, token >> 4);
|
||||
literal = src;
|
||||
src += literal_len;
|
||||
@ -55,7 +55,7 @@ bool read_sequence(u8 const * &src, u8 const * const end, u8 const * &literal,
|
||||
// Normal exit for end of stream, wrap arround check and parital match check.
|
||||
if (src > end - sizeof(u16) || src < literal)
|
||||
return false;
|
||||
|
||||
|
||||
match_dist = *src++;
|
||||
match_dist |= *src++ << 8;
|
||||
match_len = read_literal(src, end, token & 0xf) + MINMATCH;
|
||||
@ -70,7 +70,7 @@ int lz4::decompress(void const *in, size_t in_size, void *out, size_t out_size)
|
||||
{
|
||||
if (out_size <= in_size || in_size < MINSRCSIZE)
|
||||
return -1;
|
||||
|
||||
|
||||
u8 const * src = static_cast<u8 const *>(in),
|
||||
* literal = 0,
|
||||
* const src_end = src + in_size;
|
||||
@ -100,7 +100,7 @@ int lz4::decompress(void const *in, size_t in_size, void *out, size_t out_size)
|
||||
dst = overrun_copy(dst, literal, literal_len);
|
||||
out_size -= literal_len;
|
||||
}
|
||||
|
||||
|
||||
// Copy, possibly repeating, match from earlier in the
|
||||
// decoded output.
|
||||
u8 const * const pcpy = dst - match_dist;
|
||||
@ -120,7 +120,6 @@ int lz4::decompress(void const *in, size_t in_size, void *out, size_t out_size)
|
||||
if (literal > src_end - literal_len || literal_len > out_size)
|
||||
return -1;
|
||||
dst = fast_copy(dst, literal, literal_len);
|
||||
|
||||
return dst - (u8*)out;
|
||||
}
|
||||
|
||||
return int(dst - (u8*)out);
|
||||
}
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -34,7 +34,6 @@ of the License or (at your option) any later version.
|
||||
#include "inc/FileFace.h"
|
||||
#include "inc/GlyphFace.h"
|
||||
#include "inc/json.h"
|
||||
#include "inc/SegCacheStore.h"
|
||||
#include "inc/Segment.h"
|
||||
#include "inc/NameTable.h"
|
||||
#include "inc/Error.h"
|
||||
@ -142,7 +141,7 @@ bool Face::readGraphite(const Table & silf)
|
||||
{
|
||||
error_context(EC_ASILF + (i << 8));
|
||||
const uint32 offset = be::read<uint32>(p),
|
||||
next = i == m_numSilf - 1 ? silf.size() : be::peek<uint32>(p);
|
||||
next = i == m_numSilf - 1 ? uint32(silf.size()) : be::peek<uint32>(p);
|
||||
if (e.test(next > silf.size() || offset >= next, E_BADSIZE))
|
||||
return error(e);
|
||||
|
||||
@ -201,7 +200,7 @@ bool Face::runGraphite(Segment *seg, const Silf *aSilf) const
|
||||
<< "advance" << seg->advance()
|
||||
<< "chars" << json::array;
|
||||
for(size_t i = 0, n = seg->charInfoCount(); i != n; ++i)
|
||||
*dbgout << json::flat << *seg->charinfo(i);
|
||||
*dbgout << json::flat << *seg->charinfo(int(i));
|
||||
*dbgout << json::close // Close up the chars array
|
||||
<< json::close; // Close up the segment object
|
||||
}
|
||||
@ -239,7 +238,7 @@ int32 Face::getGlyphMetric(uint16 gid, uint8 metric) const
|
||||
{
|
||||
case kgmetAscent : return m_ascent;
|
||||
case kgmetDescent : return m_descent;
|
||||
default:
|
||||
default:
|
||||
if (gid >= glyphs().numGlyphs()) return 0;
|
||||
return glyphs().glyph(gid)->getMetric(metric);
|
||||
}
|
||||
@ -250,7 +249,7 @@ void Face::takeFileFace(FileFace* pFileFace GR_MAYBE_UNUSED/*takes ownership*/)
|
||||
#ifndef GRAPHITE2_NFILEFACE
|
||||
if (m_pFileFace==pFileFace)
|
||||
return;
|
||||
|
||||
|
||||
delete m_pFileFace;
|
||||
m_pFileFace = pFileFace;
|
||||
#endif
|
||||
@ -276,15 +275,13 @@ uint16 Face::languageForLocale(const char * locale) const
|
||||
|
||||
|
||||
Face::Table::Table(const Face & face, const Tag n, uint32 version) throw()
|
||||
: _f(&face), _compressed(false)
|
||||
: _f(&face), _sz(0), _compressed(false)
|
||||
{
|
||||
size_t sz = 0;
|
||||
_p = static_cast<const byte *>((*_f->m_ops.get_table)(_f->m_appFaceHandle, n, &sz));
|
||||
_sz = uint32(sz);
|
||||
_p = static_cast<const byte *>((*_f->m_ops.get_table)(_f->m_appFaceHandle, n, &_sz));
|
||||
|
||||
if (!TtfUtil::CheckTable(n, _p, _sz))
|
||||
{
|
||||
releaseBuffers(); // Make sure we release the table buffer even if the table failed it's checks
|
||||
release(); // Make sure we release the table buffer even if the table failed its checks
|
||||
return;
|
||||
}
|
||||
|
||||
@ -292,7 +289,7 @@ Face::Table::Table(const Face & face, const Tag n, uint32 version) throw()
|
||||
decompress();
|
||||
}
|
||||
|
||||
void Face::Table::releaseBuffers()
|
||||
void Face::Table::release()
|
||||
{
|
||||
if (_compressed)
|
||||
free(const_cast<byte *>(_p));
|
||||
@ -301,12 +298,11 @@ void Face::Table::releaseBuffers()
|
||||
_p = 0; _sz = 0;
|
||||
}
|
||||
|
||||
Face::Table & Face::Table::operator = (const Table & rhs) throw()
|
||||
Face::Table & Face::Table::operator = (const Table && rhs) throw()
|
||||
{
|
||||
if (_p == rhs._p) return *this;
|
||||
|
||||
this->~Table();
|
||||
new (this) Table(rhs);
|
||||
if (this == &rhs) return *this;
|
||||
release();
|
||||
new (this) Table(std::move(rhs));
|
||||
return *this;
|
||||
}
|
||||
|
||||
@ -353,7 +349,7 @@ Error Face::Table::decompress()
|
||||
|
||||
// Tell the provider to release the compressed form since were replacing
|
||||
// it anyway.
|
||||
releaseBuffers();
|
||||
release();
|
||||
|
||||
if (e)
|
||||
{
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -48,7 +48,7 @@ FileFace::FileFace(const char *filename)
|
||||
|
||||
// Get the header.
|
||||
if (!TtfUtil::GetHeaderInfo(tbl_offset, tbl_len)) return;
|
||||
if (fseek(_file, tbl_offset, SEEK_SET)) return;
|
||||
if (fseek(_file, long(tbl_offset), SEEK_SET)) return;
|
||||
_header_tbl = (TtfUtil::Sfnt::OffsetSubTable*)gralloc<char>(tbl_len);
|
||||
if (_header_tbl)
|
||||
{
|
||||
@ -59,7 +59,7 @@ FileFace::FileFace(const char *filename)
|
||||
// Get the table directory
|
||||
if (!TtfUtil::GetTableDirInfo(_header_tbl, tbl_offset, tbl_len)) return;
|
||||
_table_dir = (TtfUtil::Sfnt::OffsetSubTable::Entry*)gralloc<char>(tbl_len);
|
||||
if (fseek(_file, tbl_offset, SEEK_SET)) return;
|
||||
if (fseek(_file, long(tbl_offset), SEEK_SET)) return;
|
||||
if (_table_dir && fread(_table_dir, 1, tbl_len, _file) != tbl_len)
|
||||
{
|
||||
free(_table_dir);
|
||||
@ -88,7 +88,7 @@ const void *FileFace::get_table_fn(const void* appFaceHandle, unsigned int name,
|
||||
return 0;
|
||||
|
||||
if (tbl_offset > file_face._file_len || tbl_len > file_face._file_len - tbl_offset
|
||||
|| fseek(file_face._file, tbl_offset, SEEK_SET) != 0)
|
||||
|| fseek(file_face._file, long(tbl_offset), SEEK_SET) != 0)
|
||||
return 0;
|
||||
|
||||
tbl = malloc(tbl_len);
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -56,6 +56,3 @@ Font::Font(float ppm, const Face & f, const void * appFontHandle, const gr_font_
|
||||
{
|
||||
free(m_advances);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -46,7 +46,7 @@ namespace
|
||||
template<typename W>
|
||||
class _glat_iterator : public std::iterator<std::input_iterator_tag, std::pair<sparse::key_type, sparse::mapped_type> >
|
||||
{
|
||||
unsigned short key() const { return be::peek<W>(_e) + _n; }
|
||||
unsigned short key() const { return uint16(be::peek<W>(_e) + _n); }
|
||||
unsigned int run() const { return be::peek<W>(_e+sizeof(W)); }
|
||||
void advance_entry() { _n = 0; _e = _v; be::skip<W>(_v,2); }
|
||||
public:
|
||||
@ -84,7 +84,7 @@ const SlantBox SlantBox::empty = {0,0,0,0};
|
||||
class GlyphCache::Loader
|
||||
{
|
||||
public:
|
||||
Loader(const Face & face, const bool dumb_font); //return result indicates success. Do not use if failed.
|
||||
Loader(const Face & face); //return result indicates success. Do not use if failed.
|
||||
|
||||
operator bool () const throw();
|
||||
unsigned short int units_per_em() const throw();
|
||||
@ -115,7 +115,7 @@ private:
|
||||
|
||||
|
||||
GlyphCache::GlyphCache(const Face & face, const uint32 face_options)
|
||||
: _glyph_loader(new Loader(face, bool(face_options & gr_face_dumbRendering))),
|
||||
: _glyph_loader(new Loader(face)),
|
||||
_glyphs(_glyph_loader && *_glyph_loader && _glyph_loader->num_glyphs()
|
||||
? grzeroalloc<const GlyphFace *>(_glyph_loader->num_glyphs()) : 0),
|
||||
_boxes(_glyph_loader && _glyph_loader->has_boxes() && _glyph_loader->num_glyphs()
|
||||
@ -210,7 +210,7 @@ GlyphCache::~GlyphCache()
|
||||
}
|
||||
|
||||
const GlyphFace *GlyphCache::glyph(unsigned short glyphid) const //result may be changed by subsequent call with a different glyphid
|
||||
{
|
||||
{
|
||||
if (glyphid >= numGlyphs())
|
||||
return _glyphs[0];
|
||||
const GlyphFace * & p = _glyphs[glyphid];
|
||||
@ -239,7 +239,7 @@ const GlyphFace *GlyphCache::glyph(unsigned short glyphid) const //result m
|
||||
|
||||
|
||||
|
||||
GlyphCache::Loader::Loader(const Face & face, const bool dumb_font)
|
||||
GlyphCache::Loader::Loader(const Face & face)
|
||||
: _head(face, Tag::head),
|
||||
_hhea(face, Tag::hhea),
|
||||
_hmtx(face, Tag::hmtx),
|
||||
@ -257,7 +257,7 @@ GlyphCache::Loader::Loader(const Face & face, const bool dumb_font)
|
||||
const Face::Table maxp = Face::Table(face, Tag::maxp);
|
||||
if (!maxp) { _head = Face::Table(); return; }
|
||||
|
||||
_num_glyphs_graphics = TtfUtil::GlyphCount(maxp);
|
||||
_num_glyphs_graphics = static_cast<unsigned short>(TtfUtil::GlyphCount(maxp));
|
||||
// This will fail if the number of glyphs is wildly out of range.
|
||||
if (_glyf && TtfUtil::LocaLookup(_num_glyphs_graphics-1, _loca, _loca.size(), _head) == size_t(-2))
|
||||
{
|
||||
@ -265,52 +265,49 @@ GlyphCache::Loader::Loader(const Face & face, const bool dumb_font)
|
||||
return;
|
||||
}
|
||||
|
||||
if (!dumb_font)
|
||||
if ((m_pGlat = Face::Table(face, Tag::Glat, 0x00030000)) == NULL
|
||||
|| (m_pGloc = Face::Table(face, Tag::Gloc)) == NULL
|
||||
|| m_pGloc.size() < 8)
|
||||
{
|
||||
if ((m_pGlat = Face::Table(face, Tag::Glat, 0x00030000)) == NULL
|
||||
|| (m_pGloc = Face::Table(face, Tag::Gloc)) == NULL
|
||||
|| m_pGloc.size() < 8)
|
||||
{
|
||||
_head = Face::Table();
|
||||
return;
|
||||
}
|
||||
const byte * p = m_pGloc;
|
||||
int version = be::read<uint32>(p);
|
||||
const uint16 flags = be::read<uint16>(p);
|
||||
_num_attrs = be::read<uint16>(p);
|
||||
// We can accurately calculate the number of attributed glyphs by
|
||||
// subtracting the length of the attribids array (numAttribs long if present)
|
||||
// and dividing by either 2 or 4 depending on shor or lonf format
|
||||
_long_fmt = flags & 1;
|
||||
int tmpnumgattrs = (m_pGloc.size()
|
||||
- (p - m_pGloc)
|
||||
- sizeof(uint16)*(flags & 0x2 ? _num_attrs : 0))
|
||||
/ (_long_fmt ? sizeof(uint32) : sizeof(uint16)) - 1;
|
||||
_head = Face::Table();
|
||||
return;
|
||||
}
|
||||
const byte * p = m_pGloc;
|
||||
int version = be::read<uint32>(p);
|
||||
const uint16 flags = be::read<uint16>(p);
|
||||
_num_attrs = be::read<uint16>(p);
|
||||
// We can accurately calculate the number of attributed glyphs by
|
||||
// subtracting the length of the attribids array (numAttribs long if present)
|
||||
// and dividing by either 2 or 4 depending on shor or lonf format
|
||||
_long_fmt = flags & 1;
|
||||
ptrdiff_t tmpnumgattrs = (m_pGloc.size()
|
||||
- (p - m_pGloc)
|
||||
- sizeof(uint16)*(flags & 0x2 ? _num_attrs : 0))
|
||||
/ (_long_fmt ? sizeof(uint32) : sizeof(uint16)) - 1;
|
||||
|
||||
if (version >= 0x00020000 || tmpnumgattrs < 0 || tmpnumgattrs > 65535
|
||||
|| _num_attrs == 0 || _num_attrs > 0x3000 // is this hard limit appropriate?
|
||||
|| _num_glyphs_graphics > tmpnumgattrs
|
||||
|| m_pGlat.size() < 4)
|
||||
{
|
||||
_head = Face::Table();
|
||||
return;
|
||||
}
|
||||
if (version >= 0x00020000 || tmpnumgattrs < 0 || tmpnumgattrs > 65535
|
||||
|| _num_attrs == 0 || _num_attrs > 0x3000 // is this hard limit appropriate?
|
||||
|| _num_glyphs_graphics > tmpnumgattrs
|
||||
|| m_pGlat.size() < 4)
|
||||
{
|
||||
_head = Face::Table();
|
||||
return;
|
||||
}
|
||||
|
||||
_num_glyphs_attributes = static_cast<unsigned short>(tmpnumgattrs);
|
||||
p = m_pGlat;
|
||||
version = be::read<uint32>(p);
|
||||
if (version >= 0x00040000 || (version >= 0x00030000 && m_pGlat.size() < 8)) // reject Glat tables that are too new
|
||||
{
|
||||
_head = Face::Table();
|
||||
return;
|
||||
}
|
||||
else if (version >= 0x00030000)
|
||||
{
|
||||
unsigned int glatflags = be::read<uint32>(p);
|
||||
_has_boxes = glatflags & 1;
|
||||
// delete this once the compiler is fixed
|
||||
_has_boxes = true;
|
||||
}
|
||||
_num_glyphs_attributes = static_cast<unsigned short>(tmpnumgattrs);
|
||||
p = m_pGlat;
|
||||
version = be::read<uint32>(p);
|
||||
if (version >= 0x00040000 || (version >= 0x00030000 && m_pGlat.size() < 8)) // reject Glat tables that are too new
|
||||
{
|
||||
_head = Face::Table();
|
||||
return;
|
||||
}
|
||||
else if (version >= 0x00030000)
|
||||
{
|
||||
unsigned int glatflags = be::read<uint32>(p);
|
||||
_has_boxes = glatflags & 1;
|
||||
// delete this once the compiler is fixed
|
||||
_has_boxes = true;
|
||||
}
|
||||
}
|
||||
|
||||
@ -486,7 +483,6 @@ GlyphBox * GlyphCache::Loader::read_box(uint16 gid, GlyphBox *curr, const GlyphF
|
||||
Rect box = readbox((i & 1) ? diamax : bbox, p[0], p[2], p[1], p[3]);
|
||||
curr->addSubBox(i >> 1, i & 1, &box);
|
||||
be::skip<uint8>(p, 4);
|
||||
}
|
||||
}
|
||||
return (GlyphBox *)((char *)(curr) + sizeof(GlyphBox) + 2 * num * sizeof(Rect));
|
||||
}
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -33,16 +33,16 @@ int32 GlyphFace::getMetric(uint8 metric) const
|
||||
{
|
||||
switch (metrics(metric))
|
||||
{
|
||||
case kgmetLsb : return m_bbox.bl.x;
|
||||
case kgmetRsb : return m_advance.x - m_bbox.tr.x;
|
||||
case kgmetBbTop : return m_bbox.tr.y;
|
||||
case kgmetBbBottom : return m_bbox.bl.y;
|
||||
case kgmetBbLeft : return m_bbox.bl.x;
|
||||
case kgmetBbRight : return m_bbox.tr.x;
|
||||
case kgmetBbHeight : return m_bbox.tr.y - m_bbox.bl.y;
|
||||
case kgmetBbWidth : return m_bbox.tr.x - m_bbox.bl.x;
|
||||
case kgmetAdvWidth : return m_advance.x;
|
||||
case kgmetAdvHeight : return m_advance.y;
|
||||
case kgmetLsb : return int32(m_bbox.bl.x);
|
||||
case kgmetRsb : return int32(m_advance.x - m_bbox.tr.x);
|
||||
case kgmetBbTop : return int32(m_bbox.tr.y);
|
||||
case kgmetBbBottom : return int32(m_bbox.bl.y);
|
||||
case kgmetBbLeft : return int32(m_bbox.bl.x);
|
||||
case kgmetBbRight : return int32(m_bbox.tr.x);
|
||||
case kgmetBbHeight : return int32(m_bbox.tr.y - m_bbox.bl.y);
|
||||
case kgmetBbWidth : return int32(m_bbox.tr.x - m_bbox.bl.x);
|
||||
case kgmetAdvWidth : return int32(m_advance.x);
|
||||
case kgmetAdvHeight : return int32(m_advance.y);
|
||||
default : return 0;
|
||||
}
|
||||
}
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -183,16 +183,16 @@ void Zones::remove(float x, float xm)
|
||||
|
||||
Zones::const_iterator Zones::find_exclusion_under(float x) const
|
||||
{
|
||||
int l = 0, h = _exclusions.size();
|
||||
size_t l = 0, h = _exclusions.size();
|
||||
|
||||
while (l < h)
|
||||
{
|
||||
int const p = (l+h) >> 1;
|
||||
size_t const p = (l+h) >> 1;
|
||||
switch (_exclusions[p].outcode(x))
|
||||
{
|
||||
case 0 : return _exclusions.begin()+p;
|
||||
case 1 : h = p; break;
|
||||
case 2 :
|
||||
case 2 :
|
||||
case 3 : l = p+1; break;
|
||||
}
|
||||
}
|
||||
@ -287,7 +287,7 @@ void Zones::jsonDbgOut(Segment *seg) const {
|
||||
*_dbg << "remove" << Position(s->_excl.x, s->_excl.xm);
|
||||
else
|
||||
*_dbg << "exclude" << json::flat << json::array
|
||||
<< s->_excl.x << s->_excl.xm
|
||||
<< s->_excl.x << s->_excl.xm
|
||||
<< s->_excl.sm << s->_excl.smx << s->_excl.c
|
||||
<< json::close;
|
||||
*_dbg << json::close;
|
||||
@ -296,4 +296,3 @@ void Zones::jsonDbgOut(Segment *seg) const {
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -62,7 +62,7 @@ void JustifyTotal::accumulate(Slot *s, Segment *seg, int level)
|
||||
|
||||
float Segment::justify(Slot *pSlot, const Font *font, float width, GR_MAYBE_UNUSED justFlags jflags, Slot *pFirst, Slot *pLast)
|
||||
{
|
||||
Slot *s, *end;
|
||||
Slot *end = last();
|
||||
float currWidth = 0.0;
|
||||
const float scale = font ? font->scale() : 1.0f;
|
||||
Position res;
|
||||
@ -73,9 +73,7 @@ float Segment::justify(Slot *pSlot, const Font *font, float width, GR_MAYBE_UNUS
|
||||
if ((m_dir & 1) != m_silf->dir() && m_silf->bidiPass() != m_silf->numPasses())
|
||||
{
|
||||
reverseSlots();
|
||||
s = pFirst;
|
||||
pFirst = pLast;
|
||||
pLast = s;
|
||||
std::swap(pFirst, pLast);
|
||||
}
|
||||
if (!pFirst) pFirst = pSlot;
|
||||
while (!pFirst->isBase()) pFirst = pFirst->attachedTo();
|
||||
@ -85,22 +83,25 @@ float Segment::justify(Slot *pSlot, const Font *font, float width, GR_MAYBE_UNUS
|
||||
width = width / scale;
|
||||
if ((jflags & gr_justEndInline) == 0)
|
||||
{
|
||||
do {
|
||||
while (pLast != pFirst && pLast)
|
||||
{
|
||||
Rect bbox = theGlyphBBoxTemporary(pLast->glyph());
|
||||
if (bbox.bl.x != 0.f || bbox.bl.y != 0.f || bbox.tr.x != 0.f || bbox.tr.y == 0.f)
|
||||
break;
|
||||
pLast = pLast->prev();
|
||||
} while (pLast != pFirst);
|
||||
}
|
||||
}
|
||||
|
||||
end = pLast->nextSibling();
|
||||
pFirst = pFirst->nextSibling();
|
||||
if (pLast)
|
||||
end = pLast->nextSibling();
|
||||
if (pFirst)
|
||||
pFirst = pFirst->nextSibling();
|
||||
|
||||
int icount = 0;
|
||||
int numLevels = silf()->numJustLevels();
|
||||
if (!numLevels)
|
||||
{
|
||||
for (s = pSlot; s && s != end; s = s->nextSibling())
|
||||
for (Slot *s = pSlot; s && s != end; s = s->nextSibling())
|
||||
{
|
||||
CharInfo *c = charinfo(s->before());
|
||||
if (isWhitespace(c->unicodeChar()))
|
||||
@ -113,7 +114,7 @@ float Segment::justify(Slot *pSlot, const Font *font, float width, GR_MAYBE_UNUS
|
||||
}
|
||||
if (!icount)
|
||||
{
|
||||
for (s = pSlot; s && s != end; s = s->nextSibling())
|
||||
for (Slot *s = pSlot; s && s != end; s = s->nextSibling())
|
||||
{
|
||||
s->setJustify(this, 0, 3, 1);
|
||||
s->setJustify(this, 0, 2, 1);
|
||||
@ -124,7 +125,7 @@ float Segment::justify(Slot *pSlot, const Font *font, float width, GR_MAYBE_UNUS
|
||||
}
|
||||
|
||||
Vector<JustifyTotal> stats(numLevels);
|
||||
for (s = pFirst; s && s != end; s = s->nextSibling())
|
||||
for (Slot *s = pFirst; s && s != end; s = s->nextSibling())
|
||||
{
|
||||
float w = s->origin().x / scale + s->advance() - base;
|
||||
if (w > currWidth) currWidth = w;
|
||||
@ -146,7 +147,7 @@ float Segment::justify(Slot *pSlot, const Font *font, float width, GR_MAYBE_UNUS
|
||||
diff = width - currWidth;
|
||||
diffpw = diff / tWeight;
|
||||
tWeight = 0;
|
||||
for (s = pFirst; s && s != end; s = s->nextSibling()) // don't include final glyph
|
||||
for (Slot *s = pFirst; s && s != end; s = s->nextSibling()) // don't include final glyph
|
||||
{
|
||||
int w = s->getJustify(this, i, 3);
|
||||
float pref = diffpw * w + error;
|
||||
@ -224,8 +225,10 @@ float Segment::justify(Slot *pSlot, const Font *font, float width, GR_MAYBE_UNUS
|
||||
|
||||
if (silf()->flags() & 1)
|
||||
{
|
||||
delLineEnd(m_first);
|
||||
delLineEnd(m_last);
|
||||
if (m_first)
|
||||
delLineEnd(m_first);
|
||||
if (m_last)
|
||||
delLineEnd(m_last);
|
||||
}
|
||||
m_first = oldFirst;
|
||||
m_last = oldLast;
|
||||
@ -277,4 +280,3 @@ void Segment::delLineEnd(Slot *s)
|
||||
s->prev()->next(NULL);
|
||||
freeSlot(s);
|
||||
}
|
||||
|
||||
|
@ -51,7 +51,7 @@ NameTable::NameTable(const void* data, size_t length, uint16 platformId, uint16
|
||||
{
|
||||
m_nameData = reinterpret_cast<const uint8*>(pdata) + offset;
|
||||
setPlatformEncoding(platformId, encodingID);
|
||||
m_nameDataLength = length - offset;
|
||||
m_nameDataLength = uint16(length - offset);
|
||||
return;
|
||||
}
|
||||
}
|
||||
@ -180,7 +180,7 @@ void* NameTable::getName(uint16& languageId, uint16 nameId, gr_encform enc, uint
|
||||
utf8::iterator d = uniBuffer;
|
||||
for (utf16::const_iterator s = utf16Name, e = utf16Name + utf16Length; s != e; ++s, ++d)
|
||||
*d = *s;
|
||||
length = d - uniBuffer;
|
||||
length = uint32(d - uniBuffer);
|
||||
uniBuffer[length] = 0;
|
||||
free(utf16Name);
|
||||
return uniBuffer;
|
||||
@ -201,7 +201,7 @@ void* NameTable::getName(uint16& languageId, uint16 nameId, gr_encform enc, uint
|
||||
utf32::iterator d = uniBuffer;
|
||||
for (utf16::const_iterator s = utf16Name, e = utf16Name + utf16Length; s != e; ++s, ++d)
|
||||
*d = *s;
|
||||
length = d - uniBuffer;
|
||||
length = uint32(d - uniBuffer);
|
||||
uniBuffer[length] = 0;
|
||||
free(utf16Name);
|
||||
return uniBuffer;
|
||||
@ -252,4 +252,3 @@ uint16 NameTable::getLanguageId(const char * bcp47Locale)
|
||||
}
|
||||
return localeId;
|
||||
}
|
||||
|
||||
|
@ -97,10 +97,10 @@ bool Pass::readPass(const byte * const pass_start, size_t pass_length, size_t su
|
||||
* const pass_end = p + pass_length;
|
||||
size_t numRanges;
|
||||
|
||||
if (e.test(pass_length < 40, E_BADPASSLENGTH)) return face.error(e);
|
||||
if (e.test(pass_length < 40, E_BADPASSLENGTH)) return face.error(e);
|
||||
// Read in basic values
|
||||
const byte flags = be::read<byte>(p);
|
||||
if (e.test((flags & 0x1f) &&
|
||||
if (e.test((flags & 0x1f) &&
|
||||
(pt < PASS_TYPE_POSITIONING || !m_silf->aCollision() || !face.glyphs().hasBoxes() || !(m_silf->flags() & 0x20)),
|
||||
E_BADCOLLISIONPASS))
|
||||
return face.error(e);
|
||||
@ -191,7 +191,7 @@ bool Pass::readPass(const byte * const pass_start, size_t pass_length, size_t su
|
||||
if (pass_constraint_len)
|
||||
{
|
||||
face.error_context(face.error_context() + 1);
|
||||
m_cPConstraint = vm::Machine::Code(true, pcCode, pcCode + pass_constraint_len,
|
||||
m_cPConstraint = vm::Machine::Code(true, pcCode, pcCode + pass_constraint_len,
|
||||
precontext[0], be::peek<uint16>(sort_keys), *m_silf, face, PASS_TYPE_UNKNOWN);
|
||||
if (e.test(!m_cPConstraint, E_OUTOFMEM)
|
||||
|| e.test(m_cPConstraint.status() != Code::loaded, m_cPConstraint.status() + E_CODEFAILURE))
|
||||
@ -246,11 +246,11 @@ bool Pass::readRules(const byte * rule_map, const size_t num_entries,
|
||||
Rule * r = m_rules + m_numRules - 1;
|
||||
for (size_t n = m_numRules; r >= m_rules; --n, --r, ac_end = ac_begin, rc_end = rc_begin)
|
||||
{
|
||||
face.error_context((face.error_context() & 0xFFFF00) + EC_ARULE + ((n - 1) << 24));
|
||||
face.error_context((face.error_context() & 0xFFFF00) + EC_ARULE + int((n - 1) << 24));
|
||||
r->preContext = *--precontext;
|
||||
r->sort = be::peek<uint16>(--sort_key);
|
||||
#ifndef NDEBUG
|
||||
r->rule_idx = n - 1;
|
||||
r->rule_idx = uint16(n - 1);
|
||||
#endif
|
||||
if (r->sort > 63 || r->preContext >= r->sort || r->preContext > m_maxPreCtxt || r->preContext < m_minPreCtxt)
|
||||
return false;
|
||||
@ -291,7 +291,7 @@ bool Pass::readRules(const byte * rule_map, const size_t num_entries,
|
||||
|
||||
// Load the rule entries map
|
||||
face.error_context((face.error_context() & 0xFFFF00) + EC_APASS);
|
||||
//TODO: Coverty: 1315804: FORWARD_NULL
|
||||
//TODO: Coverity: 1315804: FORWARD_NULL
|
||||
RuleEntry * re = m_ruleMap = gralloc<RuleEntry>(num_entries);
|
||||
if (e.test(!re, E_OUTOFMEM)) return face.error(e);
|
||||
for (size_t n = num_entries; n; --n, ++re)
|
||||
@ -330,7 +330,7 @@ bool Pass::readStates(const byte * starts, const byte *states, const byte * o_ru
|
||||
*s = be::read<uint16>(starts);
|
||||
if (e.test(*s >= m_numStates, E_BADSTATE))
|
||||
{
|
||||
face.error_context((face.error_context() & 0xFFFF00) + EC_ASTARTS + ((s - m_startStates) << 24));
|
||||
face.error_context((face.error_context() & 0xFFFF00) + EC_ASTARTS + int((s - m_startStates) << 24));
|
||||
return face.error(e); // true;
|
||||
}
|
||||
}
|
||||
@ -342,7 +342,7 @@ bool Pass::readStates(const byte * starts, const byte *states, const byte * o_ru
|
||||
*t = be::read<uint16>(states);
|
||||
if (e.test(*t >= m_numStates, E_BADSTATE))
|
||||
{
|
||||
face.error_context((face.error_context() & 0xFFFF00) + EC_ATRANS + (((t - m_transitions) / m_numColumns) << 8));
|
||||
face.error_context((face.error_context() & 0xFFFF00) + EC_ATRANS + int(((t - m_transitions) / m_numColumns) << 8));
|
||||
return face.error(e);
|
||||
}
|
||||
}
|
||||
@ -357,7 +357,7 @@ bool Pass::readStates(const byte * starts, const byte *states, const byte * o_ru
|
||||
|
||||
if (e.test(begin >= rule_map_end || end > rule_map_end || begin > end, E_BADRULEMAPPING))
|
||||
{
|
||||
face.error_context((face.error_context() & 0xFFFF00) + EC_ARULEMAP + (n << 24));
|
||||
face.error_context((face.error_context() & 0xFFFF00) + EC_ARULEMAP + int(n << 24));
|
||||
return face.error(e);
|
||||
}
|
||||
s->rules = begin;
|
||||
@ -774,7 +774,7 @@ bool Pass::collisionShift(Segment *seg, int dir, json * const dbgout) const
|
||||
*dbgout << json::close << json::close; // phase-1
|
||||
#endif
|
||||
|
||||
// phase 2 : loop until happy.
|
||||
// phase 2 : loop until happy.
|
||||
for (int i = 0; i < m_numCollRuns - 1; ++i)
|
||||
{
|
||||
if (hasCollisions || moved)
|
||||
@ -820,10 +820,10 @@ bool Pass::collisionShift(Segment *seg, int dir, json * const dbgout) const
|
||||
<< json::object << "phase" << "2b" << "loop" << i << "moves" << json::array;
|
||||
#endif
|
||||
|
||||
// phase 2b : redo basic diacritic positioning pass for ALL glyphs. Each successive loop adjusts
|
||||
// glyphs from their current adjusted position, which has the effect of gradually minimizing the
|
||||
// resulting adjustment; ie, the final result will be gradually closer to the original location.
|
||||
// Also it allows more flexibility in the final adjustment, since it is moving along the
|
||||
// phase 2b : redo basic diacritic positioning pass for ALL glyphs. Each successive loop adjusts
|
||||
// glyphs from their current adjusted position, which has the effect of gradually minimizing the
|
||||
// resulting adjustment; ie, the final result will be gradually closer to the original location.
|
||||
// Also it allows more flexibility in the final adjustment, since it is moving along the
|
||||
// possible 8 vectors from successively different starting locations.
|
||||
if (moved)
|
||||
{
|
||||
@ -962,7 +962,7 @@ bool Pass::resolveCollisions(Segment *seg, Slot *slotFix, Slot *start,
|
||||
while (base->attachedTo())
|
||||
base = base->attachedTo();
|
||||
Position zero(0., 0.);
|
||||
|
||||
|
||||
// Look for collisions with the neighboring glyphs.
|
||||
for (nbor = start; nbor; nbor = isRev ? nbor->prev() : nbor->next())
|
||||
{
|
||||
@ -982,7 +982,7 @@ bool Pass::resolveCollisions(Segment *seg, Slot *slotFix, Slot *start,
|
||||
else if (nbor == slotFix)
|
||||
// Switching sides of this glyph - if we were ignoring kernable stuff before, don't anymore.
|
||||
ignoreForKern = !ignoreForKern;
|
||||
|
||||
|
||||
if (nbor != start && (cNbor->flags() & (isRev ? SlotCollision::COLL_START : SlotCollision::COLL_END)))
|
||||
break;
|
||||
}
|
||||
@ -1011,7 +1011,7 @@ bool Pass::resolveCollisions(Segment *seg, Slot *slotFix, Slot *start,
|
||||
#if !defined GRAPHITE2_NTRACING
|
||||
if (dbgout)
|
||||
{
|
||||
*dbgout << json::object
|
||||
*dbgout << json::object
|
||||
<< "missed" << objectid(dslot(seg, slotFix));
|
||||
coll.outputJsonDbg(dbgout, seg, -1);
|
||||
*dbgout << json::close;
|
||||
@ -1072,7 +1072,7 @@ float Pass::resolveKern(Segment *seg, Slot *slotFix, GR_MAYBE_UNUSED Slot *start
|
||||
}
|
||||
else
|
||||
{
|
||||
space_count = 0;
|
||||
space_count = 0;
|
||||
if (nbor != slotFix && !cNbor->ignore())
|
||||
{
|
||||
seenEnd = true;
|
||||
@ -1105,4 +1105,3 @@ float Pass::resolveKern(Segment *seg, Slot *slotFix, GR_MAYBE_UNUSED Slot *start
|
||||
}
|
||||
return 0.;
|
||||
}
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -95,4 +95,3 @@ Position Rect::constrainedAvoid(Position &offset, Rect &box, Rect &sdbox, Positi
|
||||
return res;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
@ -1,224 +0,0 @@
|
||||
/* GRAPHITE2 LICENSING
|
||||
|
||||
Copyright 2010, SIL International
|
||||
All rights reserved.
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published
|
||||
by the Free Software Foundation; either version 2.1 of License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
Lesser General Public License for more details.
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
Mozilla Public License (http://mozilla.org/MPL) or the GNU General Public
|
||||
License, as published by the Free Software Foundation, either version 2
|
||||
of the License or (at your option) any later version.
|
||||
*/
|
||||
|
||||
#include "inc/Main.h"
|
||||
#include "inc/TtfTypes.h"
|
||||
#include "inc/TtfUtil.h"
|
||||
#include "inc/SegCache.h"
|
||||
#include "inc/SegCacheEntry.h"
|
||||
#include "inc/SegCacheStore.h"
|
||||
#include "inc/CmapCache.h"
|
||||
|
||||
|
||||
using namespace graphite2;
|
||||
|
||||
#ifndef GRAPHITE2_NSEGCACHE
|
||||
|
||||
SegCache::SegCache(const SegCacheStore * store, const Features & feats)
|
||||
: m_prefixLength(ePrefixLength),
|
||||
// m_maxCachedSegLength(eMaxSpliceSize),
|
||||
m_segmentCount(0),
|
||||
m_features(feats),
|
||||
m_totalAccessCount(0l), m_totalMisses(0l),
|
||||
m_purgeFactor(1.0f / (ePurgeFactor * store->maxSegmentCount()))
|
||||
{
|
||||
m_prefixes.raw = grzeroalloc<void*>(store->maxCmapGid() + 2);
|
||||
m_prefixes.range[SEG_CACHE_MIN_INDEX] = SEG_CACHE_UNSET_INDEX;
|
||||
m_prefixes.range[SEG_CACHE_MAX_INDEX] = SEG_CACHE_UNSET_INDEX;
|
||||
}
|
||||
|
||||
void SegCache::freeLevel(SegCacheStore * store, SegCachePrefixArray prefixes, size_t level)
|
||||
{
|
||||
for (size_t i = 0; i < store->maxCmapGid(); i++)
|
||||
{
|
||||
if (prefixes.array[i].raw)
|
||||
{
|
||||
if (level + 1 < ePrefixLength)
|
||||
freeLevel(store, prefixes.array[i], level + 1);
|
||||
else
|
||||
{
|
||||
SegCachePrefixEntry * prefixEntry = prefixes.prefixEntries[i];
|
||||
delete prefixEntry;
|
||||
}
|
||||
}
|
||||
}
|
||||
free(prefixes.raw);
|
||||
}
|
||||
|
||||
void SegCache::clear(SegCacheStore * store)
|
||||
{
|
||||
freeLevel(store, m_prefixes, 0);
|
||||
m_prefixes.raw = NULL;
|
||||
}
|
||||
|
||||
SegCache::~SegCache()
|
||||
{
|
||||
assert(m_prefixes.raw == NULL);
|
||||
}
|
||||
|
||||
SegCacheEntry* SegCache::cache(SegCacheStore * store, const uint16* cmapGlyphs, size_t length, Segment * seg, size_t charOffset)
|
||||
{
|
||||
uint16 pos = 0;
|
||||
if (!length) return NULL;
|
||||
// assert(length < m_maxCachedSegLength);
|
||||
SegCachePrefixArray pArray = m_prefixes;
|
||||
while (pos + 1 < m_prefixLength)
|
||||
{
|
||||
uint16 gid = (pos < length)? cmapGlyphs[pos] : 0;
|
||||
if (!pArray.array[gid].raw)
|
||||
{
|
||||
pArray.array[gid].raw = grzeroalloc<void*>(store->maxCmapGid() + 2);
|
||||
if (!pArray.array[gid].raw)
|
||||
return NULL; // malloc failed
|
||||
if (pArray.range[SEG_CACHE_MIN_INDEX] == SEG_CACHE_UNSET_INDEX)
|
||||
{
|
||||
pArray.range[SEG_CACHE_MIN_INDEX] = gid;
|
||||
pArray.range[SEG_CACHE_MAX_INDEX] = gid;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (gid < pArray.range[SEG_CACHE_MIN_INDEX])
|
||||
pArray.range[SEG_CACHE_MIN_INDEX] = gid;
|
||||
else if (gid > pArray.range[SEG_CACHE_MAX_INDEX])
|
||||
pArray.range[SEG_CACHE_MAX_INDEX] = gid;
|
||||
}
|
||||
}
|
||||
pArray = pArray.array[gid];
|
||||
++pos;
|
||||
}
|
||||
uint16 gid = (pos < length)? cmapGlyphs[pos] : 0;
|
||||
SegCachePrefixEntry * prefixEntry = pArray.prefixEntries[gid];
|
||||
if (!prefixEntry)
|
||||
{
|
||||
prefixEntry = new SegCachePrefixEntry();
|
||||
pArray.prefixEntries[gid] = prefixEntry;
|
||||
if (pArray.range[SEG_CACHE_MIN_INDEX] == SEG_CACHE_UNSET_INDEX)
|
||||
{
|
||||
pArray.range[SEG_CACHE_MIN_INDEX] = gid;
|
||||
pArray.range[SEG_CACHE_MAX_INDEX] = gid;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (gid < pArray.range[SEG_CACHE_MIN_INDEX])
|
||||
pArray.range[SEG_CACHE_MIN_INDEX] = gid;
|
||||
else if (gid > pArray.range[SEG_CACHE_MAX_INDEX])
|
||||
pArray.range[SEG_CACHE_MAX_INDEX] = gid;
|
||||
}
|
||||
}
|
||||
if (!prefixEntry) return NULL;
|
||||
// if the cache is full run a purge - this is slow, since it walks the tree
|
||||
if (m_segmentCount + 1 > store->maxSegmentCount())
|
||||
{
|
||||
purge(store);
|
||||
assert(m_segmentCount < store->maxSegmentCount());
|
||||
}
|
||||
SegCacheEntry * pEntry = prefixEntry->cache(cmapGlyphs, length, seg, charOffset, m_totalAccessCount);
|
||||
if (pEntry) ++m_segmentCount;
|
||||
return pEntry;
|
||||
}
|
||||
|
||||
void SegCache::purge(SegCacheStore * store)
|
||||
{
|
||||
unsigned long long minAccessCount = static_cast<unsigned long long>(m_totalAccessCount * m_purgeFactor + 1);
|
||||
if (minAccessCount < 2) minAccessCount = 2;
|
||||
unsigned long long oldAccessTime = m_totalAccessCount - store->maxSegmentCount() / eAgeFactor;
|
||||
purgeLevel(store, m_prefixes, 0, minAccessCount, oldAccessTime);
|
||||
}
|
||||
|
||||
void SegCache::purgeLevel(SegCacheStore * store, SegCachePrefixArray prefixes, size_t level,
|
||||
unsigned long long minAccessCount, unsigned long long oldAccessTime)
|
||||
{
|
||||
if (prefixes.range[SEG_CACHE_MIN_INDEX] == SEG_CACHE_UNSET_INDEX) return;
|
||||
size_t maxGlyphCached = prefixes.range[SEG_CACHE_MAX_INDEX];
|
||||
for (size_t i = prefixes.range[SEG_CACHE_MIN_INDEX]; i <= maxGlyphCached; i++)
|
||||
{
|
||||
if (prefixes.array[i].raw)
|
||||
{
|
||||
if (level + 1 < ePrefixLength)
|
||||
purgeLevel(store, prefixes.array[i], level + 1, minAccessCount, oldAccessTime);
|
||||
else
|
||||
{
|
||||
SegCachePrefixEntry * prefixEntry = prefixes.prefixEntries[i];
|
||||
m_segmentCount -= prefixEntry->purge(minAccessCount,
|
||||
oldAccessTime, m_totalAccessCount);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
uint32 SegCachePrefixEntry::purge(unsigned long long minAccessCount,
|
||||
unsigned long long oldAccessTime,
|
||||
unsigned long long currentTime)
|
||||
{
|
||||
// ignore the purge request if another has been done recently
|
||||
//if (m_lastPurge > oldAccessTime)
|
||||
// return 0;
|
||||
|
||||
uint32 totalPurged = 0;
|
||||
// real length is length + 1 in this loop
|
||||
for (uint16 length = 0; length < eMaxSpliceSize; length++)
|
||||
{
|
||||
if (m_entryCounts[length] == 0)
|
||||
continue;
|
||||
uint16 purgeCount = 0;
|
||||
uint16 newIndex = 0;
|
||||
for (uint16 j = 0; j < m_entryCounts[length]; j++)
|
||||
{
|
||||
SegCacheEntry & tempEntry = m_entries[length][j];
|
||||
// purge entries with a low access count which haven't been
|
||||
// accessed recently
|
||||
if (tempEntry.accessCount() <= minAccessCount &&
|
||||
tempEntry.lastAccess() <= oldAccessTime)
|
||||
{
|
||||
tempEntry.clear();
|
||||
++purgeCount;
|
||||
}
|
||||
else
|
||||
{
|
||||
memcpy(m_entries[length] + newIndex++, m_entries[length] + j, sizeof(SegCacheEntry));
|
||||
}
|
||||
}
|
||||
if (purgeCount == m_entryCounts[length])
|
||||
{
|
||||
assert(newIndex == 0);
|
||||
m_entryCounts[length] = 0;
|
||||
m_entryBSIndex[length] = 0;
|
||||
free(m_entries[length]);
|
||||
m_entries[length] = NULL;
|
||||
}
|
||||
else if (purgeCount > 0)
|
||||
{
|
||||
assert(m_entryCounts[length] == newIndex + purgeCount);
|
||||
m_entryCounts[length] = newIndex;
|
||||
}
|
||||
totalPurged += purgeCount;
|
||||
}
|
||||
m_lastPurge = currentTime;
|
||||
return totalPurged;
|
||||
}
|
||||
|
||||
#endif
|
@ -1,108 +0,0 @@
|
||||
/* GRAPHITE2 LICENSING
|
||||
|
||||
Copyright 2010, SIL International
|
||||
All rights reserved.
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published
|
||||
by the Free Software Foundation; either version 2.1 of License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
Lesser General Public License for more details.
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
Mozilla Public License (http://mozilla.org/MPL) or the GNU General Public
|
||||
License, as published by the Free Software Foundation, either version 2
|
||||
of the License or (at your option) any later version.
|
||||
*/
|
||||
|
||||
#ifndef GRAPHITE2_NSEGCACHE
|
||||
|
||||
#include "inc/Main.h"
|
||||
#include "inc/Slot.h"
|
||||
#include "inc/Segment.h"
|
||||
#include "inc/SegCache.h"
|
||||
#include "inc/SegCacheEntry.h"
|
||||
|
||||
|
||||
using namespace graphite2;
|
||||
|
||||
SegCacheEntry::SegCacheEntry(const uint16* cmapGlyphs, size_t length, Segment * seg, size_t charOffset, long long cacheTime)
|
||||
: m_glyphLength(0), m_unicode(gralloc<uint16>(length)), m_glyph(NULL),
|
||||
m_attr(NULL), m_justs(NULL),
|
||||
m_accessCount(0), m_lastAccess(cacheTime)
|
||||
{
|
||||
if (m_unicode)
|
||||
for (size_t i = 0; i < length; i++)
|
||||
m_unicode[i] = cmapGlyphs[i];
|
||||
|
||||
const size_t glyphCount = seg->slotCount(),
|
||||
sizeof_sjust = SlotJustify::size_of(seg->silf()->numJustLevels());
|
||||
if (!glyphCount) return;
|
||||
size_t num_justs = 0,
|
||||
justs_pos = 0;
|
||||
if (seg->hasJustification())
|
||||
{
|
||||
for (const Slot * s = seg->first(); s; s = s->next())
|
||||
{
|
||||
if (s->m_justs == 0) continue;
|
||||
++num_justs;
|
||||
}
|
||||
m_justs = gralloc<byte>(sizeof_sjust * num_justs);
|
||||
}
|
||||
const Slot * slot = seg->first();
|
||||
m_glyph = new Slot[glyphCount];
|
||||
m_attr = gralloc<int16>(glyphCount * seg->numAttrs());
|
||||
if (!m_glyph || (!m_attr && seg->numAttrs())) return;
|
||||
m_glyphLength = glyphCount;
|
||||
Slot * slotCopy = m_glyph;
|
||||
m_glyph->prev(NULL);
|
||||
|
||||
uint16 pos = 0;
|
||||
while (slot)
|
||||
{
|
||||
slotCopy->userAttrs(m_attr + pos * seg->numAttrs());
|
||||
slotCopy->m_justs = m_justs ? reinterpret_cast<SlotJustify *>(m_justs + justs_pos++ * sizeof_sjust) : 0;
|
||||
slotCopy->set(*slot, -static_cast<int32>(charOffset), seg->numAttrs(), seg->silf()->numJustLevels(), length);
|
||||
slotCopy->index(pos);
|
||||
if (slot->firstChild())
|
||||
slotCopy->m_child = m_glyph + slot->firstChild()->index();
|
||||
if (slot->attachedTo())
|
||||
slotCopy->attachTo(m_glyph + slot->attachedTo()->index());
|
||||
if (slot->nextSibling())
|
||||
slotCopy->m_sibling = m_glyph + slot->nextSibling()->index();
|
||||
slot = slot->next();
|
||||
++slotCopy;
|
||||
++pos;
|
||||
if (slot)
|
||||
{
|
||||
slotCopy->prev(slotCopy-1);
|
||||
(slotCopy-1)->next(slotCopy);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void SegCacheEntry::clear()
|
||||
{
|
||||
free(m_unicode);
|
||||
free(m_attr);
|
||||
free(m_justs);
|
||||
delete [] m_glyph;
|
||||
m_unicode = NULL;
|
||||
m_glyph = NULL;
|
||||
m_glyphLength = 0;
|
||||
m_attr = NULL;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -1,47 +0,0 @@
|
||||
/* GRAPHITE2 LICENSING
|
||||
|
||||
Copyright 2010, SIL International
|
||||
All rights reserved.
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published
|
||||
by the Free Software Foundation; either version 2.1 of License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
Lesser General Public License for more details.
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
Mozilla Public License (http://mozilla.org/MPL) or the GNU General Public
|
||||
License, as published by the Free Software Foundation, either version 2
|
||||
of the License or (at your option) any later version.
|
||||
*/
|
||||
|
||||
#ifndef GRAPHITE2_NSEGCACHE
|
||||
|
||||
#include "inc/SegCacheStore.h"
|
||||
#include "inc/Face.h"
|
||||
|
||||
|
||||
using namespace graphite2;
|
||||
|
||||
SegCacheStore::SegCacheStore(const Face & face, unsigned int numSilf, size_t maxSegments)
|
||||
: m_caches(new SilfSegCache[numSilf]),
|
||||
m_numSilf(numSilf),
|
||||
m_maxSegments(maxSegments),
|
||||
m_maxCmapGid(face.glyphs().numGlyphs()),
|
||||
m_spaceGid(face.cmap()[0x20]),
|
||||
m_zwspGid(face.cmap()[0x200B])
|
||||
{
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -42,7 +42,7 @@ of the License or (at your option) any later version.
|
||||
|
||||
using namespace graphite2;
|
||||
|
||||
Segment::Segment(unsigned int numchars, const Face* face, uint32 script, int textDir)
|
||||
Segment::Segment(size_t numchars, const Face* face, uint32 script, int textDir)
|
||||
: m_freeSlots(NULL),
|
||||
m_freeJustifies(NULL),
|
||||
m_charinfo(new CharInfo[numchars]),
|
||||
@ -54,14 +54,12 @@ Segment::Segment(unsigned int numchars, const Face* face, uint32 script, int tex
|
||||
m_bufSize(numchars + 10),
|
||||
m_numGlyphs(numchars),
|
||||
m_numCharinfo(numchars),
|
||||
m_passBits(m_silf->aPassBits() ? -1 : 0),
|
||||
m_defaultOriginal(0),
|
||||
m_dir(textDir),
|
||||
m_flags(((m_silf->flags() & 0x20) != 0) << 1)
|
||||
m_flags(((m_silf->flags() & 0x20) != 0) << 1),
|
||||
m_passBits(m_silf->aPassBits() ? -1 : 0)
|
||||
{
|
||||
Slot *s = newSlot();
|
||||
if (s)
|
||||
freeSlot(s);
|
||||
freeSlot(newSlot());
|
||||
m_bufSize = log_binary(numchars)+1;
|
||||
}
|
||||
|
||||
@ -77,82 +75,17 @@ Segment::~Segment()
|
||||
free(m_collisions);
|
||||
}
|
||||
|
||||
#ifndef GRAPHITE2_NSEGCACHE
|
||||
SegmentScopeState Segment::setScope(Slot * firstSlot, Slot * lastSlot, size_t subLength)
|
||||
{
|
||||
SegmentScopeState state;
|
||||
state.numGlyphsOutsideScope = m_numGlyphs - subLength;
|
||||
state.realFirstSlot = m_first;
|
||||
state.slotBeforeScope = firstSlot->prev();
|
||||
state.slotAfterScope = lastSlot->next();
|
||||
state.realLastSlot = m_last;
|
||||
firstSlot->prev(NULL);
|
||||
lastSlot->next(NULL);
|
||||
assert(m_defaultOriginal == 0);
|
||||
m_defaultOriginal = firstSlot->original();
|
||||
m_numGlyphs = subLength;
|
||||
m_first = firstSlot;
|
||||
m_last = lastSlot;
|
||||
return state;
|
||||
}
|
||||
|
||||
void Segment::removeScope(SegmentScopeState & state)
|
||||
{
|
||||
m_numGlyphs = state.numGlyphsOutsideScope + m_numGlyphs;
|
||||
if (state.slotBeforeScope)
|
||||
{
|
||||
state.slotBeforeScope->next(m_first);
|
||||
m_first->prev(state.slotBeforeScope);
|
||||
m_first = state.realFirstSlot;
|
||||
}
|
||||
if (state.slotAfterScope)
|
||||
{
|
||||
state.slotAfterScope->prev(m_last);
|
||||
m_last->next(state.slotAfterScope);
|
||||
m_last = state.realLastSlot;
|
||||
}
|
||||
m_defaultOriginal = 0;
|
||||
}
|
||||
|
||||
#if 0
|
||||
void Segment::append(const Segment &other)
|
||||
{
|
||||
Rect bbox = other.m_bbox + m_advance;
|
||||
|
||||
m_slots.insert(m_slots.end(), other.m_slots.begin(), other.m_slots.end());
|
||||
CharInfo* pNewCharInfo = new CharInfo[m_numCharinfo+other.m_numCharinfo]; //since CharInfo has no constructor, this doesn't do much
|
||||
for (unsigned int i=0 ; i<m_numCharinfo ; ++i)
|
||||
pNewCharInfo[i] = m_charinfo[i];
|
||||
m_last->next(other.m_first);
|
||||
other.m_last->prev(m_last);
|
||||
m_userAttrs.insert(m_userAttrs.end(), other.m_userAttrs.begin(), other.m_userAttrs.end());
|
||||
|
||||
delete[] m_charinfo;
|
||||
m_charinfo = pNewCharInfo;
|
||||
pNewCharInfo += m_numCharinfo ;
|
||||
for (unsigned int i=0 ; i<m_numCharinfo ; ++i)
|
||||
pNewCharInfo[i] = other.m_charinfo[i];
|
||||
|
||||
m_numCharinfo += other.m_numCharinfo;
|
||||
m_numGlyphs += other.m_numGlyphs;
|
||||
m_advance = m_advance + other.m_advance;
|
||||
m_bbox = m_bbox.widen(bbox);
|
||||
m_passBits &= other.passBits();
|
||||
}
|
||||
#endif
|
||||
#endif // GRAPHITE2_NSEGCACHE
|
||||
|
||||
void Segment::appendSlot(int id, int cid, int gid, int iFeats, size_t coffset)
|
||||
{
|
||||
Slot *aSlot = newSlot();
|
||||
|
||||
|
||||
if (!aSlot) return;
|
||||
m_charinfo[id].init(cid);
|
||||
m_charinfo[id].feats(iFeats);
|
||||
m_charinfo[id].base(coffset);
|
||||
const GlyphFace * theGlyph = m_face->glyphs().glyphSafe(gid);
|
||||
m_charinfo[id].breakWeight(theGlyph ? theGlyph->attrs()[m_silf->aBreak()] : 0);
|
||||
|
||||
|
||||
aSlot->child(NULL);
|
||||
aSlot->setGlyph(this, gid, theGlyph);
|
||||
aSlot->originate(id);
|
||||
@ -163,7 +96,7 @@ void Segment::appendSlot(int id, int cid, int gid, int iFeats, size_t coffset)
|
||||
m_last = aSlot;
|
||||
if (!m_first) m_first = aSlot;
|
||||
if (theGlyph && m_silf->aPassBits())
|
||||
m_passBits &= theGlyph->attrs()[m_silf->aPassBits()]
|
||||
m_passBits &= theGlyph->attrs()[m_silf->aPassBits()]
|
||||
| (m_silf->numPasses() > 16 ? (theGlyph->attrs()[m_silf->aPassBits() + 1] << 16) : 0);
|
||||
}
|
||||
|
||||
@ -206,6 +139,7 @@ Slot *Segment::newSlot()
|
||||
|
||||
void Segment::freeSlot(Slot *aSlot)
|
||||
{
|
||||
if (aSlot == nullptr) return;
|
||||
if (m_last == aSlot) m_last = aSlot->prev();
|
||||
if (m_first == aSlot) m_first = aSlot->next();
|
||||
if (aSlot->attachedTo())
|
||||
@ -214,11 +148,11 @@ void Segment::freeSlot(Slot *aSlot)
|
||||
{
|
||||
if (aSlot->firstChild()->attachedTo() == aSlot)
|
||||
{
|
||||
aSlot->firstChild()->attachTo(NULL);
|
||||
aSlot->firstChild()->attachTo(nullptr);
|
||||
aSlot->removeChild(aSlot->firstChild());
|
||||
}
|
||||
else
|
||||
aSlot->firstChild(NULL);
|
||||
aSlot->firstChild(nullptr);
|
||||
}
|
||||
// reset the slot incase it is reused
|
||||
::new (aSlot) Slot(aSlot->userAttrs());
|
||||
@ -230,7 +164,7 @@ void Segment::freeSlot(Slot *aSlot)
|
||||
#endif
|
||||
// update next pointer
|
||||
if (!m_freeSlots)
|
||||
aSlot->next(NULL);
|
||||
aSlot->next(nullptr);
|
||||
else
|
||||
aSlot->next(m_freeSlots);
|
||||
m_freeSlots = aSlot;
|
||||
@ -243,7 +177,7 @@ SlotJustify *Segment::newJustify()
|
||||
const size_t justSize = SlotJustify::size_of(m_silf->numJustLevels());
|
||||
byte *justs = grzeroalloc<byte>(justSize * m_bufSize);
|
||||
if (!justs) return NULL;
|
||||
for (int i = m_bufSize - 2; i >= 0; --i)
|
||||
for (ptrdiff_t i = m_bufSize - 2; i >= 0; --i)
|
||||
{
|
||||
SlotJustify *p = reinterpret_cast<SlotJustify *>(justs + justSize * i);
|
||||
SlotJustify *next = reinterpret_cast<SlotJustify *>(justs + justSize * (i + 1));
|
||||
@ -267,64 +201,6 @@ void Segment::freeJustify(SlotJustify *aJustify)
|
||||
m_freeJustifies = aJustify;
|
||||
}
|
||||
|
||||
#ifndef GRAPHITE2_NSEGCACHE
|
||||
void Segment::splice(size_t offset, size_t length, Slot * const startSlot,
|
||||
Slot * endSlot, const Slot * srcSlot,
|
||||
const size_t numGlyphs)
|
||||
{
|
||||
size_t numChars = length;
|
||||
extendLength(numGlyphs - length);
|
||||
// remove any extra
|
||||
if (numGlyphs < length)
|
||||
{
|
||||
Slot * end = endSlot->next();
|
||||
do
|
||||
{
|
||||
endSlot = endSlot->prev();
|
||||
freeSlot(endSlot->next());
|
||||
} while (numGlyphs < --length);
|
||||
endSlot->next(end);
|
||||
if (end)
|
||||
end->prev(endSlot);
|
||||
}
|
||||
else
|
||||
{
|
||||
// insert extra slots if needed
|
||||
while (numGlyphs > length)
|
||||
{
|
||||
Slot * extra = newSlot();
|
||||
if (!extra) return;
|
||||
extra->prev(endSlot);
|
||||
extra->next(endSlot->next());
|
||||
endSlot->next(extra);
|
||||
if (extra->next())
|
||||
extra->next()->prev(extra);
|
||||
if (m_last == endSlot)
|
||||
m_last = extra;
|
||||
endSlot = extra;
|
||||
++length;
|
||||
}
|
||||
}
|
||||
|
||||
endSlot = endSlot->next();
|
||||
assert(numGlyphs == length);
|
||||
assert(offset + numChars <= m_numCharinfo);
|
||||
Slot * indexmap[eMaxSpliceSize*3];
|
||||
assert(numGlyphs < sizeof indexmap/sizeof *indexmap);
|
||||
Slot * slot = startSlot;
|
||||
for (uint16 i=0; i < numGlyphs; slot = slot->next(), ++i)
|
||||
indexmap[i] = slot;
|
||||
|
||||
for (slot = startSlot; slot != endSlot; slot = slot->next(), srcSlot = srcSlot->next())
|
||||
{
|
||||
slot->set(*srcSlot, offset, m_silf->numUser(), m_silf->numJustLevels(), numChars);
|
||||
if (srcSlot->attachedTo()) slot->attachTo(indexmap[srcSlot->attachedTo()->index()]);
|
||||
if (srcSlot->nextSibling()) slot->m_sibling = indexmap[srcSlot->nextSibling()->index()];
|
||||
if (srcSlot->firstChild()) slot->m_child = indexmap[srcSlot->firstChild()->index()];
|
||||
}
|
||||
}
|
||||
#endif // GRAPHITE2_NSEGCACHE
|
||||
|
||||
// reverse the slots but keep diacritics in their same position after their bases
|
||||
void Segment::reverseSlots()
|
||||
{
|
||||
@ -452,7 +328,7 @@ Position Segment::positionSlots(const Font *font, Slot * iStart, Slot * iEnd, bo
|
||||
}
|
||||
|
||||
|
||||
void Segment::associateChars(int offset, int numChars)
|
||||
void Segment::associateChars(int offset, size_t numChars)
|
||||
{
|
||||
int i = 0, j = 0;
|
||||
CharInfo *c, *cend;
|
||||
@ -476,7 +352,7 @@ void Segment::associateChars(int offset, int numChars)
|
||||
for (Slot *s = m_first; s; s = s->next())
|
||||
{
|
||||
int a;
|
||||
for (a = s->after() + 1; a < offset + numChars && charinfo(a)->after() < 0; ++a)
|
||||
for (a = s->after() + 1; a < offset + int(numChars) && charinfo(a)->after() < 0; ++a)
|
||||
{ charinfo(a)->after(s->index()); }
|
||||
--a;
|
||||
s->after(a);
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -199,8 +199,8 @@ bool Silf::readGraphite(const byte * const silf_start, size_t lSilf, Face& face,
|
||||
{
|
||||
uint32 pass_start = be::read<uint32>(o_passes);
|
||||
uint32 pass_end = be::peek<uint32>(o_passes);
|
||||
face.error_context((face.error_context() & 0xFF00) + EC_ASILF + (i << 16));
|
||||
if (e.test(pass_start > pass_end, E_BADPASSSTART)
|
||||
face.error_context((face.error_context() & 0xFF00) + EC_ASILF + unsigned(i << 16));
|
||||
if (e.test(pass_start > pass_end, E_BADPASSSTART)
|
||||
|| e.test(pass_start < passes_start, E_BADPASSSTART)
|
||||
|| e.test(pass_end > lSilf, E_BADPASSEND)) {
|
||||
releaseBuffers(); return face.error(e);
|
||||
@ -233,9 +233,9 @@ bool Silf::readGraphite(const byte * const silf_start, size_t lSilf, Face& face,
|
||||
template<typename T> inline uint32 Silf::readClassOffsets(const byte *&p, size_t data_len, Error &e)
|
||||
{
|
||||
const T cls_off = 2*sizeof(uint16) + sizeof(T)*(m_nClass+1);
|
||||
const size_t max_off = (be::peek<T>(p + sizeof(T)*m_nClass) - cls_off)/sizeof(uint16);
|
||||
const uint32 max_off = (be::peek<T>(p + sizeof(T)*m_nClass) - cls_off)/sizeof(uint16);
|
||||
// Check that the last+1 offset is less than or equal to the class map length.
|
||||
if (e.test(be::peek<T>(p) != cls_off, E_MISALIGNEDCLASSES)
|
||||
if (e.test(be::peek<T>(p) != cls_off, E_MISALIGNEDCLASSES)
|
||||
|| e.test(max_off > (data_len - cls_off)/sizeof(uint16), E_HIGHCLASSOFFSET))
|
||||
return ERROROFFSET;
|
||||
|
||||
@ -357,7 +357,7 @@ uint16 Silf::getClassGlyph(uint16 cid, unsigned int index) const
|
||||
bool Silf::runGraphite(Segment *seg, uint8 firstPass, uint8 lastPass, int dobidi) const
|
||||
{
|
||||
assert(seg != 0);
|
||||
unsigned int maxSize = seg->slotCount() * MAX_SEG_GROWTH_FACTOR;
|
||||
size_t maxSize = seg->slotCount() * MAX_SEG_GROWTH_FACTOR;
|
||||
SlotMap map(*seg, m_dir, maxSize);
|
||||
FiniteStateMachine fsm(map, seg->getFace()->logger());
|
||||
vm::Machine m(map);
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -40,7 +40,7 @@ Slot::Slot(int16 *user_attrs) :
|
||||
m_index(0), m_parent(NULL), m_child(NULL), m_sibling(NULL),
|
||||
m_position(0, 0), m_shift(0, 0), m_advance(0, 0),
|
||||
m_attach(0, 0), m_with(0, 0), m_just(0.),
|
||||
m_flags(0), m_attLevel(0), m_bidiCls(-1), m_bidiLevel(0),
|
||||
m_flags(0), m_attLevel(0), m_bidiCls(-1), m_bidiLevel(0),
|
||||
m_userAttr(user_attrs), m_justs(NULL)
|
||||
{
|
||||
}
|
||||
@ -57,7 +57,7 @@ void Slot::set(const Slot & orig, int charOffset, size_t sizeAttr, size_t justLe
|
||||
else
|
||||
m_before = orig.m_before + charOffset;
|
||||
if (charOffset <= 0 && orig.m_after + charOffset >= numChars)
|
||||
m_after = numChars - 1;
|
||||
m_after = int(numChars) - 1;
|
||||
else
|
||||
m_after = orig.m_after + charOffset;
|
||||
m_parent = NULL;
|
||||
@ -107,7 +107,7 @@ Position Slot::finalise(const Segment *seg, const Font *font, Position & base, R
|
||||
tAdvance = (m_advance.x - glyphFace->theAdvance().x + m_just) * scale + font->advance(glyph());
|
||||
else
|
||||
tAdvance *= scale;
|
||||
}
|
||||
}
|
||||
Position res;
|
||||
|
||||
m_position = base + shift;
|
||||
@ -142,7 +142,7 @@ Position Slot::finalise(const Segment *seg, const Font *font, Position & base, R
|
||||
Position tRes = m_sibling->finalise(seg, font, base, bbox, attrLevel, clusterMin, rtl, isFinal, depth + 1);
|
||||
if (tRes.x > res.x) res = tRes;
|
||||
}
|
||||
|
||||
|
||||
if (!m_parent && clusterMin < base.x)
|
||||
{
|
||||
Position adj = Position(m_position.x - clusterMin, 0.);
|
||||
@ -165,25 +165,25 @@ int32 Slot::clusterMetric(const Segment *seg, uint8 metric, uint8 attrLevel, boo
|
||||
switch (metrics(metric))
|
||||
{
|
||||
case kgmetLsb :
|
||||
return bbox.bl.x;
|
||||
return int32(bbox.bl.x);
|
||||
case kgmetRsb :
|
||||
return res.x - bbox.tr.x;
|
||||
return int32(res.x - bbox.tr.x);
|
||||
case kgmetBbTop :
|
||||
return bbox.tr.y;
|
||||
return int32(bbox.tr.y);
|
||||
case kgmetBbBottom :
|
||||
return bbox.bl.y;
|
||||
return int32(bbox.bl.y);
|
||||
case kgmetBbLeft :
|
||||
return bbox.bl.x;
|
||||
return int32(bbox.bl.x);
|
||||
case kgmetBbRight :
|
||||
return bbox.tr.x;
|
||||
return int32(bbox.tr.x);
|
||||
case kgmetBbWidth :
|
||||
return bbox.tr.x - bbox.bl.x;
|
||||
return int32(bbox.tr.x - bbox.bl.x);
|
||||
case kgmetBbHeight :
|
||||
return bbox.tr.y - bbox.bl.y;
|
||||
return int32(bbox.tr.y - bbox.bl.y);
|
||||
case kgmetAdvWidth :
|
||||
return res.x;
|
||||
return int32(res.x);
|
||||
case kgmetAdvHeight :
|
||||
return res.y;
|
||||
return int32(res.y);
|
||||
default :
|
||||
return 0;
|
||||
}
|
||||
@ -193,14 +193,7 @@ int32 Slot::clusterMetric(const Segment *seg, uint8 metric, uint8 attrLevel, boo
|
||||
|
||||
int Slot::getAttr(const Segment *seg, attrCode ind, uint8 subindex) const
|
||||
{
|
||||
if (ind == gr_slatUserDefnV1)
|
||||
{
|
||||
ind = gr_slatUserDefn;
|
||||
subindex = 0;
|
||||
if (seg->numAttrs() == 0)
|
||||
return 0;
|
||||
}
|
||||
else if (ind >= gr_slatJStretch && ind < gr_slatJStretch + 20 && ind != gr_slatJWidth)
|
||||
if (ind >= gr_slatJStretch && ind < gr_slatJStretch + 20 && ind != gr_slatJWidth)
|
||||
{
|
||||
int indx = ind - gr_slatJStretch;
|
||||
return getJustify(seg, indx / 5, indx % 5);
|
||||
@ -231,30 +224,32 @@ int Slot::getAttr(const Segment *seg, attrCode ind, uint8 subindex) const
|
||||
case gr_slatMeasureSol: return -1; // err what's this?
|
||||
case gr_slatMeasureEol: return -1;
|
||||
case gr_slatJWidth: return int(m_just);
|
||||
case gr_slatUserDefn : return m_userAttr[subindex];
|
||||
case gr_slatUserDefnV1: subindex = 0; GR_FALLTHROUGH;
|
||||
// no break
|
||||
case gr_slatUserDefn : return subindex < seg->numAttrs() ? m_userAttr[subindex] : 0;
|
||||
case gr_slatSegSplit : return seg->charinfo(m_original)->flags() & 3;
|
||||
case gr_slatBidiLevel: return m_bidiLevel;
|
||||
case gr_slatColFlags : { SlotCollision *c = seg->collisionInfo(this); return c ? c->flags() : 0; }
|
||||
case gr_slatColLimitblx : SLOTGETCOLATTR(limit().bl.x)
|
||||
case gr_slatColLimitbly : SLOTGETCOLATTR(limit().bl.y)
|
||||
case gr_slatColLimittrx : SLOTGETCOLATTR(limit().tr.x)
|
||||
case gr_slatColLimittry : SLOTGETCOLATTR(limit().tr.y)
|
||||
case gr_slatColShiftx : SLOTGETCOLATTR(offset().x)
|
||||
case gr_slatColShifty : SLOTGETCOLATTR(offset().y)
|
||||
case gr_slatColMargin : SLOTGETCOLATTR(margin())
|
||||
case gr_slatColMarginWt : SLOTGETCOLATTR(marginWt())
|
||||
case gr_slatColExclGlyph : SLOTGETCOLATTR(exclGlyph())
|
||||
case gr_slatColExclOffx : SLOTGETCOLATTR(exclOffset().x)
|
||||
case gr_slatColExclOffy : SLOTGETCOLATTR(exclOffset().y)
|
||||
case gr_slatSeqClass : SLOTGETCOLATTR(seqClass())
|
||||
case gr_slatSeqProxClass : SLOTGETCOLATTR(seqProxClass())
|
||||
case gr_slatSeqOrder : SLOTGETCOLATTR(seqOrder())
|
||||
case gr_slatSeqAboveXoff : SLOTGETCOLATTR(seqAboveXoff())
|
||||
case gr_slatSeqAboveWt : SLOTGETCOLATTR(seqAboveWt())
|
||||
case gr_slatSeqBelowXlim : SLOTGETCOLATTR(seqBelowXlim())
|
||||
case gr_slatSeqBelowWt : SLOTGETCOLATTR(seqBelowWt())
|
||||
case gr_slatSeqValignHt : SLOTGETCOLATTR(seqValignHt())
|
||||
case gr_slatSeqValignWt : SLOTGETCOLATTR(seqValignWt())
|
||||
case gr_slatColLimitblx:SLOTGETCOLATTR(limit().bl.x)
|
||||
case gr_slatColLimitbly:SLOTGETCOLATTR(limit().bl.y)
|
||||
case gr_slatColLimittrx:SLOTGETCOLATTR(limit().tr.x)
|
||||
case gr_slatColLimittry:SLOTGETCOLATTR(limit().tr.y)
|
||||
case gr_slatColShiftx : SLOTGETCOLATTR(offset().x)
|
||||
case gr_slatColShifty : SLOTGETCOLATTR(offset().y)
|
||||
case gr_slatColMargin : SLOTGETCOLATTR(margin())
|
||||
case gr_slatColMarginWt:SLOTGETCOLATTR(marginWt())
|
||||
case gr_slatColExclGlyph:SLOTGETCOLATTR(exclGlyph())
|
||||
case gr_slatColExclOffx:SLOTGETCOLATTR(exclOffset().x)
|
||||
case gr_slatColExclOffy:SLOTGETCOLATTR(exclOffset().y)
|
||||
case gr_slatSeqClass : SLOTGETCOLATTR(seqClass())
|
||||
case gr_slatSeqProxClass:SLOTGETCOLATTR(seqProxClass())
|
||||
case gr_slatSeqOrder : SLOTGETCOLATTR(seqOrder())
|
||||
case gr_slatSeqAboveXoff:SLOTGETCOLATTR(seqAboveXoff())
|
||||
case gr_slatSeqAboveWt: SLOTGETCOLATTR(seqAboveWt())
|
||||
case gr_slatSeqBelowXlim:SLOTGETCOLATTR(seqBelowXlim())
|
||||
case gr_slatSeqBelowWt: SLOTGETCOLATTR(seqBelowWt())
|
||||
case gr_slatSeqValignHt:SLOTGETCOLATTR(seqValignHt())
|
||||
case gr_slatSeqValignWt:SLOTGETCOLATTR(seqValignWt())
|
||||
default : return 0;
|
||||
}
|
||||
}
|
||||
@ -480,7 +475,7 @@ void Slot::setGlyph(Segment *seg, uint16 glyphid, const GlyphFace * theGlyph)
|
||||
m_advance = Position(aGlyph->theAdvance().x, 0.);
|
||||
if (seg->silf()->aPassBits())
|
||||
{
|
||||
seg->mergePassBits(theGlyph->attrs()[seg->silf()->aPassBits()]);
|
||||
seg->mergePassBits(uint8(theGlyph->attrs()[seg->silf()->aPassBits()]));
|
||||
if (seg->silf()->numPasses() > 16)
|
||||
seg->mergePassBits(theGlyph->attrs()[seg->silf()->aPassBits()+1] << 16);
|
||||
}
|
||||
@ -532,4 +527,3 @@ bool Slot::isChildOf(const Slot *base) const
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -31,7 +31,7 @@ Responsibility: Alan Ward
|
||||
Last reviewed: Not yet.
|
||||
|
||||
Description
|
||||
Implements the methods for TtfUtil class. This file should remain portable to any C++
|
||||
Implements the methods for TtfUtil class. This file should remain portable to any C++
|
||||
environment by only using standard C++ and the TTF structurs defined in Tt.h.
|
||||
-------------------------------------------------------------------------------*//*:End Ignore*/
|
||||
|
||||
@ -60,7 +60,7 @@ Description
|
||||
/***********************************************************************************************
|
||||
Local Constants and static variables
|
||||
***********************************************************************************************/
|
||||
namespace
|
||||
namespace
|
||||
{
|
||||
#ifdef ALL_TTFUTILS
|
||||
// max number of components allowed in composite glyphs
|
||||
@ -79,45 +79,45 @@ namespace
|
||||
const int kcPostNames = 258;
|
||||
|
||||
const char * rgPostName[kcPostNames] = {
|
||||
".notdef", ".null", "nonmarkingreturn", "space", "exclam", "quotedbl", "numbersign",
|
||||
"dollar", "percent", "ampersand", "quotesingle", "parenleft",
|
||||
"parenright", "asterisk", "plus", "comma", "hyphen", "period", "slash",
|
||||
"zero", "one", "two", "three", "four", "five", "six", "seven", "eight",
|
||||
"nine", "colon", "semicolon", "less", "equal", "greater", "question",
|
||||
"at", "A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M",
|
||||
"N", "O", "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z",
|
||||
"bracketleft", "backslash", "bracketright", "asciicircum",
|
||||
"underscore", "grave", "a", "b", "c", "d", "e", "f", "g", "h", "i",
|
||||
"j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", "w",
|
||||
"x", "y", "z", "braceleft", "bar", "braceright", "asciitilde",
|
||||
"Adieresis", "Aring", "Ccedilla", "Eacute", "Ntilde", "Odieresis",
|
||||
"Udieresis", "aacute", "agrave", "acircumflex", "adieresis", "atilde",
|
||||
"aring", "ccedilla", "eacute", "egrave", "ecircumflex", "edieresis",
|
||||
"iacute", "igrave", "icircumflex", "idieresis", "ntilde", "oacute",
|
||||
"ograve", "ocircumflex", "odieresis", "otilde", "uacute", "ugrave",
|
||||
"ucircumflex", "udieresis", "dagger", "degree", "cent", "sterling",
|
||||
"section", "bullet", "paragraph", "germandbls", "registered",
|
||||
"copyright", "trademark", "acute", "dieresis", "notequal", "AE",
|
||||
"Oslash", "infinity", "plusminus", "lessequal", "greaterequal", "yen",
|
||||
"mu", "partialdiff", "summation", "product", "pi", "integral",
|
||||
"ordfeminine", "ordmasculine", "Omega", "ae", "oslash", "questiondown",
|
||||
"exclamdown", "logicalnot", "radical", "florin", "approxequal",
|
||||
"Delta", "guillemotleft", "guillemotright", "ellipsis", "nonbreakingspace",
|
||||
"Agrave", "Atilde", "Otilde", "OE", "oe", "endash", "emdash",
|
||||
"quotedblleft", "quotedblright", "quoteleft", "quoteright", "divide",
|
||||
"lozenge", "ydieresis", "Ydieresis", "fraction", "currency",
|
||||
"guilsinglleft", "guilsinglright", "fi", "fl", "daggerdbl", "periodcentered",
|
||||
"quotesinglbase", "quotedblbase", "perthousand", "Acircumflex",
|
||||
"Ecircumflex", "Aacute", "Edieresis", "Egrave", "Iacute",
|
||||
"Icircumflex", "Idieresis", "Igrave", "Oacute", "Ocircumflex",
|
||||
"apple", "Ograve", "Uacute", "Ucircumflex", "Ugrave", "dotlessi",
|
||||
"circumflex", "tilde", "macron", "breve", "dotaccent", "ring",
|
||||
"cedilla", "hungarumlaut", "ogonek", "caron", "Lslash", "lslash",
|
||||
"Scaron", "scaron", "Zcaron", "zcaron", "brokenbar", "Eth", "eth",
|
||||
"Yacute", "yacute", "Thorn", "thorn", "minus", "multiply",
|
||||
"onesuperior", "twosuperior", "threesuperior", "onehalf", "onequarter",
|
||||
"threequarters", "franc", "Gbreve", "gbreve", "Idotaccent", "Scedilla",
|
||||
"scedilla", "Cacute", "cacute", "Ccaron", "ccaron",
|
||||
".notdef", ".null", "nonmarkingreturn", "space", "exclam", "quotedbl", "numbersign",
|
||||
"dollar", "percent", "ampersand", "quotesingle", "parenleft",
|
||||
"parenright", "asterisk", "plus", "comma", "hyphen", "period", "slash",
|
||||
"zero", "one", "two", "three", "four", "five", "six", "seven", "eight",
|
||||
"nine", "colon", "semicolon", "less", "equal", "greater", "question",
|
||||
"at", "A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M",
|
||||
"N", "O", "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z",
|
||||
"bracketleft", "backslash", "bracketright", "asciicircum",
|
||||
"underscore", "grave", "a", "b", "c", "d", "e", "f", "g", "h", "i",
|
||||
"j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", "w",
|
||||
"x", "y", "z", "braceleft", "bar", "braceright", "asciitilde",
|
||||
"Adieresis", "Aring", "Ccedilla", "Eacute", "Ntilde", "Odieresis",
|
||||
"Udieresis", "aacute", "agrave", "acircumflex", "adieresis", "atilde",
|
||||
"aring", "ccedilla", "eacute", "egrave", "ecircumflex", "edieresis",
|
||||
"iacute", "igrave", "icircumflex", "idieresis", "ntilde", "oacute",
|
||||
"ograve", "ocircumflex", "odieresis", "otilde", "uacute", "ugrave",
|
||||
"ucircumflex", "udieresis", "dagger", "degree", "cent", "sterling",
|
||||
"section", "bullet", "paragraph", "germandbls", "registered",
|
||||
"copyright", "trademark", "acute", "dieresis", "notequal", "AE",
|
||||
"Oslash", "infinity", "plusminus", "lessequal", "greaterequal", "yen",
|
||||
"mu", "partialdiff", "summation", "product", "pi", "integral",
|
||||
"ordfeminine", "ordmasculine", "Omega", "ae", "oslash", "questiondown",
|
||||
"exclamdown", "logicalnot", "radical", "florin", "approxequal",
|
||||
"Delta", "guillemotleft", "guillemotright", "ellipsis", "nonbreakingspace",
|
||||
"Agrave", "Atilde", "Otilde", "OE", "oe", "endash", "emdash",
|
||||
"quotedblleft", "quotedblright", "quoteleft", "quoteright", "divide",
|
||||
"lozenge", "ydieresis", "Ydieresis", "fraction", "currency",
|
||||
"guilsinglleft", "guilsinglright", "fi", "fl", "daggerdbl", "periodcentered",
|
||||
"quotesinglbase", "quotedblbase", "perthousand", "Acircumflex",
|
||||
"Ecircumflex", "Aacute", "Edieresis", "Egrave", "Iacute",
|
||||
"Icircumflex", "Idieresis", "Igrave", "Oacute", "Ocircumflex",
|
||||
"apple", "Ograve", "Uacute", "Ucircumflex", "Ugrave", "dotlessi",
|
||||
"circumflex", "tilde", "macron", "breve", "dotaccent", "ring",
|
||||
"cedilla", "hungarumlaut", "ogonek", "caron", "Lslash", "lslash",
|
||||
"Scaron", "scaron", "Zcaron", "zcaron", "brokenbar", "Eth", "eth",
|
||||
"Yacute", "yacute", "Thorn", "thorn", "minus", "multiply",
|
||||
"onesuperior", "twosuperior", "threesuperior", "onehalf", "onequarter",
|
||||
"threequarters", "franc", "Gbreve", "gbreve", "Idotaccent", "Scedilla",
|
||||
"scedilla", "Cacute", "cacute", "Ccaron", "ccaron",
|
||||
"dcroat" };
|
||||
#endif
|
||||
|
||||
@ -128,18 +128,18 @@ namespace
|
||||
***********************************************************************************************/
|
||||
|
||||
/* Note on error processing: The code guards against bad glyph ids being used to look up data
|
||||
in open ended tables (loca, hmtx). If the glyph id comes from a cmap this shouldn't happen
|
||||
but it seems prudent to check for user errors here. The code does assume that data obtained
|
||||
from the TTF file is valid otherwise (though the CheckTable method seeks to check for
|
||||
obvious problems that might accompany a change in table versions). For example an invalid
|
||||
in open ended tables (loca, hmtx). If the glyph id comes from a cmap this shouldn't happen
|
||||
but it seems prudent to check for user errors here. The code does assume that data obtained
|
||||
from the TTF file is valid otherwise (though the CheckTable method seeks to check for
|
||||
obvious problems that might accompany a change in table versions). For example an invalid
|
||||
offset in the loca table which could exceed the size of the glyf table is NOT trapped.
|
||||
Likewise if numberOf_LongHorMetrics in the hhea table is wrong, this will NOT be trapped,
|
||||
Likewise if numberOf_LongHorMetrics in the hhea table is wrong, this will NOT be trapped,
|
||||
which could cause a lookup in the hmtx table to exceed the table length. Of course, TTF tables
|
||||
that are completely corrupt will cause unpredictable results. */
|
||||
|
||||
/* Note on composite glyphs: Glyphs that have components that are themselves composites
|
||||
are not supported. IsDeepComposite can be used to test for this. False is returned from many
|
||||
of the methods in this cases. It is unclear how to build composite glyphs in some cases,
|
||||
are not supported. IsDeepComposite can be used to test for this. False is returned from many
|
||||
of the methods in this cases. It is unclear how to build composite glyphs in some cases,
|
||||
so this code represents my best guess until test cases can be found. See notes on the high-
|
||||
level GlyfPoints method. */
|
||||
namespace graphite2
|
||||
@ -167,7 +167,7 @@ bool GetHeaderInfo(size_t & lOffset, size_t & lSize)
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool CheckHeader(const void * pHdr)
|
||||
{
|
||||
const Sfnt::OffsetSubTable * pOffsetTable
|
||||
const Sfnt::OffsetSubTable * pOffsetTable
|
||||
= reinterpret_cast<const Sfnt::OffsetSubTable *>(pHdr);
|
||||
|
||||
return pHdr && be::swap(pOffsetTable->scaler_type) == Sfnt::OffsetSubTable::TrueTypeWin;
|
||||
@ -185,7 +185,7 @@ bool GetTableDirInfo(const void * pHdr, size_t & lOffset, size_t & lSize)
|
||||
lOffset = offsetof(Sfnt::OffsetSubTable, table_directory);
|
||||
lSize = be::swap(pOffsetTable->num_tables)
|
||||
* sizeof(Sfnt::OffsetSubTable::Entry);
|
||||
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -197,10 +197,10 @@ bool GetTableDirInfo(const void * pHdr, size_t & lOffset, size_t & lSize)
|
||||
bool GetTableInfo(const Tag TableTag, const void * pHdr, const void * pTableDir,
|
||||
size_t & lOffset, size_t & lSize)
|
||||
{
|
||||
const Sfnt::OffsetSubTable * pOffsetTable
|
||||
const Sfnt::OffsetSubTable * pOffsetTable
|
||||
= reinterpret_cast<const Sfnt::OffsetSubTable *>(pHdr);
|
||||
const size_t num_tables = be::swap(pOffsetTable->num_tables);
|
||||
const Sfnt::OffsetSubTable::Entry
|
||||
const Sfnt::OffsetSubTable::Entry
|
||||
* entry_itr = reinterpret_cast<const Sfnt::OffsetSubTable::Entry *>(
|
||||
pTableDir),
|
||||
* const dir_end = entry_itr + num_tables;
|
||||
@ -228,14 +228,14 @@ bool GetTableInfo(const Tag TableTag, const void * pHdr, const void * pTableDir,
|
||||
bool CheckTable(const Tag TableId, const void * pTable, size_t lTableSize)
|
||||
{
|
||||
using namespace Sfnt;
|
||||
|
||||
|
||||
if (pTable == 0 || lTableSize < 4) return false;
|
||||
|
||||
switch(TableId)
|
||||
{
|
||||
case Tag::cmap: // cmap
|
||||
{
|
||||
const Sfnt::CharacterCodeMap * const pCmap
|
||||
const Sfnt::CharacterCodeMap * const pCmap
|
||||
= reinterpret_cast<const Sfnt::CharacterCodeMap *>(pTable);
|
||||
if (lTableSize < sizeof(Sfnt::CharacterCodeMap))
|
||||
return false;
|
||||
@ -244,39 +244,39 @@ bool CheckTable(const Tag TableId, const void * pTable, size_t lTableSize)
|
||||
|
||||
case Tag::head: // head
|
||||
{
|
||||
const Sfnt::FontHeader * const pHead
|
||||
const Sfnt::FontHeader * const pHead
|
||||
= reinterpret_cast<const Sfnt::FontHeader *>(pTable);
|
||||
if (lTableSize < sizeof(Sfnt::FontHeader))
|
||||
return false;
|
||||
bool r = be::swap(pHead->version) == OneFix
|
||||
&& be::swap(pHead->magic_number) == FontHeader::MagicNumber
|
||||
&& be::swap(pHead->glyph_data_format)
|
||||
== FontHeader::GlypDataFormat
|
||||
== FontHeader::GlypDataFormat
|
||||
&& (be::swap(pHead->index_to_loc_format)
|
||||
== FontHeader::ShortIndexLocFormat
|
||||
== FontHeader::ShortIndexLocFormat
|
||||
|| be::swap(pHead->index_to_loc_format)
|
||||
== FontHeader::LongIndexLocFormat)
|
||||
== FontHeader::LongIndexLocFormat)
|
||||
&& sizeof(FontHeader) <= lTableSize;
|
||||
return r;
|
||||
}
|
||||
|
||||
case Tag::post: // post
|
||||
{
|
||||
const Sfnt::PostScriptGlyphName * const pPost
|
||||
const Sfnt::PostScriptGlyphName * const pPost
|
||||
= reinterpret_cast<const Sfnt::PostScriptGlyphName *>(pTable);
|
||||
if (lTableSize < sizeof(Sfnt::PostScriptGlyphName))
|
||||
return false;
|
||||
const fixed format = be::swap(pPost->format);
|
||||
bool r = format == PostScriptGlyphName::Format1
|
||||
|| format == PostScriptGlyphName::Format2
|
||||
|| format == PostScriptGlyphName::Format3
|
||||
bool r = format == PostScriptGlyphName::Format1
|
||||
|| format == PostScriptGlyphName::Format2
|
||||
|| format == PostScriptGlyphName::Format3
|
||||
|| format == PostScriptGlyphName::Format25;
|
||||
return r;
|
||||
}
|
||||
|
||||
case Tag::hhea: // hhea
|
||||
{
|
||||
const Sfnt::HorizontalHeader * pHhea =
|
||||
const Sfnt::HorizontalHeader * pHhea =
|
||||
reinterpret_cast<const Sfnt::HorizontalHeader *>(pTable);
|
||||
if (lTableSize < sizeof(Sfnt::HorizontalHeader))
|
||||
return false;
|
||||
@ -288,7 +288,7 @@ bool CheckTable(const Tag TableId, const void * pTable, size_t lTableSize)
|
||||
|
||||
case Tag::maxp: // maxp
|
||||
{
|
||||
const Sfnt::MaximumProfile * pMaxp =
|
||||
const Sfnt::MaximumProfile * pMaxp =
|
||||
reinterpret_cast<const Sfnt::MaximumProfile *>(pTable);
|
||||
if (lTableSize < sizeof(Sfnt::MaximumProfile))
|
||||
return false;
|
||||
@ -299,20 +299,20 @@ bool CheckTable(const Tag TableId, const void * pTable, size_t lTableSize)
|
||||
|
||||
case Tag::OS_2: // OS/2
|
||||
{
|
||||
const Sfnt::Compatibility * pOs2
|
||||
const Sfnt::Compatibility * pOs2
|
||||
= reinterpret_cast<const Sfnt::Compatibility *>(pTable);
|
||||
if (be::swap(pOs2->version) == 0)
|
||||
{ // OS/2 table version 1 size
|
||||
// if (sizeof(Sfnt::Compatibility)
|
||||
// - sizeof(uint32)*2 - sizeof(int16)*2
|
||||
// if (sizeof(Sfnt::Compatibility)
|
||||
// - sizeof(uint32)*2 - sizeof(int16)*2
|
||||
// - sizeof(uint16)*3 <= lTableSize)
|
||||
if (sizeof(Sfnt::Compatibility0) <= lTableSize)
|
||||
return true;
|
||||
}
|
||||
else if (be::swap(pOs2->version) == 1)
|
||||
{ // OS/2 table version 2 size
|
||||
// if (sizeof(Sfnt::Compatibility)
|
||||
// - sizeof(int16) *2
|
||||
// if (sizeof(Sfnt::Compatibility)
|
||||
// - sizeof(int16) *2
|
||||
// - sizeof(uint16)*3 <= lTableSize)
|
||||
if (sizeof(Sfnt::Compatibility1) <= lTableSize)
|
||||
return true;
|
||||
@ -334,7 +334,7 @@ bool CheckTable(const Tag TableId, const void * pTable, size_t lTableSize)
|
||||
|
||||
case Tag::name:
|
||||
{
|
||||
const Sfnt::FontNames * pName
|
||||
const Sfnt::FontNames * pName
|
||||
= reinterpret_cast<const Sfnt::FontNames *>(pTable);
|
||||
if (lTableSize < sizeof(Sfnt::FontNames))
|
||||
return false;
|
||||
@ -360,7 +360,7 @@ bool CheckTable(const Tag TableId, const void * pTable, size_t lTableSize)
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
size_t GlyphCount(const void * pMaxp)
|
||||
{
|
||||
const Sfnt::MaximumProfile * pTable =
|
||||
const Sfnt::MaximumProfile * pTable =
|
||||
reinterpret_cast<const Sfnt::MaximumProfile *>(pMaxp);
|
||||
return be::swap(pTable->num_glyphs);
|
||||
}
|
||||
@ -373,7 +373,7 @@ size_t GlyphCount(const void * pMaxp)
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
size_t MaxCompositeComponentCount(const void * pMaxp)
|
||||
{
|
||||
const Sfnt::MaximumProfile * pTable =
|
||||
const Sfnt::MaximumProfile * pTable =
|
||||
reinterpret_cast<const Sfnt::MaximumProfile *>(pMaxp);
|
||||
return be::swap(pTable->max_component_elements);
|
||||
}
|
||||
@ -387,7 +387,7 @@ size_t MaxCompositeComponentCount(const void * pMaxp)
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
size_t MaxCompositeLevelCount(const void * pMaxp)
|
||||
{
|
||||
const Sfnt::MaximumProfile * pTable =
|
||||
const Sfnt::MaximumProfile * pTable =
|
||||
reinterpret_cast<const Sfnt::MaximumProfile *>(pMaxp);
|
||||
return be::swap(pTable->max_component_depth);
|
||||
}
|
||||
@ -401,14 +401,14 @@ size_t MaxCompositeLevelCount(const void * pMaxp)
|
||||
size_t LocaGlyphCount(size_t lLocaSize, const void * pHead) //throw(std::domain_error)
|
||||
{
|
||||
|
||||
const Sfnt::FontHeader * pTable
|
||||
const Sfnt::FontHeader * pTable
|
||||
= reinterpret_cast<const Sfnt::FontHeader *>(pHead);
|
||||
|
||||
if (be::swap(pTable->index_to_loc_format)
|
||||
== Sfnt::FontHeader::ShortIndexLocFormat)
|
||||
// loca entries are two bytes and have been divided by two
|
||||
return (lLocaSize >> 1) - 1;
|
||||
|
||||
|
||||
if (be::swap(pTable->index_to_loc_format)
|
||||
== Sfnt::FontHeader::LongIndexLocFormat)
|
||||
// loca entries are four bytes
|
||||
@ -424,9 +424,9 @@ size_t LocaGlyphCount(size_t lLocaSize, const void * pHead) //throw(std::domain_
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
int DesignUnits(const void * pHead)
|
||||
{
|
||||
const Sfnt::FontHeader * pTable =
|
||||
const Sfnt::FontHeader * pTable =
|
||||
reinterpret_cast<const Sfnt::FontHeader *>(pHead);
|
||||
|
||||
|
||||
return be::swap(pTable->units_per_em);
|
||||
}
|
||||
|
||||
@ -436,9 +436,9 @@ int DesignUnits(const void * pHead)
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
int HeadTableCheckSum(const void * pHead)
|
||||
{
|
||||
const Sfnt::FontHeader * pTable =
|
||||
const Sfnt::FontHeader * pTable =
|
||||
reinterpret_cast<const Sfnt::FontHeader *>(pHead);
|
||||
|
||||
|
||||
return be::swap(pTable->check_sum_adjustment);
|
||||
}
|
||||
|
||||
@ -451,9 +451,9 @@ int HeadTableCheckSum(const void * pHead)
|
||||
void HeadTableCreateTime(const void * pHead,
|
||||
unsigned int * pnDateBC, unsigned int * pnDateAD)
|
||||
{
|
||||
const Sfnt::FontHeader * pTable =
|
||||
const Sfnt::FontHeader * pTable =
|
||||
reinterpret_cast<const Sfnt::FontHeader *>(pHead);
|
||||
|
||||
|
||||
*pnDateBC = be::swap(pTable->created[0]);
|
||||
*pnDateAD = be::swap(pTable->created[1]);
|
||||
}
|
||||
@ -467,9 +467,9 @@ void HeadTableCreateTime(const void * pHead,
|
||||
void HeadTableModifyTime(const void * pHead,
|
||||
unsigned int * pnDateBC, unsigned int *pnDateAD)
|
||||
{
|
||||
const Sfnt::FontHeader * pTable =
|
||||
const Sfnt::FontHeader * pTable =
|
||||
reinterpret_cast<const Sfnt::FontHeader *>(pHead);
|
||||
;
|
||||
;
|
||||
*pnDateBC = be::swap(pTable->modified[0]);
|
||||
*pnDateAD = be::swap(pTable->modified[1]);
|
||||
}
|
||||
@ -479,7 +479,7 @@ void HeadTableModifyTime(const void * pHead,
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool IsItalic(const void * pHead)
|
||||
{
|
||||
const Sfnt::FontHeader * pTable =
|
||||
const Sfnt::FontHeader * pTable =
|
||||
reinterpret_cast<const Sfnt::FontHeader *>(pHead);
|
||||
|
||||
return ((be::swap(pTable->mac_style) & 0x00000002) != 0);
|
||||
@ -518,7 +518,7 @@ bool FontOs2Style(const void *pOs2, bool & fBold, bool & fItalic)
|
||||
|
||||
fBold = (be::swap(pTable->fs_selection) & Sfnt::Compatibility::Bold) != 0;
|
||||
fItalic = (be::swap(pTable->fs_selection) & Sfnt::Compatibility::Italic) != 0;
|
||||
|
||||
|
||||
return true;
|
||||
}
|
||||
#endif
|
||||
@ -615,7 +615,7 @@ int GetLangsForNames(const void * pName, int nPlatformId, int nEncodingId,
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool Get31EngFamilyInfo(const void * pName, size_t & lOffset, size_t & lSize)
|
||||
{
|
||||
return GetNameInfo(pName, Sfnt::NameRecord::Microsoft, 1, 1033,
|
||||
return GetNameInfo(pName, Sfnt::NameRecord::Microsoft, 1, 1033,
|
||||
Sfnt::NameRecord::Family, lOffset, lSize);
|
||||
}
|
||||
|
||||
@ -628,7 +628,7 @@ bool Get31EngFamilyInfo(const void * pName, size_t & lOffset, size_t & lSize)
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool Get31EngFullFontInfo(const void * pName, size_t & lOffset, size_t & lSize)
|
||||
{
|
||||
return GetNameInfo(pName, Sfnt::NameRecord::Microsoft, 1, 1033,
|
||||
return GetNameInfo(pName, Sfnt::NameRecord::Microsoft, 1, 1033,
|
||||
Sfnt::NameRecord::Fullname, lOffset, lSize);
|
||||
}
|
||||
|
||||
@ -639,7 +639,7 @@ bool Get31EngFullFontInfo(const void * pName, size_t & lOffset, size_t & lSize)
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool Get30EngFamilyInfo(const void * pName, size_t & lOffset, size_t & lSize)
|
||||
{
|
||||
return GetNameInfo(pName, Sfnt::NameRecord::Microsoft, 0, 1033,
|
||||
return GetNameInfo(pName, Sfnt::NameRecord::Microsoft, 0, 1033,
|
||||
Sfnt::NameRecord::Family, lOffset, lSize);
|
||||
}
|
||||
|
||||
@ -652,13 +652,13 @@ bool Get30EngFamilyInfo(const void * pName, size_t & lOffset, size_t & lSize)
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool Get30EngFullFontInfo(const void * pName, size_t & lOffset, size_t & lSize)
|
||||
{
|
||||
return GetNameInfo(pName, Sfnt::NameRecord::Microsoft, 0, 1033,
|
||||
return GetNameInfo(pName, Sfnt::NameRecord::Microsoft, 0, 1033,
|
||||
Sfnt::NameRecord::Fullname, lOffset, lSize);
|
||||
}
|
||||
|
||||
/*----------------------------------------------------------------------------------------------
|
||||
Return the Glyph ID for a given Postscript name. This method finds the first glyph which
|
||||
matches the requested Postscript name. Ideally every glyph should have a unique Postscript
|
||||
matches the requested Postscript name. Ideally every glyph should have a unique Postscript
|
||||
name (except for special names such as .notdef), but this is not always true.
|
||||
On failure return value less than zero.
|
||||
-1 - table search failed
|
||||
@ -667,12 +667,12 @@ bool Get30EngFullFontInfo(const void * pName, size_t & lOffset, size_t & lSize)
|
||||
|
||||
Note: this method is not currently used by the Graphite engine.
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
int PostLookup(const void * pPost, size_t lPostSize, const void * pMaxp,
|
||||
int PostLookup(const void * pPost, size_t lPostSize, const void * pMaxp,
|
||||
const char * pPostName)
|
||||
{
|
||||
using namespace Sfnt;
|
||||
|
||||
const Sfnt::PostScriptGlyphName * pTable
|
||||
|
||||
const Sfnt::PostScriptGlyphName * pTable
|
||||
= reinterpret_cast<const Sfnt::PostScriptGlyphName *>(pPost);
|
||||
fixed format = be::swap(pTable->format);
|
||||
|
||||
@ -696,19 +696,19 @@ int PostLookup(const void * pPost, size_t lPostSize, const void * pMaxp,
|
||||
{ // format 1 - use standard Postscript names
|
||||
return iPostName;
|
||||
}
|
||||
|
||||
|
||||
if (format == PostScriptGlyphName::Format25)
|
||||
{
|
||||
{
|
||||
if (iPostName == -1)
|
||||
return -1;
|
||||
|
||||
const PostScriptGlyphName25 * pTable25
|
||||
|
||||
const PostScriptGlyphName25 * pTable25
|
||||
= static_cast<const PostScriptGlyphName25 *>(pTable);
|
||||
int cnGlyphs = GlyphCount(pMaxp);
|
||||
for (gid16 nGlyphId = 0; nGlyphId < cnGlyphs && nGlyphId < kcPostNames;
|
||||
for (gid16 nGlyphId = 0; nGlyphId < cnGlyphs && nGlyphId < kcPostNames;
|
||||
nGlyphId++)
|
||||
{ // glyph_name_index25 contains bytes so no byte swapping needed
|
||||
// search for first glyph id that uses the standard name
|
||||
// search for first glyph id that uses the standard name
|
||||
if (nGlyphId + pTable25->offset[nGlyphId] == iPostName)
|
||||
return nGlyphId;
|
||||
}
|
||||
@ -716,9 +716,9 @@ int PostLookup(const void * pPost, size_t lPostSize, const void * pMaxp,
|
||||
|
||||
if (format == PostScriptGlyphName::Format2)
|
||||
{ // format 2
|
||||
const PostScriptGlyphName2 * pTable2
|
||||
const PostScriptGlyphName2 * pTable2
|
||||
= static_cast<const PostScriptGlyphName2 *>(pTable);
|
||||
|
||||
|
||||
int cnGlyphs = be::swap(pTable2->number_of_glyphs);
|
||||
|
||||
if (iPostName != -1)
|
||||
@ -737,9 +737,9 @@ int PostLookup(const void * pPost, size_t lPostSize, const void * pMaxp,
|
||||
const char * pGlyphName = pFirstGlyphName;
|
||||
int iInNames = 0; // index in font specific names
|
||||
bool fFound = false;
|
||||
const char * const endOfTable
|
||||
const char * const endOfTable
|
||||
= reinterpret_cast<const char *>(pTable2) + lPostSize;
|
||||
while (pGlyphName < endOfTable && !fFound)
|
||||
while (pGlyphName < endOfTable && !fFound)
|
||||
{ // search Pascal strings for first matching name
|
||||
size_t nStringSize = size_t(*pGlyphName);
|
||||
if (nStrSizeGoal != nStringSize ||
|
||||
@ -770,12 +770,12 @@ int PostLookup(const void * pPost, size_t lPostSize, const void * pMaxp,
|
||||
}
|
||||
|
||||
/*----------------------------------------------------------------------------------------------
|
||||
Convert a Unicode character string from big endian (MSB first, Motorola) format to little
|
||||
endian (LSB first, Intel) format.
|
||||
nSize is the number of Unicode characters in the string. It should not include any
|
||||
terminating null. If nSize is 0, it is assumed the string is null terminated. nSize
|
||||
Convert a Unicode character string from big endian (MSB first, Motorola) format to little
|
||||
endian (LSB first, Intel) format.
|
||||
nSize is the number of Unicode characters in the string. It should not include any
|
||||
terminating null. If nSize is 0, it is assumed the string is null terminated. nSize
|
||||
defaults to 0.
|
||||
Return true if successful, false otherwise.
|
||||
Return true if successful, false otherwise.
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
void SwapWString(void * pWStr, size_t nSize /* = 0 */) //throw (std::invalid_argument)
|
||||
{
|
||||
@ -803,17 +803,17 @@ void SwapWString(void * pWStr, size_t nSize /* = 0 */) //throw (std::invalid_arg
|
||||
Get the left-side bearing and and advance width based on the given tables and Glyph ID
|
||||
Return true if successful, false otherwise. On false, one or both value could be INT_MIN
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool HorMetrics(gid16 nGlyphId, const void * pHmtx, size_t lHmtxSize, const void * pHhea,
|
||||
bool HorMetrics(gid16 nGlyphId, const void * pHmtx, size_t lHmtxSize, const void * pHhea,
|
||||
int & nLsb, unsigned int & nAdvWid)
|
||||
{
|
||||
const Sfnt::HorizontalMetric * phmtx =
|
||||
const Sfnt::HorizontalMetric * phmtx =
|
||||
reinterpret_cast<const Sfnt::HorizontalMetric *>(pHmtx);
|
||||
|
||||
const Sfnt::HorizontalHeader * phhea =
|
||||
const Sfnt::HorizontalHeader * phhea =
|
||||
reinterpret_cast<const Sfnt::HorizontalHeader *>(pHhea);
|
||||
|
||||
size_t cLongHorMetrics = be::swap(phhea->num_long_hor_metrics);
|
||||
if (nGlyphId < cLongHorMetrics)
|
||||
if (nGlyphId < cLongHorMetrics)
|
||||
{ // glyph id is acceptable
|
||||
if ((nGlyphId + 1) * sizeof(Sfnt::HorizontalMetric) > lHmtxSize) return false;
|
||||
nAdvWid = be::swap(phmtx[nGlyphId].advance_width);
|
||||
@ -899,7 +899,7 @@ bool CheckCmapSubtable4(const void * pCmapSubtable4, const void * pCmapEnd /*, u
|
||||
size_t table_len = (const byte *)pCmapEnd - (const byte *)pCmapSubtable4;
|
||||
if (!pCmapSubtable4) return false;
|
||||
const Sfnt::CmapSubTable * pTable = reinterpret_cast<const Sfnt::CmapSubTable *>(pCmapSubtable4);
|
||||
// Bob H say some freeware TT fonts have version 1 (eg, CALIGULA.TTF)
|
||||
// Bob H say some freeware TT fonts have version 1 (eg, CALIGULA.TTF)
|
||||
// so don't check subtable version. 21 Mar 2002 spec changes version to language.
|
||||
if (table_len < sizeof(*pTable) || be::swap(pTable->format) != 4) return false;
|
||||
const Sfnt::CmapSubTableFormat4 * pTable4 = reinterpret_cast<const Sfnt::CmapSubTableFormat4 *>(pCmapSubtable4);
|
||||
@ -958,7 +958,7 @@ gid16 CmapSubtable4Lookup(const void * pCmapSubtabel4, unsigned int nUnicodeId,
|
||||
const Sfnt::CmapSubTableFormat4 * pTable = reinterpret_cast<const Sfnt::CmapSubTableFormat4 *>(pCmapSubtabel4);
|
||||
|
||||
uint16 nSeg = be::swap(pTable->seg_count_x2) >> 1;
|
||||
|
||||
|
||||
uint16 n;
|
||||
const uint16 * pLeft, * pMid;
|
||||
uint16 cMid, chStart, chEnd;
|
||||
@ -1211,8 +1211,8 @@ unsigned int CmapSubtable12NextCodepoint(const void *pCmap310, unsigned int nUni
|
||||
Technically this method should return an unsigned long but it is unlikely the offset will
|
||||
exceed 2^31.
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
size_t LocaLookup(gid16 nGlyphId,
|
||||
const void * pLoca, size_t lLocaSize,
|
||||
size_t LocaLookup(gid16 nGlyphId,
|
||||
const void * pLoca, size_t lLocaSize,
|
||||
const void * pHead) // throw (std::out_of_range)
|
||||
{
|
||||
const Sfnt::FontHeader * pTable = reinterpret_cast<const Sfnt::FontHeader *>(pHead);
|
||||
@ -1252,8 +1252,8 @@ size_t LocaLookup(gid16 nGlyphId,
|
||||
void * GlyfLookup(const void * pGlyf, size_t nGlyfOffset, size_t nTableLen)
|
||||
{
|
||||
const uint8 * pByte = reinterpret_cast<const uint8 *>(pGlyf);
|
||||
if (nGlyfOffset + pByte < pByte || nGlyfOffset >= nTableLen - sizeof(Sfnt::Glyph))
|
||||
return NULL;
|
||||
if (OVERFLOW_OFFSET_CHECK(pByte, nGlyfOffset) || nGlyfOffset >= nTableLen - sizeof(Sfnt::Glyph))
|
||||
return NULL;
|
||||
return const_cast<uint8 *>(pByte + nGlyfOffset);
|
||||
}
|
||||
|
||||
@ -1261,7 +1261,7 @@ void * GlyfLookup(const void * pGlyf, size_t nGlyfOffset, size_t nTableLen)
|
||||
Get the bounding box coordinates for a simple glyf entry (non-composite).
|
||||
Return true if successful, false otherwise.
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool GlyfBox(const void * pSimpleGlyf, int & xMin, int & yMin,
|
||||
bool GlyfBox(const void * pSimpleGlyf, int & xMin, int & yMin,
|
||||
int & xMax, int & yMax)
|
||||
{
|
||||
const Sfnt::Glyph * pGlyph = reinterpret_cast<const Sfnt::Glyph *>(pSimpleGlyf);
|
||||
@ -1287,14 +1287,14 @@ int GlyfContourCount(const void * pSimpleGlyf)
|
||||
|
||||
/*----------------------------------------------------------------------------------------------
|
||||
Get the point numbers for the end points of the glyph contours for a simple
|
||||
glyf entry (non-composite).
|
||||
glyf entry (non-composite).
|
||||
cnPointsTotal - count of contours from GlyfContourCount(); (same as number of end points)
|
||||
prgnContourEndPoints - should point to a buffer large enough to hold cnPoints integers
|
||||
cnPoints - count of points placed in above range
|
||||
Return true if successful, false otherwise.
|
||||
False could indicate a multi-level composite glyphs.
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool GlyfContourEndPoints(const void * pSimpleGlyf, int * prgnContourEndPoint,
|
||||
bool GlyfContourEndPoints(const void * pSimpleGlyf, int * prgnContourEndPoint,
|
||||
int cnPointsTotal, int & cnPoints)
|
||||
{
|
||||
const Sfnt::SimpleGlyph * pGlyph = reinterpret_cast<const Sfnt::SimpleGlyph *>(pSimpleGlyf);
|
||||
@ -1316,19 +1316,19 @@ bool GlyfContourEndPoints(const void * pSimpleGlyf, int * prgnContourEndPoint,
|
||||
Get the points for a simple glyf entry (non-composite)
|
||||
cnPointsTotal - count of points from largest end point obtained from GlyfContourEndPoints
|
||||
prgnX & prgnY - should point to buffers large enough to hold cnPointsTotal integers
|
||||
The ranges are parallel so that coordinates for point(n) are found at offset n in both
|
||||
The ranges are parallel so that coordinates for point(n) are found at offset n in both
|
||||
ranges. This is raw point data with relative coordinates.
|
||||
prgbFlag - should point to a buffer a large enough to hold cnPointsTotal bytes
|
||||
This range is parallel to the prgnX & prgnY
|
||||
cnPoints - count of points placed in above ranges
|
||||
Return true if successful, false otherwise.
|
||||
Return true if successful, false otherwise.
|
||||
False could indicate a composite glyph
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool GlyfPoints(const void * pSimpleGlyf, int * prgnX, int * prgnY,
|
||||
bool GlyfPoints(const void * pSimpleGlyf, int * prgnX, int * prgnY,
|
||||
char * prgbFlag, int cnPointsTotal, int & cnPoints)
|
||||
{
|
||||
using namespace Sfnt;
|
||||
|
||||
|
||||
const Sfnt::SimpleGlyph * pGlyph = reinterpret_cast<const Sfnt::SimpleGlyph *>(pSimpleGlyf);
|
||||
int cContours = be::swap(pGlyph->number_of_contours);
|
||||
// return false for composite glyph
|
||||
@ -1341,7 +1341,7 @@ bool GlyfPoints(const void * pSimpleGlyf, int * prgnX, int * prgnY,
|
||||
// skip over bounding box data & point to byte count of instructions (hints)
|
||||
const uint8 * pbGlyph = reinterpret_cast<const uint8 *>
|
||||
(&pGlyph->end_pts_of_contours[cContours]);
|
||||
|
||||
|
||||
// skip over hints & point to first flag
|
||||
int cbHints = be::swap(*(uint16 *)pbGlyph);
|
||||
pbGlyph += sizeof(uint16);
|
||||
@ -1403,7 +1403,7 @@ bool GlyfPoints(const void * pSimpleGlyf, int * prgnX, int * prgnY,
|
||||
}
|
||||
iFlag++;
|
||||
}
|
||||
|
||||
|
||||
// load y coordinates
|
||||
iFlag = 0;
|
||||
while (iFlag < cPts)
|
||||
@ -1432,7 +1432,7 @@ bool GlyfPoints(const void * pSimpleGlyf, int * prgnX, int * prgnY,
|
||||
}
|
||||
iFlag++;
|
||||
}
|
||||
|
||||
|
||||
cnPoints = cPts;
|
||||
return true;
|
||||
}
|
||||
@ -1441,16 +1441,16 @@ bool GlyfPoints(const void * pSimpleGlyf, int * prgnX, int * prgnY,
|
||||
Fill prgnCompId with the component Glyph IDs from pSimpleGlyf.
|
||||
Client must allocate space before calling.
|
||||
pSimpleGlyf - assumed to point to a composite glyph
|
||||
cCompIdTotal - the number of elements in prgnCompId
|
||||
cCompIdTotal - the number of elements in prgnCompId
|
||||
cCompId - the total number of Glyph IDs stored in prgnCompId
|
||||
Return true if successful, false otherwise
|
||||
False could indicate a non-composite glyph or the input array was not big enough
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool GetComponentGlyphIds(const void * pSimpleGlyf, int * prgnCompId,
|
||||
bool GetComponentGlyphIds(const void * pSimpleGlyf, int * prgnCompId,
|
||||
size_t cnCompIdTotal, size_t & cnCompId)
|
||||
{
|
||||
using namespace Sfnt;
|
||||
|
||||
|
||||
if (GlyfContourCount(pSimpleGlyf) >= 0)
|
||||
return false;
|
||||
|
||||
@ -1460,13 +1460,13 @@ bool GetComponentGlyphIds(const void * pSimpleGlyf, int * prgnCompId,
|
||||
|
||||
uint16 GlyphFlags;
|
||||
size_t iCurrentComp = 0;
|
||||
do
|
||||
do
|
||||
{
|
||||
GlyphFlags = be::swap(*((uint16 *)pbGlyph));
|
||||
pbGlyph += sizeof(uint16);
|
||||
prgnCompId[iCurrentComp++] = be::swap(*((uint16 *)pbGlyph));
|
||||
pbGlyph += sizeof(uint16);
|
||||
if (iCurrentComp >= cnCompIdTotal)
|
||||
if (iCurrentComp >= cnCompIdTotal)
|
||||
return false;
|
||||
int nOffset = 0;
|
||||
nOffset += GlyphFlags & CompoundGlyph::Arg1Arg2Words ? 4 : 2;
|
||||
@ -1495,7 +1495,7 @@ bool GetComponentPlacement(const void * pSimpleGlyf, int nCompId,
|
||||
bool fOffset, int & a, int & b)
|
||||
{
|
||||
using namespace Sfnt;
|
||||
|
||||
|
||||
if (GlyfContourCount(pSimpleGlyf) >= 0)
|
||||
return false;
|
||||
|
||||
@ -1504,7 +1504,7 @@ bool GetComponentPlacement(const void * pSimpleGlyf, int nCompId,
|
||||
const uint8 * pbGlyph = reinterpret_cast<const uint8 *>(&pGlyph->end_pts_of_contours[0]);
|
||||
|
||||
uint16 GlyphFlags;
|
||||
do
|
||||
do
|
||||
{
|
||||
GlyphFlags = be::swap(*((uint16 *)pbGlyph));
|
||||
pbGlyph += sizeof(uint16);
|
||||
@ -1548,19 +1548,19 @@ bool GetComponentPlacement(const void * pSimpleGlyf, int nCompId,
|
||||
pSimpleGlyph - assumed to point to a composite glyph
|
||||
nCompId - glyph id for component of interest
|
||||
flt11, flt11, flt11, flt11 - a 2x2 matrix giving the transform
|
||||
bTransOffset - whether to transform the offset from above method
|
||||
bTransOffset - whether to transform the offset from above method
|
||||
The spec is unclear about the meaning of this flag
|
||||
Currently - initialize to true for MS rasterizer and false for Mac rasterizer, then
|
||||
on return it will indicate whether transform should apply to offset (MSDN CD 10/99)
|
||||
Return true if successful, false otherwise
|
||||
False could indicate a non-composite glyph or that component wasn't found
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool GetComponentTransform(const void * pSimpleGlyf, int nCompId,
|
||||
float & flt11, float & flt12, float & flt21, float & flt22,
|
||||
bool GetComponentTransform(const void * pSimpleGlyf, int nCompId,
|
||||
float & flt11, float & flt12, float & flt21, float & flt22,
|
||||
bool & fTransOffset)
|
||||
{
|
||||
using namespace Sfnt;
|
||||
|
||||
|
||||
if (GlyfContourCount(pSimpleGlyf) >= 0)
|
||||
return false;
|
||||
|
||||
@ -1569,7 +1569,7 @@ bool GetComponentTransform(const void * pSimpleGlyf, int nCompId,
|
||||
const uint8 * pbGlyph = reinterpret_cast<const uint8 *>(&pGlyph->end_pts_of_contours[0]);
|
||||
|
||||
uint16 GlyphFlags;
|
||||
do
|
||||
do
|
||||
{
|
||||
GlyphFlags = be::swap(*((uint16 *)pbGlyph));
|
||||
pbGlyph += sizeof(uint16);
|
||||
@ -1579,7 +1579,7 @@ bool GetComponentTransform(const void * pSimpleGlyf, int nCompId,
|
||||
pbGlyph += GlyphFlags & CompoundGlyph::Arg1Arg2Words ? 4 : 2; // skip over placement data
|
||||
|
||||
if (fTransOffset) // MS rasterizer
|
||||
fTransOffset = !(GlyphFlags & CompoundGlyph::UnscaledOffset);
|
||||
fTransOffset = !(GlyphFlags & CompoundGlyph::UnscaledOffset);
|
||||
else // Apple rasterizer
|
||||
fTransOffset = (GlyphFlags & CompoundGlyph::ScaledOffset) != 0;
|
||||
|
||||
@ -1644,13 +1644,13 @@ bool GetComponentTransform(const void * pSimpleGlyf, int nCompId,
|
||||
Since this method doesn't check for spaces, it is good to call IsSpace before using it.
|
||||
Return NULL on error.
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
void * GlyfLookup(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
void * GlyfLookup(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
size_t lGlyfSize, size_t lLocaSize, const void * pHead)
|
||||
{
|
||||
// test for valid glyph id
|
||||
// CheckTable verifies the index_to_loc_format is valid
|
||||
|
||||
const Sfnt::FontHeader * pTable
|
||||
|
||||
const Sfnt::FontHeader * pTable
|
||||
= reinterpret_cast<const Sfnt::FontHeader *>(pHead);
|
||||
|
||||
if (be::swap(pTable->index_to_loc_format) == Sfnt::FontHeader::ShortIndexLocFormat)
|
||||
@ -1670,7 +1670,7 @@ void * GlyfLookup(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
}
|
||||
}
|
||||
|
||||
long lGlyfOffset = LocaLookup(nGlyphId, pLoca, lLocaSize, pHead);
|
||||
size_t lGlyfOffset = LocaLookup(nGlyphId, pLoca, lLocaSize, pHead);
|
||||
void * pSimpleGlyf = GlyfLookup(pGlyf, lGlyfOffset, lGlyfSize); // invalid loca offset returns null
|
||||
return pSimpleGlyf;
|
||||
}
|
||||
@ -1683,7 +1683,7 @@ void * GlyfLookup(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
bool IsSpace(gid16 nGlyphId, const void * pLoca, size_t lLocaSize, const void * pHead)
|
||||
{
|
||||
size_t lGlyfOffset = LocaLookup(nGlyphId, pLoca, lLocaSize, pHead);
|
||||
|
||||
|
||||
// the +1 should always work because there is a sentinel value at the end of the loca table
|
||||
size_t lNextGlyfOffset = LocaLookup(nGlyphId + 1, pLoca, lLocaSize, pHead);
|
||||
|
||||
@ -1693,7 +1693,7 @@ bool IsSpace(gid16 nGlyphId, const void * pLoca, size_t lLocaSize, const void *
|
||||
/*----------------------------------------------------------------------------------------------
|
||||
Determine if a particular Glyph ID is a multi-level composite.
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool IsDeepComposite(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
bool IsDeepComposite(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
size_t lGlyfSize, long lLocaSize, const void * pHead)
|
||||
{
|
||||
if (IsSpace(nGlyphId, pLoca, lLocaSize, pHead)) {return false;}
|
||||
@ -1714,7 +1714,7 @@ bool IsDeepComposite(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
|
||||
for (size_t i = 0; i < cCompId; i++)
|
||||
{
|
||||
pSimpleGlyf = GlyfLookup(static_cast<gid16>(rgnCompId[i]),
|
||||
pSimpleGlyf = GlyfLookup(static_cast<gid16>(rgnCompId[i]),
|
||||
pGlyf, pLoca, lGlyfSize, lLocaSize, pHead);
|
||||
if (pSimpleGlyf == NULL) {return false;}
|
||||
|
||||
@ -1731,7 +1731,7 @@ bool IsDeepComposite(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
Return true if successful, false otherwise. On false, all point values will be INT_MIN
|
||||
False may indicate a white space glyph
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool GlyfBox(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
bool GlyfBox(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
size_t lGlyfSize, size_t lLocaSize, const void * pHead, int & xMin, int & yMin, int & xMax, int & yMax)
|
||||
{
|
||||
xMin = yMin = xMax = yMax = INT_MIN;
|
||||
@ -1750,7 +1750,7 @@ bool GlyfBox(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
Return true if successful, false otherwise. On false, cnContours will be INT_MIN
|
||||
False may indicate a white space glyph or a multi-level composite glyph.
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool GlyfContourCount(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
bool GlyfContourCount(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
size_t lGlyfSize, size_t lLocaSize, const void * pHead, size_t & cnContours)
|
||||
{
|
||||
cnContours = static_cast<size_t>(INT_MIN);
|
||||
@ -1766,7 +1766,7 @@ bool GlyfContourCount(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
cnContours = size_t(cRtnContours);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
//handle composite glyphs
|
||||
|
||||
int rgnCompId[kMaxGlyphComponents]; // assumes no glyph will be made of more than 8 components
|
||||
@ -1781,11 +1781,11 @@ bool GlyfContourCount(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
for (size_t i = 0; i < cCompId; i++)
|
||||
{
|
||||
if (IsSpace(static_cast<gid16>(rgnCompId[i]), pLoca, lLocaSize, pHead)) {return false;}
|
||||
pSimpleGlyf = GlyfLookup(static_cast<gid16>(rgnCompId[i]),
|
||||
pSimpleGlyf = GlyfLookup(static_cast<gid16>(rgnCompId[i]),
|
||||
pGlyf, pLoca, lGlyfSize, lLocaSize, pHead);
|
||||
if (pSimpleGlyf == 0) {return false;}
|
||||
// return false on multi-level composite
|
||||
if ((cTmp = GlyfContourCount(pSimpleGlyf)) < 0)
|
||||
if ((cTmp = GlyfContourCount(pSimpleGlyf)) < 0)
|
||||
return false;
|
||||
cRtnContours += cTmp;
|
||||
}
|
||||
@ -1795,7 +1795,7 @@ bool GlyfContourCount(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
}
|
||||
|
||||
/*----------------------------------------------------------------------------------------------
|
||||
Get the point numbers for the end points of the glyph contours based on the given tables
|
||||
Get the point numbers for the end points of the glyph contours based on the given tables
|
||||
and Glyph ID
|
||||
Handles both simple and composite glyphs.
|
||||
cnPoints - count of contours from GlyfContourCount (same as number of end points)
|
||||
@ -1803,7 +1803,7 @@ bool GlyfContourCount(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
Return true if successful, false otherwise. On false, all end points are INT_MIN
|
||||
False may indicate a white space glyph or a multi-level composite glyph.
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool GlyfContourEndPoints(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
bool GlyfContourEndPoints(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
size_t lGlyfSize, size_t lLocaSize, const void * pHead,
|
||||
int * prgnContourEndPoint, size_t cnPoints)
|
||||
{
|
||||
@ -1819,9 +1819,9 @@ bool GlyfContourEndPoints(gid16 nGlyphId, const void * pGlyf, const void * pLoca
|
||||
int cActualPts = 0;
|
||||
if (cContours > 0)
|
||||
return GlyfContourEndPoints(pSimpleGlyf, prgnContourEndPoint, cnPoints, cActualPts);
|
||||
|
||||
|
||||
// handle composite glyphs
|
||||
|
||||
|
||||
int rgnCompId[kMaxGlyphComponents]; // assumes no glyph will be made of more than 8 components
|
||||
size_t cCompIdTotal = kMaxGlyphComponents;
|
||||
size_t cCompId = 0;
|
||||
@ -1858,21 +1858,21 @@ bool GlyfContourEndPoints(gid16 nGlyphId, const void * pGlyf, const void * pLoca
|
||||
Handles both simple and composite glyphs.
|
||||
cnPoints - count of points from largest end point obtained from GlyfContourEndPoints
|
||||
prgnX & prgnY - should point to buffers large enough to hold cnPoints integers
|
||||
The ranges are parallel so that coordinates for point(n) are found at offset n in
|
||||
The ranges are parallel so that coordinates for point(n) are found at offset n in
|
||||
both ranges. These points are in absolute coordinates.
|
||||
prgfOnCurve - should point to a buffer a large enough to hold cnPoints bytes (bool)
|
||||
This range is parallel to the prgnX & prgnY
|
||||
Return true if successful, false otherwise. On false, all points may be INT_MIN
|
||||
False may indicate a white space glyph, a multi-level composite, or a corrupt font
|
||||
It's not clear from the TTF spec when the transforms should be applied. Should the
|
||||
transform be done before or after attachment point calcs? (current code - before)
|
||||
Should the transform be applied to other offsets? (currently - no; however commented
|
||||
out code is in place so that if CompoundGlyph::UnscaledOffset on the MS rasterizer is
|
||||
clear (typical) then yes, and if CompoundGlyph::ScaledOffset on the Apple rasterizer is
|
||||
It's not clear from the TTF spec when the transforms should be applied. Should the
|
||||
transform be done before or after attachment point calcs? (current code - before)
|
||||
Should the transform be applied to other offsets? (currently - no; however commented
|
||||
out code is in place so that if CompoundGlyph::UnscaledOffset on the MS rasterizer is
|
||||
clear (typical) then yes, and if CompoundGlyph::ScaledOffset on the Apple rasterizer is
|
||||
clear (typical?) then no). See GetComponentTransform.
|
||||
It's also unclear where point numbering with attachment poinst starts
|
||||
(currently - first point number is relative to whole glyph, second point number is
|
||||
relative to current glyph).
|
||||
It's also unclear where point numbering with attachment poinst starts
|
||||
(currently - first point number is relative to whole glyph, second point number is
|
||||
relative to current glyph).
|
||||
----------------------------------------------------------------------------------------------*/
|
||||
bool GlyfPoints(gid16 nGlyphId, const void * pGlyf,
|
||||
const void * pLoca, size_t lGlyfSize, size_t lLocaSize, const void * pHead,
|
||||
@ -1882,7 +1882,7 @@ bool GlyfPoints(gid16 nGlyphId, const void * pGlyf,
|
||||
memset(prgnX, 0x7F, cnPoints * sizeof(int));
|
||||
memset(prgnY, 0x7F, cnPoints * sizeof(int));
|
||||
|
||||
if (IsSpace(nGlyphId, pLoca, lLocaSize, pHead))
|
||||
if (IsSpace(nGlyphId, pLoca, lLocaSize, pHead))
|
||||
return false;
|
||||
|
||||
void * pSimpleGlyf = GlyfLookup(nGlyphId, pGlyf, pLoca, lGlyfSize, lLocaSize, pHead);
|
||||
@ -1900,7 +1900,7 @@ bool GlyfPoints(gid16 nGlyphId, const void * pGlyf,
|
||||
return true;
|
||||
}
|
||||
|
||||
// handle composite glyphs
|
||||
// handle composite glyphs
|
||||
int rgnCompId[kMaxGlyphComponents]; // assumes no glyph will be made of more than 8 components
|
||||
size_t cCompIdTotal = kMaxGlyphComponents;
|
||||
size_t cCompId = 0;
|
||||
@ -1924,12 +1924,12 @@ bool GlyfPoints(gid16 nGlyphId, const void * pGlyf,
|
||||
void * pCompGlyf = GlyfLookup(static_cast<gid16>(rgnCompId[i]), pGlyf, pLoca, lGlyfSize, lLocaSize, pHead);
|
||||
if (pCompGlyf == NULL) {return false;}
|
||||
// returns false on multi-level composite
|
||||
if (!GlyfPoints(pCompGlyf, prgnCurrentX, prgnCurrentY, prgbCurrentFlag,
|
||||
if (!GlyfPoints(pCompGlyf, prgnCurrentX, prgnCurrentY, prgbCurrentFlag,
|
||||
cCurrentPoints, cActualPts))
|
||||
return false;
|
||||
return false;
|
||||
if (!GetComponentPlacement(pSimpleGlyf, rgnCompId[i], fOffset, a, b))
|
||||
return false;
|
||||
if (!GetComponentTransform(pSimpleGlyf, rgnCompId[i],
|
||||
if (!GetComponentTransform(pSimpleGlyf, rgnCompId[i],
|
||||
flt11, flt12, flt21, flt22, fTransOff))
|
||||
return false;
|
||||
bool fIdTrans = flt11 == 1.0 && flt12 == 0.0 && flt21 == 0.0 && flt22 == 1.0;
|
||||
@ -1948,18 +1948,18 @@ bool GlyfPoints(gid16 nGlyphId, const void * pGlyf,
|
||||
prgnCurrentX[j] = (int)(x * flt11 + y * flt12);
|
||||
prgnCurrentY[j] = (int)(x * flt21 + y * flt22);
|
||||
}
|
||||
|
||||
|
||||
// apply placement - see main method note above
|
||||
int nXOff, nYOff;
|
||||
if (fOffset) // explicit x & y offsets
|
||||
{
|
||||
{
|
||||
/* ignore fTransOff for now
|
||||
if (fTransOff && !fIdTrans)
|
||||
if (fTransOff && !fIdTrans)
|
||||
{ // transform x & y offsets
|
||||
nXOff = (int)(a * flt11 + b * flt12);
|
||||
nYOff = (int)(a * flt21 + b * flt22);
|
||||
}
|
||||
else */
|
||||
else */
|
||||
{ // don't transform offset
|
||||
nXOff = a;
|
||||
nYOff = b;
|
||||
@ -2004,7 +2004,7 @@ bool SimplifyFlags(char * prgbFlags, int cnPoints)
|
||||
|
||||
/*----------------------------------------------------------------------------------------------
|
||||
Convert relative point coordinates to absolute coordinates
|
||||
Points are stored in the font such that they are offsets from one another except for the
|
||||
Points are stored in the font such that they are offsets from one another except for the
|
||||
first point of a glyph.
|
||||
---------------------------------------------------------------------------------------------*/
|
||||
bool CalcAbsolutePoints(int * prgnX, int * prgnY, int cnPoints)
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -28,8 +28,8 @@ of the License or (at your option) any later version.
|
||||
// Author: Tim Eves
|
||||
|
||||
// Build either this interpreter or the direct_machine implementation.
|
||||
// The call threaded interpreter is portable across compilers and
|
||||
// architectures as well as being useful to debug (you can set breakpoints on
|
||||
// The call threaded interpreter is portable across compilers and
|
||||
// architectures as well as being useful to debug (you can set breakpoints on
|
||||
// opcodes) but is slower that the direct threaded interpreter by a factor of 2
|
||||
|
||||
#include <cassert>
|
||||
@ -117,7 +117,7 @@ Machine::stack_t Machine::run(const instr * program,
|
||||
* const sb = sp;
|
||||
regbank reg = {*map, map, _map, _map.begin()+_map.context(), ip, _map.dir(), 0, _status};
|
||||
|
||||
// Run the program
|
||||
// Run the program
|
||||
while ((reinterpret_cast<ip_t>(*++ip))(dp, sp, sb, reg)) {}
|
||||
const stack_t ret = sp == _stack+STACK_GUARD+1 ? *sp-- : 0;
|
||||
|
||||
@ -136,5 +136,3 @@ const opcode_t * Machine::getOpcodeTable() throw()
|
||||
{
|
||||
return opcode_table;
|
||||
}
|
||||
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -28,12 +28,12 @@ of the License or (at your option) any later version.
|
||||
// Author: Tim Eves
|
||||
|
||||
// Build either this interpreter or the call_machine implementation.
|
||||
// The direct threaded interpreter is relies upon a gcc feature called
|
||||
// labels-as-values so is only portable to compilers that support the
|
||||
// The direct threaded interpreter is relies upon a gcc feature called
|
||||
// labels-as-values so is only portable to compilers that support the
|
||||
// extension (gcc only as far as I know) however it should build on any
|
||||
// architecture gcc supports.
|
||||
// This is twice as fast as the call threaded model and is likely faster on
|
||||
// inorder processors with short pipelines and little branch prediction such
|
||||
// architecture gcc supports.
|
||||
// This is twice as fast as the call threaded model and is likely faster on
|
||||
// inorder processors with short pipelines and little branch prediction such
|
||||
// as the ARM and possibly Atom chips.
|
||||
|
||||
|
||||
@ -65,7 +65,7 @@ const void * direct_run(const bool get_table_mode,
|
||||
Machine::status_t & status,
|
||||
SlotMap * __smap=0)
|
||||
{
|
||||
// We need to define and return to opcode table from within this function
|
||||
// We need to define and return to opcode table from within this function
|
||||
// other inorder to take the addresses of the instruction bodies.
|
||||
#include "inc/opcode_table.h"
|
||||
if (get_table_mode)
|
||||
@ -83,13 +83,13 @@ const void * direct_run(const bool get_table_mode,
|
||||
* const mapb = smap.begin()+smap.context();
|
||||
uint8 dir = _dir;
|
||||
int8 flags = 0;
|
||||
|
||||
|
||||
// start the program
|
||||
goto **ip;
|
||||
|
||||
// Pull in the opcode definitions
|
||||
#include "inc/opcodes.h"
|
||||
|
||||
|
||||
end:
|
||||
__map = map;
|
||||
*__map = is;
|
||||
@ -111,11 +111,10 @@ Machine::stack_t Machine::run(const instr * program,
|
||||
slotref * & is)
|
||||
{
|
||||
assert(program != 0);
|
||||
|
||||
|
||||
const stack_t *sp = static_cast<const stack_t *>(
|
||||
direct_run(false, program, data, _stack, is, _map.dir(), _status, &_map));
|
||||
const stack_t ret = sp == _stack+STACK_GUARD+1 ? *sp-- : 0;
|
||||
check_final_stack(sp);
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
#
|
||||
# You should also have received a copy of the GNU Lesser General Public
|
||||
# License along with this library in the file named "LICENSE".
|
||||
# If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
# Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
# If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
# Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
# internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
#
|
||||
# Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -63,9 +63,6 @@ $(_NS)_SOURCES = \
|
||||
$($(_NS)_BASE)/src/NameTable.cpp \
|
||||
$($(_NS)_BASE)/src/Pass.cpp \
|
||||
$($(_NS)_BASE)/src/Position.cpp \
|
||||
$($(_NS)_BASE)/src/SegCache.cpp \
|
||||
$($(_NS)_BASE)/src/SegCacheEntry.cpp \
|
||||
$($(_NS)_BASE)/src/SegCacheStore.cpp \
|
||||
$($(_NS)_BASE)/src/Segment.cpp \
|
||||
$($(_NS)_BASE)/src/Silf.cpp \
|
||||
$($(_NS)_BASE)/src/Slot.cpp \
|
||||
@ -104,9 +101,6 @@ $(_NS)_PRIVATE_HEADERS = \
|
||||
$($(_NS)_BASE)/src/inc/Pass.h \
|
||||
$($(_NS)_BASE)/src/inc/Position.h \
|
||||
$($(_NS)_BASE)/src/inc/Rule.h \
|
||||
$($(_NS)_BASE)/src/inc/SegCache.h \
|
||||
$($(_NS)_BASE)/src/inc/SegCacheEntry.h \
|
||||
$($(_NS)_BASE)/src/inc/SegCacheStore.h \
|
||||
$($(_NS)_BASE)/src/inc/Segment.h \
|
||||
$($(_NS)_BASE)/src/inc/Silf.h \
|
||||
$($(_NS)_BASE)/src/inc/Slot.h \
|
||||
@ -120,4 +114,3 @@ $(_NS)_PUBLIC_HEADERS = \
|
||||
$($(_NS)_BASE)/include/graphite2/Log.h \
|
||||
$($(_NS)_BASE)/include/graphite2/Segment.h \
|
||||
$($(_NS)_BASE)/include/graphite2/Types.h
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -28,7 +28,6 @@ of the License or (at your option) any later version.
|
||||
#include "inc/Face.h"
|
||||
#include "inc/FileFace.h"
|
||||
#include "inc/GlyphCache.h"
|
||||
#include "inc/CachedFace.h"
|
||||
#include "inc/CmapCache.h"
|
||||
#include "inc/Silf.h"
|
||||
#include "inc/json.h"
|
||||
@ -47,8 +46,7 @@ namespace
|
||||
telemetry::category _misc_cat(face.tele.misc);
|
||||
#endif
|
||||
Face::Table silf(face, Tag::Silf, 0x00050000);
|
||||
if (silf) options &= ~gr_face_dumbRendering;
|
||||
else if (!(options & gr_face_dumbRendering))
|
||||
if (!silf)
|
||||
return false;
|
||||
|
||||
if (!face.readGlyphs(options))
|
||||
@ -74,14 +72,24 @@ namespace
|
||||
return true;
|
||||
}
|
||||
else
|
||||
return options & gr_face_dumbRendering;
|
||||
return false;
|
||||
}
|
||||
|
||||
inline
|
||||
uint32 zeropad(const uint32 x)
|
||||
{
|
||||
if (x == 0x20202020) return 0;
|
||||
if ((x & 0x00FFFFFF) == 0x00202020) return x & 0xFF000000;
|
||||
if ((x & 0x0000FFFF) == 0x00002020) return x & 0xFFFF0000;
|
||||
if ((x & 0x000000FF) == 0x00000020) return x & 0xFFFFFF00;
|
||||
return x;
|
||||
}
|
||||
}
|
||||
|
||||
extern "C" {
|
||||
|
||||
gr_face* gr_make_face_with_ops(const void* appFaceHandle/*non-NULL*/, const gr_face_ops *ops, unsigned int faceOptions)
|
||||
//the appFaceHandle must stay alive all the time when the gr_face is alive. When finished with the gr_face, call destroy_face
|
||||
//the appFaceHandle must stay alive all the time when the gr_face is alive. When finished with the gr_face, call destroy_face
|
||||
{
|
||||
if (ops == 0) return 0;
|
||||
|
||||
@ -99,56 +107,41 @@ gr_face* gr_make_face(const void* appFaceHandle/*non-NULL*/, gr_get_table_fn tab
|
||||
return gr_make_face_with_ops(appFaceHandle, &ops, faceOptions);
|
||||
}
|
||||
|
||||
#ifndef GRAPHITE2_NSEGCACHE
|
||||
gr_face* gr_make_face_with_seg_cache_and_ops(const void* appFaceHandle/*non-NULL*/, const gr_face_ops *ops, unsigned int cacheSize, unsigned int faceOptions)
|
||||
//the appFaceHandle must stay alive all the time when the GrFace is alive. When finished with the GrFace, call destroy_face
|
||||
|
||||
gr_face* gr_make_face_with_seg_cache_and_ops(const void* appFaceHandle/*non-NULL*/, const gr_face_ops *ops, unsigned int , unsigned int faceOptions)
|
||||
{
|
||||
if (ops == 0) return 0;
|
||||
|
||||
CachedFace *res = new CachedFace(appFaceHandle, *ops);
|
||||
if (res && load_face(*res, faceOptions)
|
||||
&& res->setupCache(cacheSize))
|
||||
return static_cast<gr_face *>(static_cast<Face *>(res));
|
||||
|
||||
delete res;
|
||||
return 0;
|
||||
return gr_make_face_with_ops(appFaceHandle, ops, faceOptions);
|
||||
}
|
||||
|
||||
gr_face* gr_make_face_with_seg_cache(const void* appFaceHandle/*non-NULL*/, gr_get_table_fn getTable, unsigned int cacheSize, unsigned int faceOptions)
|
||||
gr_face* gr_make_face_with_seg_cache(const void* appFaceHandle/*non-NULL*/, gr_get_table_fn tablefn, unsigned int, unsigned int faceOptions)
|
||||
{
|
||||
const gr_face_ops ops = {sizeof(gr_face_ops), getTable, NULL};
|
||||
return gr_make_face_with_seg_cache_and_ops(appFaceHandle, &ops, cacheSize, faceOptions);
|
||||
const gr_face_ops ops = {sizeof(gr_face_ops), tablefn, NULL};
|
||||
return gr_make_face_with_ops(appFaceHandle, &ops, faceOptions);
|
||||
}
|
||||
#endif
|
||||
|
||||
gr_uint32 gr_str_to_tag(const char *str)
|
||||
{
|
||||
uint32 res = 0;
|
||||
int i = strlen(str);
|
||||
if (i > 4) i = 4;
|
||||
while (--i >= 0)
|
||||
res = (res >> 8) + (str[i] << 24);
|
||||
switch(max(strlen(str),size_t(4)))
|
||||
{
|
||||
case 4: res |= str[3]; GR_FALLTHROUGH;
|
||||
case 3: res |= str[2] << 8; GR_FALLTHROUGH;
|
||||
case 2: res |= str[1] << 16; GR_FALLTHROUGH;
|
||||
case 1: res |= str[0] << 24; GR_FALLTHROUGH;
|
||||
default: break;
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
void gr_tag_to_str(gr_uint32 tag, char *str)
|
||||
{
|
||||
int i = 4;
|
||||
while (--i >= 0)
|
||||
{
|
||||
str[i] = tag & 0xFF;
|
||||
tag >>= 8;
|
||||
}
|
||||
}
|
||||
if (!str) return;
|
||||
|
||||
inline
|
||||
uint32 zeropad(const uint32 x)
|
||||
{
|
||||
if (x == 0x20202020) return 0;
|
||||
if ((x & 0x00FFFFFF) == 0x00202020) return x & 0xFF000000;
|
||||
if ((x & 0x0000FFFF) == 0x00002020) return x & 0xFFFF0000;
|
||||
if ((x & 0x000000FF) == 0x00000020) return x & 0xFFFFFF00;
|
||||
return x;
|
||||
*str++ = char(tag >> 24);
|
||||
*str++ = char(tag >> 16);
|
||||
*str++ = char(tag >> 8);
|
||||
*str++ = char(tag);
|
||||
*str = '\0';
|
||||
}
|
||||
|
||||
gr_feature_val* gr_face_featureval_for_lang(const gr_face* pFace, gr_uint32 langname/*0 means clone default*/) //clones the features. if none for language, clones the default
|
||||
@ -246,37 +239,18 @@ gr_face* gr_make_file_face(const char *filename, unsigned int faceOptions)
|
||||
return pRes;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//error when loading
|
||||
|
||||
delete pFileFace;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
#ifndef GRAPHITE2_NSEGCACHE
|
||||
gr_face* gr_make_file_face_with_seg_cache(const char* filename, unsigned int segCacheMaxSize, unsigned int faceOptions) //returns NULL on failure. //TBD better error handling
|
||||
gr_face* gr_make_file_face_with_seg_cache(const char* filename, unsigned int, unsigned int faceOptions) //returns NULL on failure. //TBD better error handling
|
||||
//when finished with, call destroy_face
|
||||
{
|
||||
FileFace* pFileFace = new FileFace(filename);
|
||||
if (*pFileFace)
|
||||
{
|
||||
gr_face * pRes = gr_make_face_with_seg_cache_and_ops(pFileFace, &FileFace::ops, segCacheMaxSize, faceOptions);
|
||||
if (pRes)
|
||||
{
|
||||
pRes->takeFileFace(pFileFace); //takes ownership
|
||||
return pRes;
|
||||
}
|
||||
}
|
||||
|
||||
//error when loading
|
||||
|
||||
delete pFileFace;
|
||||
return NULL;
|
||||
return gr_make_file_face(filename, faceOptions);
|
||||
}
|
||||
#endif
|
||||
#endif //!GRAPHITE2_NFILEFACE
|
||||
|
||||
|
||||
} // extern "C"
|
||||
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -46,7 +46,7 @@ gr_uint16 gr_fref_feature_value(const gr_feature_ref* pfeatureref, const gr_feat
|
||||
int gr_fref_set_feature_value(const gr_feature_ref* pfeatureref, gr_uint16 val, gr_feature_val* pDest)
|
||||
{
|
||||
if (!pfeatureref || !pDest) return 0;
|
||||
|
||||
|
||||
return pfeatureref->applyValToFeature(val, *pDest);
|
||||
}
|
||||
|
||||
@ -55,7 +55,7 @@ gr_uint32 gr_fref_id(const gr_feature_ref* pfeatureref) //returns 0 if pointe
|
||||
{
|
||||
if (!pfeatureref)
|
||||
return 0;
|
||||
|
||||
|
||||
return pfeatureref->getId();
|
||||
}
|
||||
|
||||
@ -125,10 +125,10 @@ void gr_label_destroy(void * label)
|
||||
}
|
||||
|
||||
gr_feature_val* gr_featureval_clone(const gr_feature_val* pfeatures/*may be NULL*/)
|
||||
{ //When finished with the Features, call features_destroy
|
||||
{ //When finished with the Features, call features_destroy
|
||||
return static_cast<gr_feature_val*>(pfeatures ? new Features(*pfeatures) : new Features);
|
||||
}
|
||||
|
||||
|
||||
void gr_featureval_destroy(gr_feature_val *p)
|
||||
{
|
||||
delete static_cast<Features*>(p);
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -46,7 +46,7 @@ gr_font* gr_make_font(float ppm/*pixels per em*/, const gr_face *face)
|
||||
|
||||
|
||||
gr_font* gr_make_font_with_ops(float ppm/*pixels per em*/, const void* appFontHandle/*non-NULL*/, const gr_font_ops * font_ops, const gr_face * face/*needed for scaling*/)
|
||||
{ //the appFontHandle must stay alive all the time when the gr_font is alive. When finished with the gr_font, call destroy_gr_font
|
||||
{ //the appFontHandle must stay alive all the time when the gr_font is alive. When finished with the gr_font, call destroy_gr_font
|
||||
if (face == 0 || ppm <= 0) return 0;
|
||||
|
||||
Font * const res = new Font(ppm, *face, appFontHandle, font_ops);
|
||||
@ -72,7 +72,3 @@ void gr_font_destroy(gr_font *font)
|
||||
|
||||
|
||||
} // extern "C"
|
||||
|
||||
|
||||
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -225,7 +225,7 @@ json & graphite2::operator << (json & j, const dslot & ds) throw()
|
||||
}
|
||||
if (cslot)
|
||||
{
|
||||
// Note: the reason for using Positions to lump together related attributes is to make the
|
||||
// Note: the reason for using Positions to lump together related attributes is to make the
|
||||
// JSON output slightly more compact.
|
||||
j << "collision" << json::flat << json::object
|
||||
// << "shift" << cslot->shift() -- not used pass level, only within the collision routine itself
|
||||
@ -252,14 +252,14 @@ json & graphite2::operator << (json & j, const dslot & ds) throw()
|
||||
graphite2::objectid::objectid(const dslot & ds) throw()
|
||||
{
|
||||
const Slot * const p = ds.second;
|
||||
uint32 s = reinterpret_cast<size_t>(p);
|
||||
uint32 s = uint32(reinterpret_cast<size_t>(p));
|
||||
sprintf(name, "%.4x-%.2x-%.4hx", uint16(s >> 16), uint16(p ? p->userAttrs()[ds.first->silf()->numUser()] : 0), uint16(s));
|
||||
name[sizeof name-1] = 0;
|
||||
}
|
||||
|
||||
graphite2::objectid::objectid(const Segment * const p) throw()
|
||||
{
|
||||
uint32 s = reinterpret_cast<size_t>(p);
|
||||
uint32 s = uint32(reinterpret_cast<size_t>(p));
|
||||
sprintf(name, "%.4x-%.2x-%.4hx", uint16(s >> 16), 0, uint16(s));
|
||||
name[sizeof name-1] = 0;
|
||||
}
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -30,7 +30,7 @@ of the License or (at your option) any later version.
|
||||
|
||||
using namespace graphite2;
|
||||
|
||||
namespace
|
||||
namespace
|
||||
{
|
||||
|
||||
gr_segment* makeAndInitialize(const Font *font, const Face *face, uint32 script, const Features* pFeats/*must not be NULL*/, gr_encform enc, const void* pStart, size_t nChars, int dir)
|
||||
@ -42,7 +42,7 @@ namespace
|
||||
// if (!font) return NULL;
|
||||
Segment* pRes=new Segment(nChars, face, script, dir);
|
||||
|
||||
|
||||
|
||||
if (!pRes->read_text(face, pFeats, enc, pStart, nChars) || !pRes->runGraphite())
|
||||
{
|
||||
delete pRes;
|
||||
@ -53,34 +53,37 @@ namespace
|
||||
return static_cast<gr_segment*>(pRes);
|
||||
}
|
||||
|
||||
template <typename utf_iter>
|
||||
inline size_t count_unicode_chars(utf_iter first, const utf_iter last, const void **error)
|
||||
{
|
||||
size_t n_chars = 0;
|
||||
uint32 usv = 0;
|
||||
|
||||
if (last)
|
||||
{
|
||||
if (!first.validate(last))
|
||||
{
|
||||
if (error) *error = last - 1;
|
||||
return 0;
|
||||
}
|
||||
for (;first != last; ++first, ++n_chars)
|
||||
if ((usv = *first) == 0 || first.error()) break;
|
||||
}
|
||||
else
|
||||
{
|
||||
while ((usv = *first) != 0 && !first.error())
|
||||
{
|
||||
++first;
|
||||
++n_chars;
|
||||
}
|
||||
}
|
||||
|
||||
if (error) *error = first.error() ? first : 0;
|
||||
return n_chars;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
template <typename utf_iter>
|
||||
inline size_t count_unicode_chars(utf_iter first, const utf_iter last, const void **error)
|
||||
{
|
||||
size_t n_chars = 0;
|
||||
uint32 usv = 0;
|
||||
|
||||
if (last)
|
||||
{
|
||||
for (;first != last; ++first, ++n_chars)
|
||||
if ((usv = *first) == 0 || first.error()) break;
|
||||
}
|
||||
else
|
||||
{
|
||||
while ((usv = *first) != 0 && !first.error())
|
||||
{
|
||||
++first;
|
||||
++n_chars;
|
||||
}
|
||||
}
|
||||
|
||||
if (error) *error = first.error() ? first : 0;
|
||||
return n_chars;
|
||||
}
|
||||
|
||||
extern "C" {
|
||||
|
||||
size_t gr_count_unicode_characters(gr_encform enc, const void* buffer_begin, const void* buffer_end/*don't go on or past end, If NULL then ignored*/, const void** pError) //Also stops on nul. Any nul is not in the count
|
||||
@ -99,6 +102,8 @@ size_t gr_count_unicode_characters(gr_encform enc, const void* buffer_begin, con
|
||||
|
||||
gr_segment* gr_make_seg(const gr_font *font, const gr_face *face, gr_uint32 script, const gr_feature_val* pFeats, gr_encform enc, const void* pStart, size_t nChars, int dir)
|
||||
{
|
||||
if (!face) return nullptr;
|
||||
|
||||
const gr_feature_val * tmp_feats = 0;
|
||||
if (pFeats == 0)
|
||||
pFeats = tmp_feats = static_cast<const gr_feature_val*>(face->theSill().cloneFeatures(0));
|
||||
@ -132,7 +137,7 @@ float gr_seg_advance_Y(const gr_segment* pSeg/*not NULL*/)
|
||||
unsigned int gr_seg_n_cinfo(const gr_segment* pSeg/*not NULL*/)
|
||||
{
|
||||
assert(pSeg);
|
||||
return pSeg->charInfoCount();
|
||||
return static_cast<unsigned int>(pSeg->charInfoCount());
|
||||
}
|
||||
|
||||
|
||||
@ -145,7 +150,7 @@ const gr_char_info* gr_seg_cinfo(const gr_segment* pSeg/*not NULL*/, unsigned in
|
||||
unsigned int gr_seg_n_slots(const gr_segment* pSeg/*not NULL*/)
|
||||
{
|
||||
assert(pSeg);
|
||||
return pSeg->slotCount();
|
||||
return static_cast<unsigned int>(pSeg->slotCount());
|
||||
}
|
||||
|
||||
const gr_slot* gr_seg_first_slot(gr_segment* pSeg/*not NULL*/)
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -58,7 +58,7 @@ const gr_slot* gr_slot_first_attachment(const gr_slot* p/*not NULL*/) //r
|
||||
return static_cast<const gr_slot*>(p->firstChild());
|
||||
}
|
||||
|
||||
|
||||
|
||||
const gr_slot* gr_slot_next_sibling_attachment(const gr_slot* p/*not NULL*/) //returns NULL iff no more attachments.
|
||||
{ //if slot_next_sibling_attachment(p) is not NULL, then slot_attached_to(slot_next_sibling_attachment(p))==slot_attached_to(p).
|
||||
assert(p);
|
||||
@ -112,7 +112,7 @@ float gr_slot_advance_Y(const gr_slot *p/*not NULL*/, GR_MAYBE_UNUSED const gr_f
|
||||
else
|
||||
return res;
|
||||
}
|
||||
|
||||
|
||||
int gr_slot_before(const gr_slot* p/*not NULL*/)
|
||||
{
|
||||
assert(p);
|
||||
@ -170,4 +170,3 @@ size_t id(const gr_slot* p/*not NULL*/)
|
||||
|
||||
|
||||
} // extern "C"
|
||||
|
||||
|
@ -1,56 +0,0 @@
|
||||
/* GRAPHITE2 LICENSING
|
||||
|
||||
Copyright 2010, SIL International
|
||||
All rights reserved.
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published
|
||||
by the Free Software Foundation; either version 2.1 of License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
Lesser General Public License for more details.
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
Mozilla Public License (http://mozilla.org/MPL) or the GNU General Public
|
||||
License, as published by the Free Software Foundation, either version 2
|
||||
of the License or (at your option) any later version.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#ifndef GRAPHITE2_NSEGCACHE
|
||||
|
||||
#include "inc/Face.h"
|
||||
|
||||
namespace graphite2 {
|
||||
|
||||
class SegCacheStore;
|
||||
class SegCache;
|
||||
|
||||
class CachedFace : public Face
|
||||
{
|
||||
CachedFace(const CachedFace &);
|
||||
CachedFace & operator = (const CachedFace &);
|
||||
|
||||
public:
|
||||
CachedFace(const void* appFaceHandle/*non-NULL*/, const gr_face_ops & ops);
|
||||
bool setupCache(unsigned int cacheSize);
|
||||
virtual ~CachedFace();
|
||||
virtual bool runGraphite(Segment *seg, const Silf *silf) const;
|
||||
SegCacheStore * cacheStore() { return m_cacheStore; }
|
||||
private:
|
||||
SegCacheStore * m_cacheStore;
|
||||
};
|
||||
|
||||
} // namespace graphite2
|
||||
|
||||
#endif
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -64,4 +64,3 @@ private:
|
||||
} // namespace graphite2
|
||||
|
||||
struct gr_char_info : public graphite2::CharInfo {};
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -24,7 +24,7 @@ Mozilla Public License (http://mozilla.org/MPL) or the GNU General Public
|
||||
License, as published by the Free Software Foundation, either version 2
|
||||
of the License or (at your option) any later version.
|
||||
*/
|
||||
// This class represents loaded graphite stack machine code. It performs
|
||||
// This class represents loaded graphite stack machine code. It performs
|
||||
// basic sanity checks, on the incoming code to prevent more obvious problems
|
||||
// from crashing graphite.
|
||||
// Author: Tim Eves
|
||||
@ -54,11 +54,11 @@ namespace vm {
|
||||
class Machine::Code
|
||||
{
|
||||
public:
|
||||
enum status_t
|
||||
enum status_t
|
||||
{
|
||||
loaded,
|
||||
alloc_failed,
|
||||
invalid_opcode,
|
||||
alloc_failed,
|
||||
invalid_opcode,
|
||||
unimplemented_opcode_used,
|
||||
out_of_range_data,
|
||||
jump_past_end,
|
||||
@ -94,7 +94,7 @@ public:
|
||||
enum passtype pt, byte * * const _out = 0);
|
||||
Code(const Machine::Code &) throw();
|
||||
~Code() throw();
|
||||
|
||||
|
||||
Code & operator=(const Code &rhs) throw();
|
||||
operator bool () const throw() { return _code && status() == loaded; }
|
||||
status_t status() const throw() { return _status; }
|
||||
@ -107,7 +107,7 @@ public:
|
||||
void externalProgramMoved(ptrdiff_t) throw();
|
||||
|
||||
int32 run(Machine &m, slotref * & map) const;
|
||||
|
||||
|
||||
CLASS_NEW_DELETE;
|
||||
};
|
||||
|
||||
@ -128,16 +128,16 @@ inline Machine::Code::Code() throw()
|
||||
}
|
||||
|
||||
inline Machine::Code::Code(const Machine::Code &obj) throw ()
|
||||
: _code(obj._code),
|
||||
_data(obj._data),
|
||||
_data_size(obj._data_size),
|
||||
: _code(obj._code),
|
||||
_data(obj._data),
|
||||
_data_size(obj._data_size),
|
||||
_instr_count(obj._instr_count),
|
||||
_max_ref(obj._max_ref),
|
||||
_status(obj._status),
|
||||
_status(obj._status),
|
||||
_constraint(obj._constraint),
|
||||
_modify(obj._modify),
|
||||
_delete(obj._delete),
|
||||
_own(obj._own)
|
||||
_own(obj._own)
|
||||
{
|
||||
obj._own = false;
|
||||
}
|
||||
@ -145,15 +145,15 @@ inline Machine::Code::Code(const Machine::Code &obj) throw ()
|
||||
inline Machine::Code & Machine::Code::operator=(const Machine::Code &rhs) throw() {
|
||||
if (_instr_count > 0)
|
||||
release_buffers();
|
||||
_code = rhs._code;
|
||||
_code = rhs._code;
|
||||
_data = rhs._data;
|
||||
_data_size = rhs._data_size;
|
||||
_data_size = rhs._data_size;
|
||||
_instr_count = rhs._instr_count;
|
||||
_status = rhs._status;
|
||||
_status = rhs._status;
|
||||
_constraint = rhs._constraint;
|
||||
_modify = rhs._modify;
|
||||
_delete = rhs._delete;
|
||||
_own = rhs._own;
|
||||
_own = rhs._own;
|
||||
rhs._own = false;
|
||||
return *this;
|
||||
}
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -59,7 +59,7 @@ public:
|
||||
////COLL_JUMPABLE = 128, // moving glyphs may jump this stationary glyph in any direction - DELETE
|
||||
////COLL_OVERLAP = 256, // use maxoverlap to restrict - DELETE
|
||||
};
|
||||
|
||||
|
||||
// Behavior for the collision.order attribute. To GDL this is an enum, to us it's a bitfield, with only 1 bit set
|
||||
// Allows for easier inversion.
|
||||
enum {
|
||||
@ -70,10 +70,10 @@ public:
|
||||
SEQ_ORDER_NOLEFT = 16,
|
||||
SEQ_ORDER_NORIGHT = 32
|
||||
};
|
||||
|
||||
|
||||
SlotCollision(Segment *seg, Slot *slot);
|
||||
void initFromSlot(Segment *seg, Slot *slot);
|
||||
|
||||
|
||||
const Rect &limit() const { return _limit; }
|
||||
void setLimit(const Rect &r) { _limit = r; }
|
||||
SLOTCOLSETPOSITIONPROP(shift, setShift)
|
||||
@ -95,7 +95,7 @@ public:
|
||||
|
||||
float getKern(int dir) const;
|
||||
bool ignore() const;
|
||||
|
||||
|
||||
private:
|
||||
Rect _limit;
|
||||
Position _shift; // adjustment within the given pass
|
||||
@ -114,7 +114,7 @@ private:
|
||||
uint16 _seqBelowWt;
|
||||
uint16 _seqValignHt;
|
||||
uint16 _seqValignWt;
|
||||
|
||||
|
||||
}; // end of class SlotColllision
|
||||
|
||||
struct BBox;
|
||||
@ -133,7 +133,7 @@ public:
|
||||
bool initSlot(Segment *seg, Slot *aSlot, const Rect &constraint,
|
||||
float margin, float marginMin, const Position &currShift,
|
||||
const Position &currOffset, int dir, GR_MAYBE_UNUSED json * const dbgout);
|
||||
bool mergeSlot(Segment *seg, Slot *slot, const SlotCollision *cinfo, const Position &currShift, bool isAfter,
|
||||
bool mergeSlot(Segment *seg, Slot *slot, const SlotCollision *cinfo, const Position &currShift, bool isAfter,
|
||||
bool sameCluster, bool &hasCol, bool isExclusion, GR_MAYBE_UNUSED json * const dbgout);
|
||||
Position resolve(Segment *seg, bool &isCol, GR_MAYBE_UNUSED json * const dbgout);
|
||||
void addBox_slope(bool isx, const Rect &box, const BBox &bb, const SlantBox &sb, const Position &org, float weight, float m, bool minright, int mode);
|
||||
@ -164,7 +164,7 @@ protected:
|
||||
uint16 _seqClass;
|
||||
uint16 _seqProxClass;
|
||||
uint16 _seqOrder;
|
||||
|
||||
|
||||
//bool _scraping[4];
|
||||
|
||||
}; // end of class ShiftCollider
|
||||
@ -212,7 +212,7 @@ private:
|
||||
float _xbound; // max or min edge
|
||||
bool _hit;
|
||||
|
||||
#if !defined GRAPHITE2_NTRACING
|
||||
#if !defined GRAPHITE2_NTRACING
|
||||
// Debugging
|
||||
Segment * _seg;
|
||||
Vector<float> _nearEdges; // closest potential collision in each slice
|
||||
@ -243,4 +243,3 @@ KernCollider::KernCollider(GR_MAYBE_UNUSED json *dbg)
|
||||
};
|
||||
|
||||
}; // end of namespace graphite2
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -53,7 +53,7 @@ ptrdiff_t const MINMATCH = 4,
|
||||
MINSRCSIZE = 13;
|
||||
|
||||
template<int S>
|
||||
inline
|
||||
inline
|
||||
void unaligned_copy(void * d, void const * s) {
|
||||
::memcpy(d, s, S);
|
||||
}
|
||||
@ -63,7 +63,7 @@ size_t align(size_t p) {
|
||||
return (p + sizeof(unsigned long)-1) & ~(sizeof(unsigned long)-1);
|
||||
}
|
||||
|
||||
inline
|
||||
inline
|
||||
u8 * safe_copy(u8 * d, u8 const * s, size_t n) {
|
||||
while (n--) *d++ = *s++;
|
||||
return d;
|
||||
@ -73,7 +73,7 @@ inline
|
||||
u8 * overrun_copy(u8 * d, u8 const * s, size_t n) {
|
||||
size_t const WS = sizeof(unsigned long);
|
||||
u8 const * e = s + n;
|
||||
do
|
||||
do
|
||||
{
|
||||
unaligned_copy<WS>(d, s);
|
||||
d += WS;
|
||||
@ -81,7 +81,7 @@ u8 * overrun_copy(u8 * d, u8 const * s, size_t n) {
|
||||
}
|
||||
while (s < e);
|
||||
d-=(s-e);
|
||||
|
||||
|
||||
return d;
|
||||
}
|
||||
|
||||
@ -90,7 +90,7 @@ inline
|
||||
u8 * fast_copy(u8 * d, u8 const * s, size_t n) {
|
||||
size_t const WS = sizeof(unsigned long);
|
||||
size_t wn = n/WS;
|
||||
while (wn--)
|
||||
while (wn--)
|
||||
{
|
||||
unaligned_copy<WS>(d, s);
|
||||
d += WS;
|
||||
@ -102,5 +102,3 @@ u8 * fast_copy(u8 * d, u8 const * s, size_t n) {
|
||||
|
||||
|
||||
} // end of anonymous namespace
|
||||
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -52,5 +52,3 @@ namespace lz4
|
||||
int decompress(void const *in, size_t in_size, void *out, size_t out_size);
|
||||
|
||||
} // end of namespace shrinker
|
||||
|
||||
|
||||
|
@ -57,11 +57,11 @@ public:
|
||||
|
||||
template<typename T>
|
||||
inline static T read(const unsigned char * &p) {
|
||||
const T r = T(_peek<sizeof(T)>(p));
|
||||
const T r = T(_peek<sizeof(T)>(p));
|
||||
p += sizeof r;
|
||||
return r;
|
||||
}
|
||||
|
||||
|
||||
template<typename T>
|
||||
inline static T swap(const T x) {
|
||||
return T(_peek<sizeof(T)>(reinterpret_cast<const unsigned char *>(&x)));
|
||||
@ -77,7 +77,7 @@ template<>
|
||||
inline unsigned long int be::_peek<1>(const unsigned char * p) { return *p; }
|
||||
|
||||
|
||||
class le
|
||||
class le
|
||||
{
|
||||
template<int S>
|
||||
inline static unsigned long int _peek(const unsigned char * p) {
|
||||
@ -91,11 +91,11 @@ public:
|
||||
|
||||
template<typename T>
|
||||
inline static T read(const unsigned char * &p) {
|
||||
const T r = T(_peek<sizeof(T)>(p));
|
||||
const T r = T(_peek<sizeof(T)>(p));
|
||||
p += sizeof r;
|
||||
return r;
|
||||
}
|
||||
|
||||
|
||||
template<typename T>
|
||||
inline static T swap(const T x) {
|
||||
return T(_peek<sizeof(T)>(reinterpret_cast<const unsigned char *>(&x)));
|
||||
@ -109,4 +109,3 @@ public:
|
||||
|
||||
template<>
|
||||
inline unsigned long int le::_peek<1>(const unsigned char * p) { return *p; }
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -132,4 +132,3 @@ enum errors {
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -170,23 +170,23 @@ class Face::Table
|
||||
{
|
||||
const Face * _f;
|
||||
mutable const byte * _p;
|
||||
uint32 _sz;
|
||||
size_t _sz;
|
||||
bool _compressed;
|
||||
|
||||
Error decompress();
|
||||
|
||||
void releaseBuffers();
|
||||
void release();
|
||||
|
||||
public:
|
||||
Table() throw();
|
||||
Table(const Face & face, const Tag n, uint32 version=0xffffffff) throw();
|
||||
Table(const Table & rhs) throw();
|
||||
~Table() throw();
|
||||
Table(const Table && rhs) throw();
|
||||
|
||||
operator const byte * () const throw();
|
||||
|
||||
Table & operator = (const Table & rhs) throw();
|
||||
size_t size() const throw();
|
||||
Table & operator = (const Table && rhs) throw();
|
||||
};
|
||||
|
||||
inline
|
||||
@ -196,7 +196,7 @@ Face::Table::Table() throw()
|
||||
}
|
||||
|
||||
inline
|
||||
Face::Table::Table(const Table & rhs) throw()
|
||||
Face::Table::Table(const Table && rhs) throw()
|
||||
: _f(rhs._f), _p(rhs._p), _sz(rhs._sz), _compressed(rhs._compressed)
|
||||
{
|
||||
rhs._p = 0;
|
||||
@ -205,7 +205,7 @@ Face::Table::Table(const Table & rhs) throw()
|
||||
inline
|
||||
Face::Table::~Table() throw()
|
||||
{
|
||||
releaseBuffers();
|
||||
release();
|
||||
}
|
||||
|
||||
inline
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -41,7 +41,7 @@ public:
|
||||
FeatureSetting(int16 theValue, uint16 labelId) : m_label(labelId), m_value(theValue) {};
|
||||
uint16 label() const { return m_label; }
|
||||
int16 value() const { return m_value; }
|
||||
|
||||
|
||||
CLASS_NEW_DELETE;
|
||||
private:
|
||||
FeatureSetting(const FeatureSetting & fs) : m_label(fs.m_label), m_value(fs.m_value) {};
|
||||
@ -146,7 +146,7 @@ friend class SillMap;
|
||||
FeatureRef *m_feats;
|
||||
NameAndFeatureRef* m_pNamedFeats; //owned
|
||||
FeatureVal m_defaultFeatures; //owned
|
||||
|
||||
|
||||
private: //defensive on m_feats, m_pNamedFeats, and m_defaultFeatures
|
||||
FeatureMap(const FeatureMap&);
|
||||
FeatureMap& operator=(const FeatureMap&);
|
||||
@ -164,7 +164,7 @@ private:
|
||||
public:
|
||||
LangFeaturePair() : m_lang(0), m_pFeatures(0) {}
|
||||
~LangFeaturePair() { delete m_pFeatures; }
|
||||
|
||||
|
||||
uint32 m_lang;
|
||||
Features* m_pFeatures; //owns
|
||||
CLASS_NEW_DELETE
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -48,9 +48,9 @@ public:
|
||||
{
|
||||
size_t n = size();
|
||||
if (n != b.size()) return false;
|
||||
|
||||
|
||||
for(const_iterator l = begin(), r = b.begin(); n && *l == *r; --n, ++l, ++r);
|
||||
|
||||
|
||||
return n == 0;
|
||||
}
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -71,7 +71,7 @@ class GlyphBox
|
||||
GlyphBox & operator = (const GlyphBox &);
|
||||
|
||||
public:
|
||||
GlyphBox(uint8 numsubs, unsigned short bitmap, Rect *slanted) : _num(numsubs), _bitmap(bitmap), _slant(*slanted) {};
|
||||
GlyphBox(uint8 numsubs, unsigned short bitmap, Rect *slanted) : _num(numsubs), _bitmap(bitmap), _slant(*slanted) {};
|
||||
|
||||
void addSubBox(int subindex, int boundary, Rect *val) { _subs[subindex * 2 + boundary] = *val; }
|
||||
Rect &subVal(int subindex, int boundary) { return _subs[subindex * 2 + boundary]; }
|
||||
@ -115,7 +115,7 @@ public:
|
||||
bool hasBoxes() const { return _boxes != 0; }
|
||||
|
||||
CLASS_NEW_DELETE;
|
||||
|
||||
|
||||
private:
|
||||
const Rect _empty_slant_box;
|
||||
const Loader * _glyph_loader;
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -216,7 +216,7 @@ Zones::Exclusion Zones::Exclusion::weighted<XY>(float xmin, float xmax, float f,
|
||||
float m, float xi, GR_MAYBE_UNUSED float ai, float c, GR_MAYBE_UNUSED bool nega) {
|
||||
return Exclusion(xmin, xmax,
|
||||
m + f,
|
||||
m * xi,
|
||||
m * xi,
|
||||
m * xi * xi + f * a0 * a0 + c);
|
||||
}
|
||||
|
||||
@ -225,9 +225,9 @@ inline
|
||||
Zones::Exclusion Zones::Exclusion::weighted<SD>(float xmin, float xmax, float f, float a0,
|
||||
float m, float xi, float ai,float c, bool nega) {
|
||||
float xia = nega ? xi - ai : xi + ai;
|
||||
return Exclusion(xmin, xmax,
|
||||
0.25f * (m + 2.f * f),
|
||||
0.25f * m * xia,
|
||||
return Exclusion(xmin, xmax,
|
||||
0.25f * (m + 2.f * f),
|
||||
0.25f * m * xia,
|
||||
0.25f * (m * xia * xia + 2.f * f * a0 * a0) + c);
|
||||
}
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -38,12 +38,12 @@ of the License or (at your option) any later version.
|
||||
|
||||
namespace graphite2 {
|
||||
|
||||
template <typename T>
|
||||
template <typename T>
|
||||
inline
|
||||
ptrdiff_t distance(T* first, T* last) { return last-first; }
|
||||
|
||||
|
||||
template <typename T>
|
||||
template <typename T>
|
||||
class Vector
|
||||
{
|
||||
T * m_first, *m_last, *m_end;
|
||||
@ -56,32 +56,32 @@ public:
|
||||
Vector() : m_first(0), m_last(0), m_end(0) {}
|
||||
Vector(size_t n, const T& value = T()) : m_first(0), m_last(0), m_end(0) { insert(begin(), n, value); }
|
||||
Vector(const Vector<T> &rhs) : m_first(0), m_last(0), m_end(0) { insert(begin(), rhs.begin(), rhs.end()); }
|
||||
template <typename I>
|
||||
template <typename I>
|
||||
Vector(I first, const I last) : m_first(0), m_last(0), m_end(0) { insert(begin(), first, last); }
|
||||
~Vector() { clear(); free(m_first); }
|
||||
|
||||
|
||||
iterator begin() { return m_first; }
|
||||
const_iterator begin() const { return m_first; }
|
||||
|
||||
iterator end() { return m_last; }
|
||||
const_iterator end() const { return m_last; }
|
||||
|
||||
|
||||
bool empty() const { return m_first == m_last; }
|
||||
size_t size() const { return m_last - m_first; }
|
||||
size_t capacity() const{ return m_end - m_first; }
|
||||
|
||||
|
||||
void reserve(size_t n);
|
||||
void resize(size_t n, const T & v = T());
|
||||
|
||||
|
||||
reference front() { assert(size() > 0); return *begin(); }
|
||||
const_reference front() const { assert(size() > 0); return *begin(); }
|
||||
reference back() { assert(size() > 0); return *(end()-1); }
|
||||
const_reference back() const { assert(size() > 0); return *(end()-1); }
|
||||
|
||||
|
||||
Vector<T> & operator = (const Vector<T> & rhs) { assign(rhs.begin(), rhs.end()); return *this; }
|
||||
reference operator [] (size_t n) { assert(size() > n); return m_first[n]; }
|
||||
const_reference operator [] (size_t n) const { assert(size() > n); return m_first[n]; }
|
||||
|
||||
|
||||
void assign(size_t n, const T& u) { clear(); insert(begin(), n, u); }
|
||||
void assign(const_iterator first, const_iterator last) { clear(); insert(begin(), first, last); }
|
||||
iterator insert(iterator p, const T & x) { p = _insert_default(p, 1); new (p) T(x); return p; }
|
||||
@ -97,12 +97,12 @@ public:
|
||||
private:
|
||||
iterator _insert_default(iterator p, size_t n);
|
||||
};
|
||||
|
||||
|
||||
template <typename T>
|
||||
inline
|
||||
inline
|
||||
void Vector<T>::reserve(size_t n)
|
||||
{
|
||||
if (n > capacity())
|
||||
if (n > capacity())
|
||||
{
|
||||
const ptrdiff_t sz = size();
|
||||
size_t requested;
|
||||
@ -122,8 +122,8 @@ void Vector<T>::resize(size_t n, const T & v) {
|
||||
else if (d > 0) insert(end(), d, v);
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
inline
|
||||
template<typename T>
|
||||
inline
|
||||
typename Vector<T>::iterator Vector<T>::_insert_default(iterator p, size_t n)
|
||||
{
|
||||
assert(begin() <= p && p <= end());
|
||||
@ -136,8 +136,8 @@ typename Vector<T>::iterator Vector<T>::_insert_default(iterator p, size_t n)
|
||||
return p;
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
inline
|
||||
template<typename T>
|
||||
inline
|
||||
void Vector<T>::insert(iterator p, size_t n, const T & x)
|
||||
{
|
||||
p = _insert_default(p, n);
|
||||
@ -146,7 +146,7 @@ void Vector<T>::insert(iterator p, size_t n, const T & x)
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
inline
|
||||
inline
|
||||
void Vector<T>::insert(iterator p, const_iterator first, const_iterator last)
|
||||
{
|
||||
p = _insert_default(p, distance(first, last));
|
||||
|
@ -86,7 +86,7 @@ struct telemetry {};
|
||||
#define HAVE_BUILTIN_OVERFLOW
|
||||
#endif
|
||||
#if defined(__has_include)
|
||||
#if __has_include(<intsafe.h>)
|
||||
#if __has_include(<intsafe.h>) && !defined(__CYGWIN__)
|
||||
#define HAVE_INTSAFE_H
|
||||
#endif
|
||||
#elif defined(_WIN32)
|
||||
@ -172,9 +172,14 @@ inline T max(const T a, const T b)
|
||||
#define GR_MAYBE_UNUSED
|
||||
#endif
|
||||
|
||||
#if defined(__clang__) && __cplusplus >= 201103L
|
||||
/* clang's fallthrough annotations are only available starting in C++11. */
|
||||
#define GR_FALLTHROUGH [[fallthrough]]
|
||||
#ifndef __has_cpp_attribute
|
||||
# define __has_cpp_attribute(x) 0
|
||||
#endif
|
||||
|
||||
#if __has_cpp_attribute(clang::fallthrough)
|
||||
# define GR_FALLTHROUGH [[clang::fallthrough]]
|
||||
#elif __has_cpp_attribute(gnu::fallthrough)
|
||||
# define GR_FALLTHROUGH [[gnu::fallthrough]]
|
||||
#elif defined(_MSC_VER)
|
||||
/*
|
||||
* MSVC's __fallthrough annotations are checked by /analyze (Code Analysis):
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -46,11 +46,11 @@ class json;
|
||||
enum passtype;
|
||||
|
||||
class Pass
|
||||
{
|
||||
{
|
||||
public:
|
||||
Pass();
|
||||
~Pass();
|
||||
|
||||
|
||||
bool readPass(const byte * pPass, size_t pass_length, size_t subtable_base, Face & face,
|
||||
enum passtype pt, uint32 version, Error &e);
|
||||
bool runGraphite(vm::Machine & m, FiniteStateMachine & fsm, bool reverse) const;
|
||||
@ -66,7 +66,7 @@ private:
|
||||
bool testConstraint(const Rule & r, vm::Machine &) const;
|
||||
bool readRules(const byte * rule_map, const size_t num_entries,
|
||||
const byte *precontext, const uint16 * sort_key,
|
||||
const uint16 * o_constraint, const byte *constraint_data,
|
||||
const uint16 * o_constraint, const byte *constraint_data,
|
||||
const uint16 * o_action, const byte * action_data,
|
||||
Face &, enum passtype pt, Error &e);
|
||||
bool readStates(const byte * starts, const byte * states, const byte * o_rule_map, Face &, Error &e);
|
||||
@ -109,7 +109,7 @@ private:
|
||||
byte m_colThreshold;
|
||||
bool m_isReverseDir;
|
||||
vm::Machine::Code m_cPConstraint;
|
||||
|
||||
|
||||
private: //defensive
|
||||
Pass(const Pass&);
|
||||
Pass& operator=(const Pass&);
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -33,7 +33,7 @@ of the License or (at your option) any later version.
|
||||
namespace graphite2 {
|
||||
|
||||
struct Rule {
|
||||
const vm::Machine::Code * constraint,
|
||||
const vm::Machine::Code * constraint,
|
||||
* action;
|
||||
unsigned short sort;
|
||||
byte preContext;
|
||||
@ -87,7 +87,7 @@ struct State
|
||||
{
|
||||
const RuleEntry * rules,
|
||||
* rules_end;
|
||||
|
||||
|
||||
bool empty() const;
|
||||
};
|
||||
|
||||
@ -102,14 +102,14 @@ class SlotMap
|
||||
{
|
||||
public:
|
||||
enum {MAX_SLOTS=64};
|
||||
SlotMap(Segment & seg, uint8 direction, int maxSize);
|
||||
|
||||
SlotMap(Segment & seg, uint8 direction, size_t maxSize);
|
||||
|
||||
Slot * * begin();
|
||||
Slot * * end();
|
||||
size_t size() const;
|
||||
unsigned short context() const;
|
||||
void reset(Slot &, unsigned short);
|
||||
|
||||
|
||||
Slot * const & operator[](int n) const;
|
||||
Slot * & operator [] (int);
|
||||
void pushSlot(Slot * const slot);
|
||||
@ -149,11 +149,11 @@ private:
|
||||
const RuleEntry * begin() const;
|
||||
const RuleEntry * end() const;
|
||||
size_t size() const;
|
||||
|
||||
|
||||
void accumulate_rules(const State &state);
|
||||
|
||||
private:
|
||||
RuleEntry * m_begin,
|
||||
RuleEntry * m_begin,
|
||||
* m_end,
|
||||
m_rules[MAX_RULES*2];
|
||||
};
|
||||
@ -219,13 +219,13 @@ void FiniteStateMachine::Rules::accumulate_rules(const State &state)
|
||||
{
|
||||
// Only bother if there are rules in the State object.
|
||||
if (state.empty()) return;
|
||||
|
||||
|
||||
// Merge the new sorted rules list into the current sorted result set.
|
||||
const RuleEntry * lre = begin(), * rre = state.rules;
|
||||
RuleEntry * out = m_rules + (m_begin == m_rules)*MAX_RULES;
|
||||
RuleEntry * out = m_rules + (m_begin == m_rules)*MAX_RULES;
|
||||
const RuleEntry * const lrend = out + MAX_RULES,
|
||||
* const rrend = state.rules_end;
|
||||
m_begin = out;
|
||||
m_begin = out;
|
||||
while (lre != end() && out != lrend)
|
||||
{
|
||||
if (*lre < *rre) *out++ = *lre++;
|
||||
@ -233,7 +233,7 @@ void FiniteStateMachine::Rules::accumulate_rules(const State &state)
|
||||
else { *out++ = *lre++; ++rre; }
|
||||
|
||||
if (rre == rrend)
|
||||
{
|
||||
{
|
||||
while (lre != end() && out != lrend) { *out++ = *lre++; }
|
||||
m_end = out;
|
||||
return;
|
||||
@ -244,9 +244,9 @@ void FiniteStateMachine::Rules::accumulate_rules(const State &state)
|
||||
}
|
||||
|
||||
inline
|
||||
SlotMap::SlotMap(Segment & seg, uint8 direction, int maxSize)
|
||||
SlotMap::SlotMap(Segment & seg, uint8 direction, size_t maxSize)
|
||||
: segment(seg), m_size(0), m_precontext(0), m_highwater(0),
|
||||
m_maxSize(maxSize), m_dir(direction), m_highpassed(false)
|
||||
m_maxSize(int(maxSize)), m_dir(direction), m_highpassed(false)
|
||||
{
|
||||
m_slot_map[0] = 0;
|
||||
}
|
||||
|
@ -1,316 +0,0 @@
|
||||
/* GRAPHITE2 LICENSING
|
||||
|
||||
Copyright 2010, SIL International
|
||||
All rights reserved.
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published
|
||||
by the Free Software Foundation; either version 2.1 of License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
Lesser General Public License for more details.
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
Mozilla Public License (http://mozilla.org/MPL) or the GNU General Public
|
||||
License, as published by the Free Software Foundation, either version 2
|
||||
of the License or (at your option) any later version.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#ifndef GRAPHITE2_NSEGCACHE
|
||||
|
||||
#include <graphite2/Segment.h>
|
||||
#include "inc/Main.h"
|
||||
#include "inc/Slot.h"
|
||||
#include "inc/FeatureVal.h"
|
||||
#include "inc/SegCacheEntry.h"
|
||||
#include "inc/Segment.h"
|
||||
|
||||
namespace graphite2 {
|
||||
|
||||
class SegCache;
|
||||
class SegCacheEntry;
|
||||
class SegCacheStore;
|
||||
|
||||
/**
|
||||
* SegPrefixEntry stores lists of word/syllable segments
|
||||
* with one list for each word length. The prefix size should be chosen so that
|
||||
* these list sizes stay small since they will be searched iteratively.
|
||||
*/
|
||||
class SegCachePrefixEntry
|
||||
{
|
||||
SegCachePrefixEntry(const SegCachePrefixEntry &);
|
||||
SegCachePrefixEntry & operator = (const SegCachePrefixEntry &);
|
||||
|
||||
public:
|
||||
SegCachePrefixEntry() : m_lastPurge(0)
|
||||
{
|
||||
memset(m_entryCounts, 0, sizeof m_entryCounts);
|
||||
memset(m_entryBSIndex, 0, sizeof m_entryBSIndex);
|
||||
memset(m_entries, 0, sizeof m_entries);
|
||||
}
|
||||
|
||||
~SegCachePrefixEntry()
|
||||
{
|
||||
for (size_t j = 0; j < eMaxSpliceSize; j++)
|
||||
{
|
||||
if (m_entryCounts[j])
|
||||
{
|
||||
assert(m_entries[j]);
|
||||
for (size_t k = 0; k < m_entryCounts[j]; k++)
|
||||
m_entries[j][k].clear();
|
||||
|
||||
free(m_entries[j]);
|
||||
}
|
||||
}
|
||||
}
|
||||
const SegCacheEntry * find(const uint16 * cmapGlyphs, size_t length) const
|
||||
{
|
||||
if (length <= ePrefixLength)
|
||||
{
|
||||
assert(m_entryCounts[length-1] <= 1);
|
||||
if (m_entries[length-1])
|
||||
return m_entries[length-1];
|
||||
return NULL;
|
||||
}
|
||||
SegCacheEntry * entry = NULL;
|
||||
findPosition(cmapGlyphs, length, &entry);
|
||||
return entry;
|
||||
}
|
||||
SegCacheEntry * cache(const uint16* cmapGlyphs, size_t length, Segment * seg, size_t charOffset, unsigned long long totalAccessCount)
|
||||
{
|
||||
size_t listSize = m_entryBSIndex[length-1]? (m_entryBSIndex[length-1] << 1) - 1 : 0;
|
||||
SegCacheEntry * newEntries = NULL;
|
||||
if (m_entryCounts[length-1] + 1u > listSize)
|
||||
{
|
||||
if (m_entryCounts[length-1] == 0)
|
||||
listSize = 1;
|
||||
else
|
||||
{
|
||||
// the problem comes when you get incremental numeric ids in a large doc
|
||||
if (listSize >= eMaxSuffixCount)
|
||||
return NULL;
|
||||
listSize = (m_entryBSIndex[length-1] << 2) - 1;
|
||||
}
|
||||
newEntries = gralloc<SegCacheEntry>(listSize);
|
||||
if (!newEntries)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
uint16 insertPos = 0;
|
||||
if (m_entryCounts[length-1] > 0)
|
||||
{
|
||||
insertPos = findPosition(cmapGlyphs, length, NULL);
|
||||
if (!newEntries)
|
||||
{
|
||||
// same buffer, shift entries up
|
||||
memmove(m_entries[length-1] + insertPos + 1, m_entries[length-1] + insertPos,
|
||||
sizeof(SegCacheEntry) * (m_entryCounts[length-1] - insertPos));
|
||||
}
|
||||
else
|
||||
{
|
||||
memcpy(newEntries, m_entries[length-1], sizeof(SegCacheEntry) * (insertPos));
|
||||
memcpy(newEntries + insertPos + 1, m_entries[length-1] + insertPos,
|
||||
sizeof(SegCacheEntry) * (m_entryCounts[length-1] - insertPos));
|
||||
|
||||
free(m_entries[length-1]);
|
||||
m_entries[length-1] = newEntries;
|
||||
assert (m_entryBSIndex[length-1]);
|
||||
m_entryBSIndex[length-1] <<= 1;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
m_entryBSIndex[length-1] = 1;
|
||||
m_entries[length-1] = newEntries;
|
||||
}
|
||||
m_entryCounts[length-1] += 1;
|
||||
new (m_entries[length-1] + insertPos)
|
||||
SegCacheEntry(cmapGlyphs, length, seg, charOffset, totalAccessCount);
|
||||
return m_entries[length-1] + insertPos;
|
||||
}
|
||||
uint32 purge(unsigned long long minAccessCount, unsigned long long oldAccessTime,
|
||||
unsigned long long currentTime);
|
||||
CLASS_NEW_DELETE
|
||||
private:
|
||||
uint16 findPosition(const uint16 * cmapGlyphs, uint16 length, SegCacheEntry ** entry) const
|
||||
{
|
||||
int dir = 0;
|
||||
if (m_entryCounts[length-1] == 0)
|
||||
{
|
||||
if (entry) *entry = NULL;
|
||||
return 0;
|
||||
}
|
||||
else if (m_entryCounts[length-1] == 1)
|
||||
{
|
||||
// optimize single entry case
|
||||
for (int i = ePrefixLength; i < length; i++)
|
||||
{
|
||||
if (cmapGlyphs[i] > m_entries[length-1][0].m_unicode[i])
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
else if (cmapGlyphs[i] < m_entries[length-1][0].m_unicode[i])
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
if (entry)
|
||||
*entry = m_entries[length-1];
|
||||
return 0;
|
||||
}
|
||||
uint16 searchIndex = m_entryBSIndex[length-1] - 1;
|
||||
uint16 stepSize = m_entryBSIndex[length-1] >> 1;
|
||||
size_t prevIndex = searchIndex;
|
||||
do
|
||||
{
|
||||
dir = 0;
|
||||
if (searchIndex >= m_entryCounts[length-1])
|
||||
{
|
||||
dir = -1;
|
||||
searchIndex -= stepSize;
|
||||
stepSize >>= 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
for (int i = ePrefixLength; i < length; i++)
|
||||
{
|
||||
if (cmapGlyphs[i] > m_entries[length-1][searchIndex].m_unicode[i])
|
||||
{
|
||||
dir = 1;
|
||||
searchIndex += stepSize;
|
||||
stepSize >>= 1;
|
||||
break;
|
||||
}
|
||||
else if (cmapGlyphs[i] < m_entries[length-1][searchIndex].m_unicode[i])
|
||||
{
|
||||
dir = -1;
|
||||
searchIndex -= stepSize;
|
||||
stepSize >>= 1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (prevIndex == searchIndex)
|
||||
break;
|
||||
prevIndex = searchIndex;
|
||||
} while (dir != 0);
|
||||
if (entry)
|
||||
{
|
||||
if (dir == 0)
|
||||
*entry = m_entries[length-1] + searchIndex;
|
||||
else
|
||||
*entry = NULL;
|
||||
}
|
||||
else
|
||||
{
|
||||
// if entry is null, then this is for inserting a new value, which
|
||||
// shouldn't already be in the cache
|
||||
assert(dir != 0);
|
||||
if (dir > 0)
|
||||
++searchIndex;
|
||||
}
|
||||
return searchIndex;
|
||||
}
|
||||
/** m_entries is a null terminated list of entries */
|
||||
uint16 m_entryCounts[eMaxSpliceSize];
|
||||
uint16 m_entryBSIndex[eMaxSpliceSize];
|
||||
SegCacheEntry * m_entries[eMaxSpliceSize];
|
||||
unsigned long long m_lastPurge;
|
||||
};
|
||||
|
||||
|
||||
#define SEG_CACHE_MIN_INDEX (store->maxCmapGid())
|
||||
#define SEG_CACHE_MAX_INDEX (store->maxCmapGid()+1u)
|
||||
#define SEG_CACHE_UNSET_INDEX (store->maxCmapGid()+2u)
|
||||
|
||||
union SegCachePrefixArray
|
||||
{
|
||||
void ** raw;
|
||||
SegCachePrefixArray * array;
|
||||
SegCachePrefixEntry ** prefixEntries;
|
||||
uintptr * range;
|
||||
};
|
||||
|
||||
class SegCache
|
||||
{
|
||||
public:
|
||||
SegCache(const SegCacheStore * store, const Features& features);
|
||||
~SegCache();
|
||||
|
||||
const SegCacheEntry * find(const uint16 * cmapGlyphs, size_t length) const;
|
||||
SegCacheEntry * cache(SegCacheStore * store, const uint16 * cmapGlyphs, size_t length, Segment * seg, size_t charOffset);
|
||||
void purge(SegCacheStore * store);
|
||||
|
||||
long long totalAccessCount() const { return m_totalAccessCount; }
|
||||
size_t segmentCount() const { return m_segmentCount; }
|
||||
const Features & features() const { return m_features; }
|
||||
void clear(SegCacheStore * store);
|
||||
|
||||
CLASS_NEW_DELETE
|
||||
private:
|
||||
void freeLevel(SegCacheStore * store, SegCachePrefixArray prefixes, size_t level);
|
||||
void purgeLevel(SegCacheStore * store, SegCachePrefixArray prefixes, size_t level,
|
||||
unsigned long long minAccessCount, unsigned long long oldAccessTime);
|
||||
|
||||
uint16 m_prefixLength;
|
||||
// uint16 m_maxCachedSegLength;
|
||||
size_t m_segmentCount;
|
||||
SegCachePrefixArray m_prefixes;
|
||||
Features m_features;
|
||||
mutable unsigned long long m_totalAccessCount;
|
||||
mutable unsigned long long m_totalMisses;
|
||||
float m_purgeFactor;
|
||||
};
|
||||
|
||||
inline const SegCacheEntry * SegCache::find(const uint16 * cmapGlyphs, size_t length) const
|
||||
{
|
||||
uint16 pos = 0;
|
||||
if (!length || length > eMaxSpliceSize) return NULL;
|
||||
SegCachePrefixArray pEntry = m_prefixes.array[cmapGlyphs[0]];
|
||||
while (++pos < m_prefixLength - 1)
|
||||
{
|
||||
if (!pEntry.raw)
|
||||
{
|
||||
++m_totalMisses;
|
||||
return NULL;
|
||||
}
|
||||
pEntry = pEntry.array[(pos < length)? cmapGlyphs[pos] : 0];
|
||||
}
|
||||
if (!pEntry.raw)
|
||||
{
|
||||
++m_totalMisses;
|
||||
return NULL;
|
||||
}
|
||||
SegCachePrefixEntry * prefixEntry = pEntry.prefixEntries[(pos < length)? cmapGlyphs[pos] : 0];
|
||||
if (!prefixEntry)
|
||||
{
|
||||
++m_totalMisses;
|
||||
return NULL;
|
||||
}
|
||||
const SegCacheEntry * entry = prefixEntry->find(cmapGlyphs, length);
|
||||
if (entry)
|
||||
{
|
||||
++m_totalAccessCount;
|
||||
entry->accessed(m_totalAccessCount);
|
||||
}
|
||||
else
|
||||
{
|
||||
++m_totalMisses;
|
||||
}
|
||||
return entry;
|
||||
}
|
||||
|
||||
} // namespace graphite2
|
||||
|
||||
#endif
|
||||
|
@ -1,121 +0,0 @@
|
||||
/* GRAPHITE2 LICENSING
|
||||
|
||||
Copyright 2010, SIL International
|
||||
All rights reserved.
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published
|
||||
by the Free Software Foundation; either version 2.1 of License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
Lesser General Public License for more details.
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
Mozilla Public License (http://mozilla.org/MPL) or the GNU General Public
|
||||
License, as published by the Free Software Foundation, either version 2
|
||||
of the License or (at your option) any later version.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#ifndef GRAPHITE2_NSEGCACHE
|
||||
|
||||
#include "inc/Main.h"
|
||||
#include "inc/Slot.h"
|
||||
|
||||
namespace graphite2 {
|
||||
|
||||
class Segment;
|
||||
class Slot;
|
||||
class SegCacheEntry;
|
||||
class SegCachePrefixEntry;
|
||||
|
||||
enum SegCacheParameters {
|
||||
/** number of characters used in initial prefix tree */
|
||||
ePrefixLength = 2,
|
||||
/** Segments more recent than maxSegmentCount() / eAgeFactor are kept */
|
||||
eAgeFactor = 4,
|
||||
/** Segments are purged according to the formular:
|
||||
* accessCount < (totalAccesses)/(ePurgeFactor * maxSegments) */
|
||||
ePurgeFactor = 5,
|
||||
/** Maximum number of Segments to store which have the same
|
||||
* prefix. Needed to prevent unique identifiers flooding the cache */
|
||||
eMaxSuffixCount = 15
|
||||
|
||||
};
|
||||
|
||||
class SegCacheCharInfo
|
||||
{
|
||||
public:
|
||||
uint16 m_unicode;
|
||||
uint16 m_before;
|
||||
uint16 m_after;
|
||||
};
|
||||
|
||||
/**
|
||||
* SegCacheEntry stores the result of running the engine for specific unicode
|
||||
* code points in the typical mid-line situation.
|
||||
*/
|
||||
class SegCacheEntry
|
||||
{
|
||||
// Prevent any implict copying;
|
||||
SegCacheEntry(const SegCacheEntry &);
|
||||
SegCacheEntry & operator = (const SegCacheEntry &);
|
||||
|
||||
friend class SegCachePrefixEntry;
|
||||
public:
|
||||
SegCacheEntry() :
|
||||
m_glyphLength(0), m_unicode(NULL), m_glyph(NULL), m_attr(NULL), m_justs(0),
|
||||
m_accessCount(0), m_lastAccess(0)
|
||||
{}
|
||||
SegCacheEntry(const uint16 * cmapGlyphs, size_t length, Segment * seg, size_t charOffset, long long cacheTime);
|
||||
~SegCacheEntry() { clear(); };
|
||||
void clear();
|
||||
size_t glyphLength() const { return m_glyphLength; }
|
||||
const Slot * first() const { return m_glyph; }
|
||||
const Slot * last() const { return m_glyph + (m_glyphLength - 1); }
|
||||
|
||||
/** Total number of times this entry has been accessed since creation */
|
||||
unsigned long long accessCount() const { return m_accessCount; }
|
||||
/** "time" of last access where "time" is measured in accesses to the cache owning this entry */
|
||||
void accessed(unsigned long long cacheTime) const
|
||||
{
|
||||
m_lastAccess = cacheTime; ++m_accessCount;
|
||||
};
|
||||
|
||||
int compareRank(const SegCacheEntry & entry) const
|
||||
{
|
||||
if (m_accessCount > entry.m_accessCount) return 1;
|
||||
else if (m_accessCount < entry.m_accessCount) return 1;
|
||||
else if (m_lastAccess > entry.m_lastAccess) return 1;
|
||||
else if (m_lastAccess < entry.m_lastAccess) return -1;
|
||||
return 0;
|
||||
}
|
||||
unsigned long long lastAccess() const { return m_lastAccess; };
|
||||
|
||||
CLASS_NEW_DELETE;
|
||||
private:
|
||||
|
||||
size_t m_glyphLength;
|
||||
/** glyph ids resulting from cmap mapping from unicode to glyph before substitution
|
||||
* the length of this array is determined by the position in the SegCachePrefixEntry */
|
||||
uint16 * m_unicode;
|
||||
/** slots after shapping and positioning */
|
||||
Slot * m_glyph;
|
||||
int16 * m_attr;
|
||||
byte * m_justs;
|
||||
mutable unsigned long long m_accessCount;
|
||||
mutable unsigned long long m_lastAccess;
|
||||
};
|
||||
|
||||
} // namespace graphite2
|
||||
|
||||
#endif
|
@ -1,127 +0,0 @@
|
||||
/* GRAPHITE2 LICENSING
|
||||
|
||||
Copyright 2010, SIL International
|
||||
All rights reserved.
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published
|
||||
by the Free Software Foundation; either version 2.1 of License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
Lesser General Public License for more details.
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
Mozilla Public License (http://mozilla.org/MPL) or the GNU General Public
|
||||
License, as published by the Free Software Foundation, either version 2
|
||||
of the License or (at your option) any later version.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#ifndef GRAPHITE2_NSEGCACHE
|
||||
|
||||
#include "inc/Main.h"
|
||||
#include "inc/CmapCache.h"
|
||||
#include "inc/SegCache.h"
|
||||
|
||||
namespace graphite2 {
|
||||
|
||||
class SegCache;
|
||||
class Face;
|
||||
|
||||
class SilfSegCache
|
||||
{
|
||||
SilfSegCache(const SilfSegCache &);
|
||||
SilfSegCache & operator = (const SilfSegCache &);
|
||||
|
||||
public:
|
||||
SilfSegCache() : m_caches(NULL), m_cacheCount(0) {};
|
||||
~SilfSegCache()
|
||||
{
|
||||
assert(m_caches == NULL);
|
||||
}
|
||||
void clear(SegCacheStore * cacheStore)
|
||||
{
|
||||
for (size_t i = 0; i < m_cacheCount; i++)
|
||||
{
|
||||
m_caches[i]->clear(cacheStore);
|
||||
delete m_caches[i];
|
||||
}
|
||||
free(m_caches);
|
||||
m_caches = NULL;
|
||||
m_cacheCount = 0;
|
||||
}
|
||||
SegCache * getOrCreate(SegCacheStore * cacheStore, const Features & features)
|
||||
{
|
||||
for (size_t i = 0; i < m_cacheCount; i++)
|
||||
{
|
||||
if (m_caches[i]->features() == features)
|
||||
return m_caches[i];
|
||||
}
|
||||
SegCache ** newData = gralloc<SegCache*>(m_cacheCount+1);
|
||||
if (newData)
|
||||
{
|
||||
if (m_cacheCount > 0)
|
||||
{
|
||||
memcpy(newData, m_caches, sizeof(SegCache*) * m_cacheCount);
|
||||
free(m_caches);
|
||||
}
|
||||
m_caches = newData;
|
||||
m_caches[m_cacheCount] = new SegCache(cacheStore, features);
|
||||
m_cacheCount++;
|
||||
return m_caches[m_cacheCount - 1];
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
CLASS_NEW_DELETE
|
||||
private:
|
||||
SegCache ** m_caches;
|
||||
size_t m_cacheCount;
|
||||
};
|
||||
|
||||
class SegCacheStore
|
||||
{
|
||||
SegCacheStore(const SegCacheStore &);
|
||||
SegCacheStore & operator = (const SegCacheStore &);
|
||||
|
||||
public:
|
||||
SegCacheStore(const Face & face, unsigned int numSilf, size_t maxSegments);
|
||||
~SegCacheStore()
|
||||
{
|
||||
for (size_t i = 0; i < m_numSilf; i++)
|
||||
{
|
||||
m_caches[i].clear(this);
|
||||
}
|
||||
delete [] m_caches;
|
||||
m_caches = NULL;
|
||||
}
|
||||
SegCache * getOrCreate(unsigned int i, const Features & features)
|
||||
{
|
||||
return m_caches[i].getOrCreate(this, features);
|
||||
}
|
||||
bool isSpaceGlyph(uint16 gid) const { return (gid == m_spaceGid) || (gid == m_zwspGid); }
|
||||
uint16 maxCmapGid() const { return m_maxCmapGid; }
|
||||
uint32 maxSegmentCount() const { return m_maxSegments; };
|
||||
|
||||
CLASS_NEW_DELETE
|
||||
private:
|
||||
SilfSegCache * m_caches;
|
||||
uint8 m_numSilf;
|
||||
uint32 m_maxSegments;
|
||||
uint16 m_maxCmapGid;
|
||||
uint16 m_spaceGid;
|
||||
uint16 m_zwspGid;
|
||||
};
|
||||
|
||||
} // namespace graphite2
|
||||
|
||||
#endif
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -49,9 +49,6 @@ typedef Vector<Slot *> SlotRope;
|
||||
typedef Vector<int16 *> AttributeRope;
|
||||
typedef Vector<SlotJustify *> JustifyRope;
|
||||
|
||||
#ifndef GRAPHITE2_NSEGCACHE
|
||||
class SegmentScopeState;
|
||||
#endif
|
||||
class Font;
|
||||
class Segment;
|
||||
class Silf;
|
||||
@ -91,26 +88,18 @@ public:
|
||||
SEG_HASCOLLISIONS = 2
|
||||
};
|
||||
|
||||
unsigned int slotCount() const { return m_numGlyphs; } //one slot per glyph
|
||||
void extendLength(int num) { m_numGlyphs += num; }
|
||||
size_t slotCount() const { return m_numGlyphs; } //one slot per glyph
|
||||
void extendLength(ptrdiff_t num) { m_numGlyphs += num; }
|
||||
Position advance() const { return m_advance; }
|
||||
bool runGraphite() { if (m_silf) return m_face->runGraphite(this, m_silf); else return true;};
|
||||
void chooseSilf(uint32 script) { m_silf = m_face->chooseSilf(script); }
|
||||
const Silf *silf() const { return m_silf; }
|
||||
unsigned int charInfoCount() const { return m_numCharinfo; }
|
||||
size_t charInfoCount() const { return m_numCharinfo; }
|
||||
const CharInfo *charinfo(unsigned int index) const { return index < m_numCharinfo ? m_charinfo + index : NULL; }
|
||||
CharInfo *charinfo(unsigned int index) { return index < m_numCharinfo ? m_charinfo + index : NULL; }
|
||||
|
||||
Segment(unsigned int numchars, const Face* face, uint32 script, int dir);
|
||||
Segment(size_t numchars, const Face* face, uint32 script, int dir);
|
||||
~Segment();
|
||||
#ifndef GRAPHITE2_NSEGCACHE
|
||||
SegmentScopeState setScope(Slot * firstSlot, Slot * lastSlot, size_t subLength);
|
||||
void removeScope(SegmentScopeState & state);
|
||||
void append(const Segment &other);
|
||||
void splice(size_t offset, size_t length, Slot * const startSlot,
|
||||
Slot * endSlot, const Slot * srcSlot,
|
||||
const size_t numGlyphs);
|
||||
#endif
|
||||
uint8 flags() const { return m_flags; }
|
||||
void flags(uint8 f) { m_flags = f; }
|
||||
Slot *first() { return m_first; }
|
||||
@ -123,14 +112,14 @@ public:
|
||||
SlotJustify *newJustify();
|
||||
void freeJustify(SlotJustify *aJustify);
|
||||
Position positionSlots(const Font *font=0, Slot *first=0, Slot *last=0, bool isRtl = false, bool isFinal = true);
|
||||
void associateChars(int offset, int num);
|
||||
void associateChars(int offset, size_t num);
|
||||
void linkClusters(Slot *first, Slot *last);
|
||||
uint16 getClassGlyph(uint16 cid, uint16 offset) const { return m_silf->getClassGlyph(cid, offset); }
|
||||
uint16 findClassIndex(uint16 cid, uint16 gid) const { return m_silf->findClassIndex(cid, gid); }
|
||||
int addFeatures(const Features& feats) { m_feats.push_back(feats); return m_feats.size() - 1; }
|
||||
int addFeatures(const Features& feats) { m_feats.push_back(feats); return int(m_feats.size()) - 1; }
|
||||
uint32 getFeature(int index, uint8 findex) const { const FeatureRef* pFR=m_face->theSill().theFeatureMap().featureRef(findex); if (!pFR) return 0; else return pFR->getFeatureVal(m_feats[index]); }
|
||||
void setFeature(int index, uint8 findex, uint32 val) {
|
||||
const FeatureRef* pFR=m_face->theSill().theFeatureMap().featureRef(findex);
|
||||
const FeatureRef* pFR=m_face->theSill().theFeatureMap().featureRef(findex);
|
||||
if (pFR)
|
||||
{
|
||||
if (val > pFR->maxVal()) val = pFR->maxVal();
|
||||
@ -139,8 +128,8 @@ public:
|
||||
int8 dir() const { return m_dir; }
|
||||
void dir(int8 val) { m_dir = val; }
|
||||
bool currdir() const { return ((m_dir >> 6) ^ m_dir) & 1; }
|
||||
unsigned int passBits() const { return m_passBits; }
|
||||
void mergePassBits(const unsigned int val) { m_passBits &= val; }
|
||||
uint8 passBits() const { return m_passBits; }
|
||||
void mergePassBits(const uint8 val) { m_passBits &= val; }
|
||||
int16 glyphAttr(uint16 gid, uint16 gattr) const { const GlyphFace * p = m_face->glyphs().glyphSafe(gid); return p ? p->attrs()[gattr] : 0; }
|
||||
int32 getGlyphMetric(Slot *iSlot, uint8 metric, uint8 attrLevel, bool rtl) const;
|
||||
float glyphAdvance(uint16 gid) const { return m_face->glyphs().glyph(gid)->theAdvance().x; }
|
||||
@ -168,7 +157,7 @@ public: //only used by: GrSegment* makeAndInitialize(const GrFont *font, c
|
||||
void finalise(const Font *font, bool reverse=false);
|
||||
float justify(Slot *pSlot, const Font *font, float width, enum justFlags flags, Slot *pFirst, Slot *pLast);
|
||||
bool initCollisions();
|
||||
|
||||
|
||||
private:
|
||||
Position m_advance; // whole segment advance
|
||||
SlotRope m_slots; // Vector of slot buffers
|
||||
@ -183,13 +172,13 @@ private:
|
||||
const Silf * m_silf;
|
||||
Slot * m_first; // first slot in segment
|
||||
Slot * m_last; // last slot in segment
|
||||
unsigned int m_bufSize, // how big a buffer to create when need more slots
|
||||
size_t m_bufSize, // how big a buffer to create when need more slots
|
||||
m_numGlyphs,
|
||||
m_numCharinfo, // size of the array and number of input characters
|
||||
m_passBits; // if bit set then skip pass
|
||||
m_numCharinfo; // size of the array and number of input characters
|
||||
int m_defaultOriginal; // number of whitespace chars in the string
|
||||
int8 m_dir;
|
||||
uint8 m_flags; // General purpose flags
|
||||
uint8 m_flags, // General purpose flags
|
||||
m_passBits; // if bit set then skip pass
|
||||
};
|
||||
|
||||
inline
|
||||
@ -245,4 +234,3 @@ bool Segment::isWhitespace(const int cid) const
|
||||
} // namespace graphite2
|
||||
|
||||
struct gr_segment : public graphite2::Segment {};
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -73,7 +73,7 @@ class Silf
|
||||
public:
|
||||
Silf() throw();
|
||||
~Silf() throw();
|
||||
|
||||
|
||||
bool readGraphite(const byte * const pSilf, size_t lSilf, Face &face, uint32 version);
|
||||
bool runGraphite(Segment *seg, uint8 firstPass=0, uint8 lastPass=0, int dobidi = 0) const;
|
||||
uint16 findClassIndex(uint16 cid, uint16 gid) const;
|
||||
@ -121,7 +121,7 @@ private:
|
||||
uint16 m_aLig, m_numPseudo, m_nClass, m_nLinear,
|
||||
m_gEndLine;
|
||||
gr_faceinfo m_silfinfo;
|
||||
|
||||
|
||||
void releaseBuffers() throw();
|
||||
};
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -37,7 +37,6 @@ namespace graphite2 {
|
||||
typedef gr_attrCode attrCode;
|
||||
|
||||
class GlyphFace;
|
||||
class SegCacheEntry;
|
||||
class Segment;
|
||||
|
||||
struct SlotJustify
|
||||
@ -163,7 +162,6 @@ private:
|
||||
int16 *m_userAttr; // pointer to user attributes
|
||||
SlotJustify *m_justs; // pointer to justification parameters
|
||||
|
||||
friend class SegCacheEntry;
|
||||
friend class Segment;
|
||||
};
|
||||
|
||||
|
@ -138,7 +138,7 @@ sparse::sparse(I attr, const I last)
|
||||
if (ci != ci_)
|
||||
{
|
||||
ci = ci_;
|
||||
ci->offset = vi - m_array.values;
|
||||
ci->offset = key_type(vi - m_array.values);
|
||||
}
|
||||
|
||||
ci->mask |= 1UL << (SIZEOF_CHUNK - 1 - (v.first % SIZEOF_CHUNK));
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -77,11 +77,11 @@ enum
|
||||
//**********************************************************************************************
|
||||
// Table declarations
|
||||
//**********************************************************************************************
|
||||
namespace Sfnt
|
||||
namespace Sfnt
|
||||
{
|
||||
#pragma pack(1) // We need this or the structure members aren't alligned
|
||||
#pragma pack(1) // We need this or the structure members aren't aligned
|
||||
// correctly. Fortunately this form of pragma is supposed
|
||||
// to be recongnised by VS C++ too (at least according to
|
||||
// to be recognised by VS C++ too (at least according to
|
||||
// MSDN).
|
||||
|
||||
struct OffsetSubTable
|
||||
@ -99,9 +99,9 @@ namespace Sfnt
|
||||
length;
|
||||
} table_directory[1];
|
||||
|
||||
enum ScalerType
|
||||
{
|
||||
TrueTypeMac = 0x74727565U,
|
||||
enum ScalerType
|
||||
{
|
||||
TrueTypeMac = 0x74727565U,
|
||||
TrueTypeWin = 0x00010000U,
|
||||
Type1 = 0x74797031U
|
||||
};
|
||||
@ -109,7 +109,7 @@ namespace Sfnt
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
struct CharacterCodeMap
|
||||
{
|
||||
uint16 version,
|
||||
@ -137,7 +137,7 @@ namespace Sfnt
|
||||
range_shift,
|
||||
end_code[1];
|
||||
// There are arrarys after this which need their
|
||||
// start positions calculated since end_code is
|
||||
// start positions calculated since end_code is
|
||||
// seg_count uint16s long.
|
||||
};
|
||||
|
||||
@ -147,7 +147,7 @@ namespace Sfnt
|
||||
uint32 length,
|
||||
language,
|
||||
num_groups;
|
||||
struct
|
||||
struct
|
||||
{
|
||||
uint32 start_char_code,
|
||||
end_char_code,
|
||||
@ -176,9 +176,9 @@ namespace Sfnt
|
||||
int16 font_direction_hint,
|
||||
index_to_loc_format,
|
||||
glyph_data_format;
|
||||
enum
|
||||
enum
|
||||
{
|
||||
MagicNumber = 0x5F0F3CF5,
|
||||
MagicNumber = 0x5F0F3CF5,
|
||||
GlypDataFormat = 0
|
||||
};
|
||||
enum {ShortIndexLocFormat, LongIndexLocFormat};
|
||||
@ -197,37 +197,37 @@ namespace Sfnt
|
||||
min_mem_type42,
|
||||
max_mem_type42,
|
||||
min_mem_type1,
|
||||
max_mem_type1;
|
||||
enum
|
||||
max_mem_type1;
|
||||
enum
|
||||
{
|
||||
Format1 = 0x10000,
|
||||
Format1 = 0x10000,
|
||||
Format2 = 0x20000,
|
||||
Format25 = 0x28000,
|
||||
Format3 = 0x30000,
|
||||
Format4 = 0x40000
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
struct PostScriptGlyphName2 : PostScriptGlyphName
|
||||
{
|
||||
uint16 number_of_glyphs,
|
||||
glyph_name_index[1];
|
||||
};
|
||||
|
||||
|
||||
struct PostScriptGlyphName25 : PostScriptGlyphName
|
||||
{
|
||||
uint16 number_of_glyphs;
|
||||
int8 offset[1];
|
||||
};
|
||||
|
||||
|
||||
struct PostScriptGlyphName3 : PostScriptGlyphName {};
|
||||
|
||||
|
||||
struct PostScriptGlyphName4 : PostScriptGlyphName
|
||||
{
|
||||
uint16 glyph_to_char_map[1];
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
struct HorizontalHeader
|
||||
{
|
||||
fixed version;
|
||||
@ -245,7 +245,7 @@ namespace Sfnt
|
||||
metric_data_format;
|
||||
uint16 num_long_hor_metrics;
|
||||
};
|
||||
|
||||
|
||||
struct MaximumProfile
|
||||
{
|
||||
fixed version;
|
||||
@ -297,23 +297,23 @@ namespace Sfnt
|
||||
type_linegap,
|
||||
win_ascent,
|
||||
win_descent;
|
||||
|
||||
enum
|
||||
|
||||
enum
|
||||
{
|
||||
Italic =0x01,
|
||||
Underscore=0x02,
|
||||
Negative =0x04,
|
||||
Outlined =0x08,
|
||||
StrikeOut =0x10,
|
||||
Italic =0x01,
|
||||
Underscore=0x02,
|
||||
Negative =0x04,
|
||||
Outlined =0x08,
|
||||
StrikeOut =0x10,
|
||||
Bold =0x20
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
struct Compatibility1 : Compatibility0
|
||||
{
|
||||
uint32 codepage_range[2];
|
||||
};
|
||||
|
||||
|
||||
struct Compatibility2 : Compatibility1
|
||||
{
|
||||
int16 x_height,
|
||||
@ -322,12 +322,12 @@ namespace Sfnt
|
||||
break_char,
|
||||
max_context;
|
||||
};
|
||||
|
||||
|
||||
struct Compatibility3 : Compatibility2 {};
|
||||
|
||||
|
||||
typedef Compatibility3 Compatibility;
|
||||
|
||||
|
||||
|
||||
|
||||
struct NameRecord
|
||||
{
|
||||
uint16 platform_id,
|
||||
@ -337,9 +337,9 @@ namespace Sfnt
|
||||
length,
|
||||
offset;
|
||||
enum {Unicode, Mactintosh, Reserved, Microsoft};
|
||||
enum
|
||||
enum
|
||||
{
|
||||
Copyright, Family, Subfamily, UniqueSubfamily,
|
||||
Copyright, Family, Subfamily, UniqueSubfamily,
|
||||
Fullname, Version, PostScript
|
||||
};
|
||||
};
|
||||
@ -357,15 +357,15 @@ namespace Sfnt
|
||||
string_offset;
|
||||
NameRecord name_record[1];
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
struct HorizontalMetric
|
||||
{
|
||||
uint16 advance_width;
|
||||
int16 left_side_bearing;
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
struct Glyph
|
||||
{
|
||||
int16 number_of_contours;
|
||||
@ -374,11 +374,11 @@ namespace Sfnt
|
||||
x_max,
|
||||
y_max;
|
||||
};
|
||||
|
||||
|
||||
struct SimpleGlyph : Glyph
|
||||
{
|
||||
uint16 end_pts_of_contours[1];
|
||||
enum
|
||||
enum
|
||||
{
|
||||
OnCurve = 0x01,
|
||||
XShort = 0x02,
|
||||
@ -390,12 +390,12 @@ namespace Sfnt
|
||||
YIsPos = 0x20
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
struct CompoundGlyph : Glyph
|
||||
{
|
||||
uint16 flags,
|
||||
glyph_index;
|
||||
enum
|
||||
enum
|
||||
{
|
||||
Arg1Arg2Words = 0x01,
|
||||
ArgsAreXYValues = 0x02,
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -43,6 +43,8 @@ namespace graphite2
|
||||
namespace TtfUtil
|
||||
{
|
||||
|
||||
#define OVERFLOW_OFFSET_CHECK(p, o) (o + reinterpret_cast<size_t>(p) < reinterpret_cast<size_t>(p))
|
||||
|
||||
typedef long fontTableId32;
|
||||
typedef unsigned short gid16;
|
||||
|
||||
@ -51,12 +53,12 @@ typedef unsigned short gid16;
|
||||
// Enumeration used to specify a table in a TTF file
|
||||
class Tag
|
||||
{
|
||||
unsigned long _v;
|
||||
unsigned int _v;
|
||||
public:
|
||||
Tag(const char n[5]) throw() : _v(TTF_TAG(n[0],n[1],n[2],n[3])) {}
|
||||
Tag(const unsigned long tag) throw() : _v(tag) {}
|
||||
Tag(const unsigned int tag) throw() : _v(tag) {}
|
||||
|
||||
operator unsigned long () const throw () { return _v; }
|
||||
operator unsigned int () const throw () { return _v; }
|
||||
|
||||
enum
|
||||
{
|
||||
@ -100,12 +102,12 @@ public:
|
||||
size_t & lOffset, size_t & lSize);
|
||||
bool CheckTable(const Tag TableId, const void * pTable, size_t lTableSize);
|
||||
|
||||
////////////////////////////////// simple font wide info
|
||||
size_t GlyphCount(const void * pMaxp);
|
||||
////////////////////////////////// simple font wide info
|
||||
size_t GlyphCount(const void * pMaxp);
|
||||
#ifdef ALL_TTFUTILS
|
||||
size_t MaxCompositeComponentCount(const void * pMaxp);
|
||||
size_t MaxCompositeLevelCount(const void * pMaxp);
|
||||
size_t LocaGlyphCount(size_t lLocaSize, const void * pHead); // throw (std::domain_error);
|
||||
size_t LocaGlyphCount(size_t lLocaSize, const void * pHead); // throw (std::domain_error);
|
||||
#endif
|
||||
int DesignUnits(const void * pHead);
|
||||
#ifdef ALL_TTFUTILS
|
||||
@ -120,7 +122,7 @@ public:
|
||||
bool Get31EngFullFontInfo(const void * pName, size_t & lOffset, size_t & lSize);
|
||||
bool Get30EngFamilyInfo(const void * pName, size_t & lOffset, size_t & lSize);
|
||||
bool Get30EngFullFontInfo(const void * pName, size_t & lOffset, size_t & lSize);
|
||||
int PostLookup(const void * pPost, size_t lPostSize, const void * pMaxp,
|
||||
int PostLookup(const void * pPost, size_t lPostSize, const void * pMaxp,
|
||||
const char * pPostName);
|
||||
#endif
|
||||
|
||||
@ -134,8 +136,8 @@ public:
|
||||
void SwapWString(void * pWStr, size_t nSize = 0); // throw (std::invalid_argument);
|
||||
#endif
|
||||
|
||||
////////////////////////////////// cmap lookup tools
|
||||
const void * FindCmapSubtable(const void * pCmap, int nPlatformId = 3,
|
||||
////////////////////////////////// cmap lookup tools
|
||||
const void * FindCmapSubtable(const void * pCmap, int nPlatformId = 3,
|
||||
int nEncodingId = 1, size_t length = 0);
|
||||
bool CheckCmapSubtable4(const void * pCmap31, const void * pCmapEnd /*, unsigned int maxgid*/);
|
||||
gid16 CmapSubtable4Lookup(const void * pCmapSubtabel4, unsigned int nUnicodeId, int rangeKey = 0);
|
||||
@ -147,57 +149,57 @@ public:
|
||||
int * pRangeKey = 0);
|
||||
|
||||
///////////////////////////////// horizontal metric data for a glyph
|
||||
bool HorMetrics(gid16 nGlyphId, const void * pHmtx, size_t lHmtxSize,
|
||||
bool HorMetrics(gid16 nGlyphId, const void * pHmtx, size_t lHmtxSize,
|
||||
const void * pHhea, int & nLsb, unsigned int & nAdvWid);
|
||||
|
||||
////////////////////////////////// primitives for loca and glyf lookup
|
||||
size_t LocaLookup(gid16 nGlyphId, const void * pLoca, size_t lLocaSize,
|
||||
const void * pHead); // throw (std::out_of_range);
|
||||
////////////////////////////////// primitives for loca and glyf lookup
|
||||
size_t LocaLookup(gid16 nGlyphId, const void * pLoca, size_t lLocaSize,
|
||||
const void * pHead); // throw (std::out_of_range);
|
||||
void * GlyfLookup(const void * pGlyf, size_t lGlyfOffset, size_t lTableLen);
|
||||
|
||||
////////////////////////////////// primitves for simple glyph data
|
||||
bool GlyfBox(const void * pSimpleGlyf, int & xMin, int & yMin,
|
||||
bool GlyfBox(const void * pSimpleGlyf, int & xMin, int & yMin,
|
||||
int & xMax, int & yMax);
|
||||
|
||||
#ifdef ALL_TTFUTILS
|
||||
int GlyfContourCount(const void * pSimpleGlyf);
|
||||
bool GlyfContourEndPoints(const void * pSimpleGlyf, int * prgnContourEndPoint,
|
||||
int GlyfContourCount(const void * pSimpleGlyf);
|
||||
bool GlyfContourEndPoints(const void * pSimpleGlyf, int * prgnContourEndPoint,
|
||||
int cnPointsTotal, size_t & cnPoints);
|
||||
bool GlyfPoints(const void * pSimpleGlyf, int * prgnX, int * prgnY,
|
||||
bool GlyfPoints(const void * pSimpleGlyf, int * prgnX, int * prgnY,
|
||||
char * prgbFlag, int cnPointsTotal, int & cnPoints);
|
||||
|
||||
|
||||
// primitive to find the glyph ids in a composite glyph
|
||||
bool GetComponentGlyphIds(const void * pSimpleGlyf, int * prgnCompId,
|
||||
bool GetComponentGlyphIds(const void * pSimpleGlyf, int * prgnCompId,
|
||||
size_t cnCompIdTotal, size_t & cnCompId);
|
||||
// primitive to find the placement data for a component in a composite glyph
|
||||
bool GetComponentPlacement(const void * pSimpleGlyf, int nCompId,
|
||||
bool fOffset, int & a, int & b);
|
||||
bool fOffset, int & a, int & b);
|
||||
// primitive to find the transform data for a component in a composite glyph
|
||||
bool GetComponentTransform(const void * pSimpleGlyf, int nCompId,
|
||||
float & flt11, float & flt12, float & flt21, float & flt22, bool & fTransOffset);
|
||||
#endif
|
||||
|
||||
////////////////////////////////// operate on composite or simple glyph (auto glyf lookup)
|
||||
void * GlyfLookup(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
void * GlyfLookup(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
size_t lGlyfSize, size_t lLocaSize, const void * pHead); // primitive used by below methods
|
||||
|
||||
#ifdef ALL_TTFUTILS
|
||||
// below are primary user methods for handling glyf data
|
||||
bool IsSpace(gid16 nGlyphId, const void * pLoca, size_t lLocaSize, const void * pHead);
|
||||
bool IsDeepComposite(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
bool IsDeepComposite(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
size_t lGlyfSize, size_t lLocaSize, const void * pHead);
|
||||
|
||||
bool GlyfBox(gid16 nGlyphId, const void * pGlyf, const void * pLoca, size_t lGlyfSize, size_t lLocaSize,
|
||||
bool GlyfBox(gid16 nGlyphId, const void * pGlyf, const void * pLoca, size_t lGlyfSize, size_t lLocaSize,
|
||||
const void * pHead, int & xMin, int & yMin, int & xMax, int & yMax);
|
||||
bool GlyfContourCount(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
bool GlyfContourCount(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
size_t lGlyfSize, size_t lLocaSize, const void *pHead, size_t & cnContours);
|
||||
bool GlyfContourEndPoints(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
size_t lGlyfSize, size_t lLocaSize, const void * pHead, int * prgnContourEndPoint, size_t cnPoints);
|
||||
bool GlyfPoints(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
size_t lGlyfSize, size_t lLocaSize, const void * pHead, const int * prgnContourEndPoint, size_t cnEndPoints,
|
||||
bool GlyfContourEndPoints(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
size_t lGlyfSize, size_t lLocaSize, const void * pHead, int * prgnContourEndPoint, size_t cnPoints);
|
||||
bool GlyfPoints(gid16 nGlyphId, const void * pGlyf, const void * pLoca,
|
||||
size_t lGlyfSize, size_t lLocaSize, const void * pHead, const int * prgnContourEndPoint, size_t cnEndPoints,
|
||||
int * prgnX, int * prgnY, bool * prgfOnCurve, size_t cnPoints);
|
||||
|
||||
// utitily method used by high-level GlyfPoints
|
||||
// utitily method used by high-level GlyfPoints
|
||||
bool SimplifyFlags(char * prgbFlags, int cnPoints);
|
||||
bool CalcAbsolutePoints(int * prgnX, int * prgnY, int cnPoints);
|
||||
#endif
|
||||
|
@ -40,7 +40,7 @@ struct _utf_codec
|
||||
|
||||
static void put(codeunit_t * cp, const uchar_t , int8 & len) throw();
|
||||
static uchar_t get(const codeunit_t * cp, int8 & len) throw();
|
||||
static bool validate(const codeunit_t * s, const codeunit_t * e) throw();
|
||||
static bool validate(const codeunit_t * s, const codeunit_t * const e) throw();
|
||||
};
|
||||
|
||||
|
||||
@ -66,9 +66,9 @@ public:
|
||||
}
|
||||
|
||||
inline
|
||||
static bool validate(codeunit_t * s, codeunit_t * e) throw()
|
||||
static bool validate(const codeunit_t * s, const codeunit_t * const e) throw()
|
||||
{
|
||||
return e > s;
|
||||
return s <= e;
|
||||
}
|
||||
};
|
||||
|
||||
@ -101,18 +101,19 @@ public:
|
||||
l = 1;
|
||||
|
||||
if (uh < 0xD800|| uh > 0xDFFF) { return uh; }
|
||||
if (uh > 0xDBFF) { l = -1; return 0xFFFD; }
|
||||
const uint32 ul = cp[1];
|
||||
if (uh > 0xDBFF || ul < 0xDC00 || ul > 0xDFFF) { l = -1; return 0xFFFD; }
|
||||
if (ul < 0xDC00 || ul > 0xDFFF) { l = -1; return 0xFFFD; }
|
||||
++l;
|
||||
return (uh<<10) + ul + surrogate_offset;
|
||||
}
|
||||
|
||||
inline
|
||||
static bool validate(codeunit_t * s, codeunit_t * e) throw()
|
||||
static bool validate(const codeunit_t * s, const codeunit_t * const e) throw()
|
||||
{
|
||||
const ptrdiff_t n = e-s;
|
||||
if (n <= 0) return n == 0;
|
||||
const uint32 u = *(s+(n-1)); // Get the last codepoint
|
||||
const uint32 u = *(e-1); // Get the last codepoint
|
||||
return (u < 0xD800 || u > 0xDBFF);
|
||||
}
|
||||
};
|
||||
@ -166,7 +167,7 @@ public:
|
||||
}
|
||||
|
||||
inline
|
||||
static bool validate(codeunit_t * s, codeunit_t * e) throw()
|
||||
static bool validate(const codeunit_t * s, const codeunit_t * const e) throw()
|
||||
{
|
||||
const ptrdiff_t n = e-s;
|
||||
if (n <= 0) return n == 0;
|
||||
@ -175,7 +176,7 @@ public:
|
||||
if (*s >= 0xC0) return false;
|
||||
if (n == 1) return true;
|
||||
if (*--s < 0x80) return true;
|
||||
if (*s >= 0xe0) return false;
|
||||
if (*s >= 0xE0) return false;
|
||||
if (n == 2 || *s >= 0xC0) return true;
|
||||
if (*--s < 0x80) return true;
|
||||
if (*s >= 0xF0) return false;
|
||||
@ -225,6 +226,7 @@ public:
|
||||
operator codeunit_type * () const throw() { return cp; }
|
||||
|
||||
bool error() const throw() { return sl < 1; }
|
||||
bool validate(const _utf_iterator & e) { return codec::validate(cp, e.cp); }
|
||||
};
|
||||
|
||||
template <typename C>
|
||||
|
@ -73,30 +73,34 @@ inline unsigned int bit_set_count(signed long long v)
|
||||
{
|
||||
return __builtin_popcountll(v);
|
||||
}
|
||||
|
||||
#else
|
||||
|
||||
template<typename T>
|
||||
inline unsigned int bit_set_count(T v)
|
||||
{
|
||||
v = v - ((v >> 1) & T(~(0UL)/3)); // temp
|
||||
v = (v & T(~(0UL)/15*3)) + ((v >> 2) & T(~(0UL)/15*3)); // temp
|
||||
v = (v + (v >> 4)) & T(~(0UL)/255*15); // temp
|
||||
return (T)(v * T(~(0UL)/255)) >> (sizeof(T)-1)*8; // count
|
||||
static size_t const ONES = ~0;
|
||||
|
||||
v = v - ((v >> 1) & T(ONES/3)); // temp
|
||||
v = (v & T(ONES/15*3)) + ((v >> 2) & T(ONES/15*3)); // temp
|
||||
v = (v + (v >> 4)) & T(ONES/255*15); // temp
|
||||
return (T)(v * T(ONES/255)) >> (sizeof(T)-1)*8; // count
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
//TODO: Changed these to uintmax_t when we go to C++11
|
||||
template<int S>
|
||||
inline unsigned long _mask_over_val(unsigned long v)
|
||||
inline size_t _mask_over_val(size_t v)
|
||||
{
|
||||
v = _mask_over_val<S/2>(v);
|
||||
v |= v >> S*4;
|
||||
return v;
|
||||
}
|
||||
|
||||
//TODO: Changed these to uintmax_t when we go to C++11
|
||||
template<>
|
||||
inline unsigned long _mask_over_val<1>(unsigned long v)
|
||||
inline size_t _mask_over_val<1>(size_t v)
|
||||
{
|
||||
v |= v >> 1;
|
||||
v |= v >> 2;
|
||||
@ -107,7 +111,7 @@ inline unsigned long _mask_over_val<1>(unsigned long v)
|
||||
template<typename T>
|
||||
inline T mask_over_val(T v)
|
||||
{
|
||||
return _mask_over_val<sizeof(T)>(v);
|
||||
return T(_mask_over_val<sizeof(T)>(v));
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
|
@ -33,6 +33,7 @@ of the License or (at your option) any later version.
|
||||
#include "inc/Main.h"
|
||||
#include <cassert>
|
||||
#include <cstdio>
|
||||
#include <cstdint>
|
||||
#include "inc/List.h"
|
||||
|
||||
namespace graphite2 {
|
||||
@ -44,7 +45,6 @@ class json
|
||||
json & operator = (const json &);
|
||||
|
||||
typedef void (*_context_t)(json &);
|
||||
class _null_t {};
|
||||
|
||||
FILE * const _stream;
|
||||
char _contexts[128], // context stack
|
||||
@ -61,11 +61,12 @@ class json
|
||||
public:
|
||||
class closer;
|
||||
|
||||
typedef const char * string;
|
||||
typedef double number;
|
||||
typedef long signed int integer;
|
||||
typedef bool boolean;
|
||||
static const _null_t null;
|
||||
using string = const char *;
|
||||
using number = double;
|
||||
enum class integer : std::intmax_t {};
|
||||
enum class integer_u : std::uintmax_t {};
|
||||
using boolean = bool;
|
||||
static const std::nullptr_t null;
|
||||
|
||||
void setenv(unsigned int index, void *val) { _env.reserve(index + 1); if (index >= _env.size()) _env.insert(_env.end(), _env.size() - index + 1, 0); _env[index] = val; }
|
||||
void *getenv(unsigned int index) const { return _env[index]; }
|
||||
@ -85,9 +86,9 @@ public:
|
||||
json & operator << (string) throw();
|
||||
json & operator << (number) throw();
|
||||
json & operator << (integer) throw();
|
||||
json & operator << (long unsigned int d) throw();
|
||||
json & operator << (integer_u) throw();
|
||||
json & operator << (boolean) throw();
|
||||
json & operator << (_null_t) throw();
|
||||
json & operator << (std::nullptr_t) throw();
|
||||
json & operator << (_context_t) throw();
|
||||
|
||||
operator bool() const throw();
|
||||
@ -136,29 +137,34 @@ json & json::operator << (json::_context_t ctxt) throw()
|
||||
}
|
||||
|
||||
inline
|
||||
json & operator << (json & j, signed char d) throw() { return j << json::integer(d); }
|
||||
json & operator << (json & j, signed char d) throw() { return j << json::integer(d); }
|
||||
|
||||
inline
|
||||
json & operator << (json & j, short signed int d) throw() { return j << json::integer(d); }
|
||||
json & operator << (json & j, unsigned char d) throw() { return j << json::integer_u(d); }
|
||||
|
||||
inline
|
||||
json & operator << (json & j, signed int d) throw() { return j << json::integer(d); }
|
||||
json & operator << (json & j, short int d) throw() { return j << json::integer(d); }
|
||||
|
||||
inline
|
||||
json & operator << (json & j, unsigned char d) throw() { return j << json::integer(d); }
|
||||
json & operator << (json & j, unsigned short int d) throw() { return j << json::integer_u(d); }
|
||||
|
||||
inline
|
||||
json & operator << (json & j, short unsigned int d) throw() { return j << json::integer(d); }
|
||||
json & operator << (json & j, int d) throw() { return j << json::integer(d); }
|
||||
|
||||
inline
|
||||
json & operator << (json & j, unsigned int d) throw() { return j << json::integer(d); }
|
||||
json & operator << (json & j, unsigned int d) throw() { return j << json::integer_u(d); }
|
||||
|
||||
inline
|
||||
json & operator << (json & j, char c) throw ()
|
||||
{
|
||||
const char str[2] = {c,0};
|
||||
return j << str;
|
||||
}
|
||||
json & operator << (json & j, long int d) throw() { return j << json::integer(d); }
|
||||
|
||||
inline
|
||||
json & operator << (json & j, unsigned long int d) throw() { return j << json::integer_u(d); }
|
||||
|
||||
inline
|
||||
json & operator << (json & j, long long int d) throw() { return j << json::integer(d); }
|
||||
|
||||
inline
|
||||
json & operator << (json & j, unsigned long long int d) throw() { return j << json::integer_u(d); }
|
||||
|
||||
inline
|
||||
json::operator bool() const throw() { return good(); }
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -41,7 +41,7 @@ of the License or (at your option) any later version.
|
||||
// gmetric - 0 .. 11 (kgmetDescent)
|
||||
// featidx - 0 .. face.numFeatures()
|
||||
// level - any byte
|
||||
static const opcode_t opcode_table[] =
|
||||
static const opcode_t opcode_table[] =
|
||||
{
|
||||
{{do2(nop)}, 0, "NOP"},
|
||||
|
||||
@ -122,4 +122,3 @@ static const opcode_t opcode_table[] =
|
||||
// private opcodes for internal use only, comes after all other on disk opcodes.
|
||||
{{do_(temp_copy), NILOP}, 0, "TEMP_COPY"}
|
||||
};
|
||||
|
||||
|
@ -15,8 +15,8 @@
|
||||
|
||||
You should also have received a copy of the GNU Lesser General Public
|
||||
License along with this library in the file named "LICENSE".
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
If not, write to the Free Software Foundation, 51 Franklin Street,
|
||||
Suite 500, Boston, MA 02110-1335, USA or visit their web page on the
|
||||
internet at http://www.fsf.org/licenses/lgpl.html.
|
||||
|
||||
Alternatively, the contents of this file may be used under the terms of the
|
||||
@ -33,20 +33,20 @@ of the License or (at your option) any later version.
|
||||
// ==================
|
||||
// You have access to a few primitives and the full C++ code:
|
||||
// declare_params(n) Tells the interpreter how many bytes of parameter
|
||||
// space to claim for this instruction uses and
|
||||
// initialises the param pointer. You *must* before the
|
||||
// space to claim for this instruction uses and
|
||||
// initialises the param pointer. You *must* before the
|
||||
// first use of param.
|
||||
// use_params(n) Claim n extra bytes of param space beyond what was
|
||||
// use_params(n) Claim n extra bytes of param space beyond what was
|
||||
// claimed using delcare_param.
|
||||
// param A const byte pointer for the parameter space claimed by
|
||||
// this instruction.
|
||||
// binop(op) Implement a binary operation on the stack using the
|
||||
// binop(op) Implement a binary operation on the stack using the
|
||||
// specified C++ operator.
|
||||
// NOT_IMPLEMENTED Any instruction body containing this will exit the
|
||||
// NOT_IMPLEMENTED Any instruction body containing this will exit the
|
||||
// program with an assertion error. Instructions that are
|
||||
// not implemented should also be marked NILOP in the
|
||||
// opcodes tables this will cause the code class to spot
|
||||
// them in a live code stream and throw a runtime_error
|
||||
// them in a live code stream and throw a runtime_error
|
||||
// instead.
|
||||
// push(n) Push the value n onto the stack.
|
||||
// pop() Pop the top most value and return it.
|
||||
@ -62,7 +62,7 @@ of the License or (at your option) any later version.
|
||||
// ip = The current instruction pointer
|
||||
// endPos = Position of advance of last cluster
|
||||
// dir = writing system directionality of the font
|
||||
|
||||
|
||||
|
||||
// #define NOT_IMPLEMENTED assert(false)
|
||||
// #define NOT_IMPLEMENTED
|
||||
@ -96,7 +96,7 @@ ENDOP
|
||||
|
||||
STARTOP(push_short)
|
||||
declare_params(2);
|
||||
const int16 r = int16(param[0]) << 8
|
||||
const int16 r = int16(param[0]) << 8
|
||||
| uint8(param[1]);
|
||||
push(r);
|
||||
ENDOP
|
||||
@ -322,7 +322,7 @@ STARTOP(insert)
|
||||
smap.highpassed(false);
|
||||
is = newSlot;
|
||||
seg.extendLength(1);
|
||||
if (map != &smap[-1])
|
||||
if (map != &smap[-1])
|
||||
--map;
|
||||
ENDOP
|
||||
|
||||
@ -333,12 +333,12 @@ STARTOP(delete_)
|
||||
is->prev()->next(is->next());
|
||||
else
|
||||
seg.first(is->next());
|
||||
|
||||
|
||||
if (is->next())
|
||||
is->next()->prev(is->prev());
|
||||
else
|
||||
seg.last(is->prev());
|
||||
|
||||
|
||||
|
||||
if (is == smap.highwater())
|
||||
smap.highwater(is->next());
|
||||
@ -371,7 +371,7 @@ ENDOP
|
||||
|
||||
STARTOP(cntxt_item)
|
||||
// It turns out this is a cunningly disguised condition forward jump.
|
||||
declare_params(3);
|
||||
declare_params(3);
|
||||
const int is_arg = int8(param[0]);
|
||||
const size_t iskip = uint8(param[1]),
|
||||
dskip = uint8(param[2]);
|
||||
@ -387,49 +387,49 @@ ENDOP
|
||||
STARTOP(attr_set)
|
||||
declare_params(1);
|
||||
const attrCode slat = attrCode(uint8(*param));
|
||||
const int val = int(pop());
|
||||
const int val = pop();
|
||||
is->setAttr(&seg, slat, 0, val, smap);
|
||||
ENDOP
|
||||
|
||||
STARTOP(attr_add)
|
||||
declare_params(1);
|
||||
const attrCode slat = attrCode(uint8(*param));
|
||||
const int val = int(pop());
|
||||
const uint32_t val = pop();
|
||||
if ((slat == gr_slatPosX || slat == gr_slatPosY) && (flags & POSITIONED) == 0)
|
||||
{
|
||||
seg.positionSlots(0, *smap.begin(), *(smap.end()-1), seg.currdir());
|
||||
flags |= POSITIONED;
|
||||
}
|
||||
int res = is->getAttr(&seg, slat, 0);
|
||||
is->setAttr(&seg, slat, 0, val + res, smap);
|
||||
uint32_t res = uint32_t(is->getAttr(&seg, slat, 0));
|
||||
is->setAttr(&seg, slat, 0, int32_t(val + res), smap);
|
||||
ENDOP
|
||||
|
||||
STARTOP(attr_sub)
|
||||
declare_params(1);
|
||||
const attrCode slat = attrCode(uint8(*param));
|
||||
const int val = int(pop());
|
||||
const uint32_t val = pop();
|
||||
if ((slat == gr_slatPosX || slat == gr_slatPosY) && (flags & POSITIONED) == 0)
|
||||
{
|
||||
seg.positionSlots(0, *smap.begin(), *(smap.end()-1), seg.currdir());
|
||||
flags |= POSITIONED;
|
||||
}
|
||||
int res = is->getAttr(&seg, slat, 0);
|
||||
is->setAttr(&seg, slat, 0, res - val, smap);
|
||||
uint32_t res = uint32_t(is->getAttr(&seg, slat, 0));
|
||||
is->setAttr(&seg, slat, 0, int32_t(res - val), smap);
|
||||
ENDOP
|
||||
|
||||
STARTOP(attr_set_slot)
|
||||
declare_params(1);
|
||||
const attrCode slat = attrCode(uint8(*param));
|
||||
const int offset = (map - smap.begin())*int(slat == gr_slatAttTo);
|
||||
const int val = int(pop()) + offset;
|
||||
const attrCode slat = attrCode(uint8(*param));
|
||||
const int offset = int(map - smap.begin())*int(slat == gr_slatAttTo);
|
||||
const int val = pop() + offset;
|
||||
is->setAttr(&seg, slat, offset, val, smap);
|
||||
ENDOP
|
||||
|
||||
STARTOP(iattr_set_slot)
|
||||
declare_params(2);
|
||||
const attrCode slat = attrCode(uint8(param[0]));
|
||||
const size_t idx = uint8(param[1]);
|
||||
const int val = int(pop()) + (map - smap.begin())*int(slat == gr_slatAttTo);
|
||||
const attrCode slat = attrCode(uint8(param[0]));
|
||||
const uint8 idx = uint8(param[1]);
|
||||
const int val = int(pop() + (map - smap.begin())*int(slat == gr_slatAttTo));
|
||||
is->setAttr(&seg, slat, idx, val, smap);
|
||||
ENDOP
|
||||
|
||||
@ -531,7 +531,7 @@ STARTOP(push_iglyph_attr) // not implemented
|
||||
NOT_IMPLEMENTED;
|
||||
ENDOP
|
||||
#endif
|
||||
|
||||
|
||||
STARTOP(pop_ret)
|
||||
const uint32 ret = pop();
|
||||
EXIT(ret);
|
||||
@ -548,37 +548,37 @@ ENDOP
|
||||
STARTOP(iattr_set)
|
||||
declare_params(2);
|
||||
const attrCode slat = attrCode(uint8(param[0]));
|
||||
const size_t idx = uint8(param[1]);
|
||||
const int val = int(pop());
|
||||
const uint8 idx = uint8(param[1]);
|
||||
const int val = pop();
|
||||
is->setAttr(&seg, slat, idx, val, smap);
|
||||
ENDOP
|
||||
|
||||
STARTOP(iattr_add)
|
||||
declare_params(2);
|
||||
const attrCode slat = attrCode(uint8(param[0]));
|
||||
const size_t idx = uint8(param[1]);
|
||||
const int val = int(pop());
|
||||
const uint8 idx = uint8(param[1]);
|
||||
const uint32_t val = pop();
|
||||
if ((slat == gr_slatPosX || slat == gr_slatPosY) && (flags & POSITIONED) == 0)
|
||||
{
|
||||
seg.positionSlots(0, *smap.begin(), *(smap.end()-1), seg.currdir());
|
||||
flags |= POSITIONED;
|
||||
}
|
||||
int res = is->getAttr(&seg, slat, idx);
|
||||
is->setAttr(&seg, slat, idx, val + res, smap);
|
||||
uint32_t res = uint32_t(is->getAttr(&seg, slat, idx));
|
||||
is->setAttr(&seg, slat, idx, int32_t(val + res), smap);
|
||||
ENDOP
|
||||
|
||||
STARTOP(iattr_sub)
|
||||
declare_params(2);
|
||||
const attrCode slat = attrCode(uint8(param[0]));
|
||||
const size_t idx = uint8(param[1]);
|
||||
const int val = int(pop());
|
||||
const uint8 idx = uint8(param[1]);
|
||||
const uint32_t val = pop();
|
||||
if ((slat == gr_slatPosX || slat == gr_slatPosY) && (flags & POSITIONED) == 0)
|
||||
{
|
||||
seg.positionSlots(0, *smap.begin(), *(smap.end()-1), seg.currdir());
|
||||
flags |= POSITIONED;
|
||||
}
|
||||
int res = is->getAttr(&seg, slat, idx);
|
||||
is->setAttr(&seg, slat, idx, res - val, smap);
|
||||
uint32_t res = uint32_t(is->getAttr(&seg, slat, idx));
|
||||
is->setAttr(&seg, slat, idx, int32_t(res - val), smap);
|
||||
ENDOP
|
||||
|
||||
STARTOP(push_proc_state)
|
||||
@ -689,4 +689,3 @@ STARTOP(set_feat)
|
||||
seg.setFeature(fid, feat, pop());
|
||||
}
|
||||
ENDOP
|
||||
|
||||
|
@ -33,6 +33,14 @@ of the License or (at your option) any later version.
|
||||
#include <limits>
|
||||
#include "inc/json.h"
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#define FORMAT_INTMAX "%lli"
|
||||
#define FORMAT_UINTMAX "%llu"
|
||||
#else
|
||||
#define FORMAT_INTMAX "%ji"
|
||||
#define FORMAT_UINTMAX "%ju"
|
||||
#endif
|
||||
|
||||
using namespace graphite2;
|
||||
|
||||
namespace
|
||||
@ -45,7 +53,7 @@ namespace
|
||||
};
|
||||
}
|
||||
|
||||
const json::_null_t json::null = {};
|
||||
const std::nullptr_t json::null = nullptr;
|
||||
|
||||
inline
|
||||
void json::context(const char current) throw()
|
||||
@ -118,8 +126,8 @@ json & json::operator << (json::string s) throw()
|
||||
}
|
||||
|
||||
json & json::operator << (json::number f) throw()
|
||||
{
|
||||
context(seq);
|
||||
{
|
||||
context(seq);
|
||||
if (std::numeric_limits<json::number>::infinity() == f)
|
||||
fputs("Infinity", _stream);
|
||||
else if (-std::numeric_limits<json::number>::infinity() == f)
|
||||
@ -128,13 +136,12 @@ json & json::operator << (json::number f) throw()
|
||||
std::numeric_limits<json::number>::signaling_NaN() == f)
|
||||
fputs("NaN", _stream);
|
||||
else
|
||||
fprintf(_stream, "%g", f);
|
||||
return *this;
|
||||
fprintf(_stream, "%g", f);
|
||||
return *this;
|
||||
}
|
||||
json & json::operator << (json::integer d) throw() { context(seq); fprintf(_stream, "%ld", d); return *this; }
|
||||
json & json::operator << (long unsigned d) throw() { context(seq); fprintf(_stream, "%ld", d); return *this; }
|
||||
json & json::operator << (json::integer d) throw() { context(seq); fprintf(_stream, FORMAT_INTMAX, intmax_t(d)); return *this; }
|
||||
json & json::operator << (json::integer_u d) throw() { context(seq); fprintf(_stream, FORMAT_UINTMAX, uintmax_t(d)); return *this; }
|
||||
json & json::operator << (json::boolean b) throw() { context(seq); fputs(b ? "true" : "false", _stream); return *this; }
|
||||
json & json::operator << (json::_null_t) throw() { context(seq); fputs("null",_stream); return *this; }
|
||||
json & json::operator << (std::nullptr_t) throw() { context(seq); fputs("null",_stream); return *this; }
|
||||
|
||||
#endif
|
||||
|
||||
|
@ -23,7 +23,6 @@ else:
|
||||
|
||||
# This should contain all of the _SOURCES from files.mk, except *_machine.cpp
|
||||
UNIFIED_SOURCES += [
|
||||
'CachedFace.cpp',
|
||||
'CmapCache.cpp',
|
||||
'Code.cpp',
|
||||
'Collider.cpp',
|
||||
@ -46,9 +45,6 @@ UNIFIED_SOURCES += [
|
||||
'Justifier.cpp',
|
||||
'Pass.cpp',
|
||||
'Position.cpp',
|
||||
'SegCache.cpp',
|
||||
'SegCacheEntry.cpp',
|
||||
'SegCacheStore.cpp',
|
||||
'Segment.cpp',
|
||||
'Silf.cpp',
|
||||
'Slot.cpp',
|
||||
|
Loading…
Reference in New Issue
Block a user