[icu-le] Start adding a icu-layout-engine backend

Import PortableFontInstance and add shaper stub.
This commit is contained in:
Behdad Esfahbod 2012-08-23 21:23:41 -04:00
parent b5584ee4be
commit 7d242364ea
14 changed files with 1674 additions and 0 deletions

View File

@ -160,6 +160,14 @@ AM_CONDITIONAL(HAVE_ICU, $have_icu)
dnl ==========================================================================
PKG_CHECK_MODULES(ICU_LE, icu-le, have_icu_le=true, have_icu_le=false)
if $have_icu_le; then
AC_DEFINE(HAVE_ICU_LE, 1, [Have ICU Layout Engine library])
fi
AM_CONDITIONAL(HAVE_ICU_LE, $have_icu_le)
dnl ==========================================================================
PKG_CHECK_MODULES(GRAPHITE2, graphite2, have_graphite=true, have_graphite=false)
if $have_graphite; then
AC_DEFINE(HAVE_GRAPHITE2, 1, [Have Graphite library])
@ -229,6 +237,7 @@ harfbuzz.pc
src/Makefile
src/hb-version.h
src/hb-old/Makefile
src/hb-icu-le/Makefile
util/Makefile
test/Makefile
test/api/Makefile

View File

@ -163,6 +163,14 @@ HBSOURCES += hb-old.cc
endif
DIST_SUBDIRS += hb-old
if HAVE_ICU_LE
SUBDIRS += hb-icu-le
HBCFLAGS += -I$(srcdir)/hb-icu-le
HBLIBS += hb-icu-le/libhb-icu-le.la
HBSOURCES += hb-icu-le.cc
endif
DIST_SUBDIRS += hb-icu-le
# Put the library together

111
src/hb-icu-le.cc Normal file
View File

@ -0,0 +1,111 @@
/*
* Copyright © 2012 Google, Inc.
*
* This is part of HarfBuzz, a text shaping library.
*
* Permission is hereby granted, without written agreement and without
* license or royalty fees, to use, copy, modify, and distribute this
* software and its documentation for any purpose, provided that the
* above copyright notice and the following two paragraphs appear in
* all copies of this software.
*
* IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
* DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
* ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
* IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
* DAMAGE.
*
* THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
* BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
* FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
* ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
* PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
*
* Google Author(s): Behdad Esfahbod
*/
#define HB_SHAPER icu_le
#include "hb-shaper-impl-private.hh"
#include "hb-icu-le/PortableFontInstance.h"
#include "layout/loengine.h"
#include <harfbuzz.h>
#ifndef HB_DEBUG_ICU_LE
#define HB_DEBUG_ICU_LE (HB_DEBUG+0)
#endif
/*
* shaper face data
*/
struct hb_icu_le_shaper_face_data_t {};
hb_icu_le_shaper_face_data_t *
_hb_icu_le_shaper_face_data_create (hb_face_t *face)
{
return (hb_icu_le_shaper_face_data_t *) HB_SHAPER_DATA_SUCCEEDED;
}
void
_hb_icu_le_shaper_face_data_destroy (hb_icu_le_shaper_face_data_t *data)
{
}
/*
* shaper font data
*/
struct hb_icu_le_shaper_font_data_t {};
hb_icu_le_shaper_font_data_t *
_hb_icu_le_shaper_font_data_create (hb_font_t *font)
{
return (hb_icu_le_shaper_font_data_t *) HB_SHAPER_DATA_SUCCEEDED;
}
void
_hb_icu_le_shaper_font_data_destroy (hb_icu_le_shaper_font_data_t *data)
{
free (data);
}
/*
* shaper shape_plan data
*/
struct hb_icu_le_shaper_shape_plan_data_t {};
hb_icu_le_shaper_shape_plan_data_t *
_hb_icu_le_shaper_shape_plan_data_create (hb_shape_plan_t *shape_plan,
const hb_feature_t *user_features,
unsigned int num_user_features)
{
return (hb_icu_le_shaper_shape_plan_data_t *) HB_SHAPER_DATA_SUCCEEDED;
}
void
_hb_icu_le_shaper_shape_plan_data_destroy (hb_icu_le_shaper_shape_plan_data_t *data)
{
}
/*
* shaper
*/
hb_bool_t
_hb_icu_le_shape (hb_shape_plan_t *shape_plan,
hb_font_t *font,
hb_buffer_t *buffer,
const hb_feature_t *features,
unsigned int num_features)
{
return false;
}

View File

@ -0,0 +1,91 @@
/*
**********************************************************************
* Copyright (C) 2003-2008, International Business Machines
* Corporation and others. All Rights Reserved.
**********************************************************************
*/
#include "layout/LETypes.h"
#include "letest.h"
#include "FontTableCache.h"
#define TABLE_CACHE_INIT 5
#define TABLE_CACHE_GROW 5
struct FontTableCacheEntry
{
LETag tag;
const void *table;
};
FontTableCache::FontTableCache()
: fTableCacheCurr(0), fTableCacheSize(TABLE_CACHE_INIT)
{
fTableCache = NEW_ARRAY(FontTableCacheEntry, fTableCacheSize);
if (fTableCache == NULL) {
fTableCacheSize = 0;
return;
}
for (int i = 0; i < fTableCacheSize; i += 1) {
fTableCache[i].tag = 0;
fTableCache[i].table = NULL;
}
}
FontTableCache::~FontTableCache()
{
for (int i = fTableCacheCurr - 1; i >= 0; i -= 1) {
DELETE_ARRAY(fTableCache[i].table);
fTableCache[i].tag = 0;
fTableCache[i].table = NULL;
}
fTableCacheCurr = 0;
DELETE_ARRAY(fTableCache);
}
void FontTableCache::freeFontTable(const void *table) const
{
DELETE_ARRAY(table);
}
const void *FontTableCache::find(LETag tableTag) const
{
for (int i = 0; i < fTableCacheCurr; i += 1) {
if (fTableCache[i].tag == tableTag) {
return fTableCache[i].table;
}
}
const void *table = readFontTable(tableTag);
((FontTableCache *) this)->add(tableTag, table);
return table;
}
void FontTableCache::add(LETag tableTag, const void *table)
{
if (fTableCacheCurr >= fTableCacheSize) {
le_int32 newSize = fTableCacheSize + TABLE_CACHE_GROW;
fTableCache = (FontTableCacheEntry *) GROW_ARRAY(fTableCache, newSize);
for (le_int32 i = fTableCacheSize; i < newSize; i += 1) {
fTableCache[i].tag = 0;
fTableCache[i].table = NULL;
}
fTableCacheSize = newSize;
}
fTableCache[fTableCacheCurr].tag = tableTag;
fTableCache[fTableCacheCurr].table = table;
fTableCacheCurr += 1;
}

