1. 程式人生 > >ireport5.6.0+jasperreports-5.6.0+applet實現客戶端列印

ireport5.6.0+jasperreports-5.6.0+applet實現客戶端列印

       我也是第一次使用ireport這個報表工具。在網上找了各種資料,最終實現了列印功能,當把程式部署到伺服器上才知道,並不能實現客戶端列印。後來繼續百度,找到了可以通過applet實現客戶端列印的方法,也找到了很多列子,跟著敲了一邊,因為使用的jasperreports的版本不一致,所以也遇到了各種問題。

       我最開始做列印參考http://aijnecjay.iteye.com/blog/1689372 這裡寫的,因為版本不一致,在瀏覽器上不能彈出列印提示。

最終檢視java控制檯,才知道缺少什麼jar包,缺什麼就加什麼,一步一步完善。先說下需要用到的jar包,下載連結

https://download.csdn.net/download/wlj_wangjun/10579753

     1. 先寫Servlet

package com.tianjian.report.applet;


import java.io.ObjectOutputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.servlet.ServletContext;
import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import com.tianjian.report.util.DBUtil;

import net.sf.jasperreports.engine.JRException;
import net.sf.jasperreports.engine.JasperFillManager;
import net.sf.jasperreports.engine.JasperPrint;

public class printServlet extends HttpServlet {
    private static final long serialVersionUID = 1L;  
    @Override
    protected void doGet(HttpServletRequest request, HttpServletResponse response){
        ServletContext context = request.getSession().getServletContext();
        String filepath=context.getRealPath("ireport/entryExamination/Onboarding.jasper");
        
            try {
                    //這裡因為需要實現批量列印,所以使用list ,將所有需要 JasperPrint 裝在list中
                    List<JasperPrint> list = new ArrayList();
            
                    Map<String,Object> map = new HashMap();
                    map.put("peId", "100");
                    map.put("peVisitId", "6");
                    
                    JasperPrint jasperPrint = JasperFillManager.fillReport(filepath,map, DBUtil.getConnection());
                    list.add(jasperPrint);
            
                response.setContentType("application/octet-stream");   
                ServletOutputStream ouputStream = response.getOutputStream();   
                ObjectOutputStream oos = new ObjectOutputStream(ouputStream);   
                oos.writeObject(list);//將所有JasperPrint物件寫入物件輸出流中   
                oos.flush();   
                oos.close(); 
                    
            } catch (JRException e) {
                    e.printStackTrace();
                } catch (Exception e) {
                    e.printStackTrace();
                } 
    }  
    
    @Override
    protected void doPost(HttpServletRequest request, HttpServletResponse response){ 
    }          
}

2.在web.xml中配置servlet

<servlet>  
      <servlet-name>printServlet</servlet-name>  
      <servlet-class>com.tianjian.report.applet.printServlet</servlet-class>  
  </servlet>  
  <servlet-mapping>  
      <servlet-name>printServlet</servlet-name>  
      <url-pattern>/printServlet</url-pattern>  
  </servlet-mapping>

在瀏覽器中輸入 http://localhost:8080/report/printServlet 測試servlet是否編寫成功,若成功,瀏覽器會彈出 下載提示

     

3.新建一個applet類

package com.tianjian.report.applet;

import java.applet.Applet;
import java.io.PrintWriter;
import java.io.StringWriter;
import java.net.URL;
import java.util.List;

import javax.swing.JOptionPane;

import net.sf.jasperreports.engine.JasperPrint;
import net.sf.jasperreports.engine.JasperPrintManager;
import net.sf.jasperreports.engine.util.JRLoader;

public class printApplet extends Applet {

    private static final long serialVersionUID = 1L;  
    private URL url=null;  
  
    public printApplet() {  
        
    }  
  
    @SuppressWarnings("unused")
    public void init() {  
        String strUrl = "http://localhost:8080/report/printServlet"; 
          //String strUrl =getParameter("REPORT_URL");
        if (strUrl != null) {  
            try {  
                url = new URL("http://localhost:8080/report/printServlet");
                //url = new URL(getCodeBase(),strUrl); 
              } catch (Exception e) {  
                    StringWriter swriter = new StringWriter();    
                    PrintWriter pwriter = new PrintWriter(swriter);    
                    e.printStackTrace(pwriter);  
                    JOptionPane.showMessageDialog(this, swriter.toString());    
            }
            
        } else {  
            JOptionPane.showMessageDialog(this, "Source URL not specified");  
        }  
    }  
  
