接著上篇,jasperReport 實(shí)現(xiàn)客戶端主要是依靠applet,但是我們所有的操作不可能在applet中實(shí)現(xiàn)吧,這樣也不算一個(gè)好的應(yīng)用。
考慮一下幾點(diǎn):
1. javascript 和applet互相通信。applet和前臺(tái)界面交互,可以讓客戶感覺不到有applet的存在。
2. applet和后臺(tái)相互通信。applet既可以接受后臺(tái)轉(zhuǎn)遞的參數(shù)、對(duì)象流等等 還可以把信息返回到后臺(tái)。
3. applet只實(shí)現(xiàn)打印和預(yù)覽,主要的業(yè)務(wù)操作需要在后臺(tái)完成。
上篇中提到print.js:
新建一jsp頁面 PrintReportApplet.jsp
次jsp頁面就一個(gè)按鈕
<input type="submit" value="預(yù)覽" onclick="reportViewer()" />
這樣我們就可以在當(dāng)前頁面中引用到applet了,
document.applets.myApplet.reportViewer() 拿到applet的窗口句柄后調(diào)用applet的reportViewer()方法
我們也可以在此jsp頁面寫一個(gè)初始化的方法傳遞參數(shù)到applet中,當(dāng)然也可以直接傳遞參數(shù)到reportViewer(parameter String);

function getParameters()
{
return "&pid=0001"
}
在print.js中指定 <PARAM NAME="CODE" VALUE="com.isoftstone.pcis.report.print.applet.PrinterApplet" />
PrinterApplet中reportViewer
// javascript預(yù)覽報(bào)表

public void reportViewer()
{

try
{
win = JSObject.getWindow(this);
paraStr = win.eval("getParameters()").toString();


if ("".equals(paraStr) || paraStr == null)
{
return;
}
System.out.println("paraStr=======>" + paraStr);


} catch (Exception e1)
{
e1.printStackTrace();
}

if (url == null)
{

if (requestUrl != null)
{

try
{

/**//*
* applet與Servlet交互 URL傳遞頁面?zhèn)鱽淼膮?shù)請(qǐng)求服務(wù)器Servlet
* 把a(bǔ)pplet傳遞的參數(shù)追加到servlet中 2008-10-14 laoshulin
*/

url = new URL(getCodeBase(), requestUrl + "?printView=true"
+ paraStr);


if (url == null)
{
JOptionPane.showMessageDialog(this,
"Source URL not specified");

} else
{
InputStream in = url.openStream();
ObjectInputStream objIn = new ObjectInputStream(in);
Object obj = objIn.readObject();

if (obj instanceof JasperPrint)
{


} else
{
JOptionPane.showMessageDialog(this, obj.toString());
return;
}


if (jasperPrint == null)
{
// 根據(jù)Servlet返回的URL(ObjectStream)產(chǎn)生JasperPrint對(duì)象
jasperPrint = (JasperPrint) obj;

}
// 攔截出現(xiàn)空?qǐng)?bào)表問題
if (jasperPrint != null

&& jasperPrint.getPages().size() > 0)
{

/**//*
* 調(diào)用JasperReport.jar中JasperViewer繪制報(bào)表Frame
* JasperViewer繼承自JFrame,采用setDefaultCloseOperation響應(yīng)關(guān)閉窗口事件
*/

ViewerFrame viewerFrame = new ViewerFrame(this
.getAppletContext(), jasperPrint);
viewerFrame.setVisible(true);
//viewerFrame.show();

// JasperViewer viewer = new
// JasperViewer(jasperPrint);
// viewer.setVisible(true);
// viewer.setDefaultCloseOperation(javax.swing.WindowConstants.DISPOSE_ON_CLOSE);
// 如果請(qǐng)求為空彈出對(duì)話框予以提示

} else
{
JOptionPane
.showMessageDialog(this,
"Please check Your Report SQL! It resulted in empty Report! ");
return;
}
}

} catch (Exception e)
{
StringWriter swriter = new StringWriter();
PrintWriter pwriter = new PrintWriter(swriter);
e.printStackTrace(pwriter);
JOptionPane.showMessageDialog(this, swriter.toString());

} finally
{// 全打套打URL不一樣釋放對(duì)象 by laoshulin
url = null;
jasperPrint = null;
win = null;
}
}
}
}
JSObject 對(duì)象的使用google一下有很多哦,requestUrl = getParameter("REPORT_URL");為print.js中配置的請(qǐng)求,之后我們new URL帶上我們的參數(shù)去請(qǐng)求遠(yuǎn)程資源。
<servlet-mapping>
<servlet-name>ReportServlet</servlet-name>
<url-pattern>/report.view</url-pattern>
</servlet-mapping>
public void doGet(HttpServletRequest request, HttpServletResponse response)