View File

@ -0,0 +1,41 @@
/*
**********************************************************************
* Copyright (C) 2003-2008, International Business Machines
* Corporation and others. All Rights Reserved.
**********************************************************************
*/
#ifndef __FONTTABLECACHE_H
#define __FONTTABLECACHE_H
#include "layout/LETypes.h"
U_NAMESPACE_USE
struct FontTableCacheEntry;
class FontTableCache
{
public:
FontTableCache();
virtual ~FontTableCache();
const void *find(LETag tableTag) const;
protected:
virtual const void *readFontTable(LETag tableTag) const = 0;
virtual void freeFontTable(const void *table) const;
private:
void add(LETag tableTag, const void *table);
FontTableCacheEntry *fTableCache;
le_int32 fTableCacheCurr;
le_int32 fTableCacheSize;
};
#endif

25
src/hb-icu-le/Makefile.am Normal file
View File

@ -0,0 +1,25 @@
## Process this file with automake to produce Makefile.in
noinst_LTLIBRARIES = libhb-icu-le.la
libhb_icu_le_la_SOURCES = \
FontTableCache.cpp \
FontTableCache.h \
PortableFontInstance.cpp \
PortableFontInstance.h \
cmaps.cpp \
cmaps.h \
letest.h \
sfnt.h
libhb_icu_le_la_CPPFLAGS = \
-I$(top_srcdir) \
-I$(top_srcdir)/src \
-I$(top_builddir)/src \
$(ICU_LE_CFLAGS)
libhb_icu_le_la_LIBADD = \
$(ICU_LE_LIBS)
EXTRA_DIST = README license.html
-include $(top_srcdir)/git.mk

View File

