java调用打印机,自定义模板

2023-12-24 00:13:07

?前言😊

只要你能看懂中文就会用,直接CV直接改,讲究的就是CV大法的魅力!!!

?

?须知🐱?👤

我们需要了解图像尺寸和物理尺寸之间的转换关系。

在图像处理中,通常使用像素作为图像的尺寸单位。
而像素和物理尺寸之间通常有一个固定的转换关系,这个关系取决于DPI(每英寸点数)。
在这个问题中,DPI是72,这意味着1英寸等于72像素。

因此,我们可以使用以下公式来进行换算:
图像尺寸(像素) = 物理尺寸(毫米) × (DPI / 25.4)

其中,25.4是1英寸的毫米数。

A4纸的尺寸为210mm×297mm,世界上多数国家所使用的纸张尺寸都是采用这一国际标准.

所以210x297mm的尺寸换算成72的图像尺寸的计算结果为:图像的宽度是 595.28 像素,高度是 841.89 像素。


效果展示🤣

预览效果👀

?打印效果💖


?代码🐱?🐉

系统属性🎂

import java.awt.*;

public final class SystemProperties {
    public static final double SCREEN_WIDTH = Toolkit.getDefaultToolkit().getScreenSize().getWidth();
    public static final double SCREEN_HEIGHT = Toolkit.getDefaultToolkit().getScreenSize().getHeight();
    public static final String USER_DIR = System.getProperty("user.dir");
    public static final String USER_HOME = System.getProperty("user.home");
    public static final String USER_NAME = System.getProperty("user.name");
    public static final String FILE_SEPARATOR = System.getProperty("file.separator");
    public static final String LINE_SEPARATOR = System.getProperty("line.separator");
    public static final String PATH_SEPARATOR = System.getProperty("path.separator");
    public static final String JAVA_HOME = System.getProperty("java.home");
    public static final String JAVA_VENDOR = System.getProperty("java.vendor");
    public static final String JAVA_VENDOR_URL = System.getProperty("java.vendor.url");
    public static final String JAVA_VERSION = System.getProperty("java.version");
    public static final String JAVA_CLASS_PATH = System.getProperty("java.class.path");
    public static final String JAVA_CLASS_VERSION = System.getProperty("java.class.version");
    public static final String OS_NAME = System.getProperty("os.name");
    public static final String OS_ARCH = System.getProperty("os.arch");
    public static final String OS_VERSION = System.getProperty("os.version");
    public static final String[] FONT_NAME_LIST = GraphicsEnvironment.getLocalGraphicsEnvironment().getAvailableFontFamilyNames();
    public static final Font[] FONT_LIST = GraphicsEnvironment.getLocalGraphicsEnvironment().getAllFonts();

    public SystemProperties() {
    }
}

?预览弹窗👀

import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.geom.Line2D;
import java.awt.geom.Rectangle2D;
import java.awt.print.PageFormat;
import java.awt.print.PrinterException;
import java.awt.print.PrinterJob;


