999精品在线视频,手机成人午夜在线视频,久久不卡国产精品无码,中日无码在线观看,成人av手机在线观看,日韩精品亚洲一区中文字幕,亚洲av无码人妻,四虎国产在线观看 ?

基于DBGrid的數(shù)據(jù)瀏覽控件的開發(fā)

2008-12-31 00:00:00王培容
電腦知識與技術 2008年35期

摘要:Delphi的DBGrid控件使用靈活,應用廣泛,但沒有提供顯示記錄的序號,點擊列標題排序,對列寬度、順序等信息的保存與恢復功能,在實際應用中存在不便。該文闡述了DBGrid控件的內部實現(xiàn)機制,介紹了對DBGrid控件添加顯示序號,點擊列標題排序,保存與恢復列寬度、順序等信息的實現(xiàn)方法。

關鍵詞:Delphi;DBGrid控件;記錄;顯示序號;排序

中圖分類號:TP393文獻標識碼:A文章編號:1009-3044(2008)35-2406-05

The Development of Data Browsing Control Based on DBGrid

WANG Pei-rong

(College of Electronic Information and Automatization,Chongqing Institute of Technology,Chongqing 400050,China)

Abstract: DBGrid contril has been applied widely in Delphi for its flexible use,but this control does not provide these function such as displaying of record serial number,sorting of column title,saving and restoring of column width and column sequence.This paper describes the internal realization mechanism of DBGrid control,and introduces how to realize displaying of record serial number,sorting of column title and saving and restoring of column width and column sequence.

Key words: delphi; DBGrid control; record; displaying serial number; sorting

Delphi的DBGrid是顯示、編輯數(shù)據(jù)的控件,使用率相當高。在使用中,常常需要顯示記錄的序號,對表格中的記錄進行排序處理,以及對列寬度,列順序的保存與恢復,這通常都需要對DBGrid的具體事件進行特定編碼,才能滿足需要。

作者在開發(fā)一個考勤管理系統(tǒng)時,用戶就提出需要對表格中的記錄進行排序,能夠記住用戶上次對表格的列寬度、順序的調整,能夠顯示記錄序號。所以將這三個典型功能進行控件標準化,創(chuàng)建了一個新的基于DBGrid的控件,整合了上述功能,完全可以代替原有的DBGrid控件,使用起來相當方便。

1 方法

要在DBGrid中整合顯示序號,點擊列標題排序,保存列寬度等信息,最好的辦法就是定義一個從DBGrid繼承的新控件。點擊Delphi的Component菜單下的New Component,在彈出的窗口中按圖1進行設置,即可生成該新控件。

相對于DBGrid控件,本控件新增了標志排序狀態(tài)的屬性,用字符串ASCChar作為升序標志,用字符串DESCChar作為降序標志,用邏輯變量ShowRecNo作為顯示序號的控制屬性。新增方法SaveColumnsToIni,LoadColumnsFromIni分別用來保存和恢復上次列寬度,列順序等信息。

Delphi提供了DBGrid的源代碼,文件名為DBGrids.pas,該文件在Delphi6版本中存放在<安裝目錄>\\Source\\Vcl目錄下,在Delphi2005版本中存放在<安裝目錄>\\3.0\\source\\Win32\\db目錄下。打開Delphi的DBGrids.pas文件,拷貝TDBGrid類的定義內容到圖1生成的單元文件TSDBGrid.pas中,作為新控件類的定義。在TSDBGrid.pas文件的published部分增加屬性property ASCChar:string;property DESCChar:string;property ShowRecNo:Boolean;在public部分增加方法procedure SaveColumnsToIni(sect,name:string);procedure LoadColumnsFromIni(sect,name:string);之后按CTRL+SHIFT+C鍵,Delphi就會補充完整的定義框架。

1.1 顯示記錄序號

原有的DBGrid控件的第一列僅顯示記錄狀態(tài)標志,沒有顯示記錄序號,本文所述新控件將擴展該標志列,添加顯示序號功能。

DBGrid控件是從CustomDBGrid 繼承而來的,僅簡單公開一些屬性而已,所以新控件參照DBGrid,也從CustomDBGrid繼承。原有的DBGrid控件的第一列寬度是在SetColumnAttributes這個過程中實現(xiàn)的,現(xiàn)在重載這個方法,加大該列寬度,為顯示記錄序號留出位置,代碼如下。

procedure TTSDBGrid.SetColumnAttributes;

begin

inherited;

//如果要顯示標志列且顯示序號屬性為真

if(dgIndicator in Options) and FShowRecNothen

ColWidths[0] := IndicatorWidth*3;

//加大列寬度為原寬度的3倍

end;

DBGrid控件表格在屏幕上的顯示是在方法DrawCell中實現(xiàn)的,重載這個方法就能實現(xiàn)顯示記錄序號的功能,具體代碼如下。

procedure TTSDBGrid.DrawCell(ACol,ARow:Integer;ARect:TRect;

AState:TGridDrawState);

begin

inherited;

//如果是第一列且顯示序號屬性為真

if (gdFixed in AState) and (ACol<0)

and FShowRecNo then

begin

Canvas.Brush.Color:=FixedColor;

if Assigned(DataLink) and DataLink.Activethen

begin

if {(ARow <> DataLink.ActiveRecord) and}(Arow>=0) then

begin//畫第一列

Canvas.Font.Color:=clRed;

FRect:=ARect;

FRect.Top:=ARect.Top+1;

OldActive:=DataLink.ActiveRecord;

try

DataLink.ActiveRecord:=ARow;

Value:=IntToStr(DataLink.DataSet.RecNo);

//如果不能取到序號,則不顯示

if(DataLink.DataSet.RecNo<0) then Value:='';

finally

DataLink.ActiveRecord:=OldActive;

end;

//居中畫出記錄序號

DrawText(Canvas.Handle,PChar(Value),Length(Value),F(xiàn)Rect,DT_CENTER);

end;

end;

end

//處理列標題的排序標志

else if(ACol>=0) then

with Canvas do

begin

DrawColumn:=Columns[ACol];

if ARow<0 then

//調用局部過程,處理排序標志符號

DrawTitleCell(ACol,ARow+TitleOffset,DrawColumn,AState)

end;

end;

1.2 排序功能

列排序功能通過點擊列標題觸發(fā),在初始順序、升序、降序狀態(tài)間切換。重載TitleClick方法,在該方法中添加排序功能的代碼,代碼如下。

procedure TTSDBGrid.TitleClick(Column:TColumn);

var

s,cFieldName:string;

i:integer;

DataSet:TDataSet;

ASortCol:TSortCol;

begin

//如果是設計狀態(tài),不處理

if(csDesigning in ComponentState)

then exit;

//如果數(shù)據(jù)集無效,也不處理

if (Column.Grid.DataSource=nil)

or (Column.Grid.DataSource.DataSet=nil) or (not Column.Grid.DataSource.DataSet.Active) then exit;

DataSet:=Column.Grid.DataSource. DataSet;

//如果是關聯(lián)字段,計算字段,則選擇默認排序,否則表示需要排序的字段

if Column.Field.FieldKind=fkLookup

then

cFieldName:=Column.Field.KeyFields

else if Column.Field.FieldKind=fkCalculated then

cFieldName:=Column.Field.KeyFields

else

cFieldName:=Column.FieldName;

//如果是ADO記錄集類型

if DataSet is TCustomADODataSet then begin

//取出當前排序字段

s:=TCustomADODataSet(DataSet).Sort;

if s='' then begin

//為空表示沒有排序字段,將當前字段作為升序字段記下

s:=cFieldName;

ASortCol:=TSortCol.Create (Column. Index, SortASC);

end

else begin

//如果當前字段已經(jīng)在排序

if Pos(cFieldName,s)<>0 then begin

//查找當前是否是在降序中

i:=Pos('DESC',s);

//如果不是降序,就作為降序記下

if i<=0 then begin

s:=s+'DESC';

ASortCol:=TSortCol.Create (Column.Index,SortDESC);

end

else begin

//如果已經(jīng)是降序,就回到默認順序

s:='';

ASortCol:=TSortCol.Create(Column.Index,SortDefault);

end;

end

else begin

//當前字段不在排序狀態(tài),則作為升序記下

s:=cFieldName;

ASortCol:=TSortCol.Create (Column.Index,SortASC);

end;

end;

//保存排序狀態(tài),并排序

SortCol:=ASortCol;

ASortCol.Free;

TCustomADODataSet(DataSet).Sort:=s;

end

//處理TClientDataSet記錄集類型

else if DataSet is TClientDataSet then begin

end;

//可以繼續(xù)添加對其他數(shù)據(jù)集類型的支持

//…

//調用祖先的實現(xiàn),保留本事件的其他定制接口功能

inherited;

end;

將排序標志符號畫到標題列,在DrawCell中的子過程DrawTitleCell實現(xiàn),代碼如下。

procedure TTSDBGrid.DrawCell(ACol,ARow:Integer;ARect:TRect;

AState:TGridDrawState);

procedure DrawTitleCell(ACol,ARow:Integer;Column:TColumn;var AState:TGridDrawState);

begin

//列標題的矩形框計算

TextRect:=TitleRect;

TextRect.Left:=TextRect.Right-Canvas.TextWidth(ASCChar);

//用紅色字體畫排序標志

Canvas.Font.Color:=clRed;

//取出對應的排序狀態(tài)標志字符

Value:='';

if(Column.Index=SortCol.Col) then

if(SortCol.sortType=SortASC)

then Value:=ASCChar

else if(SortCol.sortType=SortDESC)

then Value:=DESCChar;

//畫出排序標志字符

DrawText(Canvas.Handle,PChar(Value),Length(Value),TextRect,DT_RIGHT);

end;

begin//主過程

DrawTitleCell(ACol,ARow+TitleOffset,DrawColumn,AState);

end;

1.3 列信息的保存與恢復

這個功能用來保存與恢復用戶在運行時對列進行順序,寬度等信息的調整,代碼如下。

procedure TTSDBGrid.SaveColumnsToIni (sect, name: string);

var

s:string;

i:integer;

ini:TIniFile;

begin

//將列信息保存到與應用程序名對應的.ini中,段名由sect參數(shù)指定,變量名由name參數(shù)指定

ini:=TIniFile.Create(ChangeFileExt (Application.ExeName,'.ini'));

try

for i:=0 to Columns.Count-1 do

begin

s:=s+Columns.Items[i]. FieldName +','+Columns.Items[i].Title. Caption+','+IntToStr(Columns. Items[i]. Width)+',';

end;

SetLength(s,Length(s)-1);

ini.WriteString(sect,name,s);

finally

ini.Free;

end;

end;

procedure TSDBGrid.LoadColumnsFromIni (sect, name: string );

var

ini:TIniFile;

s:string;

ls:TStringList;

i:integer;

begin

//將列信息從與應用程序名對應的.ini中恢復,段名由sect參數(shù)指定,變量名由name參數(shù)指定,應與保存時相一致

ls:=TStringList.Create;

ini:=TIniFile.Create( ChangeFileExt(

Application.ExeName,'.ini'));

try

s:=ini.ReadString(sect,name,'');

ls.CommaText:=s;

if(ls.Count=3*Columns.Count) then

for i:=0 to Columns.Count-1 do

begin

Columns.Items[i].FieldName:=ls.Strings[3*i];

Columns.Items[i].Title.Caption:=ls.Strings[3*i+1];

Columns.Items[i].Width:=StrToInt(ls.Strings[3*i+2]);

end;

finally

ini.Free;

ls.Free;

end;

end;

在窗體建立或釋放時調用一下保存與恢復過程即可,如下例所示。

procedure TForm1.FormCreate(Sender:TObject);

begin

//參數(shù)注意與保存時一致

TSDBGrid1.LoadColumnsFromIni

('表格信息','表格一');

end;

procedure TForm1.FormDestroy(Sender:TObject);

begin

//參數(shù)注意與恢復時一致

TSDBGrid1.SaveColumnsToIni

('表格信息','表格一');

end;

2 控件注冊

通過Delphi的Component菜單下的Install Component菜單進行控件注冊,Delphi將利用生成控件時自動生成的Register過程(過程代碼見本段后)注冊本控件。將控件注冊到控件面板上的TS Coms頁中,然后就可以象使用Delphi的標準控件一樣使用。具體注冊窗體見圖2。

procedure Register;

begin

RegisterComponents('TS Coms',[TTSDBGrid]);

end;

3 控件的使用例子

通過上述過程注冊控件后,新建一個工程文件Project1.dpr,在Form1中放入一個ADOConnection1控件,一個ADOTable1,一個DataSource1,一個本文所建立的控件TSDBGrid1(在面板的TS Coms頁中),如圖3。

設置ADOConnection1的LoginPrompt屬性為False,連接串ConnectionString指向數(shù)據(jù)庫:Provider=SQLOLEDB.1;Password=<你的數(shù)據(jù)庫密碼>;Persist Security Info=True;User ID=sa;Initial Catalog=<數(shù)據(jù)庫名>;Data Source=.。設置ADOTable1的Connection屬性為ADOConnection1,TableName屬性值為<要顯示的表名>,Active屬性為True。設置DataSource1的DataSet屬性為ADOTable1。設置TSDBGrid1的DataSource屬性為DataSource1,ShowRecNo屬性為True,并調整合適大小,得到圖3的設計結果。

編寫Form的OnCreate,OnDestroy事件代碼,如下:

procedure TForm1.FormCreate(Sender:TObject);

begin

//參數(shù)注意與保存時一致

TSDBGrid1.LoadColumnsFromIni

('表格信息','表格一');

end;

procedure TForm1.FormDestroy(Sender:TObject);

begin

//參數(shù)注意與恢復時一致

TSDBGrid1.SaveColumnsToIni

('表格信息','表格一');

end;

按F9運行,然后點擊列標題,觀察排序效果,調整表格列寬度,關閉程序,再次運行,列寬度即為上次調整后的寬度。本例子用ADOTable記錄集作為數(shù)據(jù)集,顯示了記錄序號,學號,姓名,性別,出生年月。點擊學號列標題進行升序操作,并在列標題上顯示升序符號,效果如圖4。

4 結論

該程序在WindowsXP,Delphi6,SQLServer2000下調試成功,經(jīng)比較分析,Delphi6以及Delphi 2005的DBGrids.pas代碼基本未變,所以本文所述內容在Delphi后續(xù)版本中也是適用的。

參考文獻:

[1] 黃雄波,胡永健.基于Delphi的動態(tài)模糊輸入系統(tǒng)的設計與實現(xiàn)[J].計算機應用與軟件,2008(3).

[2] 李文杰,李霄漢.在Delphi的DBGrid中添加可視組件的改進方法[J].電腦編程技巧與維護,2006(3).

[3] 杜瑾.Delphi中DBGrid控件的高級使用[J].電腦學習,2003(1).

[4] 敬喜,王昀.Delphi 7數(shù)據(jù)庫編程學習捷徑[M].北京科海電子出版社,2003.

[5] 唐世偉,高升,黃志清.改進Delphi的DBGrid實現(xiàn)表格式數(shù)據(jù)輸入[J].微型電腦應用,2001(5).

主站蜘蛛池模板: 国产一级视频在线观看网站| 国产午夜精品一区二区三区软件| 一级毛片高清| 国产理论一区| 日本免费一区视频| 亚洲天堂日韩av电影| 欧美精品伊人久久| 欧美成人怡春院在线激情| 久久亚洲欧美综合| 国产精品不卡片视频免费观看| 国产微拍一区| 国产不卡网| 亚洲视频一区| 精品自窥自偷在线看| 亚洲视频免费在线看| 亚洲欧美不卡中文字幕| 99热这里都是国产精品| 国产簧片免费在线播放| 国产成人亚洲综合A∨在线播放| 国产迷奸在线看| 黄色污网站在线观看| 波多野结衣AV无码久久一区| 日本午夜精品一本在线观看| 美女毛片在线| 亚洲第一成网站| 中文国产成人精品久久一| 2021亚洲精品不卡a| 91亚洲国产视频| 国产精品视频第一专区| 日韩欧美成人高清在线观看| 丰满人妻被猛烈进入无码| 国产欧美在线| 国产精品天干天干在线观看| 97国产在线视频| 亚洲九九视频| 高清色本在线www| 亚洲成人一区二区| 毛片在线播放a| 日本成人在线不卡视频| 99热这里只有精品国产99| 欧美色综合网站| 亚洲a级在线观看| 伊人网址在线| 97超爽成人免费视频在线播放| 国产自在线播放| 亚洲欧美h| 亚洲啪啪网| 国产一区二区丝袜高跟鞋| 九色视频一区| 午夜国产精品视频黄| 久久一级电影| 久久夜色精品国产嚕嚕亚洲av| 性网站在线观看| 国产在线精彩视频论坛| 亚洲成人免费看| 91成人在线观看视频| 伊人久久综在合线亚洲2019| 青青草原偷拍视频| 午夜精品区| 五月天在线网站| 国产激情无码一区二区APP | 五月婷婷丁香色| 亚洲成人高清无码| 国产流白浆视频| 久久久精品久久久久三级| 国产主播一区二区三区| jizz在线观看| 欧美福利在线| 色婷婷色丁香| 午夜免费小视频| 欧美福利在线| 亚洲第一网站男人都懂| 亚洲成A人V欧美综合天堂| 综合亚洲色图| 午夜影院a级片| 免费看黄片一区二区三区| 国产精品分类视频分类一区| 午夜精品影院| 亚洲永久精品ww47国产| 好久久免费视频高清| 国产一级片网址| 免费看黄片一区二区三区|