@ -0,0 +1,436 @@
/*
*******************************************************************************
*
* Copyright (C) 1999-2008, International Business Machines
* Corporation and others. All Rights Reserved.
*
*******************************************************************************
* file name: PortableFontInstance.cpp
*
* created on: 11/22/1999
* created by: Eric R. Mader
*/
#include <stdio.h>
#include "layout/LETypes.h"
#include "layout/LEFontInstance.h"
#include "layout/LESwaps.h"
#include "PortableFontInstance.h"
#include "letest.h"
#include "sfnt.h"
#include <string.h>
//
// Finds the high bit by binary searching
// through the bits in n.
//
le_int8 PortableFontInstance::highBit(le_int32 value)
{
if (value <= 0) {
return -32;
}
le_uint8 bit = 0;
if (value >= 1 << 16) {
value >>= 16;
bit += 16;
}
if (value >= 1 << 8) {
value >>= 8;
bit += 8;
}
if (value >= 1 << 4) {
value >>= 4;
bit += 4;
}
if (value >= 1 << 2) {
value >>= 2;
bit += 2;
}
if (value >= 1 << 1) {
value >>= 1;
bit += 1;
}
return bit;
}
PortableFontInstance::PortableFontInstance(const char *fileName, float pointSize, LEErrorCode &status)
: fFile(NULL), fPointSize(pointSize), fUnitsPerEM(0), fFontChecksum(0), fAscent(0), fDescent(0), fLeading(0),
fDirectory(NULL), fNAMETable(NULL), fNameCount(0), fNameStringOffset(0), fCMAPMapper(NULL), fHMTXTable(NULL), fNumGlyphs(0), fNumLongHorMetrics(0)
{
if (LE_FAILURE(status)) {
return;
}
// open the font file
fFile = fopen(fileName, "rb");
if (fFile == NULL) {
status = LE_FONT_FILE_NOT_FOUND_ERROR;
return;
}
// read in the directory
SFNTDirectory tempDir;
fread(&tempDir, sizeof tempDir, 1, fFile);
le_int32 dirSize = sizeof tempDir + ((SWAPW(tempDir.numTables) - ANY_NUMBER) * sizeof(DirectoryEntry));
const LETag headTag = LE_HEAD_TABLE_TAG;
const LETag hheaTag = LE_HHEA_TABLE_TAG;
const HEADTable *headTable = NULL;
const HHEATable *hheaTable = NULL;
// const NAMETable *nameTable = NULL;
le_uint16 numTables = 0;
fDirectory = (const SFNTDirectory *) NEW_ARRAY(char, dirSize);
if (fDirectory == NULL) {
status = LE_MEMORY_ALLOCATION_ERROR;
goto error_exit;
}
fseek(fFile, 0L, SEEK_SET);
fread((void *) fDirectory, sizeof(char), dirSize, fFile);
//
// We calculate these numbers 'cause some fonts
// have bogus values for them in the directory header.
//
numTables = SWAPW(fDirectory->numTables);
fDirPower = 1 << highBit(numTables);
fDirExtra = numTables - fDirPower;
// read unitsPerEm from 'head' table
headTable = (const HEADTable *) readFontTable(headTag);
if (headTable == NULL) {
status = LE_MISSING_FONT_TABLE_ERROR;
goto error_exit;
}
fUnitsPerEM = SWAPW(headTable->unitsPerEm);
fFontChecksum = SWAPL(headTable->checksumAdjustment);
freeFontTable(headTable);
//nameTable = (NAMETable *) readFontTable(nameTag);
//if (nameTable == NULL) {
// status = LE_MISSING_FONT_TABLE_ERROR;
// goto error_exit;
//}
//fFontVersionString = findName(nameTable, NAME_VERSION_STRING, PLATFORM_MACINTOSH, MACINTOSH_ROMAN, MACINTOSH_ENGLISH);
//if (fFontVersionString == NULL) {
// status = LE_MISSING_FONT_TABLE_ERROR;
// goto error_exit;
//}
//freeFontTable(nameTable);
hheaTable = (HHEATable *) readFontTable(hheaTag);
if (hheaTable == NULL) {
status = LE_MISSING_FONT_TABLE_ERROR;
goto error_exit;
}
fAscent = (le_int32) yUnitsToPoints((float) SWAPW(hheaTable->ascent));
fDescent = (le_int32) yUnitsToPoints((float) SWAPW(hheaTable->descent));
fLeading = (le_int32) yUnitsToPoints((float) SWAPW(hheaTable->lineGap));
fNumLongHorMetrics = SWAPW(hheaTable->numOfLongHorMetrics);
freeFontTable((void *) hheaTable);
fCMAPMapper = findUnicodeMapper();
if (fCMAPMapper == NULL) {
status = LE_MISSING_FONT_TABLE_ERROR;
goto error_exit;
}
return;
error_exit:
fclose(fFile);
fFile = NULL;
return;
}
PortableFontInstance::~PortableFontInstance()
{
if (fFile != NULL) {
fclose(fFile);
freeFontTable(fHMTXTable);
freeFontTable(fNAMETable);
delete fCMAPMapper;
DELETE_ARRAY(fDirectory);
}
}
const DirectoryEntry *PortableFontInstance::findTable(LETag tag) const
{
if (fDirectory != NULL) {
le_uint16 table = 0;
le_uint16 probe = fDirPower;
if (SWAPL(fDirectory->tableDirectory[fDirExtra].tag) <= tag) {
table = fDirExtra;
}
while (probe > (1 << 0)) {
probe >>= 1;
if (SWAPL(fDirectory->tableDirectory[table + probe].tag) <= tag) {
table += probe;
}
}
if (SWAPL(fDirectory->tableDirectory[table].tag) == tag) {
return &fDirectory->tableDirectory[table];
}
}
return NULL;
}
const void *PortableFontInstance::readTable(LETag tag, le_uint32 *length) const
{
const DirectoryEntry *entry = findTable(tag);
if (entry == NULL) {
*length = 0;
return NULL;
}
*length = SWAPL(entry->length);
void *table = NEW_ARRAY(char, *length);
if (table != NULL) {
fseek(fFile, SWAPL(entry->offset), SEEK_SET);
fread(table, sizeof(char), *length, fFile);
}
return table;
}
const void *PortableFontInstance::getFontTable(LETag tableTag) const
{
return FontTableCache::find(tableTag);
}
const void *PortableFontInstance::readFontTable(LETag tableTag) const
{
le_uint32 len;
return readTable(tableTag, &len);
}
CMAPMapper *PortableFontInstance::findUnicodeMapper()
{
LETag cmapTag = LE_CMAP_TABLE_TAG;
const CMAPTable *cmap = (CMAPTable *) readFontTable(cmapTag);
if (cmap == NULL) {
return NULL;
}
return CMAPMapper::createUnicodeMapper(cmap);
}
const char *PortableFontInstance::getNameString(le_uint16 nameID, le_uint16 platformID, le_uint16 encodingID, le_uint16 languageID) const
{
if (fNAMETable == NULL) {
LETag nameTag = LE_NAME_TABLE_TAG;
PortableFontInstance *realThis = (PortableFontInstance *) this;
realThis->fNAMETable = (const NAMETable *) readFontTable(nameTag);
if (realThis->fNAMETable != NULL) {
realThis->fNameCount = SWAPW(realThis->fNAMETable->count);
realThis->fNameStringOffset = SWAPW(realThis->fNAMETable->stringOffset);
}
}
for(le_int32 i = 0; i < fNameCount; i += 1) {
const NameRecord *nameRecord = &fNAMETable->nameRecords[i];
if (SWAPW(nameRecord->platformID) == platformID && SWAPW(nameRecord->encodingID) == encodingID &&
SWAPW(nameRecord->languageID) == languageID && SWAPW(nameRecord->nameID) == nameID) {
char *name = ((char *) fNAMETable) + fNameStringOffset + SWAPW(nameRecord->offset);
le_uint16 length = SWAPW(nameRecord->length);
char *result = NEW_ARRAY(char, length + 2);
ARRAY_COPY(result, name, length);
result[length] = result[length + 1] = 0;
return result;
}
}
return NULL;
}
const LEUnicode16 *PortableFontInstance::getUnicodeNameString(le_uint16 nameID, le_uint16 platformID, le_uint16 encodingID, le_uint16 languageID) const
{
if (fNAMETable == NULL) {
LETag nameTag = LE_NAME_TABLE_TAG;
PortableFontInstance *realThis = (PortableFontInstance *) this;
realThis->fNAMETable = (const NAMETable *) readFontTable(nameTag);
if (realThis->fNAMETable != NULL) {
realThis->fNameCount = SWAPW(realThis->fNAMETable->count);
realThis->fNameStringOffset = SWAPW(realThis->fNAMETable->stringOffset);
}
}
for(le_int32 i = 0; i < fNameCount; i += 1) {
const NameRecord *nameRecord = &fNAMETable->nameRecords[i];
if (SWAPW(nameRecord->platformID) == platformID && SWAPW(nameRecord->encodingID) == encodingID &&
SWAPW(nameRecord->languageID) == languageID && SWAPW(nameRecord->nameID) == nameID) {
LEUnicode16 *name = (LEUnicode16 *) (((char *) fNAMETable) + fNameStringOffset + SWAPW(nameRecord->offset));
le_uint16 length = SWAPW(nameRecord->length) / 2;
LEUnicode16 *result = NEW_ARRAY(LEUnicode16, length + 2);
for (le_int32 c = 0; c < length; c += 1) {
result[c] = SWAPW(name[c]);
}
result[length] = 0;
return result;
}
}
return NULL;
}
void PortableFontInstance::deleteNameString(const char *name) const
{
DELETE_ARRAY(name);
}
void PortableFontInstance::deleteNameString(const LEUnicode16 *name) const
{
DELETE_ARRAY(name);
}
void PortableFontInstance::getGlyphAdvance(LEGlyphID glyph, LEPoint &advance) const
{
TTGlyphID ttGlyph = (TTGlyphID) LE_GET_GLYPH(glyph);
if (fHMTXTable == NULL) {
LETag maxpTag = LE_MAXP_TABLE_TAG;
LETag hmtxTag = LE_HMTX_TABLE_TAG;
const MAXPTable *maxpTable = (MAXPTable *) readFontTable(maxpTag);
PortableFontInstance *realThis = (PortableFontInstance *) this;
if (maxpTable != NULL) {
realThis->fNumGlyphs = SWAPW(maxpTable->numGlyphs);
freeFontTable(maxpTable);
}
realThis->fHMTXTable = (const HMTXTable *) readFontTable(hmtxTag);
}
le_uint16 index = ttGlyph;
if (ttGlyph >= fNumGlyphs || fHMTXTable == NULL) {
advance.fX = advance.fY = 0;
return;
}
if (ttGlyph >= fNumLongHorMetrics) {
index = fNumLongHorMetrics - 1;
}
advance.fX = xUnitsToPoints(SWAPW(fHMTXTable->hMetrics[index].advanceWidth));
advance.fY = 0;
}
le_bool PortableFontInstance::getGlyphPoint(LEGlyphID /*glyph*/, le_int32 /*pointNumber*/, LEPoint &/*point*/) const
{
return FALSE;
}
le_int32 PortableFontInstance::getUnitsPerEM() const
{
return fUnitsPerEM;
}
le_uint32 PortableFontInstance::getFontChecksum() const
{
return fFontChecksum;
}
le_int32 PortableFontInstance::getAscent() const
{
return fAscent;
}
le_int32 PortableFontInstance::getDescent() const
{
return fDescent;
}
le_int32 PortableFontInstance::getLeading() const
{
return fLeading;
}
// We really want to inherit this method from the superclass, but some compilers
// issue a warning if we don't implement it...
LEGlyphID PortableFontInstance::mapCharToGlyph(LEUnicode32 ch, const LECharMapper *mapper, le_bool filterZeroWidth) const
{
return LEFontInstance::mapCharToGlyph(ch, mapper, filterZeroWidth);
}
// We really want to inherit this method from the superclass, but some compilers
// issue a warning if we don't implement it...
LEGlyphID PortableFontInstance::mapCharToGlyph(LEUnicode32 ch, const LECharMapper *mapper) const
{
return LEFontInstance::mapCharToGlyph(ch, mapper);
}
LEGlyphID PortableFontInstance::mapCharToGlyph(LEUnicode32 ch) const
{
return fCMAPMapper->unicodeToGlyph(ch);
}
float PortableFontInstance::getXPixelsPerEm() const
{
return fPointSize;
}
float PortableFontInstance::getYPixelsPerEm() const
{
return fPointSize;
}
float PortableFontInstance::getScaleFactorX() const
{
return 1.0;
}
float PortableFontInstance::getScaleFactorY() const
{
return 1.0;
}

