Added: TJDBGridControl and example (testgridctr)

git-svn-id: https://svn.code.sf.net/p/lazarus-ccr/svn@1980 8e941d3f-bd1b-0410-a28a-d453659cc2b4
This commit is contained in:
jujibo
2011-09-21 11:22:29 +00:00
parent 84a68c932c
commit 8f8180c10e
10 changed files with 893 additions and 2 deletions

View File

@ -5,6 +5,7 @@ JUJIBOUTILS
Version pre-1.0 Version pre-1.0
-------------------------------------------------- --------------------------------------------------
2011-09-21 Added: TJDBGridControl and example (testgridctr)
2011-09-20 Added: TJIntegerEdit, TJLabeledIntegerEdit 2011-09-20 Added: TJIntegerEdit, TJLabeledIntegerEdit
TJCurrencyEdit, TJLabeledCurrencyEdit TJCurrencyEdit, TJLabeledCurrencyEdit
TJDateEdit, TJLabeledDateEdit TJDateEdit, TJLabeledDateEdit

View File

@ -8,11 +8,17 @@
<OtherUnitFiles Value="src"/> <OtherUnitFiles Value="src"/>
<UnitOutputDirectory Value="lib/$(TargetCPU)-$(TargetOS)"/> <UnitOutputDirectory Value="lib/$(TargetCPU)-$(TargetOS)"/>
</SearchPaths> </SearchPaths>
<Linking>
<Debugging>
<GenerateDebugInfo Value="True"/>
<DebugInfoType Value="dsAuto"/>
</Debugging>
</Linking>
<Other> <Other>
<CompilerPath Value="$(CompPath)"/> <CompilerPath Value="$(CompPath)"/>
</Other> </Other>
</CompilerOptions> </CompilerOptions>
<Files Count="13"> <Files Count="15">
<Item1> <Item1>
<Filename Value="src/jdbintegeredit.pas"/> <Filename Value="src/jdbintegeredit.pas"/>
<HasRegisterProc Value="True"/> <HasRegisterProc Value="True"/>
@ -77,6 +83,15 @@
<HasRegisterProc Value="True"/> <HasRegisterProc Value="True"/>
<UnitName Value="JLabeledDateEdit"/> <UnitName Value="JLabeledDateEdit"/>
</Item13> </Item13>
<Item14>
<Filename Value="src/jdbgridcontrol.pas"/>
<HasRegisterProc Value="True"/>
<UnitName Value="JDBGridControl"/>
</Item14>
<Item15>
<Filename Value="src/jdbgridutils.pas"/>
<UnitName Value="jdbgridutils"/>
</Item15>
</Files> </Files>
<Type Value="RunAndDesignTime"/> <Type Value="RunAndDesignTime"/>
<RequiredPkgs Count="2"> <RequiredPkgs Count="2">

View File

@ -10,7 +10,7 @@ uses
jdbintegeredit, jdblabeledintegeredit, jdbcurrencyedit, jdbintegeredit, jdblabeledintegeredit, jdbcurrencyedit,
jdblabeledcurrencyedit, jdbdateedit, jdblabeleddateedit, jcontrolutils, jdblabeledcurrencyedit, jdbdateedit, jdblabeleddateedit, jcontrolutils,
JIntegerEdit, JLabeledIntegerEdit, JCurrencyEdit, JLabeledCurrencyEdit, JIntegerEdit, JLabeledIntegerEdit, JCurrencyEdit, JLabeledCurrencyEdit,
JDateEdit, JLabeledDateEdit, LazarusPackageIntf; JDateEdit, JLabeledDateEdit, JDBGridControl, jdbgridutils, LazarusPackageIntf;
implementation implementation
@ -28,6 +28,7 @@ begin
RegisterUnit('JLabeledCurrencyEdit', @JLabeledCurrencyEdit.Register); RegisterUnit('JLabeledCurrencyEdit', @JLabeledCurrencyEdit.Register);
RegisterUnit('JDateEdit', @JDateEdit.Register); RegisterUnit('JDateEdit', @JDateEdit.Register);
RegisterUnit('JLabeledDateEdit', @JLabeledDateEdit.Register); RegisterUnit('JLabeledDateEdit', @JLabeledDateEdit.Register);
RegisterUnit('JDBGridControl', @JDBGridControl.Register);
end; end;
initialization initialization

