win32: replace the code which moved the focus to the last focused window on application activate with the search of the top window (active stay on top windows always win), move code which restored the last active window on application activation to LCL

git-svn-id: trunk@35504 -
This commit is contained in:
paul 2012-02-20 09:24:42 +00:00
parent 2f4158711d
commit 8fc49926d2
4 changed files with 54 additions and 6 deletions

View File

@ -1424,6 +1424,7 @@ procedure TApplication.Activate;
begin begin
if AppActive in FFlags then exit; if AppActive in FFlags then exit;
Include(FFlags, AppActive); Include(FFlags, AppActive);
Screen.RestoreLastActive;
NotifyActivateHandler; NotifyActivateHandler;
end; end;

View File

@ -2012,8 +2012,14 @@ begin
begin begin
if (Window = Win32WidgetSet.AppHandle) then if (Window = Win32WidgetSet.AppHandle) then
begin begin
if not IsIconic(Window) and IsWindow(WindowLastFocused) then // if application window is still focused then move the focus
SetFocus(WindowLastFocused); // to the next top window
if not IsIconic(Window) and (GetFocus = Window) then
begin
TargetWindow := LookupTopWindow(Window);
if TargetWindow <> Window then
SetFocus(TargetWindow);
end;
Result := 0; Result := 0;
Exit; Exit;
end; end;
@ -2026,9 +2032,7 @@ begin
{$endif} {$endif}
// move focus to another application window but process event first // move focus to another application window but process event first
if (Window = Win32WidgetSet.AppHandle) then if (Window = Win32WidgetSet.AppHandle) then
PostMessage(Window, CM_ACTIVATE, 0, 0) PostMessage(Window, CM_ACTIVATE, 0, 0);
else
WindowLastFocused := Window;
// handle feature mouse-click, setfocus, mouse-click -> double-click // handle feature mouse-click, setfocus, mouse-click -> double-click
if (Window <> MouseDownWindow) and (MouseDownFocusStatus <> mfNone) then if (Window <> MouseDownWindow) and (MouseDownFocusStatus <> mfNone) then
begin begin

View File

@ -274,7 +274,6 @@ var
MouseDownWindow: HWND = 0; MouseDownWindow: HWND = 0;
MouseDownFocusWindow: HWND; MouseDownFocusWindow: HWND;
MouseDownFocusStatus: TMouseDownFocusStatus = mfNone; MouseDownFocusStatus: TMouseDownFocusStatus = mfNone;
WindowLastFocused: HWND = 0;
ComboBoxHandleSizeWindow: HWND = 0; ComboBoxHandleSizeWindow: HWND = 0;
IgnoreNextCharWindow: HWND = 0; // ignore next WM_(SYS)CHAR message IgnoreNextCharWindow: HWND = 0; // ignore next WM_(SYS)CHAR message
// set to true, if we are redirecting a WM_MOUSEWHEEL message, to prevent recursion // set to true, if we are redirecting a WM_MOUSEWHEEL message, to prevent recursion

View File

@ -94,6 +94,7 @@ procedure RemoveStayOnTopFlags(AppHandle: HWND; ASystemTopAlso: Boolean = False)
procedure RestoreStayOnTopFlags(AppHandle: HWND); procedure RestoreStayOnTopFlags(AppHandle: HWND);
procedure HidePopups(AppHandle: HWND); procedure HidePopups(AppHandle: HWND);
procedure RestorePopups; procedure RestorePopups;
function LookupTopWindow(AppHandle: HWND): HWND;
procedure AddToChangedMenus(Window: HWnd); procedure AddToChangedMenus(Window: HWnd);
procedure RedrawMenus; procedure RedrawMenus;
@ -133,6 +134,12 @@ type
AppHandle: HWND; AppHandle: HWND;
OwnersList: TFPList; OwnersList: TFPList;
end; end;
PLookupTopWindowInfo = ^TLookupTopWindowInfo;
TLookupTopWindowInfo = record
AppHandle: HWND;
TopWindow: HWND;
end;
TWindowsVersion = ( TWindowsVersion = (
wvUnknown, wvUnknown,
@ -909,6 +916,43 @@ begin
end; end;
end; end;
function EnumLookupTopWindow(Handle: HWND; Param: LPARAM): WINBOOL; stdcall;
begin
Result := True;
if IsWindowVisible(Handle) and IsWindowEnabled(Handle) then
begin
with PLookupTopWindowInfo(Param)^ do
begin
if (Handle = AppHandle) or (Handle = TopWindow) then
Exit;
if GetWindowLong(Handle, GWL_EXSTYLE) and WS_EX_TOPMOST <> 0 then
begin
// we've found the top most window => stop
TopWindow := Handle;
Result := False;
end
else
if TopWindow = 0 then
TopWindow := Handle;
end;
end;
end;
function LookupTopWindow(AppHandle: HWND): HWND;
var
Info: PLookupTopWindowInfo;
begin
New(Info);
Info^.AppHandle := AppHandle;
Info^.TopWindow := 0;
EnumThreadWindows(GetWindowThreadProcessId(AppHandle, nil),
@EnumLookupTopWindow, LPARAM(Info));
Result := Info^.TopWindow;
if Result = 0 then
Result := AppHandle;
Dispose(Info);
end;
{------------------------------------------------------------------------------- {-------------------------------------------------------------------------------
procedure AddToChangedMenus(Window: HWnd); procedure AddToChangedMenus(Window: HWnd);