View File

@ -0,0 +1,117 @@
/*
*******************************************************************************
*
* Copyright (C) 1999-2008, International Business Machines
* Corporation and others. All Rights Reserved.
*
*******************************************************************************
* file name: PortableFontInstance.h
*
* created on: 11/12/1999
* created by: Eric R. Mader
*/
#ifndef __PORTABLEFONTINSTANCE_H
#define __PORTABLEFONTINSTANCE_H
#include <stdio.h>
#include "layout/LETypes.h"
#include "layout/LEFontInstance.h"
#include "FontTableCache.h"
#include "sfnt.h"
#include "cmaps.h"
class PortableFontInstance : public LEFontInstance, protected FontTableCache
{
private:
FILE *fFile;
float fPointSize;
le_int32 fUnitsPerEM;
le_uint32 fFontChecksum;
le_int32 fAscent;
le_int32 fDescent;
le_int32 fLeading;
const SFNTDirectory *fDirectory;
le_uint16 fDirPower;
le_uint16 fDirExtra;
float fDeviceScaleX;
float fDeviceScaleY;
const NAMETable *fNAMETable;
le_uint16 fNameCount;
le_uint16 fNameStringOffset;
CMAPMapper *fCMAPMapper;
const HMTXTable *fHMTXTable;
le_uint16 fNumGlyphs;
le_uint16 fNumLongHorMetrics;
static le_int8 highBit(le_int32 value);
const DirectoryEntry *findTable(LETag tag) const;
const void *readTable(LETag tag, le_uint32 *length) const;
void getMetrics();
CMAPMapper *findUnicodeMapper();
protected:
const void *readFontTable(LETag tableTag) const;
public:
PortableFontInstance(const char *fileName, float pointSize, LEErrorCode &status);
virtual ~PortableFontInstance();
virtual const void *getFontTable(LETag tableTag) const;
virtual const char *getNameString(le_uint16 nameID, le_uint16 platform, le_uint16 encoding, le_uint16 language) const;
virtual const LEUnicode16 *getUnicodeNameString(le_uint16 nameID, le_uint16 platform, le_uint16 encoding, le_uint16 language) const;
virtual void deleteNameString(const char *name) const;
virtual void deleteNameString(const LEUnicode16 *name) const;
virtual le_int32 getUnitsPerEM() const;
virtual le_uint32 getFontChecksum() const;
virtual le_int32 getAscent() const;
virtual le_int32 getDescent() const;
virtual le_int32 getLeading() const;
// We really want to inherit this method from the superclass, but some compilers
// issue a warning if we don't implement it...
virtual LEGlyphID mapCharToGlyph(LEUnicode32 ch, const LECharMapper *mapper, le_bool filterZeroWidth) const;
// We really want to inherit this method from the superclass, but some compilers
// issue a warning if we don't implement it...
virtual LEGlyphID mapCharToGlyph(LEUnicode32 ch, const LECharMapper *mapper) const;
virtual LEGlyphID mapCharToGlyph(LEUnicode32 ch) const;
virtual void getGlyphAdvance(LEGlyphID glyph, LEPoint &advance) const;
virtual le_bool getGlyphPoint(LEGlyphID glyph, le_int32 pointNumber, LEPoint &point) const;
float getXPixelsPerEm() const;
float getYPixelsPerEm() const;
float getScaleFactorX() const;
float getScaleFactorY() const;
};
#endif

