1. 程式人生 > >delphi CxGrid用法總結(63問)

delphi CxGrid用法總結(63問)

重復 註釋 ccid nvi while ren 數據顯示 ray 序號

1. 去掉cxGrid中臺頭的Box
解決:在tableview1的optionsview的groupbybox=false;

*****************************************************************************

2.統計功能


解決:(1) tableview
tableview1的optionsviewfooter=ture
然後在cxGRid1的customize..中的summary 的footer.add需要合計的列kind= skSum
在Footer的第一列顯示[合計:]
加一個Summary項,Column設為Grid的第一列,Kind設為skNone
在該Summary項的OnGetText事件中,輸入:
procedure TFormExpense.tvExpenseTcxGridDBDataControllerTcxDataSummaryFooterSummaryItems2GetText(
Sender: TcxDataSummaryItem; const AValue: Variant; AIsFooter: Boolean;
var AText: String);
begin
AText := ‘合計:‘;
end;
(2) 按條件匯總:
在TableView的DataController->Summary->FooterSummary->OnSummary事件中,輸入:
procedure TFormExpense.tvExpenseDataControllerSummaryFooterSummaryItemsSummary(
ASender: TcxDataSummaryItems; Arguments: TcxSummaryEventArguments;
var OutArguments: TcxSummaryEventOutArguments);
begin
//得到字段名 TcxDBDataSummaryItem(Arguments.SummaryItem).FieldName;
if (ASender.DataController.Values[Arguments.RecordIndex, tvExpenseLevel.Index] > 1) //只統計Level列=1的值
and (TcxDBDataSummaryItem(Arguments.SummaryItem).Kind = skSum) then
OutArguments.Value := 0; //Level > 1的統計值設為0
end;

OptionView中屬性GroupFooters設為gfAlwaysVisible並設置需要求和的列,在summary.default for Groups 下add加入需要合計的字段,column下顯示fieldname 為統計字段,format為格式,kind為統計方法,position 為位子 spfooter 在分組的下面,spgroup 在分組的上面
或用cxGridPopupMenu1,在運行時可對任意數字類型列求和,方法是只需設置cxGridPopupMenu1的屬性Grid為cxGrid1DBTableView1的cxGrid,

*****************************************************************************

3.去掉cxgrid 中的過濾下拉箭頭
解決: 選擇tableview1.optionscustomize.columnfiltering=fasle;

****************************************************************************

4.讓“Drag a column here to group by that column”不顯示
解決:在cxGrid1DBTableView1->optionsview->groupbybox:=false即可

****************************************************************************

5.GroupPanel上面的英文[Drag a column header to group by that column]怎麽可以改成中文
解決:最簡單的方法是 TcxGridTableView.OnCustomDrawPartBackground,
也可用 OnCustomDrawGroupCell:

procedure TForm1.cxGrid1DBTableView1CustomDrawPartBackground(
Sender: TcxGridTableView; ACanvas: TcxCanvas;
AViewInfo: TcxCustomGridCellViewInfo; var ADone: Boolean);
begin
AViewInfo.Text:=‘動態設置 GroupBox 的顯示內容‘;
ACanvas.FillRect(AViewInfo.Bounds);
end;
註:改成中文後將字段拖上去中文還是會顯示,最好是設置空值

****************************************************************************

6.如何實現如下功能:
+財務部
+原材料倉庫
+成品庫
+沖壓車間
+軟件開發部
這個是部門的名稱,點擊加號就可以將本部門的人員情況顯示出來。

解決:其實這是一個主從表關系,1:填好主表的keyfieldnames
2:填好從表的keyfieldnames
3:填好從表的 detaikeyfieldNames與masterkeyfieldnames
4: 從表的數據源一定要按與主表關聯的字段排序
註:其它地方設置了主從表結構那樣就顯示不出來,比如設置了從表的Table或者Query的mastersource和
masterfield就會不能顯示數據!如果是兩個cxGrid的主從關系,這樣設置就很OK了。

****************************************************************************

7.類似PageControl顯示

解決:增加一個Level,將cxGrid1->RootLevelOptions->DetailTabsPosition設為dtpTop,然後相應的設置cxGrid1Level1,和cxGrid1Level2的Caption值。

****************************************************************************

8.如何設定左邊幾列,不能滾動

解決:使用DB Banded Table才可以實現,
在cxGrid1DBBandedTableView裏建立Band0,Band1
Band0的Fixed=tfLeft
Band1的Fixed=tfnone
設置要鎖定的字段的BandIndex=0,其它為1,就OK了。

*******************************************************************************

9. 怎樣實現如EXCEL一樣的,當前格=G14+G15+G16 這樣的功能
解決: 舉一個簡單的例子:label1.Caption := cxGrid1DBTableView1.DataController.Values[2,
3]+cxGrid1DBTableView2.DataController.Values[1, 1]+cxGrid1DBTableView3.DataController.Values[1, 1];
所以不同cxGrid1DBTableView中的數據都可以給當前格,這樣就做到了EXCEL中的當前格=G14+G15+G16 類似的功能。
****************************************************************************

10. 鼠標右擊cxGrid1DBBandedTableView1菜單裏的Edit Layout什麽用,怎麽使用?

解決:可以拖動字段,並列的可以拖成有層次感(一層層), 拖動時會顯示箭頭的,就是說可以拖一個字段放

****************************************************************************

11.怎樣將cxGrid裏的數據導入到EXCEL,HTML,XML和TEXT

解決:uses
cxExportGrid4Link; ( cxExportGrid6Link)

procedure TForm1.Button1Click(Sender: TObject);
begin
ExportGrid4ToEXCEL(‘d:/wang.xsl‘,cxGrid1,True,True);
ExportGrid4ToTEXT(‘d:/wang.txt‘,cxGrid1,True,True);
ExportGrid4ToXML(‘d:/wang.xml‘,cxGrid1,True,True);
ExportGrid4ToHTML(‘d:/wang.html‘,cxGrid1,True,True);
end;

****************************************************************************


12. 如何使滿足條件的數據顯示不同的顏色?

解決:
var
AYellowStyle: TcxStyle;

procedure TForm1.FormCreate(Sender: TObject);
begin
//行顏色
AYellowStyle := TcxStyle.Create(Self);
AYellowStyle.Color := $0080FFFF;
AYellowStyle.TextColor := clMaroon;
end;

procedure TForm1.cxGrid1DBBandedTableView1StylesGetContentStyle(
Sender: TcxCustomGridTableView; ARecord: TcxCustomGridRecord;
AItem: TcxCustomGridTableItem; out AStyle: TcxStyle);
begin
if ARecord.Values[cxGrid1DBBandedTableView1Lengthcm.Index] < 81 then
AStyle := AYellowStyle;
end;

這裏cxGrid1DBBandedTableView1Lengthcm.Index小於81時就顯示黃色

****************************************************************************
13. 如何從外邊的TXT文件導入到cxGrid?

解決:
procedure CustomizeColumns;
procedure LoadData;