throws ServletException, IOException
{

try
{


/**//*
* Servlet中可這樣取得打印或是預(yù)覽操作,添加此功能針對(duì)套打預(yù)覽 String
* view=request.getParameter("printView"); boolean
* isView="true".equalsIgnoreCase(view)?true:false; String
* print=request.getParameter("print"); boolean
* isPrint="true".equalsIgnoreCase(print)?true:false;
*/

// 拿參數(shù)
String pid = request.getParameter("pid");
String form = request.getParameter("format");
// 編譯報(bào)表耗時(shí),修改為編譯好的報(bào)表

/**//*
* JasperReport jasperReport = JasperCompileManager
* .compileReport("D:\\workspace\\report\\AppletTest.jasper");
*/
// 直接使用編譯好的文件
// JasperReport jasperReport = (JasperReport) JRLoader
// .loadObject("D:\\workspace\\report\\AppletTest.jasper");
JasperReport jasperReport = (JasperReport) JRLoader
.loadObjectFromLocation("D:\\workspace\\report\\AppletTest.jasper");
HashMap mapParam = new HashMap();
mapParam.put("imageParam", "D:\\workspace\\report\\eg_smile.gif");

/**//*
* 此參數(shù)用來控制是否顯示圖片
* 第二個(gè)參數(shù)在報(bào)表中設(shè)置為String類型
*/
mapParam.put("isShowImage", "true");
// 生成jasperPrint對(duì)象
JasperPrint jasperPrint = JasperFillManager.fillReport(jasperReport,
mapParam, new JREmptyDataSource());
System.out.println(jasperPrint.getPageHeight()+"$$$$$$$$$$$$"+jasperPrint.getPageWidth()+"**********"+jasperPrint.getPages());
response.setContentType("application/octet-stream");
response.setBufferSize(8986000);
ServletOutputStream outStream = response.getOutputStream();
ObjectOutputStream oos = new ObjectOutputStream(outStream);
oos.writeObject(jasperPrint);
// outStream.flush();
// oos.flush();
// outStream.close();
// oos.close();
//outStream.flush();
//

} catch (Exception e)
{
e.printStackTrace();
}
}
請(qǐng)求到遠(yuǎn)程資源完全可以安裝業(yè)務(wù)需求實(shí)現(xiàn)自己的jasperReport 了,最終我們只要把一個(gè)JasperPrint對(duì)象輸出到客戶端就可以了。
客戶端通過打開InputStream in = url.openStream();實(shí)現(xiàn)還原jasperPrint對(duì)象,從而實(shí)現(xiàn)打印或者預(yù)覽。
客戶端打印可以前的方法是一樣的:
編譯、填充、生成JasperPrint對(duì)象、預(yù)覽或打印
上篇有人提到打印和預(yù)覽實(shí)現(xiàn)動(dòng)態(tài)控制套打背景,建議你多看看
iReport+jasperReport之圖片控件 ,實(shí)現(xiàn)原理是一樣的,只是把JasperPrint在客戶端處理了一下哦。