public class PrintPreviewDialog extends JDialog
        implements ActionListener {
    private JButton nextButton = new JButton("下一个");
    private JButton previousButton = new JButton("以前");
    private JButton closeButton = new JButton("关闭");
    private JPanel buttonPanel = new JPanel();
    private PreviewCanvas canvas;

    public PrintPreviewDialog(Frame parent, String title, boolean modal, PrintHelp pt, String str) {
        super(parent, title, modal);
        canvas = new PreviewCanvas(pt, str);
        setLayout();
    }

    private void setLayout() {
        this.getContentPane().setLayout(new BorderLayout());
        this.getContentPane().add(canvas, BorderLayout.CENTER);

        nextButton.setMnemonic('N');
        nextButton.addActionListener(this);
        buttonPanel.add(nextButton);
        previousButton.setMnemonic('N');
        previousButton.addActionListener(this);
        buttonPanel.add(previousButton);
        closeButton.setMnemonic('N');
        closeButton.addActionListener(this);
        buttonPanel.add(closeButton);
        this.getContentPane().add(buttonPanel, BorderLayout.SOUTH);
        // 弹窗xy位置,宽高
        this.setBounds((int) ((SystemProperties.SCREEN_WIDTH - 400) / 2), (int) ((SystemProperties.SCREEN_HEIGHT - 400) / 2), 2360, 1180);
    }

    public void actionPerformed(ActionEvent evt) {
        Object src = evt.getSource();
        if (src == nextButton)
            nextAction();
        else if (src == previousButton)
            previousAction();
        else if (src == closeButton)
            closeAction();
    }

    private void closeAction() {
        this.setVisible(false);
        this.dispose();
    }

    private void nextAction() {
        canvas.viewPage(1);
    }

    private void previousAction() {
        canvas.viewPage(-1);
    }

    class PreviewCanvas extends JPanel {
        private String printStr;
        private int currentPage = 0;
        private PrintHelp preview;

        public PreviewCanvas(PrintHelp pt, String str) {
            printStr = str;
            preview = pt;
        }

        public void paintComponent(Graphics g) {
            super.paintComponent(g);
            Graphics2D g2 = (Graphics2D) g;
            PageFormat pf = PrinterJob.getPrinterJob().defaultPage();

            double xoff;
            double yoff;
            double scale;
            double px = pf.getWidth();

            double py = pf.getHeight();
            double sx = getWidth() - 1;
            double sy = getHeight() - 1;
            if (px / py < sx / sy) {
                scale = sy / py;
                xoff = 0.5 * (sx - scale * px);
                yoff = 0;
            } else {
                scale = sx / px;
                xoff = 0;
                yoff = 0.5 * (sy - scale * py);
            }
            g2.translate((float) xoff, (float) yoff);
            g2.scale((float) scale, (float) scale);
            // 白板xy轴位置,宽高
            Rectangle2D page = new Rectangle2D.Double(0, 0, px, py);
            g2.setPaint(Color.white);
            g2.fill(page);
            g2.setPaint(Color.black);
            g2.draw(page);

            try {
                preview.print(g2, pf, currentPage);
            } catch (PrinterException pe) {
                g2.draw(new Line2D.Double(0, 0, px, py));
                g2.draw(new Line2D.Double(0, px, 0, py));
            }
        }

        public void viewPage(int pos) {
            int newPage = currentPage + pos;
            if (0 <= newPage && newPage < preview.getPagesCount(printStr)) {
                currentPage = newPage;
                repaint();
            }
        }
    }
}

打印模板🐱?👤

import com.scwl.printer_jg.model.GoodsDTO;
import com.scwl.printer_jg.model.WeighingListDTO;

import javax.print.*;
import javax.print.attribute.DocAttributeSet;
import javax.print.attribute.HashDocAttributeSet;
import javax.print.attribute.HashPrintRequestAttributeSet;
import javax.print.attribute.PrintRequestAttributeSet;
import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.print.*;
import java.io.File;
import java.io.FileInputStream;
import java.util.ArrayList;
import java.util.Properties;

/**
 * @author 小影
 * @create 2023-12-22 17:05
 * @describe: JFrame:Java图形化界面设计——容器
 * java.awt.print.Printable动作事件监听器
 * java.awt.print.Printable:通用的打印 API 提供类和接口
 */
public class PrintHelp extends JFrame implements ActionListener, Printable {
    public PrintHelp() {
        this.setTitle("小影打印测试");// 窗口标题
        this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        this.setBounds((int) ((SystemProperties.SCREEN_WIDTH - 800) / 2), (int) ((SystemProperties.SCREEN_HEIGHT - 600) / 2), 800, 600);
        initLayout();
    }

    private WeighingListDTO weighingListDTO;// 参数实体类
    private int PAGES = 0;
    private JTextArea area = new JTextArea();// 用来创建一个默认的文本域
    private JPanel buttonPanel = new JPanel();// 创建面板
    private JScrollPane scroll = new JScrollPane(area);// 创建窗口
    private String printStr;
    private JButton printTextButton = new JButton("打印测试");
    private JButton previewButton = new JButton("打印预览");
    private JButton printText2Button = new JButton("打印测试2");
    private JButton printFileButton = new JButton("打印文件");
    private JButton printFrameButton = new JButton("Print Frame");
    private JButton exitButton = new JButton("退出");