procedure TForm1.CustomizeColumns;
const
cDistance = 1;
cRadius = 5;
cPeriod = 4;
cPstring = 0;
var
I: Integer;
begin
DecimalSeparator := ‘.‘;
with cxGrid1TableView2 do
for I := 0 to ColumnCount - 1 do
if I in [cDistance, cRadius] then
Columns[I].DataBinding.ValueTypeClass := TcxIntegerValueType//1,5列為Integer
else
if I in [cPstring,cPeriod] then
Columns[I].DataBinding.ValueTypeClass := TcxStringValueType//0,4列為String
else
Columns[I].DataBinding.ValueTypeClass := TcxFloatValueType;//其他為Float
end;

procedure TForm1.LoadData;
const
AFileName = ‘資產負債表.txt‘;
AHeaderLineCount = 2;

var
ARecords, AValues: TStringList;
I: Integer;

procedure InitRecord(const Str: string);
var
J: Integer;
V: Variant;
begin
AValues.CommaText := Str;
for J := 0 to AValues.Count - 1 do
if AValues.Strings[J] <> ‘-‘ then
begin
V := AValues.Strings[J];
if not VarIsNull(V) then
cxGrid1TableView2.DataController.Values[I, J] := V;
end;
end;

begin
if not FileExists(AFileName) then
raise Exception.Create(‘Data file not found‘);

ARecords := TStringList.Create;
AValues := TStringList.Create;

with ARecords do
try
LoadFromFile(AFileName);
cxGrid1TableView2.BeginUpdate;
cxGrid1TableView2.DataController.RecordCount := Count - AHeaderLineCount;
for I := 0 to Count - (AHeaderLineCount + 1) do
InitRecord(Strings[I + AHeaderLineCount]);
finally
cxGrid1TableView2.EndUpdate;
ARecords.Free;
AValues.Free;
end;
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
CustomizeColumns;
LoadData_Zcfz;
end;

****************************************************************************
14 如何改變列的顏色?
解決:
var
AFirstColumnStyle: TcxStyle;

procedure TForm1.FormCreate(Sender: TObject);
begin
//列顏色
AFirstColumnStyle := TcxStyle.Create(Self);
AFirstColumnStyle.Color := clAqua;
AFirstColumnStyle.TextColor := clBlue;
cxGrid1TableView1.Columns[1].Styles.Content := AFirstColumnStyle;
end;
****************************************************************************
15 Set as default的用法?
解決:Set as default的用法是為了解決設置參數的方便而做的,比如:
連好數據庫以後,更改cxGrid1DBBandedTableView1->OptionsCustomize-> ColumnFiltering 設為False。(這個設置可以將字段名的下拉單給去掉)更改cxGrid1DBBandedTableView1->OptionsView- >Navigator 設置為True。然後右擊cxGrid1DBBandedTableView1,在彈出的菜單欄裏面點擊Set as default。
OK,下次你再產生一個新的cxGrid1DBBandedTableView1時這些設置和剛才的一樣了。如果需要設置的參數很多的時候,這個Set as default很有用!

****************************************************************************
16. 怎樣使鼠標移動時,相應的單元裏的文字變色?
解決:
var
FTrackItem: TcxCustomGridTableItem;
FTrackRec: TcxCustomGridRecord;

procedure TForm1.cxGrid1DBTableView1CustomDrawCell(
Sender: TcxCustomGridTableView; ACanvas: TcxCanvas;
AViewInfo: TcxGridTableDataCellViewInfo; var ADone: Boolean);
begin
if (AViewInfo.GridRecord = FTrackRec) and (AViewInfo.Item = FTrackItem) then
begin
ACanvas.Font.Color := clred; //紅色字體
ACanvas.Font.Style := [fsUnderline];//帶下劃線
end;
end;

procedure TForm1.cxGrid1DBTableView1MouseMove(Sender: TObject;
Shift: TShiftState; X, Y: Integer);
var
AHitTest: TcxCustomGridHitTest;
ATrackItem: TcxCustomGridTableItem;
ATrackRec: TcxCustomGridRecord;
begin
ATrackItem := FTrackItem;
ATrackRec := FTrackRec;

AHitTest := (Sender as TcxGridSite).GridView.ViewInfo.GetHitTest(X, Y);
if AHitTest is TcxGridRecordCellHitTest then
begin
FTrackItem := TcxGridRecordCellHitTest(AHitTest).Item;
FTrackRec := TcxGridRecordCellHitTest(AHitTest).GridRecord;
end
else
begin
FTrackItem := nil;
FTrackRec := nil;
end;

if (ATrackItem <> FTrackItem) or (ATrackRec <> FTrackRec) then
begin
// Invalidate old cell
if ATrackRec <> nil then
ATrackRec.Invalidate(ATrackItem);
// Invalidate new cell
if FTrackRec <> nil then
FTrackRec.Invalidate(FTrackItem);
end;
end;

****************************************************************************
zj註:17-27轉載自http://blog.csdn.net/shuaihj/article/details/6131011

17. 怎樣設計多表頭的cxGrid?
解決:cxGrid可以解決如下的表頭:
---------------------------------
| 說明1 | 說明2 |
---------------------------------
| 字段1 | 字段2 | 字段3 | 字段4 |
| 字段5 | 字段6 |
| 字段7 | 字段8 | 字段9 |
實現這個很簡單,你可以直接在上面拖動字段名,拖動時會顯示箭頭的,放入你想顯示的位置就OK了。或者在鼠標右擊cxGrid1DBBandedTableView1菜單裏的Edit Layout裏也可以拖放。

但是cxGrid不能實現如下的多表頭形式:
---------------------------------
| 說明1 | 說明2 |
---------------------------------
| 說明3 | 說明4 | 說明5 | 說明6 |
| 字段1 | 字段2 |
| 字段3 | 字段4 | 字段5 |
不知道有誰能實現這樣的多表頭?

****************************************************************************
18. 在主從表結構時,當點開“+”時怎樣將焦點聚在相應主表的記錄上?
解決:
var
HitTest: TcxCustomGridHitTest;

procedure TColumnsShareDemoMainForm.tvProjectsMouseDown(Sender: TObject;
Button: TMouseButton; Shift: TShiftState; X, Y: Integer);
begin
// Note that the Sender parameter is a Site
HitTest := (Sender as TcxGridSite).GridView.ViewInfo.GetHitTest(X, Y);
// The point belongs to the [+]/[-] button area
if HitTest is TcxGridExpandButtonHitTest then
// Move focus to the record
TcxGridExpandButtonHitTest(HitTest).GridRecord.Focused := True;
end;

****************************************************************************
19 CXGrid4如何展開全部節點
解決:GridDBTableView1.DataController.Groups.FullExpand;

****************************************************************************
20. cxGrid如何動態創建Items的Editor的項?
解決:cxGrid的列有一個屬性,它的編輯框可以指定combobox,spinedit等.在設計時,可以為
combobox的items添加項目.請問是否可以動態創建?(run-time時由程序加入)
var
A:TDataSource:
B:TcxlookupcomboboxProperties;
begin
A:=TDataSource.create(self);
B:=tcxlookupcomboboxproperties.create(self);
A.Dataset:=Dic_ry_xb;//此處指定數據源。
b.listdource:=a;//此處指明字段的listsource屬性。
b.keyfieldnames:=‘a‘; //此處指明字段的關鍵字段
b.listfieldnames:=‘b‘; //此處指明字段的返回值。
b.listcolumns.items[0].caption:=‘x; //此處默認是會建立一個字段,但是顯示的表頭是name,所以此處讓它顯示為自己想要的中午顯示。
cxGrid1DBTableView1c1_sex_code.Properties:=b; //此處指明是那個字段。
end; //這個是初始化的代碼

