diff options
author | graemeg <graemeg@ae50a9b5-8222-0410-bf8d-8a13f76226bf> | 2009-03-20 14:28:21 +0000 |
---|---|---|
committer | graemeg <graemeg@ae50a9b5-8222-0410-bf8d-8a13f76226bf> | 2009-03-20 14:28:21 +0000 |
commit | 13ae577973bc4402f21ab6d547f423f2f95c5157 (patch) | |
tree | fc8564fe304fa808fc378c30739b7dd5669415d9 /src | |
parent | bc3cbd7679af7b609b5726f8f8ce269878b1bab6 (diff) | |
download | fpGUI-13ae577973bc4402f21ab6d547f423f2f95c5157.tar.xz |
* Minor X11 debugging improvements.
* Named internal components
* Introduced TfpgBaseCheckbox class.
* Refactored text drawing in ComboBox to a method that can be overridden in descendants.
* Implemented a new (experimental) Calendar Combo with Checkbox for optional date selection.
* Added Calendar Combo Check component to UI Designer.
* Fixed some missing properties from Calendar Combo component in UI Designer.
Diffstat (limited to 'src')
-rw-r--r-- | src/corelib/x11/fpg_x11.pas | 13 | ||||
-rw-r--r-- | src/gui/fpg_checkbox.pas | 57 | ||||
-rw-r--r-- | src/gui/fpg_combobox.pas | 28 | ||||
-rw-r--r-- | src/gui/fpg_listbox.pas | 3 | ||||
-rw-r--r-- | src/gui/fpg_popupcalendar.pas | 142 |
5 files changed, 204 insertions, 39 deletions
diff --git a/src/corelib/x11/fpg_x11.pas b/src/corelib/x11/fpg_x11.pas index 6aad85d0..a906ff2b 100644 --- a/src/corelib/x11/fpg_x11.pas +++ b/src/corelib/x11/fpg_x11.pas @@ -118,8 +118,6 @@ type TfpgWindowImpl = class; - { TfpgFontResourceImpl } - TfpgFontResourceImpl = class(TfpgFontResourceBase) private FFontData: PXftFont; @@ -949,7 +947,11 @@ begin {$IFDEF DEBUG} - WriteLn('Event ',GetXEventName(ev._type),': ', ev._type,' window: ', ev.xany.window); + w := FindWindowByHandle(ev.xany.window); + if not Assigned(w) then + WriteLn('Event ',GetXEventName(ev._type),'(', ev._type,') window: ', IntToHex(ev.xany.window,7)) + else + WriteLn('Event ',GetXEventName(ev._type),'(', ev._type,') window: ', IntToHex(ev.xany.window,7), ' name:', w.Name); // PrintKeyEvent(ev); { debug purposes only } {$ENDIF} @@ -989,11 +991,16 @@ begin msgp.keyboard.keycode := KeySymToKeycode(KeySym); msgp.keyboard.shiftstate := ConvertShiftState(ev.xkey.state); + // By default X11 sends keyboard event to window under mouse cursor. + // We need to get the corrected "focused" widget instead. kwg := FindKeyboardFocus; if kwg <> nil then w := kwg else begin + {$IFDEF DEBUG} + writeln('ERR: We couldn''t find keyboard focused window. Using event window instead!'); + {$ENDIF} w := FindWindowByHandle(ev.xkey.window); if not Assigned(w) then ReportLostWindow(ev); diff --git a/src/gui/fpg_checkbox.pas b/src/gui/fpg_checkbox.pas index 9e7c887e..95d591d1 100644 --- a/src/gui/fpg_checkbox.pas +++ b/src/gui/fpg_checkbox.pas @@ -1,7 +1,7 @@ { fpGUI - Free Pascal GUI Toolkit - Copyright (C) 2006 - 2008 See the file AUTHORS.txt, included in this + Copyright (C) 2006 - 2009 See the file AUTHORS.txt, included in this distribution, for details of the copyright. See the file COPYING.modifiedLGPL, included in this distribution, @@ -30,7 +30,7 @@ uses type - TfpgCheckBox = class(TfpgWidget) + TfpgBaseCheckBox = class(TfpgWidget) private FChecked: boolean; FOnChange: TNotifyEvent; @@ -42,25 +42,34 @@ type procedure SetChecked(const AValue: boolean); procedure SetFontDesc(const AValue: string); procedure SetText(const AValue: string); + procedure DoOnChange; protected procedure HandlePaint; override; procedure HandleLMouseDown(x, y: integer; shiftstate: TShiftState); override; procedure HandleLMouseUp(x, y: integer; shiftstate: TShiftState); override; procedure HandleKeyRelease(var keycode: word; var shiftstate: TShiftState; var consumed: boolean); override; + property Checked: boolean read FChecked write SetChecked default False; + property FontDesc: string read GetFontDesc write SetFontDesc; + property Text: string read FText write SetText; + property OnChange: TNotifyEvent read FOnChange write FOnChange; public constructor Create(AOwner: TComponent); override; destructor Destroy; override; property Font: TfpgFont read FFont; + end; + + + TfpgCheckBox = class(TfpgBaseCheckBox) published property BackgroundColor; - property Checked: boolean read FChecked write SetChecked default False; - property FontDesc: string read GetFontDesc write SetFontDesc; + property Checked; + property FontDesc; property ParentShowHint; property ShowHint; property TabOrder; - property Text: string read FText write SetText; + property Text; property TextColor; - property OnChange: TNotifyEvent read FOnChange write FOnChange; + property OnChange; property OnEnter; property OnExit; end; @@ -68,8 +77,10 @@ type function CreateCheckBox(AOwner: TComponent; x, y: TfpgCoord; AText: string): TfpgCheckBox; + implementation + function CreateCheckBox(AOwner: TComponent; x, y: TfpgCoord; AText: string): TfpgCheckBox; begin Result := TfpgCheckBox.Create(AOwner); @@ -79,9 +90,9 @@ begin Result.Width := Result.Font.TextWidth(Result.Text) + 24; end; -{ TfpgCheckBox } +{ TfpgBaseCheckBox } -procedure TfpgCheckBox.SetChecked(const AValue: boolean); +procedure TfpgBaseCheckBox.SetChecked(const AValue: boolean); begin if FChecked = AValue then Exit; //==> @@ -89,19 +100,19 @@ begin RePaint; end; -function TfpgCheckBox.GetFontDesc: string; +function TfpgBaseCheckBox.GetFontDesc: string; begin Result := FFont.FontDesc; end; -procedure TfpgCheckBox.SetFontDesc(const AValue: string); +procedure TfpgBaseCheckBox.SetFontDesc(const AValue: string); begin FFont.Free; FFont := fpgGetFont(AValue); RePaint; end; -procedure TfpgCheckBox.SetText(const AValue: string); +procedure TfpgBaseCheckBox.SetText(const AValue: string); begin if FText = AValue then Exit; //==> @@ -109,7 +120,13 @@ begin RePaint; end; -procedure TfpgCheckBox.HandlePaint; +procedure TfpgBaseCheckBox.DoOnChange; +begin + if Assigned(FOnChange) then + FOnChange(self); +end; + +procedure TfpgBaseCheckBox.HandlePaint; var r: TfpgRect; ty: integer; @@ -159,31 +176,29 @@ begin fpgStyle.DrawString(Canvas, tx, ty, FText, Enabled); end; -procedure TfpgCheckBox.HandleLMouseDown(x, y: integer; shiftstate: TShiftState); +procedure TfpgBaseCheckBox.HandleLMouseDown(x, y: integer; shiftstate: TShiftState); begin inherited HandleLMouseDown(x, y, shiftstate); FIsPressed := True; Repaint; end; -procedure TfpgCheckBox.HandleLMouseUp(x, y: integer; shiftstate: TShiftState); +procedure TfpgBaseCheckBox.HandleLMouseUp(x, y: integer; shiftstate: TShiftState); begin inherited HandleLMouseUp(x, y, shiftstate); FIsPressed := False; Checked := not FChecked; - if Assigned(FOnChange) then - FOnChange(self); + DoOnChange; end; -procedure TfpgCheckBox.HandleKeyRelease(var keycode: word; +procedure TfpgBaseCheckBox.HandleKeyRelease(var keycode: word; var shiftstate: TShiftState; var consumed: boolean); begin if (keycode = keySpace) or (keycode = keyReturn) or (keycode = keyPEnter) then begin consumed := True; Checked := not FChecked; - if Assigned(FOnChange) then - FOnChange(self); + DoOnChange; end; if consumed then @@ -192,7 +207,7 @@ begin inherited HandleKeyRelease(keycode, shiftstate, consumed); end; -constructor TfpgCheckBox.Create(AOwner: TComponent); +constructor TfpgBaseCheckBox.Create(AOwner: TComponent); begin inherited Create(AOwner); FText := 'CheckBox'; @@ -208,7 +223,7 @@ begin FOnChange := nil; end; -destructor TfpgCheckBox.Destroy; +destructor TfpgBaseCheckBox.Destroy; begin FFont.Free; inherited Destroy; diff --git a/src/gui/fpg_combobox.pas b/src/gui/fpg_combobox.pas index 06bc91a9..6e34704e 100644 --- a/src/gui/fpg_combobox.pas +++ b/src/gui/fpg_combobox.pas @@ -115,6 +115,7 @@ type protected FDropDown: TfpgPopupWindow; procedure DoDropDown; override; + procedure DoDrawText(const ARect: TfpgRect); virtual; function GetText: string; virtual; function HasText: boolean; virtual; procedure SetText(const AValue: string); virtual; @@ -167,8 +168,6 @@ uses fpg_listbox, math; -var - OriginalFocusRoot: TfpgWidget; type { This is the class representing the dropdown window of the combo box. } @@ -455,6 +454,7 @@ begin FCallerWidget := ACallerWidget; FListBox := CreateListBox(self, 0, 0, 80, 100); + FListbox.Name := '_ComboboxDropdownWindowListBox'; FListBox.PopupFrame := True; FListBox.Items.Assign(FCallerWidget.Items); FListBox.FocusItem := FCallerWidget.FocusItem; @@ -511,7 +511,6 @@ begin writeln('.... creating'); {$ENDIF} FreeAndNil(FDropDown); - OriginalFocusRoot := FocusRootWidget; FDropDown := TComboboxDropdownWindow.Create(nil, self); ddw := TComboboxDropdownWindow(FDropDown); @@ -547,6 +546,18 @@ begin end; end; +procedure TfpgBaseStaticCombo.DoDrawText(const ARect: TfpgRect); +begin + // Draw select item's text + if HasText then + fpgStyle.DrawString(Canvas, FMargin+1, FMargin, Text, Enabled) + else + begin + Canvas.SetTextColor(clShadow1); + fpgStyle.DrawString(Canvas, FMargin+1, FMargin, ExtraHint, Enabled); + end; +end; + procedure TfpgBaseStaticCombo.InternalBtnClick(Sender: TObject); begin DoDropDown; @@ -584,7 +595,7 @@ procedure TfpgBaseStaticCombo.HandleKeyPress(var keycode: word; var shiftstate: begin inherited HandleKeyPress(keycode, shiftstate, consumed); if consumed then - RePaint + RePaint; end; procedure TfpgBaseStaticCombo.HandleLMouseDown(x, y: integer; shiftstate: TShiftState); @@ -671,14 +682,7 @@ begin end; Canvas.FillRectangle(r); - // Draw select item's text - if HasText then - fpgStyle.DrawString(Canvas, FMargin+1, FMargin, Text, Enabled) - else - begin - Canvas.SetTextColor(clShadow1); - fpgStyle.DrawString(Canvas, FMargin+1, FMargin, ExtraHint, Enabled); - end; + DoDrawText(r); end; constructor TfpgBaseStaticCombo.Create(AOwner: TComponent); diff --git a/src/gui/fpg_listbox.pas b/src/gui/fpg_listbox.pas index 469cd106..8465987f 100644 --- a/src/gui/fpg_listbox.pas +++ b/src/gui/fpg_listbox.pas @@ -746,7 +746,8 @@ begin FHotTrack := False; FAutoHeight := False; - FScrollBar := TfpgScrollBar.Create(self); + FScrollBar := TfpgScrollBar.Create(self); + FScrollBar.Name := '_BaseListBoxScrollBar'; FScrollBar.OnScroll := @ScrollBarMove; FOnChange := nil; diff --git a/src/gui/fpg_popupcalendar.pas b/src/gui/fpg_popupcalendar.pas index f6dbfeac..426ec849 100644 --- a/src/gui/fpg_popupcalendar.pas +++ b/src/gui/fpg_popupcalendar.pas @@ -51,7 +51,8 @@ uses fpg_combobox, fpg_basegrid, fpg_grid, - fpg_dialogs; + fpg_dialogs{, + fpg_checkbox}; type @@ -148,7 +149,6 @@ type FHolidayColor: TfpgColor; FSelectedColor: TfpgColor; FCloseOnSelect: boolean; - procedure InternalOnValueSet(Sender: TObject; const ADate: TDateTime); procedure SetDateFormat(const AValue: string); procedure SetDateValue(const AValue: TDateTime); procedure SetMaxDate(const AValue: TDateTime); @@ -162,6 +162,7 @@ type function GetText: string; override; procedure SetCloseOnSelect(const AValue: boolean); protected + procedure InternalOnValueSet(Sender: TObject; const ADate: TDateTime); virtual; function HasText: boolean; override; procedure DoDropDown; override; public @@ -190,6 +191,27 @@ type property OnExit; end; + + TfpgCalendarCheckCombo = class(TfpgCalendarCombo) + private +// FCheckBox: TfpgCheckbox; + FChecked: boolean; + FCheckBoxRect: TfpgRect; + procedure InternalCheckBoxChanged(Sender: TObject); + procedure SetChecked(const AValue: Boolean); + protected + procedure DoDrawText(const ARect: TfpgRect); override; + procedure InternalOnValueSet(Sender: TObject; const ADate: TDateTime); override; + procedure HandleKeyPress(var keycode: word; var shiftstate: TShiftState; var consumed: boolean); override; + procedure HandlePaint; override; + public + constructor Create(AOwner: TComponent); override; + published + property Checked: Boolean read FChecked write SetChecked; + property OnKeyPress; + end; + + {@VFD_NEWFORM_DECL} implementation @@ -975,4 +997,120 @@ begin end; end; +{ TfpgCalendarCheckCombo } + +procedure TfpgCalendarCheckCombo.InternalCheckBoxChanged(Sender: TObject); +begin + RePaint; +end; + +procedure TfpgCalendarCheckCombo.SetChecked(const AValue: Boolean); +begin + if AValue = FChecked then + Exit; //==> + FChecked := Avalue; + InternalCheckBoxChanged(nil); +end; + +procedure TfpgCalendarCheckCombo.DoDrawText(const ARect: TfpgRect); +var + lRect: TfpgRect; + flags: TFTextFlags; + lColor: TfpgColor; +begin + lRect := ARect; + lRect.Left := lRect.Left+FCheckBoxRect.Width + 1; + lRect.Width := lRect.Width - (FCheckBoxRect.Width + 1) - FMargin; + flags := [txtRight, txtVCenter]; + if HasText then + begin + if not FChecked then + Canvas.SetTextColor(clShadow1) + else + begin + if Focused then + Canvas.SetTextColor(clSelectionText) + else + Canvas.SetTextColor(TextColor); + end; + fpgStyle.DrawString(Canvas, lRect.Left {FMargin+1}, {lRect.Top }FMargin, Text, Enabled); + end + else + begin + Canvas.SetTextColor(clShadow1); + fpgStyle.DrawString(Canvas, lRect.Left {FMargin+1}, {lRect.Top} FMargin, ExtraHint, Enabled); + end; +end; + +procedure TfpgCalendarCheckCombo.InternalOnValueSet(Sender: TObject; + const ADate: TDateTime); +begin + inherited InternalOnValueSet(Sender, ADate); + Checked := True; +// InternalCheckBoxChanged(nil); +end; + +procedure TfpgCalendarCheckCombo.HandleKeyPress(var keycode: word; + var shiftstate: TShiftState; var consumed: boolean); +begin + if keycode = keyEscape then + begin + consumed := True; + Checked := False; + end; + inherited HandleKeyPress(keycode, shiftstate, consumed); +end; + +procedure TfpgCalendarCheckCombo.HandlePaint; +var + r: TfpgRect; + img: TfpgImage; + ix: integer; +begin + inherited HandlePaint; + + r := FCheckBoxRect; + OffsetRect(r, 2, 2); +// r.SetRect(4, 4, 17, 17); +// PrintRect(r); + + // calculate which image to paint. + if Enabled then + begin + ix := Ord(FChecked); + //if FIsPressed then + //Inc(ix, 2); + end + else + ix := (2 + (Ord(FChecked) * 2)) - Ord(FChecked); + + // paint the check (in this case a X) +// tx := r.right + 8; + img := fpgImages.GetImage('sys.checkboxes'); // Do NOT localize + Canvas.DrawImagePart(r.Left, r.Top, img, ix*13, 0, 13, 13); +end; + +constructor TfpgCalendarCheckCombo.Create(AOwner: TComponent); +begin + inherited Create(AOwner); + FChecked := True; + FCheckBoxRect.SetRect(2, 2, 17, 17); +{ + FCheckBox := TfpgCheckBox.Create(self); + with FCheckbox do + begin + Name := '_IntCheckBox'; + SetPosition(2, 2, 18, 17); + Checked := True; + FontDesc := '#Label1'; + Text := ''; +// BackgroundColor := self.BackgroundColor; + BackgroundColor := clMagenta; + Focusable := False; + OnChange := @InternalCheckBoxChanged; + end; +} +end; + + end. |