Problem With Landscape Media Sizes 追蹤
Hello, I have developed a print daemon for Datamax M-4206 label printer; during the development, I found a problem with label definition, which has serious consequences for Java SE environment.
The daemon (=no chance of user interaction) is implemented in Java running on Windows platform. Java expects that all paper sizes provided by the system (i.e. Windows API [color="#0000FF"]DeviceCapabilities()[/color] call) are in portrait orientation; when the condition W<H is not satisfied, such media format is ignored. To be precise, when enumerating available paper sizes for a given printer, as provided by Windows API, the JRE executes [color="#0000FF"]sun.print.Win32PrintService.getMediaSizes()[/color] function. Within it, without further checking, it feeds W,H dimensions to a constructor of [color="#0000FF"]javax.print.attribute.standard.MediaSize[/color]. When width>height, the constructor throws IllegalArgumentException (see [url="http://docs.oracle.com/javase/7/docs/api/javax/print/attribute/standard/MediaSize.html#MediaSize%28float,%20float,%20int%29"]Java API docs[/url]). This exception is silently handled (=discarded) and the respective paper format is therefore removed from a result set.
The Windows API documentation for [color="#0000FF"]DeviceCapabilities()[/color] states the following assumption for query parameter DC_PAPERSIZE: "[i]Each structure contains the width (x-dimension) and length (y-dimension) of a paper size as if the paper were in the DMORIENT_PORTRAIT orientation.[/i]" (see [url="http://msdn.microsoft.com/en-us/library/windows/desktop/dd183552%28v=vs.85%29.aspx"]Windows API docs[/url])
This assumption is usually true for predefined stock sizes, but it becomes problematic when user-defined media come to play. As the custom stock setup dialog provides a preview of label roll, showing the label and margin relative dimensions, users tend to enter dimensions "incorrectly" (for labels such as 100mm x 40mm), in landscape order. The preview resembles the physical media and can be considered correct, but the consequence is that such media will not be available in Java (the condition W<H is not satisfied).
This is very problematic. I have discovered a workaround, but it makes the configuration extremely fragile. It depends on the following steps:
[*] "USER" format (ID=256) dimensions are made conforming, using arbitrary values (e.g. 150x250 mm).
[*] The actual custom size is defined (e.g. ID=257, name="My label", dimensions=100x40 mm) and is marked as default.
[/list] Then Java reports "USER" media with 150x250 mm dimensions, but with correct printable area of 100x40mm, which at least ensures that the output is fine. It is unfortunately another proof that Java Print Service API is quite a mess, however we have to live with it.
I would like to ask the developers of the Seagull Scientific driver to consider whether it would make sense to report even user-defined media sizes in portrait order, as is the case for most of the built-in definitions. Alternatively, I believe a short notice in documentation/dialog help/... would help, even though it seems that I am the first one (possibly only one) having to cope with printing stack "Seagull-Windows-Java".