2
src/hb-icu-le/README Normal file
View File

@ -0,0 +1,2 @@
This is PortableFontInstance from icu/test/testle of ICU50.
For license information, see the file license.html.

200
src/hb-icu-le/cmaps.cpp Normal file
View File

@ -0,0 +1,200 @@
/***************************************************************************
*
* Copyright (C) 1998-2003, International Business Machines
* Corporation and others. All Rights Reserved.
*
************************************************************************/
#include "layout/LETypes.h"
#include "layout/LESwaps.h"
#include "sfnt.h"
#include "cmaps.h"
#define SWAPU16(code) ((LEUnicode16) SWAPW(code))
#define SWAPU32(code) ((LEUnicode32) SWAPL(code))
//
// Finds the high bit by binary searching
// through the bits in value.
//
le_int8 highBit(le_uint32 value)
{
le_uint8 bit = 0;
if (value >= 1 << 16) {
value >>= 16;
bit += 16;
}
if (value >= 1 << 8) {
value >>= 8;
bit += 8;
}
if (value >= 1 << 4) {
value >>= 4;
bit += 4;
}
if (value >= 1 << 2) {
value >>= 2;
bit += 2;
}
if (value >= 1 << 1) {
value >>= 1;
bit += 1;
}
return bit;
}
CMAPMapper *CMAPMapper::createUnicodeMapper(const CMAPTable *cmap)
{
le_uint16 i;
le_uint16 nSubtables = SWAPW(cmap->numberSubtables);
const CMAPEncodingSubtable *subtable = NULL;
le_uint32 offset1 = 0, offset10 = 0;
for (i = 0; i < nSubtables; i += 1) {
const CMAPEncodingSubtableHeader *esh = &cmap->encodingSubtableHeaders[i];
if (SWAPW(esh->platformID) == 3) {
switch (SWAPW(esh->platformSpecificID)) {
case 1:
offset1 = SWAPL(esh->encodingOffset);
break;
case 10:
offset10 = SWAPL(esh->encodingOffset);
break;
}
}
}
if (offset10 != 0)
{
subtable = (const CMAPEncodingSubtable *) ((const char *) cmap + offset10);
} else if (offset1 != 0) {
subtable = (const CMAPEncodingSubtable *) ((const char *) cmap + offset1);
} else {
return NULL;
}
switch (SWAPW(subtable->format)) {
case 4:
return new CMAPFormat4Mapper(cmap, (const CMAPFormat4Encoding *) subtable);
case 12:
{
const CMAPFormat12Encoding *encoding = (const CMAPFormat12Encoding *) subtable;
return new CMAPGroupMapper(cmap, encoding->groups, SWAPL(encoding->nGroups));
}
default:
break;
}
return NULL;
}
CMAPFormat4Mapper::CMAPFormat4Mapper(const CMAPTable *cmap, const CMAPFormat4Encoding *header)
: CMAPMapper(cmap)
{
le_uint16 segCount = SWAPW(header->segCountX2) / 2;
fEntrySelector = SWAPW(header->entrySelector);
fRangeShift = SWAPW(header->rangeShift) / 2;
fEndCodes = &header->endCodes[0];
fStartCodes = &header->endCodes[segCount + 1]; // + 1 for reservedPad...
fIdDelta = &fStartCodes[segCount];
fIdRangeOffset = &fIdDelta[segCount];
}
LEGlyphID CMAPFormat4Mapper::unicodeToGlyph(LEUnicode32 unicode32) const
{
if (unicode32 >= 0x10000) {
return 0;
}
LEUnicode16 unicode = (LEUnicode16) unicode32;
le_uint16 index = 0;
le_uint16 probe = 1 << fEntrySelector;
TTGlyphID result = 0;
if (SWAPU16(fStartCodes[fRangeShift]) <= unicode) {
index = fRangeShift;
}
while (probe > (1 << 0)) {
probe >>= 1;
if (SWAPU16(fStartCodes[index + probe]) <= unicode) {
index += probe;
}
}
if (unicode >= SWAPU16(fStartCodes[index]) && unicode <= SWAPU16(fEndCodes[index])) {
if (fIdRangeOffset[index] == 0) {
result = (TTGlyphID) unicode;
} else {
le_uint16 offset = unicode - SWAPU16(fStartCodes[index]);
le_uint16 rangeOffset = SWAPW(fIdRangeOffset[index]);
le_uint16 *glyphIndexTable = (le_uint16 *) ((char *) &fIdRangeOffset[index] + rangeOffset);
result = SWAPW(glyphIndexTable[offset]);
}
result += SWAPW(fIdDelta[index]);
} else {
result = 0;
}
return LE_SET_GLYPH(0, result);
}
CMAPFormat4Mapper::~CMAPFormat4Mapper()
{
// parent destructor does it all
}
CMAPGroupMapper::CMAPGroupMapper(const CMAPTable *cmap, const CMAPGroup *groups, le_uint32 nGroups)
: CMAPMapper(cmap), fGroups(groups)
{
le_uint8 bit = highBit(nGroups);
fPower = 1 << bit;
fRangeOffset = nGroups - fPower;
}
LEGlyphID CMAPGroupMapper::unicodeToGlyph(LEUnicode32 unicode32) const
{
le_int32 probe = fPower;
le_int32 range = 0;
if (SWAPU32(fGroups[fRangeOffset].startCharCode) <= unicode32) {
range = fRangeOffset;
}
while (probe > (1 << 0)) {
probe >>= 1;
if (SWAPU32(fGroups[range + probe].startCharCode) <= unicode32) {
range += probe;
}
}
if (SWAPU32(fGroups[range].startCharCode) <= unicode32 && SWAPU32(fGroups[range].endCharCode) >= unicode32) {
return (LEGlyphID) (SWAPU32(fGroups[range].startGlyphCode) + unicode32 - SWAPU32(fGroups[range].startCharCode));
}
return 0;
}
CMAPGroupMapper::~CMAPGroupMapper()
{
// parent destructor does it all
}

