Я разрабатываю программу на Java для печати некоторых этикеток на листе формата А4. Я хотел бы создать метки в отдельном классе, который возвращает BufferedImage, а затем передать коллекцию BufferedImages другому классу, который реализует интерфейс Printable, который затем разместит их на странице и напечатает их.
Я могу сделать все это, но обнаруживаю, что при рисовании BufferedImage в печатном виде, более тонкие элементы, в частности текст, немного размыты. Если я рисую непосредственно в графическом объекте, предоставляемом Printable, результаты будут намного лучше, но это неудобно для структуры программы.
Я попытался установить подсказки сглаживания для текста и графики, а также попытался нарисовать изображение двойного размера, а затем уменьшить его при рисовании в Printable, но это приводит к худшим результатам.
Ниже приведена тестовая программа, которую я написал, чтобы проиллюстрировать различия. На выходе текст явно размыт, когда я использую BufferedImage того же размера, что и квадрат, нарисованный в Printable, и снова при использовании большего BufferedImage и уменьшенного размера.
package printerresolutiontest;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.RenderingHints;
import java.awt.image.BufferedImage;
import java.awt.print.PageFormat;
import java.awt.print.Paper;
import java.awt.print.Printable;
import java.awt.print.PrinterException;
import java.awt.print.PrinterJob;
public class PrinterResolutionTest implements Printable {
public static void main(String[] args) throws PrinterException {
PrinterResolutionTest printrestest = new PrinterResolutionTest();
PrinterJob pj = PrinterJob.getPrinterJob();
PageFormat pf = pj.defaultPage();
Paper paper = pf.getPaper();
paper.setImageableArea(0*72, 0*72, 8.3*72, 11.7*72);
pf.setPaper(paper);
pj.setPrintable(printrestest, pf);
Boolean PRINT_DIALOG_OK = pj.printDialog();
if (PRINT_DIALOG_OK) {
pj.print();
}
}
@Override
public int print(Graphics graphics, PageFormat pageFormat, int pageIndex) throws PrinterException {
Graphics2D g2d = (Graphics2D) graphics;
BufferedImage img1 = new BufferedImage(144, 144, BufferedImage.TYPE_INT_RGB);
BufferedImage img2 = new BufferedImage(72, 72, BufferedImage.TYPE_INT_RGB);
Graphics2D g2d_bigbuf = img1.createGraphics();
Graphics2D g2d_buf = img2.createGraphics();
if (pageIndex > 0) {
return NO_SUCH_PAGE;
}
/*************************
* Draw directly into the Printable graphics object
*/
g2d.setColor(Color.RED);
g2d.fillRect(200, 200, 72, 72);
g2d.setColor(Color.black);
g2d.drawString("test", 202, (72/2)+202);
/*************************
* Draw the same features
* into a BufferedImage
*/
g2d_buf.setColor(Color.RED);
g2d_buf.fillRect(0, 0, 72, 72);
g2d_buf.setColor(Color.black);
g2d_buf.drawString("test", 0, 72/2);
/*************************
* Draw a double sized square and
* increase font size accordingly
*/
g2d_bigbuf.setColor(Color.RED);
g2d_bigbuf.fillRect(0, 0, 144, 144);
g2d_bigbuf.setColor(Color.black);
Font currentfont = g2d_bigbuf.getFont();
Font newfont = currentfont.deriveFont(currentfont.getSize() * 2F);
g2d_bigbuf.setFont(newfont);
g2d_bigbuf.drawString("test", 0, 144/2);
// Draw the regular sided BufferedImage
g2d.drawImage(img2, 300, 200, null);
// Draw the larger BufferedImage and scale down by half
g2d.drawImage(img1.getScaledInstance(72, 72, Image.SCALE_AREA_AVERAGING), 400, 200, null);
return PAGE_EXISTS;
}
}
BufferedImage test PNG
Вот тестовый снимок экрана из файла, который я распечатал в PDF, как пример различия. В идеале я хотел бы получить то же качество изображения, используя BufferedImage, что и при рисовании непосредственно в Printable.