****************************************************************************
21. 拷貝文件時有進度顯示
解決:
procedure TForm1.mycopyfile(sourcef,targetf:string);
var
FromF, ToF: file;
NumRead, NumWritten: Integer;
Buf: array[1..2048] of Char;
n:integer;
begin
AssignFile(FromF, sourcef);
Reset(FromF, 1); { Record size = 1 }
AssignFile(ToF,targetf); { Open output file }
Rewrite(ToF, 1); { Record size = 1 }
n:=0;
repeat
BlockRead(FromF, Buf, SizeOf(Buf), NumRead);
form1.label1.caption:=IntToStr(sizeof(buf)*n*100 div FileSize(FromF))+‘100%‘;
application.ProcessMessages;
//顯示進度
BlockWrite(ToF, Buf, NumRead, NumWritten);
inc(n);
until (NumRead = 0) or (NumWritten <> NumRead);
form1.Label1.Caption:=‘100%‘;
CloseFile(FromF);
CloseFile(ToF);
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
mycopyfile(‘e:/components/tv2k-w2k.zip‘,‘c:/a.zip‘);
end;
****************************************************************************
22. cxGrid 設置斑馬線
解決:
在TcxGridDBBandedTableView.Styles屬性中有 ContentEven(奇數行風格) ContentOdd (偶數行風格) ,設定一下風格就好了。
****************************************************************************
23 根據記錄內容更改字體顏色
解決:
參考範例CustomDrawTableViewDemo,
主要在TcxGridDBBandedTableView.OnCustomDrawCell事件中實現。
如下代碼:

if (Pos(‘-‘,AViewInfo.GridRecord.DisplayTexts[colOrderProductCount.Index]) > 0) then
begin //標識負數記錄
//ACanvas.Canvas.Brush.Color:= clMoneyGreen;
ACanvas.Canvas.Font.Color:= clRed;//clActiveCaption
end;

其中colOrderProductCount是“產品訂數”列。

還要有一步就是要刷新顯示

TcxGridDBBandedTableView.LayoutChanged();
//tvCars.LayoutChanged(False);
TcxGridDBBandedTableView.Painter.Invalidate;

****************************************************************************
24 用代碼展開/收縮主從結構
解決:
Self.tvDepartment.ViewData.Expand(True);
Self.tvDepartment.ViewData.Collaspe(True);
註:tvDepartment為主表對應的TableView

****************************************************************************
25 在內置右鍵菜單的後面增加菜單項
解決:
首先應在Form上加一個cxGridPopupMenu控件 以啟用右鍵菜單
UseBuildInPopupMenus設為True

procedure TFormItemList.FormCreate(Sender: TObject);
var
AMenu: TComponent;
FMenuItem, FSubMenuItem: TMenuItem;
begin
AMenu := nil;
if cxGridPopupMenu.BuiltInPopupMenus.Count = 0 then
Exit;
AMenu := cxGridPopupMenu.BuiltInPopupMenus[0].PopupMenu; //第一個內置右鍵菜單(表頭菜單)
if Assigned(AMenu) and AMenu.InheritsFrom(TPopupMenu) then
begin
TPopupMenu(AMenu).AutoHotkeys := maManual; //手動熱鍵

//-------------------------
FMenuItem := TMenuItem.Create(Self);
FMenuItem.Caption := ‘-‘;
FMenuItem.Name := ‘miLineForGroup‘;
TPopupMenu(AMenu).Items.Add(FMenuItem);

//展開所有組
FMenuItem := TMenuItem.Create(Self);
FMenuItem.Name := ‘miExpandAllGroup‘;
FMenuItem.Caption := ‘展開所有組(&X)‘;
FMenuItem.OnClick := miExpandAllGroupClick;
TPopupMenu(AMenu).Items.Add(FMenuItem);

//收縮所有組
FMenuItem := TMenuItem.Create(Self);
FMenuItem.Name := ‘miCollapseAllGroup‘;
FMenuItem.Caption := ‘收縮所有組(&O)‘;
FMenuItem.OnClick := miCollapseAllGroupClick;
TPopupMenu(AMenu).Items.Add(FMenuItem);

//-------------------------
FMenuItem := TMenuItem.Create(Self);
FMenuItem.Caption := ‘-‘;
TPopupMenu(AMenu).Items.Add(FMenuItem);

//過濾面板
FMenuItem := TMenuItem.Create(Self);
FMenuItem.Name := ‘miFilterPanel‘;
FMenuItem.Caption := ‘過濾面板(&P)‘;
//自動顯示
FSubMenuItem := TMenuItem.Create(Self);
FSubMenuItem.Name := ‘miFilterPanelAuto‘;
FSubMenuItem.Caption := ‘自動(&A)‘;
FSubMenuItem.RadioItem := True;
FSubMenuItem.GroupIndex := 5; //指定同一組
FSubMenuItem.Checked := True;
FSubMenuItem.OnClick := miFilterPanelClick;
FMenuItem.Add(FSubMenuItem); //加入二級子菜單
//總是顯示
FSubMenuItem := TMenuItem.Create(Self);
FSubMenuItem.Name := ‘miFilterPanelAlways‘;
FSubMenuItem.Caption := ‘總是顯示(&W)‘;
FSubMenuItem.RadioItem := True;
FSubMenuItem.GroupIndex := 5;
FSubMenuItem.OnClick := miFilterPanelClick;
FMenuItem.Add(FSubMenuItem);
//從不顯示
FSubMenuItem := TMenuItem.Create(Self);
FSubMenuItem.Name := ‘miFilterPanelNerver‘;
FSubMenuItem.Caption := ‘從不顯示(&N)‘;
FSubMenuItem.RadioItem := True;
FSubMenuItem.GroupIndex := 5;
FSubMenuItem.OnClick := miFilterPanelClick;
FMenuItem.Add(FSubMenuItem);
TPopupMenu(AMenu).Items.Add(FMenuItem);

//自定義過濾
FMenuItem := TMenuItem.Create(Self);
FMenuItem.Name := ‘miCustomFilter‘;
FMenuItem.Caption := ‘自定義過濾(&M)‘;
FMenuItem.OnClick := miCustomFilterClick;
TPopupMenu(AMenu).Items.Add(FMenuItem);

//過濾管理器
FMenuItem := TMenuItem.Create(Self);
FMenuItem.Name := ‘miFilterBuilder‘;
TPopupMenu(AMenu).Images.AddImage(FormMain.ImageListExtend, 44); //添加圖標圖像
FMenuItem.ImageIndex := TPopupMenu(AMenu).Images.Count - 1; //指定圖標序號
FMenuItem.Caption := ‘過濾管理器‘;
FMenuItem.OnClick := Self.miFilterBuilderClick;
TPopupMenu(AMenu).Items.Add(FMenuItem);