View File

@ -0,0 +1,77 @@
unit JDBGridControl;
{$mode objfpc}{$H+}
interface
uses
Classes, SysUtils, LResources, Forms, Controls, Graphics, DB, DBGrids,
Dialogs, jdbgridutils;
type
{ TJDBGridControl }
TJDBGridControl = class(TDBGrid)
private
{ Private declarations }
dateDbGridControl: TJDbGridDateCtrl;
integerDbGridControl: TJDbGridIntegerCtrl;
doubleDbGridControl: TJDbGridDoubleCtrl;
protected
{ Protected declarations }
procedure SelectEditor; override;
public
{ Public declarations }
constructor Create(TheOwner: TComponent); override;
destructor Destroy; override;
published
{ Published declarations }
end;
procedure Register;
implementation
procedure Register;
begin
{$I jdbgridcontrol_icon.lrs}
RegisterComponents('Data Controls', [TJDBGridControl]);
end;
{ TJDBGridControl }
procedure TJDBGridControl.SelectEditor;
begin
inherited SelectEditor;
if Editor <> nil then
begin
case SelectedField.DataType of
ftSmallint, ftInteger: Editor := integerDbGridControl.Editor(Self);
ftDate: Editor := dateDbGridControl.Editor(Self); // TODO: ftDateTime ftTime
ftCurrency, ftFloat, ftBCD: Editor := doubleDbGridControl.Editor(Self);
// TODO: strings?
end;
end;
end;
constructor TJDBGridControl.Create(TheOwner: TComponent);
begin
inherited Create(TheOwner);
dateDbGridControl := TJDbGridDateCtrl.Create;
SelectEditor;
integerDbGridControl := TJDbGridIntegerCtrl.Create;
doubleDbGridControl := TJDbGridDoubleCtrl.Create;
end;
destructor TJDBGridControl.Destroy;
begin
dateDbGridControl.Free;
integerDbGridControl.Free;
doubleDbGridControl.Free;
inherited Destroy;
end;
end.

View File