    public static void main(String[] args) throws PrinterException {
        Book book = new Book();
        PageFormat pf = new PageFormat();
        pf.setOrientation(PageFormat.PORTRAIT);
        Paper p = new Paper();
        p.setSize(595, 283);// 纸张大小单位是像素
        p.setImageableArea(1, 5, 590, 282);// A4(595 X 842)设置打印区域,其�?0�?0应该�?72�?72,因为A4纸的默认X,Y边距�?72
        pf.setPaper(p);
        WeighingListDTO datas = new WeighingListDTO();
        datas.setUnitName("XXXXX有限公司称重计量单");
        datas.setClientName("客户名称: XXXXX里科技有限公司");
        datas.setPlateNumber("闽C:66666");
        datas.setOrderNo("过磅单:GB88888888");
        datas.setSjName("司机签名:");
        datas.setSjPhone("司机电话:");
        datas.setYssl("一式三联");

        ArrayList<GoodsDTO> goodList = new ArrayList<>();
        GoodsDTO goods = new GoodsDTO();
        GoodsDTO goods2 = new GoodsDTO();
        goods.setGoodsName("物料名称");
        goods.setNumber("件数");
        goods.setTare("皮重");
        goods.setGrossWeight("毛重");
        goods.setSuttle("净重");
        goods.setCSuttle("纯净重");
        goods.setQingTime("轻磅时间");
        goods.setZhongTime("重磅时间");

        goods2.setGoodsName("皂角");
        goods2.setNumber("100");
        goods2.setTare("15.76");
        goods2.setGrossWeight("49.80");
        goods2.setSuttle("34.0400");
        goods2.setCSuttle("34.0400");
        goods2.setQingTime("2023/12/22 09:30:00");
        goods2.setZhongTime("2023/12/22 10:30:00");
        goodList.add(goods);
        goodList.add(goods2);
        datas.setList(goodList);


        PrintHelp printHelp = new PrintHelp();
        printHelp.init(datas);
        book.append(printHelp, pf);
        PrinterJob job = PrinterJob.getPrinterJob();
        job.setPageable(book);
        // job.print();//进行打印
        printHelp.setVisible(true); // 打印窗口
    }


    public void init(WeighingListDTO datas) {
        this.weighingListDTO = datas;
    }


    private void initLayout() {
        this.getContentPane().setLayout(new BorderLayout());
        this.getContentPane().add(scroll, BorderLayout.CENTER);
        printTextButton.setMnemonic('P');
        printTextButton.addActionListener(this);
        buttonPanel.add(printTextButton);
        previewButton.setMnemonic('v');
        previewButton.addActionListener(this);
        buttonPanel.add(previewButton);
        printText2Button.setMnemonic('e');
        printText2Button.addActionListener(this);
        buttonPanel.add(printText2Button);
        printFileButton.setMnemonic('i');
        printFileButton.addActionListener(this);
        buttonPanel.add(printFileButton);
        printFrameButton.setMnemonic('F');
        printFrameButton.addActionListener(this);
        buttonPanel.add(printFrameButton);
        exitButton.setMnemonic('x');
        exitButton.addActionListener(this);
        buttonPanel.add(exitButton);
        this.getContentPane().add(buttonPanel, BorderLayout.SOUTH);
    }

    /**
     * 监听按钮
     *
     * @param evt
     */
    public void actionPerformed(ActionEvent evt) {
        Object src = evt.getSource();
        if (src == printTextButton)
            printTextAction();
        else if (src == previewButton)
            previewAction();
        else if (src == printText2Button)
            printText2Action();
        else if (src == printFileButton)
            printFileAction();
        else if (src == printFrameButton)
            printFrameAction();
        else if (src == exitButton)
            exitApp();
    }

    /**
     * 打印测试
     */
    private void printTextAction() {
        printStr = area.getText().trim();
        if (printStr != null && printStr.length() > 0) {
            PAGES = getPagesCount(printStr);
            PrinterJob myPrtJob = PrinterJob.getPrinterJob();
            PageFormat pageFormat = myPrtJob.defaultPage();
            myPrtJob.setPrintable(this, pageFormat);
            if (myPrtJob.printDialog()) {
                try {
                    myPrtJob.print();
                } catch (PrinterException pe) {
                    pe.printStackTrace();
                }
            }
        } else {
            // 需要输入内容
            JOptionPane.showConfirmDialog(null, "对不起,打印作业为空,打印取消!", "提示"
                    , JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE);
        }
    }

    /**
     * 打印预览
     */
    private void previewAction() {
        printStr = area.getText().trim();
        PAGES = getPagesCount(printStr);
        (new PrintPreviewDialog(this, "打印预览", true, this, printStr)).setVisible(true);
    }