//---------------------
FMenuItem := TMenuItem.Create(Self);
FMenuItem.Caption := ‘-‘;
TPopupMenu(AMenu).Items.Add(FMenuItem);

//導出
FMenuItem := TMenuItem.Create(Self);
FMenuItem.Name := ‘miExport‘;
TPopupMenu(AMenu).Images.AddImage(FormMain.ImageListExtend, 37);
FMenuItem.ImageIndex := TPopupMenu(AMenu).Images.Count - 1;
FMenuItem.Caption := ‘導出(&E)‘;
FMenuItem.OnClick := Self.miExportClick;
TPopupMenu(AMenu).Items.Add(FMenuItem);

//打印
FMenuItem := TMenuItem.Create(Self);
FMenuItem.Name := ‘miPrint‘;
FMenuItem.Caption := ‘打印(&P)‘;
TPopupMenu(AMenu).Images.AddImage(FormMain.ImageListExtend, 14);
FMenuItem.ImageIndex := TPopupMenu(AMenu).Images.Count - 1;
FMenuItem.OnClick := Self.miPrintClick;
TPopupMenu(AMenu).Items.Add(FMenuItem);
end;
end;

procedure TFormItemList.miExportClick(Sender: TObject);
var
FileName, FileExt, msg: String;
begin
if Self.aqyQuery.IsEmpty then
begin
msg := ‘沒有導出數據...‘;
Application.MessageBox(PChar(msg), PChar(Application.Title),
MB_OK or MB_IconWarning);
Exit;
end;

Self.SaveDialogExport.Filter := ‘Excel文件 (*.xls)|*.xls|XML文件 (*.xml)|*.xml‘
+ ‘|文本文件 (*.txt)|*.txt|網頁文件 (*.html)|*.html‘;
Self.SaveDialogExport.Title := ‘導出為‘;

if not Self.SaveDialogExport.Execute then
Exit;

FileName := Self.SaveDialogExport.FileName;
FileExt := LowerCase(ExtractFileExt(FileName));
if FileExt = ‘.xls‘ then
ExportGrid4ToExcel(FileName, Self.cxGrid1)
else if FileExt = ‘.xml‘ then
ExportGrid4ToXML(FileName, Self.cxGrid1)
else if FileExt = ‘.txt‘ then
ExportGrid4ToText(FileName, Self.cxGrid1)
else if FileExt = ‘.html‘ then
ExportGrid4ToHTML(FileName, Self.cxGrid1)
else
begin
msg := ‘不支持的導出文件類型...‘;
Application.MessageBox(PChar(msg), PChar(Application.Title),
MB_OK or MB_IconError);
Exit;
end;

msg := ‘導出完成...‘;
Application.MessageBox(PChar(msg), PChar(Application.Title),
MB_OK or MB_IconInformation);
end;

procedure TFormItemList.miPrintClick(Sender: TObject);
begin
//打印
Self.dxComponentPrinter.Preview(True, Self.dxComponentPrinterLink1);
end;

procedure TFormItemList.cxGridPopupMenuPopup(ASenderMenu: TComponent;
AHitTest: TcxCustomGridHitTest; X, Y: Integer; var AllowPopup: Boolean);
begin
if GetHitTypeByHitCode(AHitTest.HitTestCode) = gvhtColumnHeader then //右擊列標題時
begin
//if tvResult.DataController.Groups.GroupingItemCount > 0 then
if tvResult.GroupedColumnCount > 0 then //有分組時顯示
begin
TMenuItem(Self.FindComponent(‘miLineForGroup‘)).Visible := True;
TMenuItem(Self.FindComponent(‘miExpandAllGroup‘)).Visible := True;
TMenuItem(Self.FindComponent(‘miCollapseAllGroup‘)).Visible := True;
end
else
begin
TMenuItem(Self.FindComponent(‘miLineForGroup‘)).Visible := False;
TMenuItem(Self.FindComponent(‘miExpandAllGroup‘)).Visible := False;
TMenuItem(Self.FindComponent(‘miCollapseAllGroup‘)).Visible := False;
end;
end;
end;

procedure TFormItemList.miFilterBuilderClick(Sender: TObject);
begin
//過濾管理器
//彈出Filter Builder Dialog對話框
tvResult.Filtering.RunCustomizeDialog;
end;

procedure TFormItemList.miCustomFilterClick(Sender: TObject);
var
AHitTest: TcxCustomGridHitTest;
begin
//自定義過濾
//彈出Custom Filter Dialog對話框
AHitTest := cxGridPopupMenu.HitTest;
if GetHitTypeByHitCode(AHitTest.HitTestCode) = gvhtColumnHeader then //獲得右擊的列
tvResult.Filtering.RunCustomizeDialog(TcxGridColumnHeaderHitTest(AHitTest).Column);
end;

procedure TFormItemList.miFilterPanelClick(Sender: TObject);
var
mi: TMenuItem;
begin
//隱藏/顯示過濾面板
mi := TMenuItem(Sender);
mi.Checked := True;
if mi.Name = ‘miFilterPanelAlways‘ then
tvResult.Filtering.Visible := fvAlways
else if mi.Name = ‘miFilterPanelNerver‘ then
tvResult.Filtering.Visible := fvNever
else
tvResult.Filtering.Visible := fvNonEmpty;
end;

procedure TFormItemList.miExpandAllGroupClick(Sender: TObject);
begin
//展開所有組
tvResult.DataController.Groups.FullExpand;
end;

procedure TFormItemList.miCollapseAllGroupClick(Sender: TObject);
begin
//收縮所有組
tvResult.DataController.Groups.FullCollapse;
end;

****************************************************************************
26 根據某列的值設定其它列的可編輯性
解決:
procedure TFormUser.tvUserEditing(Sender: TcxCustomGridTableView;
AItem: TcxCustomGridTableItem; var AAllow: Boolean);
begin
//如果第三列值為True,則第4列不能修改
if (tvUser.Controller.FocusedRecord.Values[2] = True) and (AItem.Index = 4) then
AAllow := False
else
AAllow := True;
end;

****************************************************************************
27 保存/恢復Grid布局
解決:
網格左上角的自定義布局按鈕:
TableView-?OptionsCustiomize?ColumnsQuickCustomization true;
//恢復布局
IniFileName := ExtractFilePath(Application.ExeName) + ‘Layout/‘ + Self.Name + ‘.ini‘;
if FileExists(IniFileName) then
Self.tvResult.RestoreFromIniFile(IniFileName) //從布局文件中恢復
else
begin
Self.tvResult.BeginUpdate;
for i := 0 to Self.tvResult.ItemCount - 1 do
Self.tvResult.Items[i].ApplyBestFit; //調整為最佳寬度
Self.tvResult.EndUpdate;
end;

//保存布局
IniFileName := ExtractFilePath(Application.ExeName) + ‘Layout/‘ + Self.Name + ‘.ini‘;
if not DirectoryExists(ExtractFileDir(IniFileName)) then
CreateDir(ExtractFileDir(IniFileName));
Self.tvResult.StoreToIniFile(IniFileName); //保存為布局文件


