第1章 概述
本文介绍一种实用方法,可以实现每页一个小计的功能,以便可以对一个周期内的数据进行统计。例如一页对应一个月的销售数据,使用页小计可以统计出一个月的销售额总和。又或者一页对应某一天内每小时的气温状况,使用页小计可以计算出一天的平均气温。
第2章 实现方式
实现页小计功能的关键是使用GroupByRow公式(详细说明参见《UniEAP Report公式查询手册》)。大致思路是:用GroupByRow公式按每页显示的行数进行分组,让“合计”单元格依赖于前者,计算出的即是一页的合计。下面用一个例子具体说明。
2.1 每页显示固定行数
如果每页显示的行数不需要变化,例如总是一页20行,报表可以按如下的方式定义。
具体说明如下:
1.因为“合计”也要占用一行,所以当“显示行数”为20时,实际显示的数据行数为19,因此GroupByRow公式的第四个参数是19而不是20。
2.例子中由于订单号是有重复的,直接在GroupByRow中使用订单号进行分组,组内的行数会超过19(一组有19个不同的ORDERID)。这里用到了Oracle数据库提供的Rownum进行分组。
3.A3格使用GroupByRow公式,纵向扩展,数据行、合计行的单元格都要依赖于A3。(本例中因为有B列,所以实际上是B3依赖于A3,C3~H3依赖于B3,C4~H4依赖于A3。)
4.A、B两列不需要显示在页面上,故将它们设为隐藏。
5.报表如果有标题或表头,不能选择成“数据区”类型,否则也会计入行数,导致第一页显示的实际数据行数不够,“合计”会被显示到下一页。另外要在“导出设置”中将“标题计入行数”设为否。
2.2 每页显示行数不固定的情况
如果想要在展现时切换每页显示的行数,同时仍然显示每一页的合计,这时GroupByRow公式第四个参数的值要根据每页行数发生变化。这里提供一种方法,借助系统变量来实现。
【注意】切换每页行数时,默认会从缓存中取报表实例,此时不会重新计算系统变量的值。如果可以直接通过url的方式访问报表,只需在url上添加表示每页行数的linage参数和表示重新生成实例的newReport=true。如果是在已有页面中点击的方式访问报表,有两个方法可以解决这个问题:一是后台服务禁用实例缓存,但这样所有的报表都不会从缓存中取;二是在doResult.js中,发送切换每页行数的请求时,通过报表id判断是否为此报表,如果是则添加newReport=true参数。
首先,自定义一个系统变量rowNumPerPage,用于获取当前每页的显示行数。系统变量的实现方法参见《UniEAP Report二次开发手册》。
报表展现页面的右上方有用于切换每页行数的下拉列表,用它切换每页行数时,会重新发送请求到后台,请求参数中有显示行数的值。在系统变量中获取此值并返回即可:
因为第一次打开报表时不会传linage参数,所以返回Null值。
其次,在报表定义中,将GroupByRow公式改为如下形式:=GroupByRow('ds1','ROWNUM',null,Case(Nvl($rowNumPerPage),19,$RowNumPerPage-1))。即当系统变量为Null时,使用报表定义中的显示行数;否则使用系统变量的值。因为合计要占一行,所以这两个值都需要减1。