    private void printText2Action() {
        printStr = area.getText().trim();
        if (printStr != null && printStr.length() > 0) {
            PAGES = getPagesCount(printStr);
            DocFlavor flavor = DocFlavor.SERVICE_FORMATTED.PRINTABLE;
            PrintService printService = PrintServiceLookup.lookupDefaultPrintService();
            DocPrintJob job = printService.createPrintJob();
            PrintRequestAttributeSet pras = new HashPrintRequestAttributeSet();
            DocAttributeSet das = new HashDocAttributeSet();
            Doc doc = new SimpleDoc(this, flavor, das);

            try {
                job.print(doc, pras);
            } catch (PrintException pe) {
                pe.printStackTrace();
            }
        } else {
            JOptionPane.showConfirmDialog(null, "Sorry, Printer Job is Empty, Print Cancelled!", "Empty"
                    , JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE);
        }
    }

    private void printFileAction() {
        JFileChooser fileChooser = new JFileChooser(SystemProperties.USER_DIR);
        int state = fileChooser.showOpenDialog(this);
        if (state == fileChooser.APPROVE_OPTION) {
            File file = fileChooser.getSelectedFile();
            PrintRequestAttributeSet pras = new HashPrintRequestAttributeSet();
            DocFlavor flavor = DocFlavor.INPUT_STREAM.AUTOSENSE;
            PrintService printService[] = PrintServiceLookup.lookupPrintServices(flavor, pras);
            PrintService defaultService = PrintServiceLookup.lookupDefaultPrintService();
            PrintService service = ServiceUI.printDialog(null, 200, 200, printService
                    , defaultService, flavor, pras);
            if (service != null) {
                try {
                    DocPrintJob job = service.createPrintJob();
                    FileInputStream fis = new FileInputStream(file);
                    DocAttributeSet das = new HashDocAttributeSet();
                    Doc doc = new SimpleDoc(fis, flavor, das);
                    job.print(doc, pras);
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        }
    }

    private void printFrameAction() {
        Toolkit kit = Toolkit.getDefaultToolkit();
        Properties props = new Properties();
        props.put("awt.print.printer", "durango");
        props.put("awt.print.numCopies", "2");
        if (kit != null) {
            PrintJob printJob = kit.getPrintJob(this, "Print Frame", props);
            if (printJob != null) {
                Graphics pg = printJob.getGraphics();
                if (pg != null) {
                    try {
                        this.printAll(pg);
                    } finally {
                        pg.dispose();
                    }
                }
                printJob.end();
            }
        }
    }

    /**
     * 退出
     */
    private void exitApp() {
        this.setVisible(false);
        this.dispose();
        System.exit(0);
    }


    /**
     * 获取页数数量
     *
     * @param curStr
     * @return
     */
    public int getPagesCount(String curStr) {
        int page = 0;
        int position, count = 0;
        String str = curStr;
        while (str.length() > 0) {
            position = str.indexOf('\n');
            count += 1;
            if (position != -1)
                str = str.substring(position + 1);
            else
                str = "";
        }

        if (count > 0)
            page = count / 54 + 1;

        return page;
    }

    /**
     * 打印模板
     *
     * @param g    将页面绘制到其中的上下文
     * @param pf   正在绘制的页面的大小和方向
     * @param page 要绘制的页的从零开始的索引
     * @return
     * @throws PrinterException
     */
    @Override
    public int print(Graphics g, PageFormat pf, int page) throws PrinterException {
        // 转换成Graphics2D
        Graphics2D g2 = (Graphics2D) g;
        // 设置打印颜色为黑
        // 抗锯齿就是减少图形边缘的锯齿状像素格,使画面看上去更精细而不是满屏的马赛克
        g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
        g2.setColor(Color.black);// 黑色

        // 打印起点坐标 对象的可成像区域左上方点的x 坐标 和左上的y坐标
        double x = pf.getImageableX();// 返回与此 PageFormat 相关 Paper
        double y = pf.getImageableY();

        switch (page) {
            case 0:
                // 新建 个打印字体样式(1.字体名称 2.样式(加粗).3字号大小
                Font font = new Font("微软雅黑", Font.PLAIN, 16);
                // 给g2设置字体
                g2.setFont(font);
                // 保存虚线的宽
                float[] dash1 = {2.0f};
                // 设置打印线的属 1.线宽 2 3、不知道 4、空白的宽度 5、虚线的宽度 6、偏移量
                g2.setStroke(new BasicStroke(0.5f, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER, 2.0f, dash1, 0.0f));
                float fontHeigth1 = font.getSize2D();// 字体大小

                // 左上40起点  中间160  右边400起点
                // 240高起点
                // 标题 (渲染的值,X轴,Y轴)
                g2.drawString(weighingListDTO.getUnitName(), 220, 40);

                // 如果把握不好尺寸就打印(g2.drawString(weighingListDTO.getUnitName() + "2", 50, 20);),然后再自己慢慢推敲出来想要的位置
                // g2.drawString(weighingListDTO.getUnitName() + "2", 50, 20);
                // g2.drawString(weighingListDTO.getUnitName() + "3", 60, 40);
                // g2.drawString(weighingListDTO.getUnitName() + "4", 70, 60);
                // g2.drawString(weighingListDTO.getUnitName() + "5", 80, 80);
                // g2.drawString(weighingListDTO.getUnitName() + "6", 90, 100);
                // g2.drawString(weighingListDTO.getUnitName() + "7", 100, 120);
                // g2.drawString(weighingListDTO.getUnitName() + "8", 110, 140);
                // g2.drawString(weighingListDTO.getUnitName() + "9", 120, 160);
                // g2.drawString(weighingListDTO.getUnitName() + "11", 130, 180);
                // g2.drawString(weighingListDTO.getUnitName() + "12", 140, 200);
                // g2.drawString(weighingListDTO.getUnitName() + "13", 150, 220);
                // g2.drawString(weighingListDTO.getUnitName() + "14", 160, 240);
                // g2.drawString(weighingListDTO.getUnitName() + "15", 170, 260);


                // 新建个字体
                Font font2 = new Font("微软雅黑", Font.PLAIN, 10);
                g2.setFont(font2);// 设置字体
                g2.setStroke(new BasicStroke(0.5f, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER, 2.0f, dash1, 0.0f));
                float fontHeigth2 = (int) font.getSize2D();// 字体2的高
                int tempHeight = (int) (fontHeigth1 * 2 + 50);// 临时高。字体1的高2倍 +50
                Integer hang_juInteger = 15;// 行距


                g2.drawString(weighingListDTO.getClientName(), 40, 60); 客户/供应商
                g2.drawString(weighingListDTO.getPlateNumber(), 250, 60);// 车牌号
                g2.drawString(weighingListDTO.getOrderNo(), 440, 60);// 磅单号

                int listY = 80;
                for (GoodsDTO dto : weighingListDTO.getList()) {
                    // 物料名称
                    g2.drawString(dto.getGoodsName(), 40, listY);
                    // 件数
                    g2.drawString(dto.getNumber(), 90,listY);
                    // 皮重
                    g2.drawString(dto.getTare(), 130,listY);
                    // 毛重
                    g2.drawString(dto.getGrossWeight(), 170,listY);
                    // 净重
                    g2.drawString(dto.getSuttle(), 210,listY);
                    // 纯净重
                    g2.drawString(dto.getSuttle(), 250,listY);
                    // 轻榜时间
                    g2.drawString(dto.getQingTime(), 320,listY);
                   // 重磅时间
                    g2.drawString(dto.getZhongTime(), 430,listY);
                    listY += 20;// 每行间距20像素
                }

                // 司机签名
                g2.drawString(weighingListDTO.getSjName(), 40,230);
                // // 司机电话
                g2.drawString(weighingListDTO.getSjPhone(), 160,230 );
                // // 一式三联
                g2.drawString(weighingListDTO.getYssl(), 500, 230);
                return PAGE_EXISTS;
            default:
                return NO_SUCH_PAGE;
        }
    }

}

注意:💖

如果要改成接口触发打印就需要改一下启动类,否则会报错:java.awt.HeadlessException: null

@SpringBootApplication
public class PrinterJgApplication {
    public static void main(String[] args) {
        SpringApplicationBuilder builder = new SpringApplicationBuilder(PrinterJgApplication.class);
        builder.headless(false).run(args);
    }
}

文章来源:https://blog.csdn.net/weixin_46522803/article/details/135161820
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。