저는 C++ Bulider 4.0, 5.0 사용자 입니다.
-----------------------------------------
업무용 프로그램에서 숫자를 많이 사용하고 있습니다.
Numedit.pas를 컴포넌트 작성후 사용하고 있음.
Windows 98, Me, XP : C++ Bulider 4.0에서는 정상작동
C++ Bulider 5.0에서는 Error 발생함.
컴포넌트는 완성되었으나 직접사용하면 Error발생함,...
고수님들 부탁합니다.
+------------------------------------+
| 좋은방법 부탁 드립니다. |
| 삼겹살에 소주한잔 대접하겠음,... |
+------------------------------------+
예 : 586
123,000
23,000,000
125,255,000
//NumEdit 수정
{작성자 : 김상면}
{수정자 : 호수영}
{수정자 : 손상익} //2001-12-15 <C++ Builder 사용자>, 02-3424-8838
{초기값:Value
소수점:Scale -> 0, 1, 2, 3 가능
정 렬:Alignment -> 좌측, 중앙, 우측}
{지가 만들어 놓고도 다시 보니깐 뭐가 뭔지 잘 모르것 네요...쩝..^_O
주석달기가 습관이 안돼시리...(깊이 반성..)
이 소스는 마음대로 수정하셔서 다시 쓰셔도 좋습니다...
기능을 추가하신 분들은 한델 자료실(
http://www.delphi.co.kr/)에 꼭 수정 소스 꼭 올려 주세요...
꼭 부탁입니다...
아참 이거 버그라고 해야돼나...
OnKeyDown Event에서 펑션키 안먹습니다...
OnKeyDown Event에서 펑션키 쓰실 분은 OnKeyUp에 정의하세요...}
unit NumEdit;
interface
uses
Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
StdCtrls;
type
TNumEdit = class(TCustomEdit)
private
FAlignment: TAlignment;
FTextValue: Extended;
OTextValue: Extended;
OCheck: Boolean;
KeyCheck: Boolean;
FScale: Integer;
ScaleFormat: String;
ColPos: Integer;
ColPosL: Integer;
ColCheck: Boolean;
procedure SetTextValue(Value: Extended);
procedure FormatText;
procedure UnFormatText;
procedure WMSetFocus (var Message: TWMSetFocus); message WM_SETFOCUS;
procedure CMExit(var Message: TCMExit); message CM_EXIT;
protected
procedure CreateParams(var Params: TCreateParams); override;
Procedure SetAlignment(Value: TAlignment);
Procedure SetScale(Value: Integer);
procedure KeyDown(var Key: Word; Shift: TShiftState); override;
procedure KeyPress(var Key: Char); override;
procedure Change; override;
procedure KeyUp(var Key: Word; Shift: TShiftState); override;
public
constructor Create(AOwner: TComponent); override;
published
property Alignment: TAlignment read FAlignment write SetAlignment default taRightJustify;
property Anchors;
property AutoSelect;
property AutoSize;
property BiDiMode;
property BorderStyle;
property CharCase;
property Color;
property Constraints;
property Ctl3D;
property DragCursor;
property DragKind;
property DragMode;
property Enabled;
property Font;
property HideSelection;
property ImeMode;
property ImeName;
property MaxLength;
property OEMConvert;
property ParentBiDiMode;
property ParentColor;
property ParentCtl3D;
property ParentFont;
property ParentShowHint;
property PasswordChar;
property PopupMenu;
property ReadOnly;
property Scale: Integer read FScale write SetScale default 0;
property ShowHint;
property TabOrder;
property TabStop;
// property Text;
property TextValue: Extended read FTextValue write SetTextValue;
property Visible;
property OnChange;
property OnClick;
property OnDblClick;
property OnDragDrop;
property OnDragOver;
property OnEndDock;
property OnEndDrag;
property OnEnter;
property OnExit;
property OnKeyDown;
property OnKeyPress;
property OnKeyUp;
property OnMouseDown;
property OnMouseMove;
property OnMouseUp;
property OnStartDock;
property OnStartDrag;
end;
procedure Register;
implementation
procedure Register;
begin
RegisterComponents('Power', [TNumEdit]);
end;
constructor TNumEdit.Create(AOwner : TComponent);
begin
inherited Create(AOwner);
ColCheck := False;
OCheck := True;
KeyCheck := False; // Text := '' 일때 TextValue 초기값 넣기 위해서..
AutoSize := False;
//ParentCtl3D := False;
//Ctl3D := False;
//Height := 18;
//Font.Name := '굴림체';
//Font.Size := 10;
SetAlignment(taRightJustify);
SetScale(FScale);
end;
procedure TNumEdit.CreateParams(var Params: TCreateParams);
const
Alignments: array[TAlignment] of Longint = (ES_LEFT, ES_RIGHT, ES_CENTER);
begin
inherited CreateParams(Params);
Params.Style := Params.Style or ES_MULTILINE or Alignments[FAlignment];
end;
procedure TNumEdit.SetAlignment(Value: TAlignment);
begin
if FAlignment <> Value then
begin
FAlignment := Value;
RecreateWnd;
end;
end;
procedure TNumEdit.SetTextValue(Value: Extended);
begin
if FTextValue <> Value then
begin
FTextValue := Value;
if OCheck and (KeyCheck = False)then // 초기값으로 돌리는 루틴...
OTextValue := FTextValue;
OCheck := False;
end;
FormatText;
end;
procedure TNumEdit.SetScale(Value: Integer);
begin
if FScale <> Value then
FScale := Value;
case FScale of
0 : ScaleFormat := '#,##0';
1 : ScaleFormat := '#,##0.0';
2 : ScaleFormat := '#,##0.00';
3 : ScaleFormat := '#,##0.000';
end;
SetTextValue(FTextValue);
end;
procedure TNumEdit.FormatText;
begin
Text := FormatFloat(ScaleFormat, TextValue);
end;
procedure TNumEdit.UnFormatText;
var
TmpText : String;
Tmp : Byte;
begin
TmpText := '';
for Tmp := 1 to Length(Text) do
if Text[Tmp] in ['0'..'9','-','.'] then
TmpText := TmpText + Text[Tmp];
try
if (length(TmpText) <> 0) then
TextValue := StrToFloat(TmpText)
else
TextValue := 0;
except
MessageBeep(mb_IconAsterisk);
end;
end;
procedure TNumEdit.WMSetFocus(var Message: TWMSETFOCUS);
begin
SelectAll;
inherited;
if FScale = 0 then
SelStart := Length(Text) - FScale
else
SelStart := Length(Text) - FScale - 1;
SelectAll;
end;
procedure TNumEdit.KeyDown(var Key: Word; Shift: TShiftState);
begin
if Key in [VK_RIGHT, VK_LEFT] then
begin
ColPosL := Length(Text);
ColPos := ColPosL - SelStart + 1;
end
else if Key in [VK_DELETE] then
begin
ColCheck := True;
ColPosL := Length(Text);
if FScale = 0 then
ColPos := ColPosL - SelStart - 1
else
begin
if (SelStart = (Length(Text) - FScale - 1)) then
Key := 0; // 소숫점 앞쪽에 커서가 있을 경우 ..
if (SelStart <> (Length(Text) - FScale - 1)) then
begin
if SelStart < (Length(Text) - FScale) then // 소숫점 왼쪽 자리..
ColPos := ColPosL - SelStart - 1
else if SelStart >= (Length(Text) - FScale) then //소숫점 뒤 한자리
ColPos := ColPosL - SelStart;
end;
end;
end
else if (KEY IN [VK_RETURN, VK_PRIOR, VK_NEXT, VK_DOWN, VK_UP, VK_ESCAPE]) then
begin
inherited KeyDown( Key ,shift);
key := 0;
end;
end;
procedure TNumEdit.KeyPress(var Key: Char);
begin
inherited KeyPress(Key);
KeyCheck := True;
if not(Key in ['0'..'9', '-', '.', #8]) then
Key := #0;
if Key in ['0'..'9'] then
begin
ColCheck := True;
ColPosL := Length(Text);
if FScale = 0 then
begin
if SelStart > 0 then
ColPos := ColPosL - SelStart
else ColPos := 0;
end
else
begin
if SelStart < (Length(Text) - FScale) then // 소숫점 왼쪽 자리..
ColPos := ColPosL - SelStart
else if SelStart >= (Length(Text) - FScale) then //소숫점 뒤 한자리
begin
SelStart := SelStart + 1;
SelLength := -1;
ColPos := ColPosL - SelStart - 1;
end;
end;
end;
if Key = #8 then
begin
ColCheck := True;
ColPosL := Length(Text);
if FScale = 0 then
ColPos := ColPosL - SelStart
else
begin
if SelStart < (Length(Text) - FScale) then
ColPos := ColPosL - SelStart
else if (SelStart = Length(Text) - FScale) then
Key := #0 // 소숫점 뒤에서 백스페이스 들어오면 널...
else if SelStart > (Length(Text) - FScale) then
begin
Key := #0;
SelLength := -1;
Key := '0';
end;
ColPos := ColPosL - SelStart;
end;
end;
if Key = '.' then
begin
if FScale = 0 then
Key := #0
else
begin
Key := #0;
SelStart := Length(Text) - FScale; // 소숫점 다음 자리로 커서 이동
end;
end;
if (Key in ['0'..'9', '-', '.', #8]) and
(Copy(Text, 1, 1) = '0') and (SelStart = 1) then
SelLength := -1;
end;
procedure TNumEdit.Change;
begin
if (Trim(Text) = '') and (KeyCheck = False) then // 초기값으로 돌리는 루틴...
TextValue := OTextValue;
end;
procedure TNumEdit.KeyUp(var Key: Word; Shift: TShiftState);
begin
inherited KeyUp(Key, Shift);
if ColCheck then
begin
UnFormatText;
SelStart := Length(Text) - ColPos;
ColCheck := False;
end;
end;
procedure TNumEdit.CMExit(var Message: TCMExit);
begin
KeyCheck := False;
UnFormatText;
FormatText;
inherited;
end;
end.