實例:
IniFileName: string;

procedure TMainFM.FormCreate(Sender: TObject); //窗體創建時讀取布局
var i: Integer;
begin
qyHed.Open;
IniFileName := ExtractFilePath(Application.ExeName) + ‘/Layout/‘ + cxGrd.Owner.ClassName + cxGrd.Name + ‘.ini‘;
if FileExists(IniFileName) then
Self.cxTbv.RestoreFromIniFile(IniFileName) //從布局文件中恢復
else
begin
Self.cxTbv.BeginUpdate;
for i := 0 to Self.cxTbv.ItemCount - 1 do
Self.cxTbv.Items[i].ApplyBestFit; //調整為最佳寬度
Self.cxTbv.EndUpdate;
end;
end;

procedure TMainFM.NSaveGrdClick(Sender: TObject); //保存布局文件
begin
try
IniFileName := ExtractFilePath(Application.ExeName) + ‘/Layout/‘ + cxGrd.Owner.ClassName + cxGrd.Name + ‘.ini‘;
if not DirectoryExists(ExtractFileDir(IniFileName)) then
CreateDir(ExtractFileDir(IniFileName));
Self.cxTbv.StoreToIniFile(IniFileName);
except
end;
end;
****************************************************************************

28保存/恢復帶匯總行的布局解決:
<TableView>.StoreToIniFile(‘c:/Grid.ini‘, True, [gsoUseSummary]);
<GridView>.RestoreFromIniFile(<inifilename>,True,False{or True,optional},[gsoUseSummary]);

zj:本條與50條重復

****************************************************************************

(以下原博主轉載自http://hi.baidu.com/jangill/blog/item/2cf3c782f82f0798f703a67f.html)

****************************************************************************
28 在主從TableView中根據主TableView得到對應的從TableView
解決:

var
ADetailDC: TcxGridDataController;
AView: TcxCustomGridTableView;
begin
with cxGrid1DBTableView1.DataController do
ADetailDC := TcxGridDataController(GetDetailDataController(FocusedRecordIndex, 0));
AView := ADetailDC.GridView;
end;

==============================================================================

29 定位在第一行並顯示內置編輯器

cxDBVerticalGrid1.FocusedRow := cxDBVerticalGrid1.Rows[0];
cxDBVerticalGrid1.ShowEdit;

==============================================================================

30 隱藏 "<No data to display>" 字符串

該文本存儲在scxGridNoDataInfoText資源字符串,可以將該資源字符串的內容設為空
來隱藏該文本。

uses cxClasses, cxGridStrs;
...
cxSetResourceString(@scxGridNoDataInfoText, ‘‘);

//如果"<No data to display>" 字符串已經顯示,需要調用:
<View>.LayoutChanged;

============================================================

31 刪除應用過濾後的行

var
I: Integer;
begin
with <GridView> do
for I := 0 to ViewData.RecordCount - 1 do
begin
ViewData.Records[0].Focused := True;
DataController.DataSet.Delete;
end;

=============================================================

32 根據單元的值設置樣式
解決:
procedure <aForm>.<aColumn>StylesGetContentStyle(
Sender: TcxCustomGridTableView; ARecord: TcxCustomGridRecord;
AItem: TcxCustomGridTableItem; out AStyle: TcxStyle);
begin
if ARecord.Values[AItem.Index] = aSomeValue then
AStyle := <aSomeStyle>;
end;

procedure <aForm>.<aView>StylesGetContentStyle(
Sender: TcxCustomGridTableView; ARecord: TcxCustomGridRecord;
AItem: TcxCustomGridTableItem; out AStyle: TcxStyle);
var
AColumn: TcxCustomGridTableItem;
begin
AColumn := (Sender as TcxGridDBTableView).GetColumnByFieldName(‘Email‘);
if VarToStr(ARecord.Values[AColumn.Index]) = ‘‘ then
AStyle := cxStyleNullEmail;
end;

======================================================================

TcxCustomGridTableView.FindItemByName, TcxGridDBTableView.GetColumnByFieldName or
TcxGridDBDataController.GetItemByFieldName

with cxGrid1DBBandedTableView1.DataController do
AValue := Values[FocusedRecordIndex, GetItemByFieldName(‘SomeFieldName‘).Index];

****************************************************************************
33 動態生成BandedView
解決:
var
AView: TcxCustomGridView;
begin
AView := <cxGrid>.CreateView(TcxGridDBBandedTableView);
TcxGridDBBandedTableView(AView).DataController.DataSource := <DataSource>;
TcxGridDBBandedTableView(AView).Bands.Add;
with TcxGridDBBandedTableView(AView).Bands.Add do
begin
Visible := False;
FixedKind := fkLeft;
end;
TcxGridDBBandedTableView(AView).DataController.CreateAllItems;
<cxGridLevel>.GridView := AView;
end;
****************************************************************************
34 當底層數據集為空時顯示一條空記錄
解決:
procedure <Form>.<cxGrid>Enter(Sender: TObject);
var
View: TcxGridDBTableView;
begin
View := TcxGridDBTableView((Sender as TcxGrid).FocusedView);
if View.DataController.DataSet.IsEmpty then
begin
View.DataController.DataSet.Append;
View.Controller.EditingController.ShowEdit;
end;
end;
****************************************************************************
35 在當前View插入記錄
解決:
使用FocusedView屬性得到當前焦點View,用View.DataController得到對應的Data Controller,
之後使用Data Controller的方法來操作數據:
- Append
- Insert
- Post
- Cancel
- DeleteFocused
- DeleteSelection

示例:
var
ARecIndex: Integer;

View.DataController.Append;
ARecIndex := View.DataController.FocusedRecordIndex;
View.DataController.Values[ARecIndex, SomeItemIndex] := SomeValue;
View.DataController.Post;

另外一種方法是使用View.DataController.DataSource.DataSet得到底層數據集後,再用數據集的方法來操作數據。

****************************************************************************
36 激活內置編輯控件
解決:
1) <aView>.Controller.EditingController.ShowEdit(<aColumn>);
2) <aView>.Controller.EditingController.StartEditShowingTimer(<aColumn>);
3) <aView>.Controller.EditingItem := <aColumn>;
4) <aColumn>.Editing := True;
****************************************************************************
37 隱藏內置編輯控件
解決:
<aView>.Controller.EditingController.HideEdit(True);
****************************************************************************
38 移除一個分組列
解決:
<aColumn>.GroupIndex := -1;
<aColumn>.Visible := True;
****************************************************************************
39 保存修改到數據庫
解決:
procedure <aForm>.FormClose(Sender: TObject; var Action: TCloseAction);
begin
if (<aGrid>.FocusedView <> nil)
and (<aGrid>.FocusedView.DataController.EditState <> []) then
<aGrid>.FocusedView.DataController.Post;
end;
****************************************************************************
40 設置內置右鍵菜單
解決:
內置右鍵菜單包括二個菜單:cxGridStdHeaderMenu, TcxGridStdFooterMenu
uses cxGridStdPopupMenu;

