如何在指定打印机上打印Jasper报表?

11
我想做的就是在没有用户选择打印机的情况下打印JasperReport。我搜索了一下,但没有一个好的解决方案能够实现。这是我的代码的相关部分:
//compile to .jasper
String report = JasperCompileManager.compileReportToFile(sourceFileName);

//fill the report
JasperPrint jasperPrint = JasperFillManager.fillReport(report, parameter, dataSource);

//print the report      
JasperPrintManager.printReport(jasperPrint, true);

我希望选择一个打印机而不是简单地打印报告。 有什么办法可以做到这一点吗?


1
我肯定不是唯一一个遇到这个问题的人... - PRO_gramista
4个回答

10

这就是预期的结果:

try {

    String report = JasperCompileManager.compileReportToFile(sourceFileName);

    JasperPrint jasperPrint = JasperFillManager.fillReport(report, para, ds);

    PrinterJob printerJob = PrinterJob.getPrinterJob();

    PageFormat pageFormat = PrinterJob.getPrinterJob().defaultPage();
    printerJob.defaultPage(pageFormat);

    int selectedService = 0;

    AttributeSet attributeSet = new HashPrintServiceAttributeSet(new PrinterName(printerNameShort, null));

    PrintService[] printService = PrintServiceLookup.lookupPrintServices(null, attributeSet);

    try {
        printerJob.setPrintService(printService[selectedService]);

    } catch (Exception e) {

        System.out.println(e);
    }
    JRPrintServiceExporter exporter;
    PrintRequestAttributeSet printRequestAttributeSet = new HashPrintRequestAttributeSet();
    printRequestAttributeSet.add(MediaSizeName.NA_LETTER);
    printRequestAttributeSet.add(new Copies(1));

    // these are deprecated
    exporter = new JRPrintServiceExporter();
    exporter.setParameter(JRExporterParameter.JASPER_PRINT, jasperPrint);
    exporter.setParameter(JRPrintServiceExporterParameter.PRINT_SERVICE, printService[selectedService]);
    exporter.setParameter(JRPrintServiceExporterParameter.PRINT_SERVICE_ATTRIBUTE_SET, printService[selectedService].getAttributes());
    exporter.setParameter(JRPrintServiceExporterParameter.PRINT_REQUEST_ATTRIBUTE_SET, printRequestAttributeSet);
    exporter.setParameter(JRPrintServiceExporterParameter.DISPLAY_PAGE_DIALOG, Boolean.FALSE);
    exporter.setParameter(JRPrintServiceExporterParameter.DISPLAY_PRINT_DIALOG, Boolean.FALSE);
    exporter.exportReport();

} catch (JRException e) {
    e.printStackTrace();
}

6

这里有一个简单的解决方案,可以将Jasper报告打印在指定的打印机上 创建一个选择打印机并打印报告的方法

private void PrintReportToPrinter(JasperPrint jp) throws JRException {
    // TODO Auto-generated method stub
    PrintRequestAttributeSet printRequestAttributeSet = new HashPrintRequestAttributeSet();
    // printRequestAttributeSet.add(MediaSizeName.ISO_A4); //setting page size
    printRequestAttributeSet.add(new Copies(1));

    PrinterName printerName = new PrinterName("Microsoft XPS Document Writer", null); //gets printer 

    PrintServiceAttributeSet printServiceAttributeSet = new HashPrintServiceAttributeSet();
    printServiceAttributeSet.add(printerName);

    JRPrintServiceExporter exporter = new JRPrintServiceExporter();

    exporter.setParameter(JRExporterParameter.JASPER_PRINT, jp);
    exporter.setParameter(JRPrintServiceExporterParameter.PRINT_REQUEST_ATTRIBUTE_SET, printRequestAttributeSet);
    exporter.setParameter(JRPrintServiceExporterParameter.PRINT_SERVICE_ATTRIBUTE_SET, printServiceAttributeSet);
    exporter.setParameter(JRPrintServiceExporterParameter.DISPLAY_PAGE_DIALOG, Boolean.FALSE);
    exporter.setParameter(JRPrintServiceExporterParameter.DISPLAY_PRINT_DIALOG, Boolean.FALSE);
    exporter.exportReport();
}

然后像这样调用该方法:
/* your code*/
Map parameters = new HashMap();
parameters.put("ckotid", kid);

