自动打印在Java中不起作用 [英] Automatic print is not working in Java

查看:143
本文介绍了自动打印在Java中不起作用的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我需要以两种不同的方式打印pdf文件 - 通过网页,用户将看到打印预览并选择打印机并进行打印。第二种方法是自动化打印,只需单击一个按钮,就可以将pdf发送到打印机。

I have a requirement to print pdf files in two different ways -one through web page where user will see the print preview and choose the printer and print it. Second way is to automate the printing, just by clicking a button, the pdf should be sent to printer.

第一种打印方式是通过网页工作正常,但不是第二种方式。成功检索默认打印机以进行自动打印,但未打印,我也没有收到任何错误。以下是我的分析:

The first way of printing is through web page is working fine, but not the second way. The default printer is successfully retrieved for automatic printing, but is not getting printed and I am not getting any error as well. Following are my analysis:


  1. 最初,我认为不支持 DocFlavor 。然后我在该打印机支持的 DocFlavor 中列出
    ,其中一个是
    application / octet-stream,这是 DocFlavor.INPUT_STREAM.AUTOSENSE
    因此打印机支持这种风格。

  2. 然后,我添加 PrintJobListener 来检查打印作业是否为
    失败了。当我将该监听器添加到printJob时,它会打印
    No_More_Events DATA_TRANSFER_COMPLETE ,这应该打印
    JOB_COMPLETE ,如果作业成功。

  3. 最后一步是调试Java代码。当我执行
    job.print()行时,它会进入 Win32PrintJob.print()方法。我做了F6到
    执行每一行,看看它在做什么。我将它与进行了比较。 java#Win32PrintJob.print%28javax.print.Doc%2Cjavax.print.attribute.PrintRequestAttributeSet%29> GrepCode ,因为源代码未在eclipse中加载。它
    一切正常,我看不到任何错误。它没有进入
    的唯一地方是这个块,它检查 mDestination
    值,因为我没有提供它,它没有经过。

  1. Initially, I thought the DocFlavor is not supported. Then I listed down the supported DocFlavor of that printer and one of them was application/octet-stream, which is DocFlavor.INPUT_STREAM.AUTOSENSE. So the flavor is supported by printer.
  2. Then, I added the PrintJobListener to check if the print job is failed. When I added that listener to the printJob, it prints No_More_Events and DATA_TRANSFER_COMPLETE, which should have printed JOB_COMPLETE, if the job is success.
  3. Final step is to debug the Java code. When I executed the line job.print(), it goes into Win32PrintJob.print() method. I did F6 to execute each line to see what its doing. I compared it with the code in GrepCode, as the source code was not loaded in eclipse. It was going fine and I could not see any error. The only place it did not go into is this block where it checks for the mDestination value, since I have not provided it, it did not go through.

请参阅以下代码:

if (mDestination != null) { // if destination attribute is set
    try {
        FileOutputStream fos = new FileOutputStream(mDestination);
        byte [] buffer = new byte[1024];
        int cread;

        while ((cread = instream.read(buffer, 0, buffer.length)) >= 0) {
            fos.write(buffer, 0, cread);
        }
        fos.flush();
        fos.close();
    } catch (FileNotFoundException fnfe) {
        notifyEvent(PrintJobEvent.JOB_FAILED);
        throw new PrintException(fnfe.toString());
    } catch (IOException ioe) {
        notifyEvent(PrintJobEvent.JOB_FAILED);
        throw new PrintException(ioe.toString());
    }
    notifyEvent(PrintJobEvent.DATA_TRANSFER_COMPLETE);
    notifyEvent(PrintJobEvent.JOB_COMPLETE);
    service.wakeNotifier();
    return;
}

这是唯一一个说JOB_COMPLETE的地方。我认为这个块是写入一个文件,这对我来说是不需要的。

This is the only place where it says JOB_COMPLETE. I think this block is to write into a file, which is not needed for me.

我认为实际打印在Win32PrintJob.print()的相同方法中发生在以下行中。

I think the actual printing takes place in the following line in the same method Win32PrintJob.print().

private native boolean More ...printRawData(byte[] data, int count);

但这个是本机方法,因此我不知道其中发生了什么。

But this one is native method and so I don't know what is happening inside this.