procedure TForm1.cxGridPopupMenu1Popup(ASenderMenu: TComponent;
AHitTest: TcxCustomGridHitTest; X, Y: Integer; var AllowPopup: Boolean);
begin
if ASenderMenu is TcxGridStdHeaderMenu then
TcxGridStdHeaderMenu(ASenderMenu).OnPopup := StdHeaderMenuPopup;
end;

procedure TForm1.StdHeaderMenuPopup(Sender: TObject);
var
I: Integer;
begin
with TcxGridStdHeaderMenu(Sender).Items do
for I := 0 to Count - 1 do
if Items[I].Caption = ‘Group By Box‘ then
begin
Items[I].Enabled := False;
System.Break;
end
end;
****************************************************************************
41 得到選中記錄的值
解決:
1) View.DataController.DataModeController.GridMode = False時

RecIdx := View.Controller.SelectedRecords[i].RecordIndex;
ColIdx := View.DataController.GetItemByFieldName(AFieldName).Index;
OutputVal := View.DataController.Values[RecIdx, ColIdx];

//RecID := View.DataController.GetRecordId(RecIdx);
//OutputVal := ADataSet.Lookup(View.DataController.KeyFieldNames, RecID, AFieldName);

2) View.DataController.DataModeController.GridMode = True時
Bkm := View.DataController.GetSelectedBookmark(ASelectedRecordIndex);
if ADataSet.BookmarkValid(TBookmark(Bkm)) then
begin
ADataSet.Bookmark := TBookmark(Bkm);
OutputVal := ADataSet.FieldByName(AFieldName).Value;
end;

View.BeginUpdate;
View.DataController.BeginLocate;
try
// make changes here…
finally
View.DataController.EndLocate;
View.EndUpdate;
end;
****************************************************************************
42 在GridMode禁用內置的右鍵Footer菜單
解決:
uses cxGridStdPopupMenu;

procedure cxGridPopupMenuOnPopup(...)
begin
if (ASenderMenu is TcxGridStdFooterMenu) and
<GridView>.DataController.DataModeController.GridMode then
AllowPopup := False;
end;
****************************************************************************
43 主從表任何時候只能展開一個組
解決:
procedure TForm1.ADetailDataControllerCollapsing(
ADataController: TcxCustomDataController; ARecordIndex: Integer;
var AAllow: Boolean);
var
I: Integer;
C: Integer;
begin
AAllow := False;
C := 0;
for I := 0 to ADataController.RecordCount - 1 do
begin
if ADataController.GetDetailExpanding(I) then
Inc(C);
if C > 1 then
AAllow := True;
end;
end;

procedure TForm1.ADetailDataControllerExpanding(
ADataController: TcxCustomDataController; ARecordIndex: Integer;
var AAllow: Boolean);
begin
ADataController.CollapseDetails;
end;

procedure TForm1.FormCreate(Sender: TObject);
begin cxGrid1DBTableView1.DataController.OnDetailExpanding:=ADetailDataControllerExpanding; cxGrid1DBTableView1.DataController.OnDetailCollapsing:=ADetailDataControllerCollapsing;
end;
****************************************************************************
44 動態創建層次(Level)和視圖(View)
解決:
var
Grid: TcxGrid;
Level: TcxGridLevel;
View: TcxGridDBTableView;
begin
// Creates a Grid instance
Grid := TcxGrid.Create(SomeOwner);
Grid.Parent := SomeParent;
// Creates a Level
Level := Grid.Levels.Add;
Level.Name := ‘SomeLevelName‘;
// Creates a View
View := Grid.CreateView(TcxGridDBTableView) as TcxGridDBTableView;
View.Name := ‘SomeViewName‘;
// … and binds it to the Level
Level.GridView := View;
// Hooks up the View to the data
View.DataController.DataSource := SomeDataSource;
// … and creates all columns
View.DataController.CreateAllItems;
end;

****************************************************************************
45 獲得Group Footer合計行對應的記錄
解決:
procedure TForm1.cxGrid1DBTableView1CustomDrawFooterCell(
Sender: TcxGridTableView; ACanvas: TcxCanvas;
AViewInfo: TcxGridColumnHeaderViewInfo; var ADone: Boolean);
var
ALevel, ADataGroupIndex: Integer;
AGridRecord, AGroupRecord: TcxCustomGridRecord;
begin
if AViewInfo is TcxGridRowFooterCellViewInfo and // Row footer
(TcxGridDBColumn(AViewInfo.Column).DataBinding.FieldName = ‘Area‘) then // Area column
begin
AGridRecord:= TcxGridRowFooterCellViewInfo(AViewInfo).GridRecord;
ALevel:= TcxGridRowFooterCellViewInfo(AViewInfo).Container.GroupLevel;
ADataGroupIndex:=Sender.DataController.Groups.DataGroupIndexByRowIndex[AGridRecord.Index];
if ADataGroupIndex <> -1 then
begin
AGroupRecord := AGridRecord;
while AGroupRecord.Level <> ALevel do
AGroupRecord := AGroupRecord.ParentRecord;
AViewInfo.Text := AGroupRecord.DisplayTexts[0];
end;
end;
end;

****************************************************************************
46 訪問過濾之後的記錄
解決:
var
I: Integer;
begin
Memo1.Lines.Clear;
with cxGrid1DBTableView1.DataController do
for I := 0 to FilteredRecordCount - 1 do
Memo1.Lines.Add(DisplayTexts[FilteredRecordIndex[I], 0]);
end;

****************************************************************************
47 獲得單元的Font
解決:
cxGrid1DBTableView1.ViewInfo.RecordsViewInfo.Items[1].GetCellViewInfoByItem(
cxGrid1DBTableView1Company).EditViewInfo.Font;
****************************************************************************
48 根據Level名稱找到Level對象
解決:
function GetLevelByName(AGrid: TcxGrid; ALevelName: string): TcxGridLevel;

function LoopThroughLevels(ALevel: TcxGridLevel; ALevelName: string): TcxGridLevel;
var
I: Integer;
begin
Result := nil;
for I := 0 to ALevel.Count - 1 do
begin
if ALevel[I].Name = ALevelName then
begin
Result := ALevel[I];
Exit;
end;
if ALevel[I].Count > 0 then
begin
Result := LoopThroughLevels(ALevel[I], ALevelName);
if Result <> nil then
Exit;
end;
end;
end;

var
I: Integer;
begin
Result := nil;
for I := 0 to AGrid.Levels.Count - 1 do
begin
if AGrid.Levels[I].Name = ALevelName then
begin
Result := AGrid.Levels[I];
Exit;
end;
if AGrid.Levels[I].Count > 0 then
begin
Result := LoopThroughLevels(AGrid.Levels[I], ALevelName);
if Result <> nil then
Exit;
end;
end;
end;
****************************************************************************

49 指定Filter Builder打開/保存過濾文件的默認路徑
解決:
uses
..., cxFilterControlDialog;

procedure TForm.GridView1FilterControlDialogShow(
Sender: TObject);
begin
TfmFilterControlDialog(Sender).OpenDialog.InitialDir := ‘D:/‘
end;
****************************************************************************

50 保存/恢復帶匯總行的布局