try {
    JasperDesign jsd = JRXmlLoader.load("report\\bill\\check_kot.jrxml");
    JasperReport jr = JasperCompileManager.compileReport(jsd);
    JasperPrint jp = JasperFillManager.fillReport(jr, parameters, con);
    //JasperPrintManager.printPage(jp, 0, false);
    //JasperPrint jp =reportEngine.fillReport() ;//it returns stream 
    PrintReportToPrinter(jp);//call method

我想在共享打印机上打印,如何识别共享打印机的名称。我使用的打印机名称是“POS”,在共享打印机名称中显示为“服务器上的POS”。 - WARRW
你需要从打印机设置中找到打印机名称,并在代码中使用它,就像我使用了“Microsoft XPS 文档编写器”一样。为了避免冗余的代码编译,你可以将打印机名称存储在数据库中,并在打印机名称更改时进行更新。 - CyberAbhay
问题是它对于网络共享打印机无法正常工作。我已经在打印机设置中使用了名称,但对我来说无效。 - WARRW

4
这些代码已经过时。 在JasperReports 5.6中,JRPrintServiceExporter.setParameter变为废弃。他们引入了新的接口Exporter,并更新了所有导出器以具有ExporterInput、ReportExportConfiguration、ExporterConfiguration和ExporterOutput。请参见下面的链接。

http://jasperreports.sourceforge.net/api/net/sf/jasperreports/export/Exporter.html

这意味着您需要创建配置,而不是使用setParameter。
private void PrintReportToPrinter(JasperPrint jasperPrint) throws JRException {

//Get the printers names
PrintService[] services = PrintServiceLookup.lookupPrintServices(null, null);

//Lets set the printer name based on the registered printers driver name (you can see the printer names in the services variable at debugging) 
String selectedPrinter = "Microsoft XPS Document Writer";   
// String selectedPrinter = "\\\\S-BPPRINT\\HP Color LaserJet 4700"; // examlpe to network shared printer

System.out.println("Number of print services: " + services.length);
PrintService selectedService = null;

//Set the printing settings
PrintRequestAttributeSet printRequestAttributeSet = new HashPrintRequestAttributeSet();
printRequestAttributeSet.add(MediaSizeName.ISO_A4);
printRequestAttributeSet.add(new Copies(1));
if (jasperPrint.getOrientationValue() == net.sf.jasperreports.engine.type.OrientationEnum.LANDSCAPE) { 
  printRequestAttributeSet.add(OrientationRequested.LANDSCAPE); 
} else { 
  printRequestAttributeSet.add(OrientationRequested.PORTRAIT); 
} 
PrintServiceAttributeSet printServiceAttributeSet = new HashPrintServiceAttributeSet();
printServiceAttributeSet.add(new PrinterName(selectedPrinter, null));

JRPrintServiceExporter exporter = new JRPrintServiceExporter();
SimplePrintServiceExporterConfiguration configuration = new SimplePrintServiceExporterConfiguration();
configuration.setPrintRequestAttributeSet(printRequestAttributeSet);
configuration.setPrintServiceAttributeSet(printServiceAttributeSet);
configuration.setDisplayPageDialog(false);
configuration.setDisplayPrintDialog(false);

exporter.setExporterInput(new SimpleExporterInput(jasperPrint));
exporter.setConfiguration(configuration);

//Iterate through available printer, and once matched with our <selectedPrinter>, go ahead and print!
if(services != null && services.length != 0){
  for(PrintService service : services){
      String existingPrinter = service.getName();
      if(existingPrinter.equals(selectedPrinter))
      {
          selectedService = service;
          break;
      }
  }
}
if(selectedService != null)
{   
  try{
      //Lets the printer do its magic!
      exporter.exportReport();
  }catch(Exception e){
System.out.println("JasperReport Error: "+e.getMessage());
  }
}else{
  System.out.println("JasperReport Error: Printer not found!");
}}

您也可以使用此代码将内容打印到网络共享打印机。

2

只需使用这个代码,不需要更多的代码,它可以处理Jasper。

JasperPrintManager.printReport(jasperPrint, false);

如果您使用“true”,它将显示窗口。

我已经测试过爱普生TM T82,它可以正常工作。


POS系统在商店等场所使用,那么他们每次在Windows中如何选择打印机呢? - CyberAbhay
在应用程序运行时无需选择打印机。您已将爱普生打印机设置为计算机的默认打印机。 - Zcon
2
如果他们安装了两台打印机,一台用于个人使用,另一台用于客户(POS),那么呢?如果他们有酒店计费系统:前台有一台打印机,厨房有一台打印机,那么呢?如果他们有两台打印机,那么就要想出新的解决方案。如果将默认设置为 POS,则每天的打印都会发送到 POS。 - CyberAbhay

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接