函数。
function RealGetName(Old:String):String;这个函数名是无所谓的,也可以是GetName。
在OnUserFunction的事件处理中有如下代码即可完成自定义函数在报表中的使用。
if CompareText(MethodName,'GetName')=0 then Result:=RealGetName(VarToStr(Params[0]));
我一般都是使用CompareText来比较函数名,因为我发现二个版本的Fastreport,一个是MethodName全部自动变成了小写,一个是全部自动变成
了大写,所以干脆用CompareText来比较,肯定不会出错。
如果有多个参数,则依次传递Params[0],Params[1]即可,要保持顺序一致。
这里要注意一点,如果参数为指针,则不能直接使用Pointer(Integer(Params[0]))。因为实际传递过来的是指针的整数值,可以使用Pointer
(StrToInt(VarToStr(Params[0])))。
******使用脚本,脚本中使用变量
很多时候,我们希望把对报表的控制放到报表的脚本中,通常我这样做有二个原因:
1)能够根据字段内容的变化而使用不同的设置,因为如果想在程序中实现这样功能,就不得不用自定义函数,函数的实现要放到程序中,函数
可能需要传递很多参数,效率低下。
2)把不同报表的控制放到脚本中,可以实现报表的模块化,
程序只是简单的设置数据集的关系,并加载硬盘上的报表文件,不同报表的不同实
现方式,显示方式,均放到报表文件中,程序简洁,易维护,易升级。
当然,这样的缺点就是程序中加载报表时的数据集别名必须与设计报表时的别名一致。
脚本的使用与通常程序的使用并没有太多的区别,就是像正常的程序那样引用控件的名称即可。
但注意对变量的使用,需要把变量名或表达式用<>括起来。
******在脚本中根据字段名改变Tfrxmemoview的内容
假设有数据表“用户”,字段ID为用户标识,Name为用户名,打印时要求,如果用户名为空,则打印
“无用户名”,否则打印出“用户名:实
际的用户”,则可以在ID的Tfrxmemoview控件的OnAfterData事件中写如下脚本。
if
='' then
Memo2.Text:='无用户名'
else
Memo2.Text:='用户名:[frxDBDataSet1."Name"]'
Memo2是放置用户名称数据的Tfrxmemoview控件。
这里注意,要在脚本中访问变量需要把变量用<>包括起来。
******实现连续打印
很多人认为Fr不能实现连续打印,以为只能通过自己写函数调用打印函数来实现连续打印,实际上,Fr可以轻易的实现连续打印,同时,实现
时又是非常简单,你甚至可以在你的程序的打印设置中简单的让客户选择是否连续打印,其它都可以保持不变。
function PelsTomm(Pels:Extended):Extended;
begin
Result:=Pels/Screen.PixelsPerInch*25.4;
end;
procedure PrintSerial(Frx:TFrxReport;SequencePage:Byte=0);
var
P:TfrxReportPage;
R,R1:Extended;
begin
{必须是二遍报表,否则无法计算总页数。
下面的方法只适用于没有页脚的情况,因为如果有页脚的话
FreeSpace就始终为0了。可以用报表脚来代替。
因为是连续打印,也可以看作只有一页,报表脚也就相当于页脚了}
if not Frx.Engine.DoublePass then Exit;
//SequencePage指要连续打印的页面,普通报表就是0
P:=TfrxReportPage(Frx.Pages[SequencePage]);
R1:=P.TopMargin+P.BottomMargin;
while Frx.PrepareReport do
begin
if (Frx.Engine.TotalPages<=1) then Break;
R:=Pelstomm(Frx.Engine.TotalPages*Frx.Engine.PageHeight-
Frx.Engine.FreeSpace)+R1;
P:=TfrxReportPage(Frx.Pages[SequencePage]);
P.PaperHeight:=R;
end;
{必须用上面的循环代码来得到准确的空白区域
不能用通过计算总页数减去各页的页边距的方法来获得空白区域
因为如果碰到一条记录过宽的情况导致换页,就不准确了。}
R:=Pelstomm(Frx.Engine.TotalPages*Frx.Engine.PageHei