85
src/hb-icu-le/cmaps.h Normal file
View File

@ -0,0 +1,85 @@
/***************************************************************************
*
* Copyright (C) 1998-2006, International Business Machines
* Corporation and others. All Rights Reserved.
*
************************************************************************/
#ifndef __CMAPS_H
#define __CMAPS_H
#include "layout/LETypes.h"
#include "letest.h"
#include "sfnt.h"
class CMAPMapper
{
public:
virtual LEGlyphID unicodeToGlyph(LEUnicode32 unicode32) const = 0;
virtual ~CMAPMapper();
static CMAPMapper *createUnicodeMapper(const CMAPTable *cmap);
protected:
CMAPMapper(const CMAPTable *cmap);
CMAPMapper() {};
private:
const CMAPTable *fcmap;
};
class CMAPFormat4Mapper : public CMAPMapper
{
public:
CMAPFormat4Mapper(const CMAPTable *cmap, const CMAPFormat4Encoding *header);
virtual ~CMAPFormat4Mapper();
virtual LEGlyphID unicodeToGlyph(LEUnicode32 unicode32) const;
protected:
CMAPFormat4Mapper() {};
private:
le_uint16 fEntrySelector;
le_uint16 fRangeShift;
const le_uint16 *fEndCodes;
const le_uint16 *fStartCodes;
const le_uint16 *fIdDelta;
const le_uint16 *fIdRangeOffset;
};
class CMAPGroupMapper : public CMAPMapper
{
public:
CMAPGroupMapper(const CMAPTable *cmap, const CMAPGroup *groups, le_uint32 nGroups);
virtual ~CMAPGroupMapper();
virtual LEGlyphID unicodeToGlyph(LEUnicode32 unicode32) const;
protected:
CMAPGroupMapper() {};
private:
le_int32 fPower;
le_int32 fRangeOffset;
const CMAPGroup *fGroups;
};
inline CMAPMapper::CMAPMapper(const CMAPTable *cmap)
: fcmap(cmap)
{
// nothing else to do
}
inline CMAPMapper::~CMAPMapper()
{
DELETE_ARRAY(fcmap);
}
#endif

49
src/hb-icu-le/letest.h Normal file
View File

@ -0,0 +1,49 @@
/*
*******************************************************************************
*
* Copyright (C) 1999-2011, International Business Machines
* Corporation and others. All Rights Reserved.
*
*******************************************************************************
* file name: letest.h
*
* created on: 11/06/2000
* created by: Eric R. Mader
*/
#ifndef __LETEST_H
#define __LETEST_H
#include "layout/LETypes.h"
/*#include "unicode/ctest.h"*/
#include <stdlib.h>
#include <string.h>
U_NAMESPACE_USE
#define ARRAY_SIZE(array) (sizeof array / sizeof array[0])
#define ARRAY_COPY(dst, src, count) memcpy((void *) (dst), (void *) (src), (count) * sizeof (src)[0])
#define NEW_ARRAY(type,count) (type *) malloc((count) * sizeof(type))
#define DELETE_ARRAY(array) free((void *) (array))
#define GROW_ARRAY(array,newSize) realloc((void *) (array), (newSize) * sizeof (array)[0])
struct TestResult
{
le_int32 glyphCount;
LEGlyphID *glyphs;
le_int32 *indices;
float *positions;
};
#ifndef __cplusplus
typedef struct TestResult TestResult;
#endif
//U_CFUNC void addCTests(TestNode **root);
#endif

View File

@ -0,0 +1,51 @@
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=us-ascii"></meta>
<title>ICU License - ICU 1.8.1 and later</title>
</head>
<body BGCOLOR="#ffffff">
<h2>ICU License - ICU 1.8.1 and later</h2>
<p>COPYRIGHT AND PERMISSION NOTICE</p>
<p>
Copyright (c) 1995-2012 International Business Machines Corporation and others
</p>
<p>
All rights reserved.
</p>
<p>
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"),
to deal in the Software without restriction, including without limitation
the rights to use, copy, modify, merge, publish, distribute, and/or sell
copies of the Software, and to permit persons
to whom the Software is furnished to do so, provided that the above
copyright notice(s) and this permission notice appear in all copies
of the Software and that both the above copyright notice(s) and this
permission notice appear in supporting documentation.
</p>
<p>
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
PARTICULAR PURPOSE AND NONINFRINGEMENT OF THIRD PARTY RIGHTS. IN NO EVENT SHALL
THE COPYRIGHT HOLDER OR HOLDERS INCLUDED IN THIS NOTICE BE LIABLE FOR ANY CLAIM,
OR ANY SPECIAL INDIRECT OR CONSEQUENTIAL DAMAGES, OR ANY DAMAGES WHATSOEVER
RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE
USE OR PERFORMANCE OF THIS SOFTWARE.
</p>
<p>
Except as contained in this notice, the name of a copyright holder shall not be
used in advertising or otherwise to promote the sale, use or other dealings in
this Software without prior written authorization of the copyright holder.
</p>
<hr>
<p><small>
All trademarks and registered trademarks mentioned herein are the property of their respective owners.
</small></p>
</body>
</html>

