Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

8265761: Font with missed font family name is not properly printed on Windows #3631

Closed

Conversation

@AlexanderScherbatiy
Copy link

@AlexanderScherbatiy AlexanderScherbatiy commented Apr 22, 2021

PDFBox 1.8 uses Graphics2D.drawGlyphVector() method with scaled glyphs to print a text and PDF 2.0 uses Graphics2D.fill() to print glyphs path. Both methods finally calls WPathGraphics.convertToWPath(...) in jdk on Windows which call GDI FillPath.

Using a custom PageDrawer to draw a text in PDFBox with Graphics2D.drawString() method reveals the fact that some pdf documents which are properly printed by PDFBox 1.8 and PDF 2.0 on Linux and Windows have issues with printing them on Windows.

The reason is that such docs use fonts which have empty font family name.
The awt_PrintJob.jFontToWFontA(...) method is not able to select the required font when the passed font family name is empty.

static jboolean jFontToWFontA(JNIEnv *env, HDC printDC, jstring fontName,

The proposed solution returns false from WPrinterJob.setFont(...) method when the font family is empty so the text printing falls back to printing a text by GDI FillPath method:

protected boolean setFont(String family, float size, int style,

To reproduce the issue I created a simple SampleBowMissedFamilyName.ttf font which contains only capital letters "ABCDEF" and saved it with empty font family name.

Here is a simple PrintFontSample.java program that helps to reproduce the issue using the SampleBowMissedFamilyName.ttf font.

The PrintFontSample program draws a text using three methods:

  • Graphics2D.drawString(...)
  • Graphics2D.drawGlyphVector(...)
  • Graphics2D.drawGlyphVector(...) using transformed glyphs

Running the program with jdk 16 on Windows (without the fix)

java PrintFontSample SampleBowMissedFamilyName.ttf

shows that the first and the second lines are not properly printed: sample-doc-without-fix.pdf
Running the program with the fix properly prints all three lines: sample-doc-with-fix.pdf

The provided manual test uses the created SampleBowMissedFamilyName.ttf font with empty font family name.


Progress

  • Change must not contain extraneous whitespace
  • Commit message must refer to an issue
  • Change must be properly reviewed

Issue

  • JDK-8265761: Font with missed font family name is not properly printed on Windows

Reviewers

Reviewing

Using git

Checkout this PR locally:
$ git fetch https://git.openjdk.java.net/jdk pull/3631/head:pull/3631
$ git checkout pull/3631

Update a local copy of the PR:
$ git checkout pull/3631
$ git pull https://git.openjdk.java.net/jdk pull/3631/head

Using Skara CLI tools

Checkout this PR locally:
$ git pr checkout 3631

View PR using the GUI difftool:
$ git pr show -t 3631

Using diff file

Download this PR as a diff file:
https://git.openjdk.java.net/jdk/pull/3631.diff

@bridgekeeper
Copy link

@bridgekeeper bridgekeeper bot commented Apr 22, 2021

👋 Welcome back alexsch! A progress list of the required criteria for merging this PR into master will be added to the body of your pull request. There are additional pull request commands available for use with this pull request.

@openjdk openjdk bot added the rfr label Apr 22, 2021
@openjdk
Copy link

@openjdk openjdk bot commented Apr 22, 2021

@AlexanderScherbatiy The following labels will be automatically applied to this pull request:

  • 2d
  • awt

When this pull request is ready to be reviewed, an "RFR" email will be sent to the corresponding mailing lists. If you would like to change these labels, use the /label pull request command.

@mlbridge
Copy link

@mlbridge mlbridge bot commented Apr 22, 2021

Webrevs

@AlexanderScherbatiy
Copy link
Author

@AlexanderScherbatiy AlexanderScherbatiy commented Apr 22, 2021

The java/awt/print and java/awt/PrintJob automated and manual tests were run with the fix.

The automated tests pass.
The following manual tests fail with and without the fix:

java/awt/print/Dialog/DialogOrient.java Error. Parse Exception: Arguments to `manual' option not supported: yesno
java/awt/print/Dialog/DialogType.java Error. Parse Exception: Arguments to `manual' option not supported: yesno
java/awt/print/PrinterJob/ImagePrinting/ClippedImages.java Error. Parse Exception: Arguments to `manual' option not supported: yesno
java/awt/print/PrinterJob/ImagePrinting/ImageTypes.java Error. Parse Exception: Arguments to `manual' option not supported: yesno
java/awt/print/PrinterJob/ImagePrinting/PrintARGBImage.java Error. Parse Exception: Arguments to `manual' option not supported: yesno
java/awt/print/PrinterJob/PageDialogTest.java Error. Parse Exception: Arguments to `manual' option not supported: yesno
java/awt/print/PrinterJob/PageRanges.java Error. Parse Exception: Arguments to `manual' option not supported: yesno
java/awt/print/PrinterJob/PageRangesDlgTest.java Error. Parse Exception: Arguments to `manual' option not supported: yesno
java/awt/print/PrinterJob/PrintGlyphVectorTest.java Error. Parse Exception: Arguments to `manual' option not supported: yesno
java/awt/print/PrinterJob/PrintLatinCJKTest.java Error. Parse Exception: Arguments to `manual' option not supported: yesno
java/awt/print/PrinterJob/PrintTextTest.java Error. Parse Exception: Arguments to `manual' option not supported: yesno
java/awt/print/PrinterJob/SwingUIText.java Error. Parse Exception: Arguments to `manual' option not supported: yesno
java/awt/PrintJob/ConstrainedPrintingTest/ConstrainedPrintingTest.java Error. Parse Exception: Arguments to `manual' option not supported: yesno
java/awt/PrintJob/PageSetupDlgBlockingTest/PageSetupDlgBlockingTest.java Error. Parse Exception: Arguments to `manual' option not supported: yesno
java/awt/PrintJob/SaveDialogTitleTest.java Error. Parse Exception: Arguments to `manual' option not supported: yesno
java/awt/print/Dialog/PrintDlgPageable.java Error. java.lang.IllegalAccessException: class com.sun.javatest.regtest.agent.MainWrapper$MainThread cannot access a member of class PrintDlgPageable with modifiers "public static"
java/awt/PrintJob/PrintCheckboxTest/PrintCheckboxManualTest.java Error. Can't find HTML file: test\jdk\java\awt\PrintJob\PrintCheckboxTest\PrintCheckboxManualTest.html

@@ -1157,6 +1157,10 @@ protected boolean selectStylePen(int cap, int join, float width,
protected boolean setFont(String family, float size, int style,
int rotation, float awScale) {

if (family.isEmpty()) {
Copy link
Member

@mrserb mrserb Apr 23, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not sure that the non-empty family, but spaces only will work.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would it be better to use isBlank() instead of isEmpty() to check a font family name is blank?

        if (family.isBlank()) {
            return false;
        }

Copy link
Member

@mrserb mrserb Apr 25, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think so.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I changed the test SampleBow font family name to one space SampleBowOneSpaceFamilyName.ttf and to two spaces SampleBowTwoSpacesFamilyName.ttf

The PrintFontSample sample program properly prints text drawn by Graphics2D.drawString() and Graphics2D.drawGlyphVector() on Windows with jdk 16 with these two fonts.
It looks like the problem is only with selecting a font in GDI with empty font family name.

@prrace
Copy link
Contributor

@prrace prrace commented Apr 26, 2021

I dumped the font you attached and it has

	Data: 43 6F 70 79 72 69 67 68 74 20  >  Copyright 
	      73 74 65 6C 6C 61 72 73 70 6F  >  stellarspo
	      74 20 32 30 32 31              >  t 2021

Who are stellarspot ? We can't put their copyrighted font into openjdk. If you created this font by editing
someone else's font that is a no-no. You would have to create a font from scratch and assert you own
the font and the design of all glyphs and contribute it under OCA.

The fix itself is probably fine .. I am surprised you get this far with a font with no name

@AlexanderScherbatiy
Copy link
Author

@AlexanderScherbatiy AlexanderScherbatiy commented Apr 27, 2021

The stellarpot is my account which I used to create SampleBow font in fontconstruct.
I put a link to my github page in the fontconstruct profile.

If it is necessary, I can recreate the font or create an another font under my name and the required license. What is the right license that I can use to create a simple font for openjdk test? What is the way to contribute the font and the design of all glyphs under OCA?

@prrace
Copy link
Contributor

@prrace prrace commented Apr 27, 2021

We don't have a lot of precedent here. Your name .. BellSoft .. Oracle .. OpenJDK .. nothing at all .. some message like "created for OpenJDK might help !".
Something so that 10 years from now when someone looks at the font and has no reference back to this that they can say "Oh this is OK" and not "uh, oh, who is that ?"

@AlexanderScherbatiy
Copy link
Author

@AlexanderScherbatiy AlexanderScherbatiy commented Apr 28, 2021

I updated the font so now it uses "Alexander Scherbatiy" as a designer, "SampleFont Regular created for OpenJDK" as name for humans, and copyright:

Copyright (c) 2021, Oracle and/or its affiliates. All rights reserved.
Copyright (c) 2021, BELLSOFT. All rights reserved.
DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
...

mrserb
mrserb approved these changes Apr 28, 2021
@openjdk
Copy link

@openjdk openjdk bot commented Apr 28, 2021

@AlexanderScherbatiy This change now passes all automated pre-integration checks.

ℹ️ This project also has non-automated pre-integration requirements. Please see the file CONTRIBUTING.md for details.

After integration, the commit message for the final commit will be:

8265761: Font with missed font family name is not properly printed on Windows

Reviewed-by: serb, prr

You can use pull request commands such as /summary, /contributor and /issue to adjust it as needed.

At the time when this comment was updated there had been 129 new commits pushed to the master branch:

  • 3f9879f: 8266190: mark hotspot compiler/codecache tests which ignore VM flags
  • d12e01a: 8264472: Add a test group for running CDS tests with -XX:+VerifySharedSpaces
  • b3b2bb2: 8265773: incorrect jdeps message "jdk8internals" to describe a removed JDK internal API
  • 2780577: 8196415: Disable SHA-1 Signed JARs
  • 21f65f8: 8266206: Build failure after JDK-8264752 with older GCCs
  • c71c268: 8266165: TestNoWarningLoopStripMiningIterSet is runnable only on VM w/ G1, Shenandoah, Z and Epsilon
  • 8954bef: 8266188: mark hotspot compiler/cpuflags tests which ignore VM flags
  • 19d3c45: 8266184: a few compiler/debug tests don't check exit code
  • 7e3bc4c: 8228442: DHKeyExchange/LegacyDHEKeyExchange.java failed due to "SSLException: An established connection was aborted by the software in your host machine"
  • f40bf1d: 8266087: Move 'buffer' declaration in get_user_name_slow() inside of linux specific code
  • ... and 119 more: https://git.openjdk.java.net/jdk/compare/e16d568c1f5d7030b9e038e21fb3815ae5b1163a...master

As there are no conflicts, your changes will automatically be rebased on top of these commits when integrating. If you prefer to avoid this automatic rebasing, please check the documentation for the /integrate command for further details.

➡️ To integrate this PR with the above commit message to the master branch, type /integrate in a new comment.

@openjdk openjdk bot added the ready label Apr 28, 2021
prrace
prrace approved these changes Apr 28, 2021
@AlexanderScherbatiy
Copy link
Author

@AlexanderScherbatiy AlexanderScherbatiy commented Apr 30, 2021

/integrate

@openjdk openjdk bot closed this Apr 30, 2021
@openjdk openjdk bot added integrated and removed ready rfr labels Apr 30, 2021
@openjdk
Copy link

@openjdk openjdk bot commented Apr 30, 2021

@AlexanderScherbatiy Since your change was applied there have been 173 commits pushed to the master branch:

  • 3554dc2: 8264395: WB_EnqueueInitializerForCompilation fails with "method holder must be initialized" when called for uninitialized class
  • 4d77171: 8249903: jdk/javadoc/doclet/testSerializedForm/TestSerializedForm.java needs to be updated after 8146022 got closed
  • 51b2188: 8266267: Remove unnecessary jumps in Intel Math Library StubRoutines
  • 2c381e0: 8262376: ReplaceCriticalClassesForSubgraphs.java fails if --with-build-jdk is used
  • 5ecef01: 8266217: ZGC: Improve the -Xlog:gc+init output for NUMA
  • 5d8c1cc: 8255410: Add ChaCha20 and Poly1305 support to SunPKCS11 provider
  • 46b4a14: 8266315: Problem list failing test java/awt/font/TextLayout/LigatureCaretTest.java
  • 42af7da: 8265933: Move Java monitor related fields from class Thread to JavaThread
  • 1afbab6: 8263998: Remove mentions of mc region in comments
  • 51b2fb5: 8266299: ProblemList runtime/stringtable/StringTableCleaningTest.java on linux-aarch64 with ZGC
  • ... and 163 more: https://git.openjdk.java.net/jdk/compare/e16d568c1f5d7030b9e038e21fb3815ae5b1163a...master

Your commit was automatically rebased without conflicts.

Pushed as commit e9370a1.

💡 You may see a message that your pull request was closed with unmerged commits. This can be safely ignored.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
3 participants