@ -0,0 +1,49 @@
LazarusResources.Add('tjdbgridcontrol','PNG',[
#137'PNG'#13#10#26#10#0#0#0#13'IHDR'#0#0#0#24#0#0#0#24#8#6#0#0#0#224'w='#248#0
+#0#0#1'sRGB'#0#174#206#28#233#0#0#0#6'bKGD'#0#255#0#255#0#255#160#189#167#147
+#0#0#0#9'pHYs'#0#0#11#19#0#0#11#19#1#0#154#156#24#0#0#0#7'tIME'#7#219#9#20#16
+#18#26#255#246#206','#0#0#3#246'IDATH'#199#205#149'_L[U'#28#199'?'#23#26'`'
+#225'O'#11#27't'#197#177#133'f'#27#148'A'#209#153#193#22#196#145'e3l{(Y'#140
+'4q'#178#196'Db'#226#147#241'aDG'#178',.'#218#140'D'#231#166#209'L'#30'x'#152
+#217#147#177#219#18#163#200#164#2#153#27#130#161#22'A'#152'EJ'#219#155#20'&'
+#5'Zho{'#239#245'aiC'#217'p'#211#185#196'or'#30#206#249#222's'#190#247#251
+#253#253#238'='#130#162'('#8#130#192#147#130#160#170'jrr'#165'OT/]w'#223#247
+#144'*K'#28#217'9'#143'47>o0'#24#242#221'n'#183''''#24#12#190#4'L'#235't'#186
+#1#163#209'h'#20'Eq'#222#231#243#189#231'r'#185'>q8'#28#225#20#129#213#7#159
+#127#163#154#202#173'9'#184'<!'#2#193'('#226#221'07'#191#251#146#157#250'4'
+#154#155#155#9#135#195'x'#189'^z{{'#167'$I'#242#182#180#180#212'h4'#154'LQ'
+#20#25#26#26#162#187#187#251#156#223#239'?544$'#1'h'#0'.]wc'#222'Q@'#169'~'#3
+#129'`'#20#23#16#8'F'#9',H'#252#252#211#143'd'#197#2#212'7'#28#231#173#211#31
+'1?'#227#228#169'b'#3'UUU'#165#162'('#150'vtt'#224#247#251#229#220#220#220'o'
+#155#154#154'v'#149#149#149#181#250'|'#190'~'#224'jR'#192'X'#146#135's'#242
+'O'#156#147'P'#164'3'#2#16'X'#144#8#4#163#252'19'#138#185'$'#155#139'_M"'#230
+#28'BY'#25#196'j'#181#146#159#159'O('#20'bvv'#150#238#249'sir'#186#255#240
+#236#236#236#235'Z'#173#246'CA'#16#158'K'#17#0#216'WUH'#145'6'#131#181'5XY'
+#204'$'#223''''#178#163#166#134#200#173#175#17'Q'#176#217'ldgg'#3#16#14#135
+')>&'#9#165'z'#19#253#209#143'?'#213#249#246#7'c'#177#216'Tb'#191#6#192'='
+#179#136'^W'#8#192';/'#151's'#192#188'1Y'#131#209#241't'#6#174'}'#142'fa'#140
+#163#7'j'#217#208#184#23#199#202#7'('#242'"'#146#18'''&'#203#20#23'l'#199#180
+#185#150#165'H'#152#145'2'#187'6'#222#175's'#164#8#24'K'#242#184'=:'#135#172
+#168'Tn+Oq'#176'Q'#191#133#138#134'W'#232#185#246#25#197#133'Z'#178#178'2'#16
+'j%'#14'U'#158'@V'#21'dEFA'#197#191'0C'#213#150':B'#210#138#16'<'#238#24'1'
+#191#155#150#225'<'#165#168#201#136'jvm'#162'H'#155#193#217#203#227#156#189
+#188#182'Q5'#236'{'#241'4'#225#136'L('#18'G'#141#247'!'#171#10#211'w'''#137
+')q'#226'J'#140#152#28'c1'#186#196#211'%'#245#132'b'#203#154'[S'#253#17' s'
+#221#136#218#218'.'#164'H'#196']'#144#201#189#225#221#30'!.'#199#209#231'm%'
+#174#200#200#170#130#184#224#161' g3'#195'3'#3'8'#239'L'#176','#163'{hD'#13
+#13#229#184#221#243'46>'#203#204#140'7'#185'~~,J'#215#205#14#162#138'D4.a'
+#220'T'#193'^'#227#11#12'N'#247'3'#225#191#131'%'#189#157'C'#7#205#203#128' '
+#168#170#202'k'#23#127'Q'#245#186'L'#138#180#25#216#251'}'#0#236#17#134#31
+#249'w'#240'M'#246#219'To'#171'e'#228#183#9#14#202'o'#146#142#134#163#135#171
+#169#223#255#188#160#1#152#246'-'#161#215'e'#174#137'h'#152#134#134'r<'#158
+'%Z['#143#165#28'h'#179'uq'#242#228#137#228#188#251#253'3|?'#209#203#239'g"h'
+#210'5'#216'l]I.'#13#224#213'#'#165#220#30#157'K'#190'}'#2'&'#211#189#184#236
+'v;f'#179#25#179#217#204#224#224'`'#146'O'#172#197#190'0'#160#189'Z'#193#238
+'gv'#167#240#201#26'X'#235#13#130#181#222#192#149'>QMt'#209#30#1#198#198#198
+#1#176'X,X,'#150#228#166#27'7~'#5#192#233't>0'#178#4#159't'#144#128#181#222
+' '#244#216#234#132#30'['#157#240'O'#28'$'#134#221'n'#231#254#6#255#27#252'['
+#7#143',`2'#149#227#241#12'b'#183#219'ioo'#7#160#179#179'3'#197#193'Z'#172
+#230#159#152#131'uk'#240' '#7#255#251#26#164#220#201#171#209#214'vA}'#156#203
+'>'#241'%'#175'+'#0#208#231#248#225#177'D'#30'*'#240'_'#224'/''a'#5#159#194
+' '#131'*'#0#0#0#0'IEND'#174'B`'#130
]);

View File

