diff options
author | graemeg <graemeg@ae50a9b5-8222-0410-bf8d-8a13f76226bf> | 2007-08-18 22:45:51 +0000 |
---|---|---|
committer | graemeg <graemeg@ae50a9b5-8222-0410-bf8d-8a13f76226bf> | 2007-08-18 22:45:51 +0000 |
commit | b1881506db03ae8c30647ad6812d26348b6e3f3a (patch) | |
tree | 70c875632be90309e3359b5ab8de8ed8a702f511 | |
parent | e7a953faecc77e8c6c45509518a8b74692aceeed (diff) | |
download | fpGUI-b1881506db03ae8c30647ad6812d26348b6e3f3a.tar.xz |
* Moved and renamed gui_popupwindows.pas unit from GUI to CoreLib.
* X11: Completed popup window support.
* GUI: Amended TfpgComboBox to rather use a popup window for the dropdown portion of the control.
* The previous change fixed the issue in the FileDialog where you couldn't select a combo box item with the mouse.
-rw-r--r-- | examples/gui/filedialog/filedialog.lpi | 8 | ||||
-rw-r--r-- | examples/gui/fontselect/fontselect.lpi | 107 | ||||
-rw-r--r-- | src/corelib/gdi/gfx_gdi.pas | 5 | ||||
-rw-r--r-- | src/corelib/gdi/gfx_impl.pas | 16 | ||||
-rw-r--r-- | src/corelib/gfx_msgqueue.inc | 6 | ||||
-rw-r--r-- | src/corelib/gfx_popupwindow.pas (renamed from src/gui/gui_popupwindow.pas) | 50 | ||||
-rw-r--r-- | src/corelib/x11/fpgfx_package.lpk | 10 | ||||
-rw-r--r-- | src/corelib/x11/fpgfx_package.pas | 2 | ||||
-rw-r--r-- | src/corelib/x11/gfx_impl.pas | 16 | ||||
-rw-r--r-- | src/corelib/x11/gfx_x11.pas | 31 | ||||
-rw-r--r-- | src/gui/fpgui_package.lpk | 56 | ||||
-rw-r--r-- | src/gui/fpgui_package.pas | 7 | ||||
-rw-r--r-- | src/gui/gui_combobox.pas | 39 |
13 files changed, 217 insertions, 136 deletions
diff --git a/examples/gui/filedialog/filedialog.lpi b/examples/gui/filedialog/filedialog.lpi index ec79c6ee..c7b1f38a 100644 --- a/examples/gui/filedialog/filedialog.lpi +++ b/examples/gui/filedialog/filedialog.lpi @@ -1,7 +1,7 @@ <?xml version="1.0"?> <CONFIG> <ProjectOptions> - <PathDelim Value="\"/> + <PathDelim Value="/"/> <Version Value="5"/> <General> <Flags> @@ -9,7 +9,7 @@ </Flags> <SessionStorage Value="InProjectDir"/> <MainUnit Value="0"/> - <IconPath Value=".\"/> + <IconPath Value="./"/> <TargetFileExt Value=""/> </General> <VersionInfo> @@ -17,14 +17,13 @@ </VersionInfo> <PublishOptions> <Version Value="2"/> - <DestinationDirectory Value="$(TestDir)\publishedproject\"/> <IncludeFileFilter Value="*.(pas|pp|inc|lfm|lpr|lrs|lpi|lpk|sh|xml)"/> <ExcludeFileFilter Value="*.(bak|ppu|ppw|o|so);*~;backup"/> </PublishOptions> <RunParams> <local> <FormatVersion Value="1"/> - <LaunchingApplication PathPlusParams="\usr\X11R6\bin\xterm -T 'Lazarus Run Output' -e $(LazarusDir)\tools\runwait.sh $(TargetCmdLine)"/> + <LaunchingApplication PathPlusParams="/usr/X11R6/bin/xterm -T 'Lazarus Run Output' -e $(LazarusDir)/tools/runwait.sh $(TargetCmdLine)"/> </local> </RunParams> <RequiredPackages Count="1"> @@ -43,7 +42,6 @@ </ProjectOptions> <CompilerOptions> <Version Value="5"/> - <PathDelim Value="\"/> <CodeGeneration> <Generate Value="Faster"/> </CodeGeneration> diff --git a/examples/gui/fontselect/fontselect.lpi b/examples/gui/fontselect/fontselect.lpi index 7cb6ee37..230ba30c 100644 --- a/examples/gui/fontselect/fontselect.lpi +++ b/examples/gui/fontselect/fontselect.lpi @@ -1,54 +1,53 @@ -<?xml version="1.0"?>
-<CONFIG>
- <ProjectOptions>
- <PathDelim Value="\"/>
- <Version Value="5"/>
- <General>
- <Flags>
- <SaveOnlyProjectUnits Value="True"/>
- </Flags>
- <SessionStorage Value="InProjectDir"/>
- <MainUnit Value="0"/>
- <IconPath Value=".\"/>
- <TargetFileExt Value=""/>
- </General>
- <VersionInfo>
- <ProjectVersion Value=""/>
- </VersionInfo>
- <PublishOptions>
- <Version Value="2"/>
- <IncludeFileFilter Value="*.(pas|pp|inc|lfm|lpr|lrs|lpi|lpk|sh|xml)"/>
- <ExcludeFileFilter Value="*.(bak|ppu|ppw|o|so);*~;backup"/>
- </PublishOptions>
- <RunParams>
- <local>
- <FormatVersion Value="1"/>
- <LaunchingApplication PathPlusParams="\usr\X11R6\bin\xterm -T 'Lazarus Run Output' -e $(LazarusDir)\tools\runwait.sh $(TargetCmdLine)"/>
- </local>
- </RunParams>
- <RequiredPackages Count="1">
- <Item1>
- <PackageName Value="fpgui_package"/>
- <MinVersion Minor="5" Valid="True"/>
- </Item1>
- </RequiredPackages>
- <Units Count="1">
- <Unit0>
- <Filename Value="fontselect.lpr"/>
- <IsPartOfProject Value="True"/>
- <UnitName Value="fontselect"/>
- </Unit0>
- </Units>
- </ProjectOptions>
- <CompilerOptions>
- <Version Value="5"/>
- <PathDelim Value="\"/>
- <CodeGeneration>
- <Generate Value="Faster"/>
- </CodeGeneration>
- <Other>
- <CustomOptions Value="-FUunits"/>
- <CompilerPath Value="$(CompPath)"/>
- </Other>
- </CompilerOptions>
-</CONFIG>
+<?xml version="1.0"?> +<CONFIG> + <ProjectOptions> + <PathDelim Value="/"/> + <Version Value="5"/> + <General> + <Flags> + <SaveOnlyProjectUnits Value="True"/> + </Flags> + <SessionStorage Value="InProjectDir"/> + <MainUnit Value="0"/> + <IconPath Value="./"/> + <TargetFileExt Value=""/> + </General> + <VersionInfo> + <ProjectVersion Value=""/> + </VersionInfo> + <PublishOptions> + <Version Value="2"/> + <IncludeFileFilter Value="*.(pas|pp|inc|lfm|lpr|lrs|lpi|lpk|sh|xml)"/> + <ExcludeFileFilter Value="*.(bak|ppu|ppw|o|so);*~;backup"/> + </PublishOptions> + <RunParams> + <local> + <FormatVersion Value="1"/> + <LaunchingApplication PathPlusParams="/usr/X11R6/bin/xterm -T 'Lazarus Run Output' -e $(LazarusDir)/tools/runwait.sh $(TargetCmdLine)"/> + </local> + </RunParams> + <RequiredPackages Count="1"> + <Item1> + <PackageName Value="fpgui_package"/> + <MinVersion Minor="5" Valid="True"/> + </Item1> + </RequiredPackages> + <Units Count="1"> + <Unit0> + <Filename Value="fontselect.lpr"/> + <IsPartOfProject Value="True"/> + <UnitName Value="fontselect"/> + </Unit0> + </Units> + </ProjectOptions> + <CompilerOptions> + <Version Value="5"/> + <CodeGeneration> + <Generate Value="Faster"/> + </CodeGeneration> + <Other> + <CustomOptions Value="-FUunits"/> + <CompilerPath Value="$(CompPath)"/> + </Other> + </CompilerOptions> +</CONFIG> diff --git a/src/corelib/gdi/gfx_gdi.pas b/src/corelib/gdi/gfx_gdi.pas index 83b25bbf..ed1f9e15 100644 --- a/src/corelib/gdi/gfx_gdi.pas +++ b/src/corelib/gdi/gfx_gdi.pas @@ -10,7 +10,8 @@ uses Windows, Classes, SysUtils, - gfxbase; + gfxbase, + gfx_impl; { Constants missing on windows unit } const @@ -24,7 +25,7 @@ var type - TfpgWinHandle = HWND; +// TfpgWinHandle = HWND; TfpgGContext = HDC; type diff --git a/src/corelib/gdi/gfx_impl.pas b/src/corelib/gdi/gfx_impl.pas new file mode 100644 index 00000000..2f8eddf2 --- /dev/null +++ b/src/corelib/gdi/gfx_impl.pas @@ -0,0 +1,16 @@ +unit gfx_impl; + +{$mode objfpc}{$H+} + +interface + +uses + Windows; + +type + TfpgWinHandle = HWND; + +implementation + +end. + diff --git a/src/corelib/gfx_msgqueue.inc b/src/corelib/gfx_msgqueue.inc index bcf247b2..58eeaa16 100644 --- a/src/corelib/gfx_msgqueue.inc +++ b/src/corelib/gfx_msgqueue.inc @@ -52,7 +52,7 @@ begin Elem.Prev.Next := Elem.Next; end; -function pgfAllocateMessage: PfpgMessageRec; +function fpgAllocateMessage: PfpgMessageRec; var e: TMessageListElement; begin @@ -111,7 +111,7 @@ begin if Dest = nil then Exit; //==> - p := pgfAllocateMessage; + p := fpgAllocateMessage; if p <> nil then begin p^.MsgCode := MsgCode; @@ -130,7 +130,7 @@ begin if Dest = nil then Exit; //==> - p := pgfAllocateMessage; + p := fpgAllocateMessage; if p <> nil then begin p^.MsgCode := MsgCode; diff --git a/src/gui/gui_popupwindow.pas b/src/corelib/gfx_popupwindow.pas index 2d78687d..5d933b5d 100644 --- a/src/gui/gui_popupwindow.pas +++ b/src/corelib/gfx_popupwindow.pas @@ -1,4 +1,4 @@ -unit gui_popupwindow; +unit gfx_popupwindow; {$mode objfpc}{$H+} @@ -13,14 +13,16 @@ uses SysUtils, gfxbase, fpgfx, - gfx_widget; + gfx_widget, + gfx_impl; type TfpgPopupWindow = class(TfpgWidget) + private + FDontCloseWidget: TfpgWidget; protected procedure MsgClose(var msg: TfpgMessageRec); message FPGM_CLOSE; procedure AdjustWindowStyle; override; - procedure SetWindowParameters; override; procedure HandleShow; override; procedure HandleHide; override; procedure HandleClose; virtual; @@ -28,9 +30,16 @@ type constructor Create(AOwner: TComponent); override; procedure ShowAt(AWidget: TfpgWidget; x, y: TfpgCoord); procedure Close; + property DontCloseWidget: TfpgWidget read FDontCloseWidget write FDontCloseWidget; end; +procedure ClosePopups; +function PopupListFirst: TfpgPopupWindow; +function PopupListFind(AWinHandle: TfpgWinHandle): TfpgPopupWindow; +function PopupDontCloseWidget(AWidget: TfpgWidget): boolean; + + implementation @@ -124,7 +133,7 @@ begin Result := nil; end; -{ + function PopupListFind(AWinHandle: TfpgWinHandle): TfpgPopupWindow; var p: PPopupListRec; @@ -141,7 +150,27 @@ begin end; Result := nil; end; -} + +function PopupDontCloseWidget(AWidget: TfpgWidget): boolean; +var + p: PPopupListRec; +begin + Result := False; + if AWidget = nil then + Exit; //==> + + p := uFirstPopup; + while p <> nil do + begin + if p^.Widget.DontCloseWidget = AWidget then + begin + Result := True; + Exit; //==> + end; + p := p^.Next; + end; +end; + { TfpgPopupWindow } @@ -157,11 +186,6 @@ begin Exclude(FWindowAttributes, waSizeable); end; -procedure TfpgPopupWindow.SetWindowParameters; -begin - inherited SetWindowParameters; -end; - procedure TfpgPopupWindow.HandleShow; begin inherited HandleShow; @@ -183,12 +207,17 @@ constructor TfpgPopupWindow.Create(AOwner: TComponent); begin inherited Create(AOwner); WindowType := wtPopup; + FDontCloseWidget := nil; + Parent := nil; end; procedure TfpgPopupWindow.ShowAt(AWidget: TfpgWidget; x, y: TfpgCoord); var pt: TPoint; begin + PopupListAdd(self); + DontCloseWidget := nil; + // translate coordinates pt := WindowToScreen(AWidget, Point(x, y)); // reposition @@ -200,6 +229,7 @@ end; procedure TfpgPopupWindow.Close; begin + PopupListRemove(self); HandleHide; end; diff --git a/src/corelib/x11/fpgfx_package.lpk b/src/corelib/x11/fpgfx_package.lpk index 009c6ca3..222667ee 100644 --- a/src/corelib/x11/fpgfx_package.lpk +++ b/src/corelib/x11/fpgfx_package.lpk @@ -24,7 +24,7 @@ <License Value="Modified LGPL "/> <Version Minor="5"/> - <Files Count="13"> + <Files Count="15"> <Item1> <Filename Value="x11_xft.pas"/> <UnitName Value="x11_xft"/> @@ -77,6 +77,14 @@ <Filename Value="gfx_utils.pas"/> <UnitName Value="gfx_utils"/> </Item13> + <Item14> + <Filename Value="../gfx_popupwindow.pas"/> + <UnitName Value="gfx_popupwindow"/> + </Item14> + <Item15> + <Filename Value="gfx_impl.pas"/> + <UnitName Value="gfx_impl"/> + </Item15> </Files> <RequiredPkgs Count="1"> <Item1> diff --git a/src/corelib/x11/fpgfx_package.pas b/src/corelib/x11/fpgfx_package.pas index 7385fd5b..b4d63034 100644 --- a/src/corelib/x11/fpgfx_package.pas +++ b/src/corelib/x11/fpgfx_package.pas @@ -9,7 +9,7 @@ interface uses x11_xft, x11_keyconv, gfxbase, gfx_x11, fpgfx, gfx_stdimages, gfx_imgfmt_bmp, gfx_widget, gfx_UTF8utils, gfx_extinterpolation, gfx_cmdlineparams, - gfx_clipboard, gfx_utils; + gfx_clipboard, gfx_utils, gfx_popupwindow, gfx_impl; implementation diff --git a/src/corelib/x11/gfx_impl.pas b/src/corelib/x11/gfx_impl.pas new file mode 100644 index 00000000..0bd6b311 --- /dev/null +++ b/src/corelib/x11/gfx_impl.pas @@ -0,0 +1,16 @@ +unit gfx_impl; + +{$mode objfpc}{$H+} + +interface + +uses + x; + +type + TfpgWinHandle = TXID; + +implementation + +end. + diff --git a/src/corelib/x11/gfx_x11.pas b/src/corelib/x11/gfx_x11.pas index f11bfd38..76b6f1ff 100644 --- a/src/corelib/x11/gfx_x11.pas +++ b/src/corelib/x11/gfx_x11.pas @@ -14,10 +14,11 @@ uses XUtil, x11_xft, // x11_keyconv, - gfxbase; + gfxbase, + gfx_impl; type - TfpgWinHandle = TXID; +// TfpgWinHandle = TXID; TfpgGContext = Xlib.TGc; type @@ -204,7 +205,8 @@ uses xatom, gfx_utf8utils, _netlayer, - cursorfont; + cursorfont, + gfx_popupwindow; var xapplication: TfpgApplication; @@ -657,6 +659,7 @@ var rfds: TFDSet; xfd: integer; KeySym: TKeySym; + Popup: TfpgWidget; // debug purposes only procedure PrintKeyEvent(const event: TXEvent); @@ -713,6 +716,10 @@ begin // According to a comment in X.h, the valid event types start with 2! if ev._type < 2 then exit; + + + Popup := PopupListFirst; + // WriteLn('Event ',GetXEventName(ev._type),': ', ev._type,' window: ', ev.xany.window); // PrintKeyEvent(ev); { debug purposes only } @@ -764,6 +771,24 @@ begin msgp.mouse.Buttons := ev.xbutton.button; msgp.mouse.shiftstate := ConvertShiftState(ev.xbutton.state); + { This closes popup windows when you click the mouse elsewhere } + + if (Popup <> nil) then + begin + w := FindWindowByHandle(ev.xbutton.window); + ew := w; + while (w <> nil) and (w.Parent <> nil) do + w := TfpgWindowImpl(w.Parent); // check the actual usage of Parent and where it gets set!! + + if (w <> nil) and (PopupListFind(w.WinHandle) = nil) and (not PopupDontCloseWidget(TfpgWidget(ew))) then + begin + ClosePopups; + Popup := nil; + fpgPostMessage(nil, ew, FPGM_POPUPCLOSE); + //blockmsg := true; + end; + end; + w := FindWindowByHandle(ev.xbutton.window); if xapplication.TopModalForm <> nil then begin diff --git a/src/gui/fpgui_package.lpk b/src/gui/fpgui_package.lpk index c4cd6963..f6cab529 100644 --- a/src/gui/fpgui_package.lpk +++ b/src/gui/fpgui_package.lpk @@ -18,7 +18,7 @@ <Description Value="fpGUI - multi-handle redesign"/> <License Value="Modified LGPL"/> <Version Minor="5"/> - <Files Count="22"> + <Files Count="21"> <Item1> <Filename Value="gui_button.pas"/> <UnitName Value="gui_button"/> @@ -52,61 +52,57 @@ <UnitName Value="gui_memo"/> </Item8> <Item9> - <Filename Value="gui_popupwindow.pas"/> - <UnitName Value="gui_popupwindow"/> - </Item9> - <Item10> <Filename Value="gui_scrollbar.pas"/> <UnitName Value="gui_scrollbar"/> - </Item10> - <Item11> + </Item9> + <Item10> <Filename Value="gui_bevel.pas"/> <UnitName Value="gui_bevel"/> - </Item11> - <Item12> + </Item10> + <Item11> <Filename Value="gui_checkbox.pas"/> <UnitName Value="gui_checkbox"/> - </Item12> - <Item13> + </Item11> + <Item12> <Filename Value="gui_radiobutton.pas"/> <UnitName Value="gui_radiobutton"/> - </Item13> - <Item14> + </Item12> + <Item13> <Filename Value="gui_trackbar.pas"/> <UnitName Value="gui_trackbar"/> - </Item14> - <Item15> + </Item13> + <Item14> <Filename Value="gui_tab.pas"/> <UnitName Value="gui_tab"/> - </Item15> - <Item16> + </Item14> + <Item15> <Filename Value="gui_basegrid.pas"/> <UnitName Value="gui_basegrid"/> - </Item16> - <Item17> + </Item15> + <Item16> <Filename Value="gui_listview.pas"/> <UnitName Value="gui_listview"/> - </Item17> - <Item18> + </Item16> + <Item17> <Filename Value="gui_customgrid.pas"/> <UnitName Value="gui_customgrid"/> - </Item18> - <Item19> + </Item17> + <Item18> <Filename Value="gui_progressbar.pas"/> <UnitName Value="gui_progressbar"/> - </Item19> - <Item20> + </Item18> + <Item19> <Filename Value="gui_menu.pas"/> <UnitName Value="gui_menu"/> - </Item20> - <Item21> + </Item19> + <Item20> <Filename Value="gui_style.pas"/> <UnitName Value="gui_style"/> - </Item21> - <Item22> + </Item20> + <Item21> <Filename Value="gui_grid.pas"/> <UnitName Value="gui_grid"/> - </Item22> + </Item21> </Files> <RequiredPkgs Count="2"> <Item1> diff --git a/src/gui/fpgui_package.pas b/src/gui/fpgui_package.pas index f9368801..a633053b 100644 --- a/src/gui/fpgui_package.pas +++ b/src/gui/fpgui_package.pas @@ -8,10 +8,9 @@ interface uses gui_button, gui_combobox, gui_dialogs, gui_edit, gui_form, gui_label, - gui_listbox, gui_memo, gui_popupwindow, gui_scrollbar, gui_bevel, - gui_checkbox, gui_radiobutton, gui_trackbar, gui_tab, gui_basegrid, - gui_listview, gui_customgrid, gui_progressbar, gui_menu, gui_style, - gui_grid; + gui_listbox, gui_memo, gui_scrollbar, gui_bevel, gui_checkbox, + gui_radiobutton, gui_trackbar, gui_tab, gui_basegrid, gui_listview, + gui_customgrid, gui_progressbar, gui_menu, gui_style, gui_grid; implementation diff --git a/src/gui/gui_combobox.pas b/src/gui/gui_combobox.pas index 565a886c..38594794 100644 --- a/src/gui/gui_combobox.pas +++ b/src/gui/gui_combobox.pas @@ -8,10 +8,10 @@ uses Classes, SysUtils, gfx_widget, - gui_form, gfxbase, gui_button, - fpgfx; + fpgfx, + gfx_popupwindow; type @@ -20,7 +20,7 @@ type TfpgCustomComboBox = class(TfpgWidget) private FDropDownCount: integer; - FDropDown: TfpgForm; + FDropDown: TfpgPopupWindow; FBackgroundColor: TfpgColor; FFocusItem: integer; FFont: TfpgFont; @@ -39,7 +39,7 @@ type FMargin: integer; procedure SetEnabled(const AValue: boolean); override; property DropDownCount: integer read FDropDownCount write SetDropDownCount default 8; - procedure HandleLMouseDown(x, y: integer; shiftstate: TShiftState); override; + procedure HandleLMouseUp(x, y: integer; shiftstate: TShiftState); override; procedure HandlePaint; override; property Items: TStringList read FItems; {$Note Make this read/write } property FocusItem: integer read FFocusItem write SetFocusItem; @@ -72,20 +72,16 @@ function CreateComboBox(AOwner: TComponent; x, y, w: TfpgCoord; AList: TStringLi implementation uses - Math, gui_listbox; var OriginalFocusRoot: TfpgWidget; type - // This is so we can access protected methods - TPrivateWidget = class(TfpgWidget) - end; - - { TDropDownWindow } - TDropDownWindow = class(TfpgForm) + { This is the class representing the dropdown window of the combo box. } + + TDropDownWindow = class(TfpgPopupWindow) private FCallerWidget: TfpgWidget; protected @@ -131,7 +127,7 @@ begin ListBox.Height := Height; inherited HandleShow; - CaptureMouse; +// CaptureMouse; end; procedure TDropDownWindow.HandleHide; @@ -146,9 +142,9 @@ end; constructor TDropDownWindow.Create(AOwner: TComponent); begin inherited Create(AOwner); - WindowType := wtPopup; - WindowAttributes := []; - WindowPosition := wpUser; +// WindowType := wtPopup; +// WindowAttributes := []; +// WindowPosition := wpUser; ListBox := TfpgListBox.Create(self); ListBox.PopupFrame := True; @@ -156,7 +152,7 @@ end; destructor TDropDownWindow.Destroy; begin - ReleaseMouse; +// ReleaseMouse; inherited Destroy; end; @@ -198,18 +194,14 @@ end; procedure TfpgCustomComboBox.DoDropDown; var - pt: TPoint; ddw: TDropDownWindow; rowcount: integer; begin if (not Assigned(FDropDown)) or (not FDropDown.HasHandle) then begin OriginalFocusRoot := FocusRootWidget; - pt := WindowToScreen(Parent, Point(Left, Top+Height)); FDropDown := TDropDownWindow.Create(nil); ddw := TDropDownWindow(FDropDown); - ddw.Left := pt.X; - ddw.Top := pt.Y; ddw.Width := Width; // adjust the height of the dropdown rowcount := FItems.Count; @@ -225,7 +217,7 @@ begin ddw.ListBox.Items.Assign(FItems); ddw.ListBox.FocusItem := FFocusItem; - FDropDown.Show; + FDropDown.ShowAt(Parent, Left, Top+Height); ddw.ListBox.SetFocus; end else @@ -281,9 +273,10 @@ begin FInternalBtn.Enabled := AValue; end; -procedure TfpgCustomComboBox.HandleLMouseDown(x, y: integer; shiftstate: TShiftState); +procedure TfpgCustomComboBox.HandleLMouseUp(x, y: integer; + shiftstate: TShiftState); begin - inherited HandleLMouseDown(x, y, shiftstate); + inherited HandleLMouseUp(x, y, shiftstate); DoDropDown; end; |