请让我知道为什么我无法打印PDF。

Please let me know why I am not able to print the PDF.

编辑:

附上打印文件的代码:

PrintService pss = PrintServiceLookup.lookupDefaultPrintService();
DocPrintJob job = pss.createPrintJob();
DocAttributeSet das = new HashDocAttributeSet();
Doc document;
try {
    document = new SimpleDoc(new FileInputStream(new File(fileName)), DocFlavor.INPUT_STREAM.AUTOSENSE, das);

    PrintRequestAttributeSet pras = new HashPrintRequestAttributeSet();
    job.addPrintJobListener(new PrintJobWatcher());
    job.print(document, pras);
}

注意:我尝试过不同的风格,如PDF,PCL。没有什么工作,我得到运行时错误,它不受支持。

NOTE: I tried different flavors like PDF, PCL. Nothing is working and I get runtime error that it is not supported.

推荐答案

我最近有同样的任务和答案对于第二个打印选项来说并不是那么直接(也尝试过JPedal,Samba和其他解决方案......)。
最简单的打印方式(我最终尝试过)只是将文件放在打印机队列中,a.k.a是根位置。例如:MY_SERVER \PRINTER_NAME \

I've recently had the same task and the answer is not so straight forward for the second printing option (also tried JPedal, Samba, and other solutions..). The most simple way to print (which I ultimately tried) was to simply place the file in the printer queue, a.k.a the root location. Ex : MY_SERVER\PRINTER_NAME\

问题现在变为环境/ O.S一个,而不是Java环境。
通过安装在Windows机器上的应用程序,您可以访问该文件夹,复制要打印的文件,然后瞧。
此外,使用您使用的方法,您还可以为打印作业指定名称,份数等。

The problem now becomes an environnement/O.S one, and not a Java one. Through an app installed on a Windows machine, you could possibly access that folder, copy the file you want printed, and voila. Furthermore, using the methods you use, you could also give the print job a name, number of copies, etc.

但是,一旦安装了应用程序在服务器上,这是一个完全不同的球类游戏,特别是如果你正在使用Linux服务器。

However, once the app is installed on the server, it's a whole different ball game, especially if you are working with Linux servers.

首先,你必须将Windows地址转换为Linux地址到甚至尝试复制文件/打印它。

First of all you would have to translate the Windows adresses to Linux ones to even try to copy the file/print it.

其次,这是关键,打印机只是接受文件是非常罕见/困难的用于打印,如果它不是更复杂/专有的数据流的一部分。例如,当您执行Ctrl + P时,您可以找到打印机与服务器甚至机器的通信语言..这将主要是.xml文件或其他格式。

Second of all, and this is key, it is very rare/difficult for a printer to just "accept a file" for printing, if it is not part of a more complicated/proprietary Stream of data. For example you could find out the printers "communication language" with the server or even your machine when you do "Ctrl+P"..this will be mostly .xml files or some other format.

但/并且为了弄清楚这种格式,你必须开发(最终在Java中)一个可以调用该打印机的applet。

But/and in order to "figure" out this format you would have to develop (ultimately in Java) an applet that would call that printer.

当然,您也可以尝试在该服务器上安装Cups4j或安装打印机服务器(假设您的工作位置不合适),但这会在打印机更改,添加到网络等时出现问题。

You could of course, also try to install Cups4j on that server or have a printer server setup (assuming where you work this isn't in place), but this will cause problems when printers will change, be added to the network, etc.

最后你要坚持使用Ctrl + P方法,制作一个在浏览器中调用CTRL + P的小型JS脚本,或者开始重新创建轮子,这不是一件坏事(因为有人也选择这种方法..但我没有在任何地方找到一个例子),但是你可能花费的时间比你多。

Ultimately either you would stick to the "Ctrl+P" approach, make a little JS script that calls "CTRL+P" in the browser or start re-creating the wheel, which is not a bad thing (since there are people who choose this approach also..but I haven't found an exemple anywhere), but would take you probably more time than you have.

希望我能以某种方式提供帮助(对不起这篇文章很遗憾......但是这是我搜索并研究了很长一段时间的主题。

Hope I helped in some way (sorry for the long post..but it's a subject I've searched and worked on for a good period of time).

这篇关于自动打印在Java中不起作用的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