@ -0,0 +1,504 @@
{ jdbgridutils
Copyright (C) 2011 Julio Jiménez Borreguero
Contact: jujibo at gmail dot com
This library is free software; you can redistribute it and/or modify it
under the same terms as the Lazarus Component Library (LCL)
See the file license-jujiboutils.txt and COPYING.LGPL, included in this distribution,
for details about the license.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
}
unit jdbgridutils;
{$mode objfpc}{$H+}
interface
uses
Classes, SysUtils, Grids, Dialogs, LCLType, DBGrids, Controls, DB,
jcontrolutils;
type
{ TJDbGridDateCtrl }
TJDbGridDateCtrl = class(TObject)
private
Field: TField;
updated: boolean;
theValue: TDateTime;
fFormat: string;
function getFormat: string;
procedure myEditEnter(Sender: TObject);
procedure myEditOnEditingDone(Sender: TObject);
procedure formatInput;
procedure setFormat(const AValue: string);
procedure OnKeyPress(Sender: TObject; var key: char);
procedure OnKeyDown(Sender: TObject; var Key: word; Shift: TShiftState);
public
CellEditor: TStringCellEditor;
theGrid: TDBGrid;
function isNull: boolean;
property format: string read getFormat write setFormat;
constructor Create;
destructor Destroy; override;
function Editor(aGrid: TDBGrid): TStringCellEditor;
end;
{ TJDbGridIntegerCtrl }
TJDbGridIntegerCtrl = class(TObject)
private
theValue: integer;
updated: boolean;
Field: TField;
procedure myEditOnEnter(Sender: TObject);
procedure OnKeyPress(Sender: TObject; var key: char);
procedure OnKeyDown(Sender: TObject; var Key: word; Shift: TShiftState);
procedure myEditOnEditingDone(Sender: TObject);
function IsValidInteger(const Value: string): boolean;
public
CellEditor: TStringCellEditor;
theGrid: TDBGrid;
constructor Create;
destructor Destroy; override;
function Editor(aGrid: TDBGrid): TStringCellEditor;
end;
{ TJDbGridDoubleCtrl }
TJDbGridDoubleCtrl = class(TObject)
private
Field: TField;
updated: boolean;
theValue: double;
fDecimales: integer;
function getDecimales: integer;
procedure myEditOnEnter(Sender: TObject);
procedure myEditOnEditingDone(Sender: TObject);
procedure setDecimales(const AValue: integer);
procedure OnKeyPress(Sender: TObject; var key: char);
procedure OnKeyDown(Sender: TObject; var Key: word; Shift: TShiftState);
function IsValidFloat(const Value: string): boolean;
function textNumber(const aValue: string): string;
public
CellEditor: TStringCellEditor;
theGrid: TDBGrid;
property decimales: integer read getDecimales write setDecimales;
constructor Create;
destructor Destroy; override;
function Editor(aGrid: TDBGrid; aDecimals: integer = 2): TStringCellEditor;
end;
implementation
uses
Math;
{ TJDbGridDateCtrl }
function TJDbGridDateCtrl.getFormat: string;
begin
Result := fFormat;
end;
procedure TJDbGridDateCtrl.myEditEnter(Sender: TObject);
begin
Field := theGrid.SelectedField;
CellEditor.BoundsRect := theGrid.SelectedFieldRect;
CellEditor.Text := Field.AsString;
CellEditor.OnKeyPress := @OnKeyPress; // Recuperamos el control :-p
CellEditor.OnKeyDown := @OnKeyDown;
theValue := Field.AsDateTime;
updated := False;
CellEditor.SelectAll;
end;
procedure TJDbGridDateCtrl.myEditOnEditingDone(Sender: TObject);
begin
CellEditor.Caption := NormalizeDate(CellEditor.Caption, theValue);
if Length(CellEditor.Caption) = 0 then
theValue := 0
else
if IsValidDateString(CellEditor.Caption) then
begin
if (not updated) then
begin
theValue := StrToDate(CellEditor.Caption);
Field.DataSet.Edit;
Field.AsDateTime := theValue;
end;
end
else
begin
ShowMessage(CellEditor.Caption + ' no es una fecha válida');
CellEditor.Text := FormatDateTime(format, theValue);
end;
//formatInput;
end;
procedure TJDbGridDateCtrl.formatInput;
begin
if theValue <> 0 then
CellEditor.Caption := FormatDateTime(format, theValue);
end;
procedure TJDbGridDateCtrl.setFormat(const AValue: string);
begin
fFormat := AValue;
formatInput;
end;
procedure TJDbGridDateCtrl.OnKeyPress(Sender: TObject; var key: char);
begin
if not (Key in ['0'..'9', #8, #9, '.', '-', '/']) then
Key := #0;
end;
procedure TJDbGridDateCtrl.OnKeyDown(Sender: TObject; var Key: word;
Shift: TShiftState);
begin
if Length(CellEditor.Caption) <> 0 then
if (Key in [VK_RETURN, VK_TAB, VK_UP, VK_DOWN, VK_LEFT, VK_RIGHT]) and
(not IsValidDateString(NormalizeDate(CellEditor.Caption, theValue))) then
begin
ShowMessage(CellEditor.Caption + ' no es una fecha válida');
CellEditor.Text := FormatDateTime(format, theValue);
CellEditor.SelectAll;
Key := VK_UNKNOWN;
end
else
if key = VK_ESCAPE then
begin
if Field.IsNull then
CellEditor.Text := ''
else
CellEditor.Text := FormatDateTime(format, Field.AsDateTime);
updated := True;
theGrid.SetFocus; // No perder el foco
end
else
if Key in [VK_UP, VK_DOWN] then
begin
Key := VK_UNKNOWN;
end
else
if Key in [VK_RETURN, VK_TAB, VK_RIGHT, VK_LEFT] then
begin
CellEditor.Caption := NormalizeDate(CellEditor.Caption, theValue);
if Length(CellEditor.Caption) = 0 then
theValue := 0
else
if IsValidDateString(CellEditor.Caption) then
begin
theValue := StrToDate(CellEditor.Caption);
Field.DataSet.Edit;
Field.AsDateTime := theValue;
CellEditor.SelectAll;
updated := True;
end;
end;
end;
function TJDbGridDateCtrl.isNull: boolean;
begin
Result := theValue = 0;
end;
constructor TJDbGridDateCtrl.Create;
begin
inherited Create;
CellEditor := TStringCellEditor.Create(nil);
CellEditor.OnEnter := @myEditEnter;
CellEditor.OnKeyDown := @OnKeyDown;
CellEditor.OnEditingDone := @myEditOnEditingDone;
CellEditor.OnKeyPress := @OnKeyPress; // se sobreescribe por el Grid :(
format := ShortDateFormat;
end;
destructor TJDbGridDateCtrl.Destroy;
begin
CellEditor.Free;
inherited Destroy;
end;
function TJDbGridDateCtrl.Editor(aGrid: TDBGrid): TStringCellEditor;
begin
theGrid := aGrid;
Result := CellEditor;
end;
{ TJDbGridDoubleCtrl }
function TJDbGridDoubleCtrl.getDecimales: integer;
begin
Result := fDecimales;
end;
procedure TJDbGridDoubleCtrl.myEditOnEnter(Sender: TObject);
begin
Field := theGrid.SelectedField;
CellEditor.BoundsRect := theGrid.SelectedFieldRect;
CellEditor.Text := Field.AsString;
CellEditor.OnKeyPress := @OnKeyPress; // Recuperamos el control :-p
CellEditor.OnKeyDown := @OnKeyDown;
theValue := Field.AsFloat;
updated := False;
CellEditor.SelectAll;
end;
procedure TJDbGridDoubleCtrl.myEditOnEditingDone(Sender: TObject);
begin
if IsValidFloat(CellEditor.Caption) then
begin
if (not updated) then
begin
theValue := StrToFloat(CellEditor.Caption);
Field.DataSet.Edit;
//theValue := redondear(theValue, fDecimales);
Field.AsFloat := theValue;
// normalize value
Field.Value := textNumber(Field.DisplayText);
end;
end
else
begin
ShowMessage(CellEditor.Caption + ' no es un número válido');
CellEditor.Text := FloatToStr(theValue);
end;
end;
procedure TJDbGridDoubleCtrl.setDecimales(const AValue: integer);
begin
if (AValue >= 0) and (AValue < 5) then
fDecimales := AValue;
end;
procedure TJDbGridDoubleCtrl.OnKeyPress(Sender: TObject; var key: char);
begin
if (Key in ['.', ',']) then
Key := Decimalseparator;
if (key = DecimalSeparator) and (Pos(key, CellEditor.Caption) > 0) then
key := #0;
if not (Key in ['0'..'9', DecimalSeparator, '+', '-', #8, #9]) then
Key := #0;
if (Key = DecimalSeparator) and (fDecimales = 0) then
Key := #0;
end;
procedure TJDbGridDoubleCtrl.OnKeyDown(Sender: TObject; var Key: word;
Shift: TShiftState);
begin
if (Key in [VK_RETURN, VK_TAB, VK_UP, VK_DOWN, VK_LEFT, VK_RIGHT]) and
(not IsValidFloat(CellEditor.Caption)) then
begin
ShowMessage(CellEditor.Caption + ' no es número válido');
CellEditor.Text := FloatToStr(theValue);
CellEditor.SelectAll;
Key := VK_UNKNOWN;
end
else
if key = VK_ESCAPE then
begin
if Field.IsNull then
CellEditor.Text := ''
else
CellEditor.Text := FloatToStr(Field.AsFloat);
//CellEditor.Text := CurrToStr(redondear(Field.AsCurrency, fDecimales));
updated := True;
theGrid.SetFocus; // No perder el foco
end
else
if key in [VK_UP, VK_DOWN] then
begin
Key := VK_UNKNOWN;
end
else
if Key in [VK_RETURN, VK_TAB] then
begin
if IsValidFloat(CellEditor.Caption) then
begin
theValue := StrToFloat(CellEditor.Caption);
Field.DataSet.Edit;
Field.AsFloat := theValue;//redondear(theValue, fDecimales);
// normalize value
Field.Value := textNumber(Field.DisplayText);
CellEditor.Text := Field.AsString;
updated := True;
end;
end;
end;
function TJDbGridDoubleCtrl.IsValidFloat(const Value: string): boolean;
begin
if StrToFloatDef(Value, MaxDouble) = MaxDouble then
Result := False
else
Result := True;
end;
function TJDbGridDoubleCtrl.textNumber(const aValue: string): string;
var
i: integer;
aText: string;
begin
// Because there is no way to know the number scale (or I don't know how
// use display format to get a valid number with the desired scale (decimals)
// so if display format is 0.00 we'll get a number rounded to two decimals
// This is a bit tricky but works mostly...
aText := '';
if Length(aValue) = 0 then
aText := aValue
else
begin
if aValue[1] = '-' then
aText := '-'; // negative number?
for i := 1 to length(aValue) do
if aValue[i] in ['0'..'9', DecimalSeparator] then
aText += aValue[i];
end;
Result := aText;
end;
constructor TJDbGridDoubleCtrl.Create;
begin
inherited Create;
CellEditor := TStringCellEditor.Create(nil);
CellEditor.OnEnter := @myEditOnEnter;
CellEditor.OnKeyDown := @OnKeyDown;
CellEditor.OnEditingDone := @myEditOnEditingDone;
fDecimales := 2;
end;
destructor TJDbGridDoubleCtrl.Destroy;
begin
CellEditor.Free;
inherited Destroy;
end;
function TJDbGridDoubleCtrl.Editor(aGrid: TDBGrid;
aDecimals: integer): TStringCellEditor;
begin
decimales := aDecimals;
theGrid := aGrid;
Result := CellEditor;
end;
{ TJDbGridIntegerCtrl }
procedure TJDbGridIntegerCtrl.myEditOnEnter(Sender: TObject);
begin
Field := theGrid.SelectedField;
CellEditor.BoundsRect := theGrid.SelectedFieldRect;
CellEditor.Text := Field.AsString;
CellEditor.OnKeyPress := @OnKeyPress; // Recuperamos el control :-p
CellEditor.OnKeyDown := @OnKeyDown;
theValue := Field.AsInteger;
CellEditor.SelectAll;
updated := False;
end;
procedure TJDbGridIntegerCtrl.OnKeyPress(Sender: TObject; var key: char);
begin
if not (Key in ['0'..'9', #8, #9, '-']) then
Key := #0;
end;
procedure TJDbGridIntegerCtrl.OnKeyDown(Sender: TObject; var Key: word;
Shift: TShiftState);
begin
if (Key in [VK_RETURN, VK_TAB, VK_UP, VK_DOWN, VK_LEFT, VK_RIGHT]) and
(not IsValidInteger(CellEditor.Caption)) then
begin
ShowMessage(CellEditor.Caption + ' no es un número válido');
CellEditor.Text := IntToStr(theValue);
CellEditor.SelectAll;
Key := VK_UNKNOWN;
end
else
if (Key = VK_ESCAPE) then
begin
if Field.IsNull then
CellEditor.Text := ''
else
CellEditor.Text := IntToStr(Field.AsInteger);
updated := True;
theGrid.SetFocus; // No perder el foco
end
else
if key in [VK_UP, VK_DOWN] then
begin
Key := VK_UNKNOWN;
end
else
if Key in [VK_RETURN, VK_TAB] then
begin
if IsValidInteger(CellEditor.Caption) then
begin
theValue := StrToInt(CellEditor.Caption);
Field.DataSet.Edit;
Field.AsInteger := theValue;
updated := True;
end;
end;
end;
procedure TJDbGridIntegerCtrl.myEditOnEditingDone(Sender: TObject);
begin
if IsValidInteger(CellEditor.Caption) then
begin
if (not updated) then
begin
theValue := StrToInt(CellEditor.Caption);
Field.DataSet.Edit;
Field.AsInteger := theValue;
end;
end
else
begin
ShowMessage(CellEditor.Caption + ' no es un número válido');
CellEditor.Text := IntToStr(theValue);
end;
end;
function TJDbGridIntegerCtrl.IsValidInteger(const Value: string): boolean;
begin
if StrToIntDef(Value, MaxInt) = MaxInt then
Result := False
else
Result := True;
end;
constructor TJDbGridIntegerCtrl.Create;
begin
inherited Create;
CellEditor := TStringCellEditor.Create(nil);
CellEditor.OnEnter := @myEditOnEnter;
CellEditor.OnKeyDown := @OnKeyDown;
CellEditor.OnEditingDone := @myEditOnEditingDone;
CellEditor.OnKeyPress := @OnKeyPress; // se sobreescribe por el Grid :(
end;
destructor TJDbGridIntegerCtrl.Destroy;
begin
CellEditor.Free;
inherited Destroy;
end;
function TJDbGridIntegerCtrl.Editor(aGrid: TDBGrid): TStringCellEditor;
begin
theGrid := aGrid;
Result := CellEditor;
end;
end.

View File

@ -0,0 +1,85 @@
object Form1: TForm1
Left = 311
Height = 347
Top = 162
Width = 419
Caption = 'Form1'
ClientHeight = 347
ClientWidth = 419
OnCreate = FormCreate
LCLVersion = '0.9.31'
object DBNavigator1: TDBNavigator
Left = 8
Height = 25
Top = 60
Width = 241
BevelOuter = bvNone
ChildSizing.EnlargeHorizontal = crsScaleChilds
ChildSizing.EnlargeVertical = crsScaleChilds
ChildSizing.ShrinkHorizontal = crsScaleChilds
ChildSizing.ShrinkVertical = crsScaleChilds
ChildSizing.Layout = cclLeftToRightThenTopToBottom
ChildSizing.ControlsPerLine = 100
ClientHeight = 25
ClientWidth = 241
DataSource = Datasource1
Options = []
TabOrder = 0
end
object JDBGridControl1: TJDBGridControl
Left = 8
Height = 192
Top = 112
Width = 392
Color = clWindow
Columns = <
item
Title.Caption = 'ID'
Title.PrefixOption = poNone
FieldName = 'ID'
end
item
Title.Caption = 'DATE'
Title.PrefixOption = poNone
FieldName = 'DATE'
end
item
Title.Caption = 'QUANTITY'
Title.PrefixOption = poNone
Width = 150
FieldName = 'QUANTITY'
DisplayFormat = '#,0.00000€'
end>
DataSource = Datasource1
TabOrder = 1
end
object MemDataset1: TMemDataset
Active = True
FieldDefs = <
item
Name = 'ID'
DataType = ftInteger
Precision = 0
Size = 0
end
item
Name = 'DATE'
DataType = ftDate
Precision = 0
Size = 0
end
item
Name = 'QUANTITY'
DataType = ftFloat
Precision = 0
Size = 0
end>
left = 232
top = 8
end
object Datasource1: TDatasource
DataSet = MemDataset1
left = 324
top = 7
end
end

View File

@ -0,0 +1,53 @@
unit main;
{$mode objfpc}{$H+}
interface
uses
Classes, SysUtils, memds, db, FileUtil, Forms, Controls, Graphics, Dialogs,
DbCtrls, DBGrids, JDBGridControl;
type
{ TForm1 }
TForm1 = class(TForm)
Datasource1: TDatasource;
DBNavigator1: TDBNavigator;
JDBGridControl1: TJDBGridControl;
MemDataset1: TMemDataset;
procedure FormCreate(Sender: TObject);
private
{ private declarations }
public
{ public declarations }
end;
var
Form1: TForm1;
implementation
{$R *.lfm}
{ TForm1 }
procedure TForm1.FormCreate(Sender: TObject);
var
i: integer;
begin
// populate the memDataset
for i := 1 to 10 do
begin
MemDataset1.Append;
MemDataset1.FieldByName('ID').AsInteger := i;
MemDataset1.FieldByName('DATE').AsDateTime := Now;
MemDataset1.FieldByName('QUANTITY').AsFloat := i * i * i;
MemDataset1.Post;
end;
MemDataset1.First;
end;
end.

View File

@ -0,0 +1,85 @@
<?xml version="1.0"?>
<CONFIG>
<ProjectOptions>
<Version Value="9"/>
<General>
<MainUnit Value="0"/>
<ResourceType Value="res"/>
<UseXPManifest Value="True"/>
<Icon Value="0"/>
</General>
<i18n>
<EnableI18N LFM="False"/>
</i18n>
<VersionInfo>
<StringTable ProductVersion=""/>
</VersionInfo>
<BuildModes Count="1">
<Item1 Name="Default" Default="True"/>
</BuildModes>
<PublishOptions>
<Version Value="2"/>
<DestinationDirectory Value="$(TestDir)/testgridctr/"/>
<IncludeFileFilter Value="*.(pas|pp|inc|lfm|lpr|lrs|lpi|lpk|sh|xml)"/>
<ExcludeFileFilter Value="*.(bak|ppu|o|so);*~;backup"/>
</PublishOptions>
<RunParams>
<local>
<FormatVersion Value="1"/>
<LaunchingApplication PathPlusParams="/usr/bin/xterm -T 'Lazarus Run Output' -e $(LazarusDir)/tools/runwait.sh $(TargetCmdLine)"/>
</local>
</RunParams>
<RequiredPackages Count="4">
<Item1>
<PackageName Value="jujibocontrols"/>
</Item1>
<Item2>
<PackageName Value="FCL"/>
</Item2>
<Item3>
<PackageName Value="MemDSLaz"/>
</Item3>
<Item4>
<PackageName Value="LCL"/>
</Item4>
</RequiredPackages>
<Units Count="2">
<Unit0>
<Filename Value="testgridctr.lpr"/>
<IsPartOfProject Value="True"/>
<UnitName Value="testgridctr"/>
</Unit0>
<Unit1>
<Filename Value="main.pas"/>
<IsPartOfProject Value="True"/>
<ComponentName Value="Form1"/>
<ResourceBaseClass Value="Form"/>
<UnitName Value="main"/>
</Unit1>
</Units>
</ProjectOptions>
<CompilerOptions>
<Version Value="10"/>
<Target>
<Filename Value="testgridctr"/>
</Target>
<SearchPaths>
<IncludeFiles Value="$(ProjOutDir)"/>
<UnitOutputDirectory Value="lib/$(TargetCPU)-$(TargetOS)"/>
</SearchPaths>
<Linking>
<Debugging>
<GenerateDebugInfo Value="True"/>
<DebugInfoType Value="dsAuto"/>
</Debugging>
<Options>
<Win32>
<GraphicApplication Value="True"/>
</Win32>
</Options>
</Linking>
<Other>
<CompilerPath Value="$(CompPath)"/>
</Other>
</CompilerOptions>
</CONFIG>

View File

@ -0,0 +1,21 @@
program testgridctr;
{$mode objfpc}{$H+}
uses
{$IFDEF UNIX}{$IFDEF UseCThreads}
cthreads,
{$ENDIF}clocale,{$ENDIF}
Interfaces, // this includes the LCL widgetset
Forms, memdslaz, main
{ you can add units after this };
{$R *.res}
begin
RequireDerivedFormResource := True;
Application.Initialize;
Application.CreateForm(TForm1, Form1);
Application.Run;
end.