From dc92adaf0c8d1d8b71b4a4cabe6f42c3a17f62a1 Mon Sep 17 00:00:00 2001
From: Vadim Zeitlin <vadim@wxwidgets.org>
Date: Tue, 7 Sep 2004 21:02:55 +0000
Subject: [PATCH] added wxTopLevelWindow::RequestUserAttention(); documented it
 and implemented it for MSW

git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@29044 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
---
 docs/changes.txt          |  1 +
 docs/latex/wx/tlw.tex     | 18 ++++++++++++++++
 include/wx/msw/toplevel.h |  1 +
 include/wx/toplevel.h     | 12 +++++++++++
 src/msw/toplevel.cpp      | 45 +++++++++++++++++++++++++++++++++++++++
 5 files changed, 77 insertions(+)

diff --git a/docs/changes.txt b/docs/changes.txt
index c721c433f6..1cc4baf929 100644
--- a/docs/changes.txt
+++ b/docs/changes.txt
@@ -224,6 +224,7 @@ All (GUI):
 - added status bar fields styles support (Tim Kosse)
 - added samples/splash
 - added support for stock buttons
+- added wxTopLevelWindow::RequestUserAttention()
 
 Unix:
 
diff --git a/docs/latex/wx/tlw.tex b/docs/latex/wx/tlw.tex
index 71ae9bc300..f2e2fa1c03 100644
--- a/docs/latex/wx/tlw.tex
+++ b/docs/latex/wx/tlw.tex
@@ -116,6 +116,24 @@ This function only works under Windows.
 \helpref{wxTopLevelWindow::Iconize}{wxtoplevelwindowiconize}
 
 
+\membersection{wxTopLevelWindow::RequestUserAttention}\label{wxtoplevelwindowrequestuserattention}
+
+\func{void}{RequestUserAttention}{\param{int }{flags = wxUSER\_ATTENTION\_INFO}}
+
+Use a system-dependent way to attract users attention to the window when it is
+in background.
+
+\arg{flags} may have the value of either \texttt{wxUSER\_ATTENTION\_INFO}
+(default) or \texttt{wxUSER\_ATTENTION\_ERROR} which results in a more drastic
+action. When in doubt, use the default value.
+
+Note that this function should normally be only used when the application is
+not already in foreground.
+
+This function is currently only implemented for Win32 where it flashes the
+window icon in the taskbar.
+
+
 \membersection{wxTopLevelWindow::SetIcon}\label{wxtoplevelwindowseticon}
 
 \func{void}{SetIcon}{\param{const wxIcon\& }{icon}}
diff --git a/include/wx/msw/toplevel.h b/include/wx/msw/toplevel.h
index fab04867f6..c4b7e47287 100644
--- a/include/wx/msw/toplevel.h
+++ b/include/wx/msw/toplevel.h
@@ -61,6 +61,7 @@ public:
 #ifndef __WXWINCE__
     virtual bool SetShape(const wxRegion& region);
 #endif // __WXWINCE__
+    virtual void RequestUserAttention(int flags = wxUSER_ATTENTION_INFO);
 
     virtual bool Show(bool show = true);
 
diff --git a/include/wx/toplevel.h b/include/wx/toplevel.h
index d7517e5cb3..a193d5edd4 100644
--- a/include/wx/toplevel.h
+++ b/include/wx/toplevel.h
@@ -104,6 +104,13 @@ enum
                                wxFULLSCREEN_NOCAPTION
 };
 
+// Styles for RequestUserAttention
+enum
+{
+    wxUSER_ATTENTION_INFO = 1,
+    wxUSER_ATTENTION_ERROR = 2
+};
+
 // ----------------------------------------------------------------------------
 // wxTopLevelWindow: a top level (as opposed to child) window
 // ----------------------------------------------------------------------------
@@ -164,6 +171,11 @@ public:
     // operation is successful.)
     virtual bool SetShape(const wxRegion& WXUNUSED(region)) { return FALSE; }
 
+    // Attracts the users attention to this window if the application is
+    // inactive (should be called when a background event occurs)
+    virtual void RequestUserAttention(int flags = wxUSER_ATTENTION_INFO);
+
+
     // implementation only from now on
     // -------------------------------
 
diff --git a/src/msw/toplevel.cpp b/src/msw/toplevel.cpp
index 3163947741..11b0b43600 100644
--- a/src/msw/toplevel.cpp
+++ b/src/msw/toplevel.cpp
@@ -40,6 +40,7 @@
 #endif //WX_PRECOMP
 
 #include "wx/module.h"
+#include "wx/dynlib.h"
 
 #include "wx/msw/private.h"
 #if defined(__WXWINCE__) && !defined(__HANDHELDPC__)
@@ -901,6 +902,50 @@ bool wxTopLevelWindowMSW::SetShape(const wxRegion& region)
 
 #endif // !__WXWINCE__
 
+void wxTopLevelWindowMSW::RequestUserAttention(int flags)
+{
+    // check if we can use FlashWindowEx()
+#ifdef FLASHW_STOP
+    // available in the headers, check if it is supported by the system
+    typedef BOOL (WINAPI *FlashWindowEx_t)(FLASHWINFO *pfwi);
+    FlashWindowEx_t s_pfnFlashWindowEx = NULL;
+    if ( !s_pfnFlashWindowEx )
+    {
+        wxDynamicLibrary dllUser32(_T("user32.dll"));
+        s_pfnFlashWindowEx = (FlashWindowEx_t)
+                                dllUser32.GetSymbol(_T("FlashWindowEx"));
+
+        // we can safely unload user32.dll here, it's goign to remain loaded as
+        // long as the program is running anyhow
+    }
+
+    if ( s_pfnFlashWindowEx )
+    {
+        WinStruct<FLASHWINFO> fwi;
+        fwi.hwnd = GetHwnd();
+        fwi.dwFlags = FLASHW_ALL;
+        if ( flags & wxUSER_ATTENTION_INFO )
+        {
+            // just flash a few times
+            fwi.uCount = 3;
+        }
+        else // wxUSER_ATTENTION_ERROR
+        {
+            // flash until the user notices it
+            fwi.dwFlags |= FLASHW_TIMERNOFG;
+        }
+
+        s_pfnFlashWindowEx(&fwi);
+    }
+    else // FlashWindowEx() not available
+#endif // FLASHW_STOP
+    {
+        wxUnusedVar(flags);
+
+        ::FlashWindow(GetHwnd(), TRUE);
+    }
+}
+
 // ----------------------------------------------------------------------------
 // wxTopLevelWindow event handling
 // ----------------------------------------------------------------------------
-- 
2.50.0

