⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 teedbcrosstab.pas

📁 第三方控件:PaintGrid.pas 网格型仪表控件源文件 Mymeter.pas 圆型仪表控件源文件 Project1是这两个控件的使用范例。 该
💻 PAS
📖 第 1 页 / 共 2 页
字号:
{**********************************************}
{   TeeChart Database Cross-Tab Source         }
{   Copyright (c) 1996-2005 by David Berneda   }
{**********************************************}
unit TeeDBCrossTab;
{$I TeeDefs.inc}

interface

{ The procedure below creates an array of Chart Series
  and fills them using the DataSet parameter.

  The Series are created using the "AGroupField" parameter.

  The "ASeries" parameter will be used to duplicate it many times,
  one for each "group", thus using it as a template.

  Example of use:
  ---------------

  Imagine you have a table with "Product sales".

  In this table you have the following fields:

  Product    ( Cars, Bikes, Trucks... )
  Country    ( USA, UK, Germany, Australia... )
  Amount     ( $1234... )

  Now we want to create a crosstab Chart consisting of one Bar
  Series for each "Product", each one showing the sum of
  "Amount" for each "Country".

  So,
  our "GroupField" is "Product",
  our "LabelField" is "Country" and
  our "ValueField" is "Amount".

  Choose between 1 or 2:

  1) Calling a direct global procedure:

  FillDataSet( Table1, BarSeries1, "Product", "Country", "Amount", gfSum );

  After calling this procedure, the Chart will show several Series,
  one for each "Product".
  Each series will show the "Sum of Amount" by "Country".

  You can access and modify these Series as usually, like for example
  changing the Series Color, Title, etc.

  2) Use a TDBCrossTabSource component, set properties and Active:=True;

}
uses
  {$IFNDEF LINUX}
  Windows, Messages,
  {$ENDIF}
  SysUtils, Classes,
  {$IFDEF CLX}
  QGraphics, QControls, QForms, QDialogs, QStdCtrls, QExtCtrls,
  {$ELSE}
  Graphics, Controls, Forms, Dialogs, StdCtrls, ExtCtrls,
  {$ENDIF}
  DB, Chart, DBChart, TeEngine, TeeProcs, TeeSourceEdit, TeeDBEdit, TeCanvas;

type
  TGroupFormula = (gfCount, gfSum); { count records or sum record values }

  TDBCrossTabSource=class(TTeeSeriesDBSource)
  private
    FCase       : Boolean;
    FDataSet    : TDataSet;
    FFormula    : TGroupFormula;
    FGroup      : String;
    FHideSeries : Boolean;
    FLabel      : String;
    FValue      : String;

    ISource : TDBChartDataSource;
    procedure DataSourceCheckDataSet(ADataSet: TDataSet);
    procedure DataSourceCloseDataSet(ADataSet: TDataSet);
    Procedure LoadDataSet;
    procedure RemoveSeries;
    procedure SetDataSet(const Value: TDataSet);
    procedure SetFormula(const Value: TGroupFormula);
    procedure SetGroup(const Value: String);
    procedure SetLabel(const Value: String);
    procedure SetValue(const Value: String);
    procedure SetCase(const Value: Boolean);
  protected
    KeepDataOnClose : Boolean;

    Procedure Notification(AComponent: TComponent; Operation: TOperation); override; // 7.01
    procedure SetActive(const Value:Boolean); override;
  public
    Constructor Create(AOwner:TComponent); override;
    Destructor Destroy; override;

    class Function Available(AChart: TCustomAxisPanel):Boolean; override;
    class Function Description:String; override;
    class Function Editor:TComponentClass; override;
    class Function HasSeries(ASeries:TChartSeries):Boolean; override;
    Procedure Load; override;
  published
    property Active;
    property CaseSensitive:Boolean read FCase write SetCase default True;
    property DataSet:TDataSet read FDataSet write SetDataSet;
    property Formula:TGroupFormula read FFormula write SetFormula default gfSum;
    property GroupField:String read FGroup write SetGroup;
    property HideSeries:Boolean read FHideSeries write FHideSeries default True; // 7.06
    property LabelField:String read FLabel write SetLabel;
    property Series;
    property ValueField:String read FValue write SetValue;
  end;

  TDBChartCrossTabEditor = class(TBaseDBChartEditor)
    Label1: TLabel;
    Label2: TLabel;
    Label3: TLabel;
    CBAgg: TComboFlat;
    CBValue: TComboFlat;
    CBGroup: TComboFlat;
    Label4: TLabel;
    CBLabels: TComboFlat;
    CBActive: TCheckBox;
    CBCase: TCheckBox;
    CBHide: TCheckBox;
    procedure CBSourcesChange(Sender: TObject);
    procedure FormShow(Sender: TObject);
    procedure BApplyClick(Sender: TObject);
    procedure CBAggChange(Sender: TObject);
    procedure FormDestroy(Sender: TObject);
    procedure CBActiveClick(Sender: TObject);
    procedure CBCaseClick(Sender: TObject);
    procedure CBHideClick(Sender: TObject);
  private
    { Private declarations }
    DataSource : TDBCrossTabSource;
    Procedure EnableCombos;
  public
    { Public declarations }
  end;

