# HG changeset patch # User bae # Date 1543609265 -10800 # Node ID df92f1126c589a550efc80c0f903fab40a3b36c6 # Parent 84cc04e403ab651a49fca5ac0f8fca99da0a2285 8139178: Wrong fontMetrics when printing in Landscape (OpenJDK) Reviewed-by: prr diff -r 84cc04e403ab -r df92f1126c58 src/java.desktop/share/native/libfontmanager/freetypeScaler.c --- a/src/java.desktop/share/native/libfontmanager/freetypeScaler.c Fri Nov 30 12:21:39 2018 -0800 +++ b/src/java.desktop/share/native/libfontmanager/freetypeScaler.c Fri Nov 30 23:21:05 2018 +0300 @@ -461,6 +461,14 @@ /* See https://bugs.debian.org/cgi-bin/bugreport.cgi?bug=657854 */ #define FT_MulFixFloatShift6(a, b) (((float) (a)) * ((float) (b)) / 65536.0 / 64.0) +#define contextAwareMetricsX(x, y) \ + (FTFixedToFloat(context->transform.xx) * (x) - \ + FTFixedToFloat(context->transform.xy) * (y)) + +#define contextAwareMetricsY(x, y) \ + (-FTFixedToFloat(context->transform.yx) * (x) + \ + FTFixedToFloat(context->transform.yy) * (y)) + /* * See FreeType source code: src/base/ftobjs.c ft_recompute_scaled_metrics() * http://icedtea.classpath.org/bugzilla/show_bug.cgi?id=1659 @@ -491,9 +499,13 @@ my = 0; metrics = (*env)->NewObject(env, - sunFontIDs.strikeMetricsClass, - sunFontIDs.strikeMetricsCtr, - ax, ay, dx, dy, bx, by, lx, ly, mx, my); + sunFontIDs.strikeMetricsClass, + sunFontIDs.strikeMetricsCtr, + contextAwareMetricsX(ax, ay), contextAwareMetricsY(ax, ay), + contextAwareMetricsX(dx, dy), contextAwareMetricsY(dx, dy), + bx, by, + contextAwareMetricsX(lx, ly), contextAwareMetricsY(lx, ly), + contextAwareMetricsX(mx, my), contextAwareMetricsY(mx, my)); return metrics; } diff -r 84cc04e403ab -r df92f1126c58 test/jdk/java/awt/font/Rotate/RotatedFontMetricsTest.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/test/jdk/java/awt/font/Rotate/RotatedFontMetricsTest.java Fri Nov 30 23:21:05 2018 +0300 @@ -0,0 +1,79 @@ +/* + * Copyright (c) 2018, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code 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 General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ + +/* + * @test RotatedFontMetricsTest + * @bug 8139178 + * @summary This test verifies that rotation does not affect font metrics. + * @run main RotatedFontMetricsTest + */ + +import java.awt.Font; +import java.awt.FontMetrics; +import java.awt.Graphics2D; +import java.awt.image.BufferedImage; + +public class RotatedFontMetricsTest { + static final int FONT_SIZE = Integer.getInteger("font.size", 20); + + public static void main(String ... args) { + Font font = new Font(Font.DIALOG, Font.PLAIN, FONT_SIZE); + Graphics2D g2d = createGraphics(); + + FontMetrics ref = null; + RuntimeException failure = null; + for (int a = 0; a < 360; a += 15) { + Graphics2D g = (Graphics2D)g2d.create(); + g.rotate(Math.toRadians(a)); + FontMetrics m = g.getFontMetrics(font); + g.dispose(); + + boolean status = true; + if (ref == null) { + ref = m; + } else { + status = ref.getAscent() == m.getAscent() && + ref.getDescent() == m.getDescent() && + ref.getLeading() == m.getLeading() && + ref.getMaxAdvance() == m.getMaxAdvance(); + } + + System.out.printf("Metrics a%d, d%d, l%d, m%d (%d) %s\n", + m.getAscent(), m.getDescent(), m.getLeading(), m.getMaxAdvance(), + (int)a, status ? "OK" : "FAIL"); + + if (!status && failure == null) { + failure = new RuntimeException("Font metrics differ for angle " + a); + } + } + if (failure != null) { + throw failure; + } + System.out.println("done"); + } + + private static Graphics2D createGraphics() { + BufferedImage dst = new BufferedImage(100, 100, BufferedImage.TYPE_INT_RGB); + return dst.createGraphics(); + } +}