<TableView>.StoreToIniFile(‘c:\Grid.ini‘, True, [gsoUseSummary]);
<GridView>.RestoreFromIniFile(<inifilename>,True,False {or True, optional},[gsoUseSummary]);

****************************************************************************
51 取消過濾時移到第一行
解決:
uses
cxCustomData;

procedure TYour_Form.AViewDataControllerFilterChanged(Sender: TObject);
var
Filter: TcxDataFilterCriteria;
begin
with Sender as TcxDataFilterCriteria do
if IsEmpty then
DataController.FocusedRowIndex := 0;
end;
****************************************************************************
52 排序後移到第一行
解決:
可以設置DataController.Options.FocusTopRowAfterSorting := True,也可以使用如下的代碼:

uses
cxCustomData;

procedure TYour_Form.Your_ViewDataControllerSortingChanged(Sender: TObject);
begin
TcxCustomDataController(Sender).FocusedRowIndex := 0;
end;
****************************************************************************
53 判斷當前行是否第一行或最後一行
解決:
可以使用DataController的IsBOF, IsEOF方法,或者:
<AView>.Controller.Controller.FocusedRow.IsFirst
<AView>.Controller.Controller.FocusedRow.IsLast
****************************************************************************
54 根據指定值查找記錄
解決:
DataController提供了好幾個方法來得到指定值對應的RecordIndex
對於Bound View可以使用FindRecordIndexByKeyValue方法
****************************************************************************
55 編輯和顯示Blob字段
解決:
該字段的Properties設置為BlobEdit,並將BlobPaintStyle 屬性設為 bpsText
****************************************************************************
56 得到可見行數
解決:
<View>.ViewInfo.VisibleRecordCount
****************************************************************************
57 保存後的行設置為當前行
解決:
const
CM_SETFOCUSEDRECORD = WM_USER + 1002;

type
TForm1 = class(TForm)
cxGrid1DBTableView1: TcxGridDBTableView;
cxGrid1Level1: TcxGridLevel;
cxGrid1: TcxGrid;
dxMemData1: TdxMemData;
dxMemData1Field1: TStringField;
dxMemData1Field2: TIntegerField;
DataSource1: TDataSource;
cxGrid1DBTableView1RecId: TcxGridDBColumn;
cxGrid1DBTableView1Field1: TcxGridDBColumn;
cxGrid1DBTableView1Field2: TcxGridDBColumn;
Timer1: TTimer;
CheckBox1: TCheckBox;
procedure Timer1Timer(Sender: TObject);
procedure dxMemData1AfterPost(DataSet: TDataSet);
procedure CheckBox1Click(Sender: TObject);
private
procedure CMSetFocusedRecord(var Msg: TMessage); message CM_SETFOCUSEDRECORD;
public
{ Public declarations }
end;

var
Form1: TForm1;
FocusedIdx: Integer;


implementation

{$R *.dfm}

procedure TForm1.Timer1Timer(Sender: TObject);
begin
dxMemData1.AppendRecord([‘‘, IntToStr(Random(1000)), Random(1000)]);
end;

procedure TForm1.dxMemData1AfterPost(DataSet: TDataSet);
begin
PostMessage(Handle, CM_SETFOCUSEDRECORD, Integer(cxGrid1DBTableView1), MakeLParam(cxGrid1DBTableView1.Controller.FocusedRowIndex, cxGrid1DBTableView1.Controller.TopRowIndex));
end;

procedure TForm1.CMSetFocusedRecord(var Msg: TMessage);
begin
TcxGridDBTableView(msg.WParam).Controller.FocusedRowIndex := Msg.LParamLo;
TcxGridDBTableView(msg.WParam).Controller.TopRowIndex := Msg.LParamHi;
end;

procedure TForm1.CheckBox1Click(Sender: TObject);
begin
Timer1.Enabled := TCheckBox(Sender).Checked;
end;

end.
****************************************************************************
58 刪除記錄並獲得焦點
解決:
procedure TForm1.BtnDeleteClick(Sender: TObject);
var
FocusedRow, TopRow: Integer;
View: TcxGridTableView;
DataController: TcxGridDataController;
begin
View := cxGrid1.FocusedView as TcxGridTableView;
DataController := View.DataController;

// Remember the top row (the vertical scrollbar position)
TopRow := View.Controller.TopRowIndex;
// Remember the focused row(!) index
FocusedRow := DataController.FocusedRowIndex;

DataController.DeleteFocused;

// After deletion the same row must be focused,
// although it will correspond to a different data record
DataController.FocusedRowIndex := FocusedRow;
// Restore the top row
View.Controller.TopRowIndex := TopRow;
end;
****************************************************************************
59 cxGrid的 TableView 數據排序與對應的數據集同步
解決:
COPYRIGHT BY cnCharles, ALL RIGHTS RESERVED.
delphi群: 16497064, blog: http://hi.baidu.com/cnCharles

//描述: cxGrid的 TableView 數據排序與對應的數據集同步, 該方法主要用於打印時
// 的排序與所見到的排序保持一致;
//參數: @tv: 排序的cxGridTableView
//說明: @tv: 對應的數據集只支持 ADOQuery與 ClientDataSet;
procedure cxGridSortSyncToDataSet(tv: TcxGridDBTableView); overload;

//描述: 功能同上, 實現代碼一樣, 如果有更改就同步更改
procedure cxGridSortSyncToDataSet(tv: TcxGridDBBandedTableView); overload;

procedure cxGridSortSyncToDataSet(tv: TcxGridDBTableView);
const
SortArray: array[soAscending..soDescending] of string = (’ASC’, ’DESC’);
var
AscFields, DescFields, S, SortOrder: string;
IndexPrint: string;
I: integer;
Index: integer;
cds: TClientDataSet;
begin
S := ’’;
AscFields := ’’;
DescFields := ’’;
if tv.SortedItemCount = 0 then
Exit;
if tv.DataController.DataSource.DataSet is TADOQuery then begin
for I := 0 to tv.SortedItemCount - 1 do begin
SortOrder := SortArray[tv.SortedItems[I].SortOrder];
if S <> ’’ then
S := S + ’, ’;
Index := tv.SortedItems[I].Index;
S := S + tv.Columns[Index].DataBinding.Field.FieldName + ’ ’ + SortOrder;
end;
(tv.DataController.DataSource.DataSet as TADOQuery).Sort := S;
end else if (tv.DataController.DataSource.DataSet is TClientDataSet) then begin
Cds := tv.DataController.DataSource.DataSet as TClientDataSet;
for I := 0 to tv.SortedItemCount - 1 do begin
Index := tv.SortedItems[I].Index;
S := tv.Columns[Index].DataBinding.Field.FieldName +’;’;
AscFields := AscFields + S;
if tv.SortedItems[I].SortOrder = soDescending then
DescFields := DescFields + S;
end;
if AscFields <> ’’ then
Delete(AscFields, Length(AscFields), 1); //刪除 ;

if DescFields <> ’’ then
Delete(DescFields, Length(DescFields), 1);
IndexPrint := TimeToStr(Now());
Cds.IndexDefs.Clear;
IndexPrint := TimeToStr(Now());
cds.AddIndex(IndexPrint, AscFields, [], DescFields);
cds.IndexName := IndexPrint;
end;
end;
****************************************************************************
60 cxGRID怎麽遍歷已經選擇的單元格
解決:
n := cxGrid1DBTableView1.DataController.GetSelectedCount;