Procedure FillDataSet( ADataSet:TDataSet;
                       ASeries:TChartSeries;
                       Const AGroupField,ALabelField,AValueField:String;
                       GroupFormula:TGroupFormula);

implementation

{$IFNDEF CLX}
{$IFNDEF LCL}
{$R *.DFM}
{$ENDIF}
{$ELSE}
{$R *.xfm}
{$ENDIF}

{$IFDEF CLR}
uses Variants;
{$ENDIF}

Const TeeMsg_CrossTab ='CrossTab';

type TSeriesAccess=class(TChartSeries);

{ Create a cross-tab of Series using DataSet records. }
Procedure FillDataSet( ADataSet:TDataSet;
                       ASeries:TChartSeries;
                       Const AGroupField,ALabelField,AValueField:String;
                       GroupFormula:TGroupFormula);
begin
  with TDBCrossTabSource.Create(nil) do
  try
    Series:=ASeries;
    DataSet:=ADataSet;
    GroupField:=AGroupField;
    LabelField:=ALabelField;
    ValueField:=AValueField;
    Formula:=GroupFormula;
    KeepDataOnClose:=True;
    Open;
  finally
    Free;
  end;
end;

type TChartAccess=class(TCustomAxisPanel);

Procedure TDBCrossTabSource.LoadDataSet;

   Function LocateSeries(Const ATitle:String):TChartSeries;
   var t : Integer;
       tmp : String;
   begin
     With Series.ParentChart do
     if FCase then
     begin
       for t:=0 to SeriesCount-1 do
           if Series[t].Title=ATitle then
           begin
             result:=Series[t];
             exit;
           end;
     end
     else
     begin
       tmp:=UpperCase(ATitle);
       for t:=0 to SeriesCount-1 do
           if UpperCase(Series[t].Title)=tmp then
           begin
             result:=Series[t];
             exit;
           end;
     end;

     result:=nil;
   end;

var tmpGroup   : String;
    tmpSeries  : TChartSeries;
    tmpLabel   : String;
    tmpValue   : Double;
    t,tt       : Integer;
    tmpPoint   : Integer;
    tmpBookMark : TBookMark;
    tmpGroupField,
    tmpValueField,
    tmpLabelField : TField;
begin
  RemoveSeries;

  With DataSet do
  begin
    tmpBookMark:=GetBookMark;

    DisableControls;
    try
      if LabelField='' then tmpLabelField:=nil
                       else tmpLabelField:=FieldByName(LabelField);

      if GroupField='' then
      begin
        tmpSeries:=Series;
        Series.Title:=ValueField;
        tmpGroupField:=nil;
      end
      else
      begin
        tmpSeries:=nil;
        tmpGroupField:=FieldByName(GroupField);
      end;

      tmpValueField:=FieldByName(ValueField);

      tmpValue:=1;

      First;

      While not eof do
      begin
        if GroupField<>'' then
        begin
          tmpGroup:=tmpGroupField.AsString;
          tmpSeries:=LocateSeries(tmpGroup);

          if tmpSeries=nil then
          begin
            if Series.Title='' then
               tmpSeries:=Series
            else
            begin
              with Series do
              begin
                tmpSeries:=CreateNewSeries(Owner,ParentChart,
                                          TChartSeriesClass(ClassType));

                tmpSeries.Clear;
                TSeriesAccess(tmpSeries).ManualData:=True;
                tmpSeries.AssignFormat(Series);
                tmpSeries.ShowInLegend:=ShowInLegend;
                tmpSeries.Active:=Active;
                tmpSeries.Brush:=Brush;
                tmpSeries.Pen:=Pen;
                TSeriesAccess(tmpSeries).DontSerialize:=True;
                tmpSeries.ShowInEditor:=not HideSeries;
              end;

              tmpSeries.SeriesColor:=Series.ParentChart.GetFreeSeriesColor;
              tmpSeries.Tag:={$IFDEF CLR}Variant{$ELSE}Integer{$ENDIF}(Series);

              for t:=0 to Series.Count-1 do
                  tmpSeries.Add(0,Series.Labels[t]);
            end;

            tmpSeries.Title:=tmpGroup;
          end;
        end;

        if Formula<>gfCount then tmpValue:=tmpValueField.AsFloat;

        if not Assigned(tmpLabelField) then
        begin
          tmpLabel:='';
          if tmpSeries.Count>0 then tmpPoint:=0
                               else tmpPoint:=-1;
        end
        else
        begin
          tmpLabel:=tmpLabelField.AsString;
          tmpPoint:=tmpSeries.Labels.IndexOfLabel(tmpLabel,FCase);
        end;

        if tmpPoint=-1 then

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -