BCB调用FastReport4合并单元格

来源:互联网 发布:魔伴windows桌面下载 编辑:程序博客网 时间:2024/05/21 11:23

注意:需要在控制报表的BCB程序头文件.h中加上类TfrxDBDataSet的头文件 #include "frxCustomDBRTTI.hpp" ,在.cpp文件的头部加上#pragma link "frxCustomDBRTTI"。如果不加则会报没有定义类型TfrxDBDataSet的错误。

合并单元格实现原理:

在报表开始前先计算出需要合并的行的高度数组,在打印前根据这个高度数组设置对应打印对象的高度和显示。

实现方法如下:

设置Page1的OnBeforePrint事件,MasterData1的OnBeforePrint事件,代码如下:

Var  iRowCount:Integer; AryStatHeight:Array of Extended; AryRoadHeight:Array of Extended; AryStation:Array of String; AryLine:Array of String;         procedure Page1OnBeforePrint(Sender: TfrxComponent);var  i,j,iRepeat: Integer; sLastValue,sCurValue: String; MyDataSet:TfrxDBDataSet;          begin    MyDataSet := TfrxDBDataSet(Report.GetDataSet('frxdbdtst1'));    iRowCount := MyDataSet.RecordCount;        //逐记录取值,同一个入口站的则记录要合并的单元格      SetLength(AryStatHeight,iRowCount);    SetLength(AryStation,iRowCount);            MyDataSet.First;      sCurValue := '';    j := 1;            for i := 0 to iRowCount - 1 do    begin       sLastValue := sCurValue;       sCurValue := MyDataSet.DataSet.FieldByName('EnRoadID').AsString + MyDataSet.DataSet.FieldByName('EnStationID').AsString;       //若有重复单元格,则标记当前重复单元格的高度为0,第一个重复单元格的高度为重复单元格高度的和       if (sLastValue <> '') and (sLastValue = sCurValue)           and ((i + 36 - 31) mod 36<>0) then         //           begin          iRepeat := iRepeat + 1;          AryStatHeight[i] := 0;          AryStatHeight[i - iRepeat] := MasterData1.Height * (iRepeat + 1);       end                      else       begin          iRepeat := 0;          AryStatHeight[i] := MasterData1.Height;       end;       //若有重复单元格,则标记该重复单元格的行号为空                               if (sLastValue <> '') and (sLastValue = sCurValue) then         begin          AryStation[i] := '';                  end         else       begin                               AryStation[i] := IntToStr(j);          j := j + 1;                            end;                  MyDataSet.Next;    end;    //逐记录取值,同个入口路段的则记录要合并的单元格    SetLength(AryRoadHeight,iRowCount);              MyDataSet.First;    sCurValue := '';                       for i := 0 to iRowCount - 1 do    begin       sLastValue := sCurValue;       sCurValue := MyDataSet.DataSet.FieldByName('EnRoadID').AsString;       //若有重复单元格,则标记当前重复单元格的高度为0,第一个重复单元格的高度为重复单元格高度的和       if (sLastValue <> '') and (sLastValue = sCurValue) and ((i + 36 - 31) mod 36<>0) then       begin          iRepeat := iRepeat + 1;          AryRoadHeight[i] := 0;          AryRoadHeight[i - iRepeat] := MasterData1.Height * (iRepeat + 1);       end         else       begin          iRepeat := 0;          AryRoadHeight[i] := MasterData1.Height;                             end;                                                                                              MyDataSet.Next;    end;        //重新控制报表显示行号    SetLength(AryLine,iRowCount);            MyDataSet.First;    sCurValue := '';    j := 1;                      for i := 0 to iRowCount - 1 do    begin       sLastValue := sCurValue;       sCurValue := MyDataSet.DataSet.FieldByName('EnRoadID').AsString;       //若有重复单元格,则标记该重复单元格的行号为空,非重复单元格则行号递增       if (sLastValue <> '') and (sLastValue = sCurValue) then       begin          AryLine[i] := '';                  end         else       begin                               AryLine[i] := IntToStr(j);          j := j + 1;                            end;                                                                                              MyDataSet.Next;    end;         end;     procedure MasterData1OnBeforePrint(Sender: TfrxComponent);begin    //同一入口站合并    if AryStatHeight[<Line#> - 1] = 0 then    begin       Memo56.Visible := False;                 Memo57.Visible := False;       Memo59.Visible := False;     end    else    begin       Memo56.Visible := True;       Memo56.Height := AryStatHeight[<Line#> - 1];                 Memo57.Visible := True;       Memo57.Height := AryStatHeight[<Line#> - 1];       Memo59.Visible := True;       Memo59.Height := AryStatHeight[<Line#> - 1];                end;    //同一入口路段合并    if AryRoadHeight[<Line#> - 1] = 0 then    begin                              Memo48.Visible := False;       Memo49.Visible := False;       Memo61.Visible := False;       Memo62.Visible := False;       Memo1.Visible := False;        Memo2.Visible := False;    end    else    begin       Memo48.Visible := True;       Memo48.Height := AryRoadHeight[<Line#> - 1];       Memo49.Visible := True;       Memo49.Height := AryRoadHeight[<Line#> - 1];       Memo61.Visible := True;       Memo61.Height := AryRoadHeight[<Line#> - 1];       Memo62.Visible := True;       Memo62.Height := AryRoadHeight[<Line#> - 1];       Memo1.Visible := True;       Memo1.Height := AryRoadHeight[<Line#> - 1];       Memo2.Visible := True;       Memo2.Height := AryRoadHeight[<Line#> - 1];               end;    if AryStation[<Line#> - 1] = '' then    begin                                Memo56.Font.Color:=clWhite;       Memo57.Font.Color:=clWhite;       Memo59.Font.Color:=clWhite;               end    else                  begin                               Memo56.Font.Color:=clBlack;       Memo57.Font.Color:=clBlack;       Memo59.Font.Color:=clBlack;               end;        if AryLine[<Line#> - 1] = '' then    begin       Memo48.Memo.Clear();       Memo49.Font.Color:=clWhite;       Memo61.Font.Color:=clWhite;       Memo62.Font.Color:=clWhite;       Memo1.Font.Color:=clWhite;       Memo2.Font.Color:=clWhite;                 end    else                  begin       Memo48.Memo.Clear();       Memo48.Memo.Add(AryLine[<Line#> - 1]);                     Memo49.Font.Color:=clBlack;               Memo61.Font.Color:=clBlack;       Memo62.Font.Color:=clBlack;       Memo1.Font.Color:=clBlack;       Memo2.Font.Color:=clBlack;                 end;        end;beginend.

流程:

第一步.准备好要合并单元格的报表;

第二步.双击事件的‘OneBeforePrint’对应CODE代码(确保完成第三步,否则代码无法生效,完成后直接预览),首先是Page1的事件设置,   其次是MasterDate1的事件设置;

第三步.在CODE页写入代码。




0 0
原创粉丝点击