int main(int argc, char *argv[]) { le_int32 failures = 0; for (le_int32 test = 0; test < testCount; test += 1) { LEErrorCode fontStatus = LE_NO_ERROR; printf("Test %d, font = %s... ", test, testInputs[test].fontName); PortableFontInstance fontInstance(testInputs[test].fontName, 12, fontStatus); if (LE_FAILURE(fontStatus)) { printf("could not open font.\n"); continue; } LEErrorCode success = LE_NO_ERROR; LayoutEngine *engine = LayoutEngine::layoutEngineFactory(&fontInstance, testInputs[test].scriptCode, -1, success); le_int32 textLength = testInputs[test].textLength; le_bool result; TestResult actual; if (LE_FAILURE(success)) { // would be nice to print the script name here, but // don't want to maintain a table, and don't want to // require ICU just for the script name... printf("could not create a LayoutEngine.\n"); continue; } actual.glyphCount = engine->layoutChars(testInputs[test].text, 0, textLength, textLength, testInputs[test].rightToLeft, 0, 0, success); actual.glyphs = new LEGlyphID[actual.glyphCount]; actual.indices = new le_int32[actual.glyphCount]; actual.positions = new float[actual.glyphCount * 2 + 2]; engine->getGlyphs(actual.glyphs, success); engine->getCharIndices(actual.indices, success); engine->getGlyphPositions(actual.positions, success); result = compareResults(test, &testResults[test], &actual); if (result) { printf("passed.\n"); } else { failures += 1; printf("failed.\n"); } delete[] actual.positions; delete[] actual.indices; delete[] actual.glyphs; delete engine; } return failures; }
/* * Class: sun_font_SunLayoutEngine * Method: nativeLayout * Signature: (Lsun/font/FontStrike;[CIIIIZLjava/awt/geom/Point2D$Float;Lsun/font/GlyphLayout$GVData;)V */ JNIEXPORT void JNICALL Java_sun_font_SunLayoutEngine_nativeLayout (JNIEnv *env, jclass cls, jobject font2d, jobject strike, jfloatArray matrix, jint gmask, jint baseIndex, jcharArray text, jint start, jint limit, jint min, jint max, jint script, jint lang, jint typo_flags, jobject pt, jobject gvdata, jlong upem, jlong layoutTables) { // fprintf(stderr, "nl font: %x strike: %x script: %d\n", font2d, strike, script); fflush(stderr); float mat[4]; env->GetFloatArrayRegion(matrix, 0, 4, mat); FontInstanceAdapter fia(env, font2d, strike, mat, 72, 72, (le_int32) upem, (TTLayoutTableCache *) layoutTables); LEErrorCode success = LE_NO_ERROR; LayoutEngine *engine = LayoutEngine::layoutEngineFactory(&fia, script, lang, typo_flags & TYPO_MASK, success); if (min < 0) min = 0; if (max < min) max = min; /* defensive coding */ // have to copy, yuck, since code does upcalls now. this will be soooo slow jint len = max - min; jchar buffer[256]; jchar* chars = buffer; if (len > 256) { size_t size = len * sizeof(jchar); if (size / sizeof(jchar) != len) { return; } chars = (jchar*)malloc(size); if (chars == 0) { return; } } // fprintf(stderr, "nl chars: %x text: %x min %d len %d typo %x\n", chars, text, min, len, typo_flags); fflush(stderr); env->GetCharArrayRegion(text, min, len, chars); jfloat x, y; getFloat(env, pt, x, y); jboolean rtl = (typo_flags & TYPO_RTL) != 0; int glyphCount = engine->layoutChars(chars, start - min, limit - start, len, rtl, x, y, success); // fprintf(stderr, "sle nl len %d -> gc: %d\n", len, glyphCount); fflush(stderr); engine->getGlyphPosition(glyphCount, x, y, success); // fprintf(stderr, "layout glyphs: %d x: %g y: %g\n", glyphCount, x, y); fflush(stderr); if (putGV(env, gmask, baseIndex, gvdata, engine, glyphCount)) { // !!! hmmm, could use current value in positions array of GVData... putFloat(env, pt, x, y); } if (chars != buffer) { free(chars); } delete engine; }