8186317: Cache font layout tables for use by harfbuzz
Reviewed-by: srl, pnarayanan
This commit is contained in:
parent
05aa9c6d1d
commit
4211e523ea
@ -192,7 +192,8 @@ public final class SunLayoutEngine implements LayoutEngine, LayoutEngineFactory
|
|||||||
if (font instanceof FileFont) {
|
if (font instanceof FileFont) {
|
||||||
pScaler = ((FileFont)font).getScaler().nativeScaler;
|
pScaler = ((FileFont)font).getScaler().nativeScaler;
|
||||||
}
|
}
|
||||||
shape(font, strike, ptSize, mat, pScaler, pNativeFont, isAAT(font),
|
shape(font, strike, ptSize, mat, pScaler, pNativeFont,
|
||||||
|
layoutTables, isAAT(font),
|
||||||
tr.text, data, key.script(),
|
tr.text, data, key.script(),
|
||||||
tr.start, tr.limit, baseIndex, pt,
|
tr.start, tr.limit, baseIndex, pt,
|
||||||
typo_flags, gmask);
|
typo_flags, gmask);
|
||||||
@ -210,7 +211,7 @@ public final class SunLayoutEngine implements LayoutEngine, LayoutEngineFactory
|
|||||||
/* Native method to invoke harfbuzz layout engine */
|
/* Native method to invoke harfbuzz layout engine */
|
||||||
private static native boolean
|
private static native boolean
|
||||||
shape(Font2D font, FontStrike strike, float ptSize, float[] mat,
|
shape(Font2D font, FontStrike strike, float ptSize, float[] mat,
|
||||||
long pscaler, long pNativeFont, boolean aat,
|
long pscaler, long pNativeFont, long layoutTables, boolean aat,
|
||||||
char[] chars, GVData data,
|
char[] chars, GVData data,
|
||||||
int script, int offset, int limit,
|
int script, int offset, int limit,
|
||||||
int baseIndex, Point2D.Float pt, int typo_flags, int slot);
|
int baseIndex, Point2D.Float pt, int typo_flags, int slot);
|
||||||
|
@ -119,6 +119,7 @@ typedef struct GlyphInfo {
|
|||||||
#define GSUB_TAG 0x47535542 /* 'GSUB' */
|
#define GSUB_TAG 0x47535542 /* 'GSUB' */
|
||||||
#define GPOS_TAG 0x47504F53 /* 'GPOS' */
|
#define GPOS_TAG 0x47504F53 /* 'GPOS' */
|
||||||
#define GDEF_TAG 0x47444546 /* 'GDEF' */
|
#define GDEF_TAG 0x47444546 /* 'GDEF' */
|
||||||
|
#define HEAD_TAG 0x68656164 /* 'head' */
|
||||||
#define MORT_TAG 0x6D6F7274 /* 'mort' */
|
#define MORT_TAG 0x6D6F7274 /* 'mort' */
|
||||||
#define MORX_TAG 0x6D6F7278 /* 'morx' */
|
#define MORX_TAG 0x6D6F7278 /* 'morx' */
|
||||||
#define KERN_TAG 0x6B65726E /* 'kern' */
|
#define KERN_TAG 0x6B65726E /* 'kern' */
|
||||||
@ -126,9 +127,10 @@ typedef struct GlyphInfo {
|
|||||||
typedef struct TTLayoutTableCacheEntry {
|
typedef struct TTLayoutTableCacheEntry {
|
||||||
const void* ptr;
|
const void* ptr;
|
||||||
int len;
|
int len;
|
||||||
|
int tag;
|
||||||
} TTLayoutTableCacheEntry;
|
} TTLayoutTableCacheEntry;
|
||||||
|
|
||||||
#define LAYOUTCACHE_ENTRIES 6
|
#define LAYOUTCACHE_ENTRIES 7
|
||||||
|
|
||||||
typedef struct TTLayoutTableCache {
|
typedef struct TTLayoutTableCache {
|
||||||
TTLayoutTableCacheEntry entries[LAYOUTCACHE_ENTRIES];
|
TTLayoutTableCacheEntry entries[LAYOUTCACHE_ENTRIES];
|
||||||
|
@ -203,6 +203,7 @@ JDKFontInfo*
|
|||||||
jfloat ptSize,
|
jfloat ptSize,
|
||||||
jlong pScaler,
|
jlong pScaler,
|
||||||
jlong pNativeFont,
|
jlong pNativeFont,
|
||||||
|
jlong layoutTables,
|
||||||
jfloatArray matrix,
|
jfloatArray matrix,
|
||||||
jboolean aat) {
|
jboolean aat) {
|
||||||
|
|
||||||
@ -215,6 +216,7 @@ JDKFontInfo*
|
|||||||
fi->font2D = font2D;
|
fi->font2D = font2D;
|
||||||
fi->fontStrike = fontStrike;
|
fi->fontStrike = fontStrike;
|
||||||
fi->nativeFont = pNativeFont;
|
fi->nativeFont = pNativeFont;
|
||||||
|
fi->layoutTables = (TTLayoutTableCache*)layoutTables;
|
||||||
fi->aat = aat;
|
fi->aat = aat;
|
||||||
(*env)->GetFloatArrayRegion(env, matrix, 0, 4, fi->matrix);
|
(*env)->GetFloatArrayRegion(env, matrix, 0, 4, fi->matrix);
|
||||||
fi->ptSize = ptSize;
|
fi->ptSize = ptSize;
|
||||||
@ -241,6 +243,7 @@ JNIEXPORT jboolean JNICALL Java_sun_font_SunLayoutEngine_shape
|
|||||||
jfloatArray matrix,
|
jfloatArray matrix,
|
||||||
jlong pScaler,
|
jlong pScaler,
|
||||||
jlong pNativeFont,
|
jlong pNativeFont,
|
||||||
|
jlong layoutTables,
|
||||||
jboolean aat,
|
jboolean aat,
|
||||||
jcharArray text,
|
jcharArray text,
|
||||||
jobject gvdata,
|
jobject gvdata,
|
||||||
@ -269,7 +272,7 @@ JNIEXPORT jboolean JNICALL Java_sun_font_SunLayoutEngine_shape
|
|||||||
|
|
||||||
JDKFontInfo *jdkFontInfo =
|
JDKFontInfo *jdkFontInfo =
|
||||||
createJDKFontInfo(env, font2D, fontStrike, ptSize,
|
createJDKFontInfo(env, font2D, fontStrike, ptSize,
|
||||||
pScaler, pNativeFont, matrix, aat);
|
pScaler, pNativeFont, layoutTables, matrix, aat);
|
||||||
if (!jdkFontInfo) {
|
if (!jdkFontInfo) {
|
||||||
return JNI_FALSE;
|
return JNI_FALSE;
|
||||||
}
|
}
|
||||||
|
@ -273,34 +273,63 @@ _hb_jdk_get_font_funcs (void)
|
|||||||
static void _do_nothing(void) {
|
static void _do_nothing(void) {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void _free_nothing(void*) {
|
||||||
|
}
|
||||||
|
|
||||||
static hb_blob_t *
|
static hb_blob_t *
|
||||||
reference_table(hb_face_t *face HB_UNUSED, hb_tag_t tag, void *user_data) {
|
reference_table(hb_face_t *face HB_UNUSED, hb_tag_t tag, void *user_data) {
|
||||||
|
|
||||||
JDKFontInfo *jdkFontInfo = (JDKFontInfo*)user_data;
|
JDKFontInfo *jdkFontInfo = (JDKFontInfo*)user_data;
|
||||||
JNIEnv* env = jdkFontInfo->env;
|
JNIEnv* env = jdkFontInfo->env;
|
||||||
jobject font2D = jdkFontInfo->font2D;
|
jobject font2D = jdkFontInfo->font2D;
|
||||||
jsize length;
|
jsize length = 0;
|
||||||
jbyte* buffer;
|
void* buffer = NULL;
|
||||||
|
int cacheIdx = 0;
|
||||||
|
|
||||||
// HB_TAG_NONE is 0 and is used to get the whole font file.
|
// HB_TAG_NONE is 0 and is used to get the whole font file.
|
||||||
// It is not expected not be needed for JDK.
|
// It is not expected to be needed for JDK.
|
||||||
if (tag == 0) {
|
if (tag == 0 || jdkFontInfo->layoutTables == NULL) {
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (cacheIdx=0; cacheIdx<LAYOUTCACHE_ENTRIES; cacheIdx++) {
|
||||||
|
if (tag == jdkFontInfo->layoutTables->entries[cacheIdx].tag) break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (cacheIdx < LAYOUTCACHE_ENTRIES) { // if found
|
||||||
|
if (jdkFontInfo->layoutTables->entries[cacheIdx].len != -1) {
|
||||||
|
length = jdkFontInfo->layoutTables->entries[cacheIdx].len;
|
||||||
|
buffer = (void*)jdkFontInfo->layoutTables->entries[cacheIdx].ptr;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (buffer == NULL) {
|
||||||
jbyteArray tableBytes = (jbyteArray)
|
jbyteArray tableBytes = (jbyteArray)
|
||||||
env->CallObjectMethod(font2D, sunFontIDs.getTableBytesMID, tag);
|
env->CallObjectMethod(font2D, sunFontIDs.getTableBytesMID, tag);
|
||||||
if (tableBytes == NULL) {
|
if (tableBytes == NULL) {
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
length = env->GetArrayLength(tableBytes);
|
length = env->GetArrayLength(tableBytes);
|
||||||
buffer = (jbyte *)calloc(length, sizeof(jbyte));
|
buffer = calloc(length, sizeof(jbyte));
|
||||||
env->GetByteArrayRegion(tableBytes, 0, length, buffer);
|
env->GetByteArrayRegion(tableBytes, 0, length, (jbyte*)buffer);
|
||||||
|
|
||||||
|
if (cacheIdx >= LAYOUTCACHE_ENTRIES) { // not a cacheable table
|
||||||
return hb_blob_create((const char *)buffer, length,
|
return hb_blob_create((const char *)buffer, length,
|
||||||
HB_MEMORY_MODE_WRITABLE,
|
HB_MEMORY_MODE_WRITABLE,
|
||||||
buffer, free);
|
buffer, free);
|
||||||
|
} else {
|
||||||
|
jdkFontInfo->layoutTables->entries[cacheIdx].len = length;
|
||||||
|
jdkFontInfo->layoutTables->entries[cacheIdx].ptr = buffer;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return hb_blob_create((const char *)buffer, length,
|
||||||
|
HB_MEMORY_MODE_READONLY,
|
||||||
|
NULL, _free_nothing);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
hb_face_t*
|
hb_face_t*
|
||||||
hb_jdk_face_create(JDKFontInfo *jdkFontInfo,
|
hb_jdk_face_create(JDKFontInfo *jdkFontInfo,
|
||||||
hb_destroy_func_t destroy) {
|
hb_destroy_func_t destroy) {
|
||||||
|
@ -29,6 +29,7 @@
|
|||||||
#include "hb.h"
|
#include "hb.h"
|
||||||
#include <jni.h>
|
#include <jni.h>
|
||||||
#include <sunfontids.h>
|
#include <sunfontids.h>
|
||||||
|
#include <fontscalerdefs.h>
|
||||||
|
|
||||||
# ifdef __cplusplus
|
# ifdef __cplusplus
|
||||||
extern "C" {
|
extern "C" {
|
||||||
@ -39,6 +40,7 @@ typedef struct JDKFontInfo_Struct {
|
|||||||
jobject font2D;
|
jobject font2D;
|
||||||
jobject fontStrike;
|
jobject fontStrike;
|
||||||
long nativeFont;
|
long nativeFont;
|
||||||
|
TTLayoutTableCache *layoutTables;
|
||||||
float matrix[4];
|
float matrix[4];
|
||||||
float ptSize;
|
float ptSize;
|
||||||
float xPtSize;
|
float xPtSize;
|
||||||
|
@ -350,6 +350,13 @@ JNIEXPORT TTLayoutTableCache* newLayoutTableCache() {
|
|||||||
for(i=0;i<LAYOUTCACHE_ENTRIES;i++) {
|
for(i=0;i<LAYOUTCACHE_ENTRIES;i++) {
|
||||||
ltc->entries[i].len = -1;
|
ltc->entries[i].len = -1;
|
||||||
}
|
}
|
||||||
|
ltc->entries[0].tag = GDEF_TAG;
|
||||||
|
ltc->entries[1].tag = GPOS_TAG;
|
||||||
|
ltc->entries[2].tag = GSUB_TAG;
|
||||||
|
ltc->entries[3].tag = HEAD_TAG;
|
||||||
|
ltc->entries[4].tag = KERN_TAG;
|
||||||
|
ltc->entries[5].tag = MORT_TAG;
|
||||||
|
ltc->entries[6].tag = MORX_TAG;
|
||||||
}
|
}
|
||||||
return ltc;
|
return ltc;
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user