How to add dynamic to the report catalog

Description of Requirement:

In doing some similar word report format of the report, in order to have better reading results, often you need to add a directory navigation page on the home page so that data can be quickly aware of concerns in the first few pages, but the report is different from the word document, word the document format is fixed, it is possible to easily and quickly build directory pages in the report data is dynamic, and often involves dynamic expansion, and difficult to fix directory entries, and since the dynamic expansion of data, the corresponding it is difficult to get accurate page, look below through an example, if the dynamic increase in reports directory.

solution:

Report data is dynamic, so do not use a fixed catalog design, to know that the data in the first few pages, Run Dry statements provides a report to calculate the required report calculates the listener class, you can obtain reports dynamically in java program after the calculation result, the cell value and can be changed dynamically in the program.

First, look at the report template design interface:

This report should be of the order data meta-analysis by region, and present detailed data required for the navigation area directory to be set, five lines before the report is a directory page, third line, profiling generally fixed, write here fixed line, page 2 is provided on the line.

A4: = ds1.group (owner region; owner Region: 1), expressions grouped by region, i.e. this show as the directory area corresponding to cell E4 arranged subsequent to the directory page, here temporarily empty.

A5: directory is usually the first page, so here is set after a line pagination

A7: a fixed summary is described, may be inside the fixed text string and splicing the dynamic data display spliced ​​together.

A8: = ds1.group (owner region; owner Region: 1), grouped by region

A9: make the region a summary description data

A10: = ds1.select (order ID), taking the number of orders, B10 and so on back.

To the A9, left nominative A10, A11, A12 cells arranged A8, A8 according to this tile data longitudinal extension, so that the result is a report showing:

Here you can see, the directory entry list at the corresponding areas, then look down, if the increase in the corresponding page number to the region.

从报表结果中看到,第一页中的目录名称和报表中的地区名称相同,这样就可以根据这两个名称做匹配,判断如果名称相同获取数据区域的名称所在的页码,放到对应目录行就行,如数据区域的“东北”在第 2 页,那么目录中东北的页码应该为 2,接下来看下,如何给目录设置动态的页码。

这里就用到了之前说到的报表侦听类的使用,源码如下:

import com.raqsoft.common.Area;
import com.raqsoft.report.usermodel.Context;
import com.raqsoft.report.usermodel.IPagerListener;
import com.raqsoft.report.usermodel.IReport;
import com.raqsoft.report.usermodel.IReportListener;
import com.raqsoft.report.usermodel.PageBuilder;
import com.raqsoft.report.util.ReportUtils;

public class createmulu implements IReportListener {
	 public void afterCalc(Context arg0, IReport arg2) { 
		 PageBuilder arg1 = null;
		try {
			arg1 = new PageBuilder(arg2);
		} catch (Throwable e1) {
			// TODO Auto-generated catch block
			e1.printStackTrace();
		}
			System.out.println("报表总页数"+arg1.getPageCount());
			IReport p1;
			try {
				 p1=arg1.getPage(1);//目录通常在第一页,所以获取第一页为目录页
				 int page=2;//设置数据初始循环页,通常为第二页
				 for(int i=3;i<=p1.getRowCount();i++){//目录行从第三行开始
					String muluName=(String)p1.getCell(i, 2).getValue() ;//报表中设置第二页为目录名称
					for(int j=page;j<=arg1.getPageCount();j++){//按照页数进行循环,分别取分页后每页报表对象
						for(int k=1;k<=arg1.getPage(j).getRowCount();k++){//每页中按照每行进行循环		
						String mName=arg1.getPage(j).getCell(k,1).getValue() != null ? arg1.getPage(j).getCell(k,1).getValue().toString() : "";//本例中目录项在报表中的第一列,也就是A8单元格
						if(mName!="" && mName==muluName){//判断每页中的目录项和第一页中的目录名称是否相同
							arg2.getCell(i, 5).setValue(j);//如果相同,则设置目录页第5列对应的值为对应页码,注意,此处是arg2对象
							arg2.getCell(i, 5).setHyperlink("javaScript:toPage('report1',"+j+")");//设置超链接
							page=j;//为提高计算效率,下次在循环时,不用从第2页开始,从上次终端的页码开始就行
							break;//找到页码,跳出此处循环,提高效率
						}	
						}
					} 
				 }
			} catch (Exception e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			} 
	   } 
	   public void beforeCalc(Context arg0, IReport arg1) { 
	   } 
	
}

 核心思路就是在类中根据名称进行匹配,获取页码,放到对应单元格中,将编译好的类放到报表类路径中,如:应用的 WEB-INF\classes 下,注意如果有包路径,此处要要带相应的路径,放置过去后重启应用,在页面端访问报表,结果如下:

可以看到,目录后边会生成对应的页码,word 中目录有个功能点是,点击页码,能够快速跳转到对应的页数,报表中同样可以增加对应的功能,报表提供了一个跳转页数的 js 函数,toPage,在 java 类中,在对应的页码单元格设置了一个超链接,调用这个 js 就行:

 
arg2.getCell(i, 5).setHyperlink("javaScript:toPage('report1',"+j+")"); 

这样,在页面端点击页码,就能够快速跳转到对应页数,当然,此功能要求报表在页面端分页后才有效,否则无法跳转,并且如果导出到 word 的话,只能显示页数,无法跳转。

通过这个例子可以看到,通过拿目录项中的单元格数据和数据表中的单元格进行匹配,来获取页码,但是在实际使用中,目录页中的目录名称和报表中的数据名称可能并不完全一致,比如目录页中叫东北,报表数据中叫东北地区,很难严格匹配,这样可以换种变通的方法,报表单元格属性栏中有个注释属性,可以在这个里边写上和目录项匹配的值,然后 java 类中可以根据这个属性的值做匹配,这样能够实现更加灵活的效果,更多 api 接口可以参考报表帮助文档《程序员参考》,后续带来更多 api 在报表实际需求中的应用。

Guess you like

Origin www.cnblogs.com/shiGuangShiYi/p/12112617.html