449
src/hb-icu-le/sfnt.h Normal file
View File

@ -0,0 +1,449 @@
/***************************************************************************
*
* Copyright (C) 1998-2011, International Business Machines
* Corporation and others. All Rights Reserved.
*
************************************************************************/
#ifndef __SFNT_H
#define __SFNT_H
#include "layout/LETypes.h"
U_NAMESPACE_USE
#ifndef ANY_NUMBER
#define ANY_NUMBER 1
#endif
struct DirectoryEntry
{
le_uint32 tag;
le_uint32 checksum;
le_uint32 offset;
le_uint32 length;
};
#ifndef __cplusplus
typedef struct DirectoryEntry DirectoryEntry;
#endif
struct SFNTDirectory
{
le_uint32 scalerType;
le_uint16 numTables;
le_uint16 searchRange;
le_uint16 entrySelector;
le_uint16 rangeShift;
DirectoryEntry tableDirectory[ANY_NUMBER];
};
#ifndef __cplusplus
typedef struct SFNTDirectory SFNTDirectory;
#endif
struct CMAPEncodingSubtableHeader
{
le_uint16 platformID;
le_uint16 platformSpecificID;
le_uint32 encodingOffset;
};
#ifndef __cplusplus
typedef struct CMAPEncodingSubtableHeader CMAPEncodingSubtableHeader;
#endif
struct CMAPTable
{
le_uint16 version;
le_uint16 numberSubtables;
CMAPEncodingSubtableHeader encodingSubtableHeaders[ANY_NUMBER];
};
#ifndef __cplusplus
typedef struct CMAPTable CMAPTable;
#endif
struct CMAPEncodingSubtable
{
le_uint16 format;
le_uint16 length;
le_uint16 language;
};
#ifndef __cplusplus
typedef struct CMAPEncodingSubtable CMAPEncodingSubtable;
#endif
#ifdef __cplusplus
struct CMAPFormat0Encoding : CMAPEncodingSubtable
{
le_uint8 glyphIndexArray[256];
};
#else
struct CMAPFormat0Encoding
{
CMAPEncodingSubtable base;
le_uint8 glyphIndexArray[256];
};
typedef struct CMAPFormat0Encoding CMAPFormat0Encoding;
#endif
struct CMAPFormat2Subheader
{
le_uint16 firstCode;
le_uint16 entryCount;
le_int16 idDelta;
le_uint16 idRangeOffset;
};
#ifndef __cplusplus
typedef struct CMAPFormat2Subheader CMAPFormat2Subheader;
#endif
#ifdef __cplusplus
struct CMAPFormat2Encoding : CMAPEncodingSubtable
{
le_uint16 subHeadKeys[256];
CMAPFormat2Subheader subheaders[ANY_NUMBER];
};
#else
struct CMAPFormat2Encoding
{
CMAPEncodingSubtable base;
le_uint16 subHeadKeys[256];
CMAPFormat2Subheader subheaders[ANY_NUMBER];
};
typedef struct CMAPFormat2Encoding CMAPFormat2Encoding;
#endif
#ifdef __cplusplus
struct CMAPFormat4Encoding : CMAPEncodingSubtable
{
le_uint16 segCountX2;
le_uint16 searchRange;
le_uint16 entrySelector;
le_uint16 rangeShift;
le_uint16 endCodes[ANY_NUMBER];
/*
le_uint16 reservedPad;
le_uint16 startCodes[ANY_NUMBER];
le_uint16 idDelta[ANY_NUMBER];
le_uint16 idRangeOffset[ANY_NUMBER];
le_uint16 glyphIndexArray[ANY_NUMBER];
*/
};
#else
struct CMAPFormat4Encoding
{
CMAPEncodingSubtable base;
le_uint16 segCountX2;
le_uint16 searchRange;
le_uint16 entrySelector;
le_uint16 rangeShift;
le_uint16 endCodes[ANY_NUMBER];
/*
// le_uint16 reservedPad;
// le_uint16 startCodes[ANY_NUMBER];
// le_uint16 idDelta[ANY_NUMBER];
// le_uint16 idRangeOffset[ANY_NUMBER];
// le_uint16 glyphIndexArray[ANY_NUMBER];
*/
};
typedef struct CMAPFormat4Encoding CMAPFormat4Encoding;
#endif
#ifdef __cplusplus
struct CMAPFormat6Encoding : CMAPEncodingSubtable
{
le_uint16 firstCode;
le_uint16 entryCount;
le_uint16 glyphIndexArray[ANY_NUMBER];
};
#else
struct CMAPFormat6Encoding
{
CMAPEncodingSubtable base;
le_uint16 firstCode;
le_uint16 entryCount;
le_uint16 glyphIndexArray[ANY_NUMBER];
};
typedef struct CMAPFormat6Encoding CMAPFormat6Encoding;
#endif
struct CMAPEncodingSubtable32
{
le_uint32 format;
le_uint32 length;
le_uint32 language;
};
#ifndef __cplusplus
typedef struct CMAPEncodingSubtable32 CMAPEncodingSubtable32;
#endif
struct CMAPGroup
{
le_uint32 startCharCode;
le_uint32 endCharCode;
le_uint32 startGlyphCode;
};
#ifndef __cplusplus
typedef struct CMAPGroup CMAPGroup;
#endif
#ifdef __cplusplus
struct CMAPFormat8Encoding : CMAPEncodingSubtable32
{
le_uint32 is32[65536/32];
le_uint32 nGroups;
CMAPGroup groups[ANY_NUMBER];
};
#else
struct CMAPFormat8Encoding
{
CMAPEncodingSubtable32 base;
le_uint32 is32[65536/32];
le_uint32 nGroups;
CMAPGroup groups[ANY_NUMBER];
};
typedef struct CMAPFormat8Encoding CMAPFormat8Encoding;
#endif
#ifdef __cplusplus
struct CMAPFormat10Encoding : CMAPEncodingSubtable32
{
le_uint32 startCharCode;
le_uint32 numCharCodes;
le_uint16 glyphs[ANY_NUMBER];
};
#else
struct CMAPFormat10Encoding
{
CMAPEncodingSubtable32 base;
le_uint32 startCharCode;
le_uint32 numCharCodes;
le_uint16 glyphs[ANY_NUMBER];
};
typedef struct CMAPFormat10Encoding CMAPFormat10Encoding;
#endif
#ifdef __cplusplus
struct CMAPFormat12Encoding : CMAPEncodingSubtable32
{
le_uint32 nGroups;
CMAPGroup groups[ANY_NUMBER];
};
#else
struct CMAPFormat12Encoding
{
CMAPEncodingSubtable32 base;
le_uint32 nGroups;
CMAPGroup groups[ANY_NUMBER];
};
typedef struct CMAPFormat12Encoding CMAPFormat12Encoding;
#endif
typedef le_int32 fixed;
struct BigDate
{
le_uint32 bc;
le_uint32 ad;
};
#ifndef __cplusplus
typedef struct BigDate BigDate;
#endif
struct HEADTable
{
fixed version;
fixed fontRevision;
le_uint32 checksumAdjustment;
le_uint32 magicNumber;
le_uint16 flags;
le_uint16 unitsPerEm;
BigDate created;
BigDate modified;
le_int16 xMin;
le_int16 yMin;
le_int16 xMax;
le_int16 yMax;
le_int16 lowestRecPPEM;
le_int16 fontDirectionHint;
le_int16 indexToLocFormat;
le_int16 glyphDataFormat;
};
#ifndef __cplusplus
typedef struct HEADTable HEADTable;
#endif
struct MAXPTable
{
fixed version;
le_uint16 numGlyphs;
le_uint16 maxPoints;
le_uint16 maxContours;
le_uint16 maxComponentPoints;
le_uint16 maxComponentContours;
le_uint16 maxZones;
le_uint16 maxTwilightPoints;
le_uint16 maxStorage;
le_uint16 maxFunctionDefs;
le_uint16 maxInstructionDefs;
le_uint16 maxStackElements;
le_uint16 maxSizeOfInstructions;
le_uint16 maxComponentElements;
le_uint16 maxComponentDepth;
};
#ifndef __cplusplus
typedef struct MAXPTable MAXPTable;
#endif
struct HHEATable
{
fixed version;
le_int16 ascent;
le_int16 descent;
le_int16 lineGap;
le_uint16 advanceWidthMax;
le_int16 minLeftSideBearing;
le_int16 minRightSideBearing;
le_int16 xMaxExtent;
le_int16 caretSlopeRise;
le_int16 caretSlopeRun;
le_int16 caretOffset;
le_int16 reserved1;
le_int16 reserved2;
le_int16 reserved3;
le_int16 reserved4;
le_int16 metricDataFormat;
le_uint16 numOfLongHorMetrics;
};
#ifndef __cplusplus
typedef struct HHEATable HHEATable;
#endif
struct LongHorMetric
{
le_uint16 advanceWidth;
le_int16 leftSideBearing;
};
#ifndef __cplusplus
typedef struct LongHorMetric LongHorMetric;
#endif
struct HMTXTable
{
LongHorMetric hMetrics[ANY_NUMBER]; /* ANY_NUMBER = numOfLongHorMetrics from hhea table */
/* le_int16 leftSideBearing[ANY_NUMBER]; ANY_NUMBER = numGlyphs - numOfLongHorMetrics */
};
#ifndef __cplusplus
typedef struct HMTXTable HMTXTable;
#endif
enum PlatformID
{
PLATFORM_UNICODE = 0,
PLATFORM_MACINTOSH = 1,
PLATFORM_ISO = 2,
PLATFORM_MICROSOFT = 3,
PLATFORM_CUSTOM = 4
};
enum MacintoshEncodingID
{
MACINTOSH_ROMAN = 0
};
enum MacintoshLanguageID
{
MACINTOSH_ENGLISH = 0
};
enum MicrosoftEncodingID
{
MICROSOFT_UNICODE_BMP = 1,
MICROSOFT_UNICODE_FULL = 10
};
enum MicrosoftLanguageID
{
MICROSOFT_ENGLISH = 0x409
};
enum NameID
{
NAME_COPYRIGHT_NOTICE = 0,
NAME_FONT_FAMILY = 1,
NAME_FONT_SUB_FAMILY = 2,
NAME_UNIQUE_FONT_ID = 3,
NAME_FULL_FONT_NAME = 4,
NAME_VERSION_STRING = 5,
NAME_POSTSCRIPT_NAME = 6,
NAME_TRADEMARK = 7,
NAME_MANUFACTURER = 8,
NAME_DESIGNER = 9,
NAME_DESCRIPTION = 10,
NAME_VENDOR_URL = 11,
NAME_DESIGNER_URL = 12,
NAME_LICENSE_DESCRIPTION = 13,
NAME_LICENSE_URL = 14,
NAME_RESERVED = 15,
NAME_PREFERRED_FAMILY = 16,
NAME_PREFERRED_SUB_FAMILY = 17,
NAME_COMPATIBLE_FULL = 18,
NAME_SAMPLE_TEXT = 19,
NAME_POSTSCRIPT_CID = 20
};
struct NameRecord
{
le_uint16 platformID;
le_uint16 encodingID;
le_uint16 languageID;
le_uint16 nameID;
le_uint16 length;
le_uint16 offset;
};
#ifndef __cplusplus
typedef struct NameRecord NameRecord;
#endif
struct NAMETable
{
le_uint16 version;
le_uint16 count;
le_uint16 stringOffset;
NameRecord nameRecords[ANY_NUMBER];
};
#ifndef __cplusplus
typedef struct NAMETable NAMETable;
#endif
#endif