    public void start() {  
        System.out.println("..........................start()");
        if (url != null) {  
            try {  
                //JasperPrint obj = (JasperPrint)JRLoader.loadObject(url);
                List<JasperPrint> list = (List<JasperPrint>) JRLoader.loadObject(url);
                System.out.println(list.size());
                for(int i=0;i<list.size();i++){
                    
                    JasperPrintManager.printReport(list.get(i), true); //true:彈出印表機視窗,false不彈出印表機視窗
                }
                //JasperPrintManager.printReport(obj, true);
            } catch (Exception e) {  
                e.printStackTrace();   
            }  
        } else {  
            JOptionPane.showMessageDialog(this, "start():Source URL not specified");  
        }  
    }  
}
可以右鍵 Run as -> java Applet  成功則會彈出下面的彈窗。

 

 

 

接下來修改 printApplet

4.取出printApplet的class檔案,包也帶上。我的是 com.tianjian.report.applet 。

在本地新建一個檔案print。

把 com/tianjian/report/applet/printApplet.class 資料夾和檔案一起放進來。

然後把 jasperreports-applet-5.6.0.jar 解壓後的檔案全部放入print資料夾內。

使用命令的方式將這個 print資料夾重新打成jar包。

在print資料夾內的位址列輸入 cmd,

輸入 jar cvf print.jar *   資料夾內就會有一個print.jar。

現在給print.jar包簽名 以下操作都是在命令視窗執行。

(一).keytool生成證書:keytool -genkey -alias printkey -keystore printstore -validity 3650     (注意:-validity 3650 標識證書的有效期是10年,如果不寫,預設是3個月。)

(二).keytool匯出證書:keytool -export -keystore printstore -alias printkey  -file print.cer      (需要輸入一些資訊,我隨便填寫的,會在print資料夾內生成一個print.cer的檔案,這個檔名字可以隨意取。)

(三).用jarsigner給jar包簽名 :   jarsigner -keystore printstore print.jar printkey 

(jasperreports-5.6.0.jar也要簽名,現在把這個包放到print檔案內,在執行一遍 jarsigner -keystore printstore jasperreports-5.6.0.jar printkey) 不是 這個 jasperreports-applet-5.6.0.jar,看仔細了。

5.  在webapp目錄下新建一個資料夾 叫applet,(我的專案是maven專案,所以有webapp資料夾,普通專案就是webRoot檔案夾了)

把所需的jar包 和 剛才簽名的jar包,還有print.cer檔案放進來。jasperreports-applet-5.6.0.jar這個包可以不要了,因為print.jar已經包含這個包了。

 

6.安裝jre_1.8_0_181版本,因為這個版本不會在瀏覽器上頻繁的彈出安全提示。下載地址:java.com

安裝完成之後,

在控制面板中 點選java  會彈出一個java控制面板,選擇 java- 點選檢視 裡面有個列表,把剛才安裝的jre新增進去,勾選,確定。

在 java控制面板中 點選 安全 - 裡面有一個"例外站點列表",為了簡單,將我們的專案訪問路徑 新增進去例如:localhost:8080/   ; 就把 以localhost:8080/..... 開頭的所有url都設定成例外站點。 點選應用--確定。

設定ie瀏覽器,我的是iE11,開啟internet選項,

選擇安全,選擇-受信任的站點,-點選 站點-將 http://localhost:8080/地址新增進去,把下面的對該區域中的所有站點要求伺服器驗證(https:)選項去掉。關閉

7.以上都準備好 以後,在jsp中寫個方法

function print(){

var print = document.getElementById("print");
var url="printServlet";

var appletStr='<APPLET ID="JrPrt" CODE="com.tianjian.report.applet.printApplet.class" CODEBASE = "./" ARCHIVE = "applet/xerces-2.9.0.jar, applet/batik-all-1.5.1.jar,applet/batik-dom-1.6-1.jar,applet/batik-svg-dom-1.6-1.jar,applet/commons-digester-2.1.jar,applet/batik-1.1.1.jar,applet/batik-bridge-1.6-1.jar,applet/jasperreports-5.6.0.jar,applet/print.jar,applet/commons-logging-1.1.1.jar,applet/commons-collections-3.2.1.jar" WIDTH = "0" HEIGHT = "0"><PARAM NAME = "type" VALUE="application/x-java-applet;version=1.2.2"><PARAM NAME = "scriptable" VALUE="false"><PARAM NAME = "REPORT_URL" VALUE ="'+url+'"></APPLET>';
 

print.innerHTML = appletStr;

}

寫個onclick事件,呼叫print方法。成功後會彈出印表機選項視窗。至此 一個applet列印已經做好了。有不足的地方歡迎大家指正。