unit DateEdit;
interface
uses
VCL.ExtCtrls,
VCL.StdCtrls, Classes, DateUtils, SysUtils,
VCL.Controls,
VCL.Forms;
type
TDateFormatStyle = (fsDDMMYYYY, fsYYYYMMDD, fsMMDDYYYY);
TFormatStyle = fsDDMMYYYY..fsMMDDYYYY;
TCustomDateEdit =
class(TPanel)
private
FDate: Integer;
FMinDate: Integer;
FMaxDate: Integer;
FFormatStyle: TFormatStyle;
FFourDigit: Boolean;
FAutoExpansionYear: Boolean;
FEnabled: Boolean;
dIndex: Byte;
mIndex: Byte;
yIndex: Byte;
FEdit:
Array [0..2]
of TEdit;
function CheckDate(
const y,m,d: Word): Boolean;
procedure SetDate(Value: Integer);
procedure SetMinDate(Value: Integer);
procedure SetMaxDate(Value: Integer);
procedure SetFormatStyle(Value: TFormatStyle);
procedure SetFourDigit(Value: Boolean);
procedure SetAutoExpansionYear(Value: Boolean);
function BoolToInt(B: Boolean): Integer;
protected
procedure SetEnabled(Value: Boolean);
override;
procedure PanelExit(Sender: TObject);
procedure FEditKeyPress(Sender: TObject;
var Key: Char);
procedure FEditExit(Sender: TObject);
property Date: Integer
read FDate
write SetDate
default 0;
property MinDate: Integer
read FMinDate
write SetMinDate
default 0;
property MaxDate: Integer
read FMaxDate
write SetMaxDate
default 0;
property FormatStyle: TFormatStyle
read FFormatStyle
write SetFormatStyle
default fsDDMMYYYY;
property FourDigit: Boolean
read FFourDigit
write SetFourDigit
default True;
property AutoExpansionYear: Boolean
read FAutoExpansionYear
write SetAutoExpansionYear
default False;
property Enabled: Boolean
read FEnabled
write SetEnabled
default True;
// property Hint: Integer read FHint write SetHint default 0;
public
constructor Create(AOwner: TComponent);
override;
destructor Destroy;
override;
published
end;
TDateEdit =
class(TCustomDateEdit)
published
property AutoExpansionYear;
property Caption;
property Color;
property Date;
property Enabled;
property FormatStyle;
property FourDigit;
property Hint;
property MinDate;
property MaxDate;
property ShowHint;
property Visible;
end;
procedure Register;
implementation
uses
VCL.Dialogs,
VCL.Graphics;
procedure Register;
begin
RegisterComponents('
Test', [TDateEdit]);
end;
function TCustomDateEdit.BoolToInt(B: Boolean): Integer;
begin
if B
then
result := 1
else
result := 0;
end;
function TCustomDateEdit.CheckDate(
const y,m,d: Word): Boolean;
var dAllow: Integer;
begin
Result:= True;
if Result
and (m>12)
then begin
MessageDLG('
Ungültige Monatsangabe!',mtError,[mbOk],0);
FEdit[mIndex].SetFocus;
Result:= False;
end;
if Result
then begin
if m=0
then dAllow:= 31
else dAllow:= DaysInAMonth(y,m);
if d>dAllow
then begin
MessageDLG('
Ungültiger Tag im Monat!',mtError,[mbOk],0);
FEdit[dIndex].SetFocus;
Result:= False;
end;
end;
if Result
and (y>0)
and FFourDigit
and (y<1000)
then begin
MessageDLG('
Ungültige Jahresangabe! Da FourDigit gesetzt wurde, muss die Jahreszahl 4 Zeichen lang sein.',mtError,[mbOk],0);
FEdit[yIndex].SetFocus;
Result:= False;
end;
if Result
and (y>0)
and (y*10000+m*100+d<FMinDate)
then begin
MessageDLG('
Das Datum ist kleiner als das angegebene Mindestdatum!',mtError,[mbOk],0);
FEdit[yIndex].SetFocus;
Result:= False;
end;
if Result
and (FMaxDate>0)
and (y*10000+m*100+d>FMaxDate)
then begin
MessageDLG('
Das Datum ist größer als das angegebene Höchstdatum!',mtError,[mbOk],0);
FEdit[yIndex].SetFocus;
Result:= False;
end;
end;
constructor TCustomDateEdit.Create(AOwner: TComponent);
var x: Integer;
begin
inherited Create(AOwner);
Color:= clBtnFace;
BevelOuter:= bvNone;
Height:= 25;
Constraints.MaxWidth:= Width;
Constraints.MinWidth:= Width;
Width:= 85;
Constraints.MaxHeight:= Height;
Constraints.MinHeight:= Height;
UseDockManager:= True;
OnExit:= PanelExit;
//Self.Enabled := True;
ControlStyle := ControlStyle - [csSetCaption];
// <- kein Text
for x:= 0
to Length(FEdit)-1
do begin
FEdit[x]:= TEdit.Create(self);
// <- self
FEdit[x].Parent:= Self;
FEdit[X].SetSubComponent(True);
// <- SetSubComponent
FEdit[x].Tag:= x;
FEdit[x].Top:= 2;
FEdit[x].Left:= 2+(x*24);
FEdit[x].Width:= 21+(Trunc(x/2)*12);
FEdit[x].MaxLength:= 2+(Trunc(x/2)*2);
FEdit[x].OnKeyPress:= FEditKeyPress;
FEdit[x].OnExit:= FEditExit;
end;
dIndex:= 0;
mIndex:= 1;
yIndex:= 2;
Caption:= '
';
Enabled := True;
// <- Enabled
end;
destructor TCustomDateEdit.Destroy;
var x: Integer;
begin
for x:= 0
to Length(FEdit)-1
do FEdit[x].Free;
inherited Destroy;
end;
procedure TCustomDateEdit.FEditKeyPress(Sender: TObject;
var Key: Char);
var w: Word;
begin
w:= (Sender
as TEdit).Tag;
case Key
of
'
0'..'
9':
begin
if (Length(FEdit[w].Text)-FEdit[w].SelLength=FEdit[w].MaxLength-1)
and (w<2)
then
FEdit[w+1].SetFocus;
end;
'
.':
begin
if (FFormatStyle=fsDDMMYYYY)
and (w<2)
and (FEdit[w].Text<>'
')
then
FEdit[w+1].SetFocus;
Key:= #0;
end;
'
-':
begin
if (FFormatStyle=fsYYYYMMDD)
and (w<2)
and (FEdit[w].Text<>'
')
then
FEdit[w+1].SetFocus;
Key:= #0;
end;
'
/':
begin
if (FFormatStyle=fsMMDDYYYY)
and (w<2)
and (FEdit[w].Text<>'
')
then
FEdit[w+1].SetFocus;
Key:= #0;
end;
#8:
begin
if (FEdit[w].Text='
')
and (w>0)
then begin
FEdit[w-1].Text:= Copy(FEdit[w-1].Text,1,Length(FEdit[w-1].Text)-1);
FEdit[w-1].SetFocus;
FEdit[w-1].SelStart:= -1;
Key:= #0;
end;
end;
else Key:= #0;
end;
end;
procedure TCustomDateEdit.FEditExit(Sender: TObject);
var E: TEdit;
i: Integer;
begin
E:= (Sender
as TEdit);
i:= StrToInt(E.Text);
if FAutoExpansionYear
and (E.Tag=yIndex)
and (i>0)
and (Length(E.Text)<3)
then begin
if i<50
then Inc(i,2000)
else Inc(i,1900);
E.Text:= IntToStr(i);
end;
end;
procedure TCustomDateEdit.PanelExit(Sender: TObject);
var d,m,y: Word;
begin
d:= StrToInt(FEdit[dIndex].Text);
m:= StrToInt(FEdit[mIndex].Text);
y:= StrToInt(FEdit[yIndex].Text);
if CheckDate(y,m,d)
then FDate:= d+m*100+y*10000;
end;
procedure TCustomDateEdit.SetDate(Value: Integer);
var d,m,y: Word;
i: Integer;
begin
y:= Value
div 10000;
i:= Value
mod 10000;
m:= i
div 100;
d:= i
mod 100;
FEdit[dIndex].Text:= FormatFloat('
00',d);
FEdit[mIndex].Text:= FormatFloat('
00',m);
FEdit[yIndex].Text:= IntToStr(y);
if CheckDate(y,m,d)
then FDate:= Value;
end;
procedure TCustomDateEdit.SetMinDate(Value: Integer);
begin
FMinDate:= Value;
end;
procedure TCustomDateEdit.SetMaxDate(Value: Integer);
begin
FMaxDate:= Value;
end;
procedure TCustomDateEdit.SetFormatStyle(Value: TFormatStyle);
var y,m,d:
string;
i,Pix: Integer;
IsYear: Boolean;
begin
if FFormatStyle<>Value
then begin
FFormatStyle:= Value;
d:= FEdit[dIndex].Text;
m:= FEdit[mIndex].Text;
y:= FEdit[yIndex].Text;
if FFormatStyle=fsDDMMYYYY
then begin
dIndex:= 0;
mIndex:= 1;
yIndex:= 2;
end
else if FFormatStyle=fsMMDDYYYY
then begin
dIndex:= 1;
mIndex:= 0;
yIndex:= 2;
end
else begin
dIndex:= 2;
mIndex:= 1;
yIndex:= 0;
end;
Pix:= 2;
for i:= 0
to 2
do begin
IsYear:= i=yIndex;
FEdit[i].Left:= Pix;
FEdit[i].Width:= 21+(BoolToInt(IsYear)*12);
FEdit[i].MaxLength:= 2+(BoolToInt(IsYear)*2);
Inc(Pix,FEdit[i].Width+3);
if i=dIndex
then FEdit[i].Text:= d
else if i=mIndex
then FEdit[i].Text:= m
else FEdit[i].Text:= y;
end;
end;
end;
procedure TCustomDateEdit.SetFourDigit(Value: Boolean);
begin
FFourDigit:= Value;
end;
procedure TCustomDateEdit.SetAutoExpansionYear(Value: Boolean);
begin
FAutoExpansionYear:= Value;
end;
procedure TCustomDateEdit.SetEnabled(Value: Boolean);
var i: Integer;
begin
FEnabled:= Value;
for i:= 0
to 2
do FEdit[i].Enabled:= Value;
end;
end.