for i:=0 to n - 1 do
begin
Index := cxGrid1DBTableView1.DataController.GetSelectedRowIndex(i);
if Index < 0 then continue;
AccID :=
cxGrid1DBTableView1.DataController.GetRowvalue(
cxGrid1DBTableView1.DataController.GetRowInfo(Index)
,0);
AccID := dsData.DataSet.FieldByName(’AccountID’).AsString;

end;
n := cxGrid1DBTableView1.DataController.GetSelectedCount;
for i:=0 to n - 1 do
begin
Index := cxGrid1DBTableView1.DataController.GetSelectedRowIndex(i);
if Index < 0 then continue;
AccID := cxGrid1DBTableView1.DataController.GetRowvalue(
cxGrid1DBTableView1.DataController.GetRowInfo(Index)
,0);//這裏的0是列的索引,能指定,也可用通過GridView獲取

end;
****************************************************************************
61 動態設置顯示格式
解決:
procedure SetDisplayFormat(ACtrlData: TClientDataSet;
TbView: TcxGridDBTableView);
var
i: integer;
begin
if ACtrlData.RecordCount <= 0 then Exit;
try
TbView.ClearItems;
ACtrlData.First;
for i := 0 to ACtrlData.RecordCount - 1 do
begin
if ACtrlData.FieldByName(‘SQBF_DisplayInGrid‘).AsString = ‘1‘ then //在表格中顯示
with TbView.CreateColumn do
begin
DataBinding.FieldName := ACtrlData.FieldByName(‘SQBF_FieldName‘).AsString;
Caption := ACtrlData.FieldByName(‘SQBF_Caption‘).AsString; //字段中文標題
Hint := ACtrlData.FieldByName(‘SQBF_Hint‘).AsString;
Width := ACtrlData.FieldByName(‘SQBF_Width‘).AsInteger;
HeaderAlignmentHorz := taCenter;
end;
ACtrlData.Next;
end;
except
on E: Exception do
SaveLog(‘設置顯示格式時出錯:‘ + E.Message);
end;
end;
****************************************************************************
62 給cxGRID加序號列
解決:
procedure SetRowNumber(var ASender: TcxGridTableView;
AViewInfo: TcxCustomGridIndicatorItemViewInfo;
var ACanvas: TcxCanvas; var ADone: boolean);

uses cxLookAndFeelPainters;

procedure SetRowNumber(var ASender: TcxGridTableView; AViewInfo: TcxCustomGridIndicatorItemViewInfo;
var ACanvas: TcxCanvas; var ADone: boolean);
var
AIndicatorViewInfo: TcxGridIndicatorRowItemViewInfo;
ATextRect: TRect;
AFont: TFont;
AFontTextColor, AColor: TColor;
begin
AFont := ACanvas.Font;
AColor := clBtnFace;
AFontTextColor := clWindowText ;
if (AViewInfo is TcxGridIndicatorHeaderItemViewInfo) then begin
ATextRect := AViewInfo.Bounds;
InflateRect(ATextRect, -1, -1);

ASender.LookAndFeelPainter.DrawHeader(ACanvas, AViewInfo.Bounds,
ATextRect, [], cxBordersAll, cxbsNormal, taCenter, vaCenter,
False, False, ‘序號‘, AFont, AFontTextColor, AColor);
ADone := True;
end ;
if not (AViewInfo is TcxGridIndicatorRowItemViewInfo) then
Exit;
ATextRect := AViewInfo.ContentBounds;
AIndicatorViewInfo := AViewInfo as TcxGridIndicatorRowItemViewInfo;
InflateRect(ATextRect, -1, -1);
ASender.LookAndFeelPainter.DrawHeader(ACanvas, AViewInfo.ContentBounds,
ATextRect, [], [bBottom, bLeft, bRight], cxbsNormal, taCenter, vaCenter,
False, False, IntToStr(AIndicatorViewInfo.GridRecord.Index + 1),
AFont, AFontTextColor, AColor);
ADone := True;
ASender.LookAndFeelPainter.DrawIndicatorImage(ACanvas,ATextRect, AIndicatorViewInfo.IndicatorKind);
end;

如果你不要行標誌的話,你可以不改控件
直接註釋掉這一行: ASender.LookAndFeelPainter.DrawIndicatorImage(ACanvas, ATextRect, AIndicatorViewInfo.IndicatorKind);
要標誌的話,在DrawIndicatorImage 從這裏跟進去(Ctrl+左鍵單擊)
在 cxLookAndFeelPainters 單元中作如下修改:

class procedure TcxCustomLookAndFeelPainter.DrawIndicatorImage(ACanvas: TcxCanvas;
const R: TRect; AKind: TcxIndicatorKind);
var
X, Y: Integer;
begin
if AKind = ikNone then Exit;
with cxIndicatorImages, R do
begin
X := (Left + Right - Width); //靠右
Y := (Top + Bottom - Height) div 2; //居中
end;
cxIndicatorImages.Draw(ACanvas.Canvas, X, Y, Ord(AKind) - 1);
end;

註意,我已註明靠右的那一行, 就是去掉 DIV 2 了,
還要改一個地方:
SKIN控件目錄下的dxSkinLookAndFeelPainter單元,找到
TdxSkinLookAndFeelPainter.DrawIndicatorImage 函數

OffsetRect(ARect, (Left + Right - cx div 2) , (Top + Bottom - cy) div 2);
這一行,將 (Left + Right - cx div 2) 改為(Left + Right - cx) 也是去掉 div 2 就是靠右;
修改後: OffsetRect(ARect, (Left + Right - cx) , (Top + Bottom - cy) div 2);

使用
procedure TForm1.cxGrid1DBTableView1CustomDrawIndicatorCell(
Sender: TcxGridTableView; ACanvas: TcxCanvas;
AViewInfo: TcxCustomGridIndicatorItemViewInfo; var ADone: Boolean);
begin
SetRowNumber(Sender,AviewInfo,ACanvas,ADone);
end;

另外序號列的列寬最好改為25以上!
效果圖:

****************************************************************************
63 cxGrid自帶過濾後數據也數據集同步
解決:
在cxGrid的View Filter事件的OnBeforeChange中寫代碼就可以了.
procedure TForm1.tvcxgd1DBTableView1DataControllerFilterBeforeChange( Sender: TcxDBDataFilterCriteria; ADataSet: TDataSet; const AFilterText: String); begin //這裏可以增加數據集控件的filter:=false; //如:adoquery.filter:=false; //如果使用的是cxgrid的漢化版本,可以將AFilterText中的中文等於,小於 替換成 = <等 //adoquery.filter:=替換了中文的AFilterText; ShowMessage(AFilterText); end; 寫了上述步驟後可以在tvcxgd1DBTableView1DataControllerFilterChanged寫 adoquery.filter:=true; 這樣就起到了cxgrid過濾後的數據同步到adoquery

delphi CxGrid用法總結(63問)