]> git.saurik.com Git - wxWidgets.git/commitdiff
Check for task dialog availability even under Vista and later.
authorVadim Zeitlin <vadim@wxwidgets.org>
Fri, 15 Oct 2010 23:46:19 +0000 (23:46 +0000)
committerVadim Zeitlin <vadim@wxwidgets.org>
Fri, 15 Oct 2010 23:46:19 +0000 (23:46 +0000)
Task dialogs are not always available under Vista and later Windows versions
because we might not be using the right (i.e. 6+) version of comctl32.dll.

Improve the check for task dialog availability and fall back to the classic
message box if we can't use it.

Closes #12553.

git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@65816 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775

include/wx/msw/msgdlg.h
src/msw/msgdlg.cpp

index 3a91076877efab302b66541e16d282a7be4b0d32..784d339b61364e19e150095ce6fa3f5e80baa4c6 100644 (file)
@@ -59,8 +59,6 @@ private:
     // aren't available.
     int ShowMessageBox();
 
     // aren't available.
     int ShowMessageBox();
 
-    // used by ShowModal() to display a task dialog.
-    int ShowTaskDialog();
 
     WXHANDLE m_hook; // HHOOK used to position the message box
 
 
     WXHANDLE m_hook; // HHOOK used to position the message box
 
index ce8d4eafe56d4c85d1e418321cf64d2ca44d8ccc..f6057f73611fd8eda54650ed064c79db47fade9e 100644 (file)
@@ -573,39 +573,29 @@ int wxMessageDialog::ShowMessageBox()
     return MSWTranslateReturnCode(msAns);
 }
 
     return MSWTranslateReturnCode(msAns);
 }
 
-int wxMessageDialog::ShowTaskDialog()
+int wxMessageDialog::ShowModal()
 {
 #ifdef wxHAS_MSW_TASKDIALOG
 {
 #ifdef wxHAS_MSW_TASKDIALOG
-    TaskDialogIndirect_t taskDialogIndirect = GetTaskDialogIndirectFunc();
-    if ( !taskDialogIndirect )
-        return wxID_CANCEL;
-
-    WinStruct<TASKDIALOGCONFIG> tdc;
-    wxMSWTaskDialogConfig wxTdc( *this );
-    wxTdc.MSWCommonTaskDialogInit( tdc );
-
-    int msAns;
-    HRESULT hr = taskDialogIndirect( &tdc, &msAns, NULL, NULL );
-    if ( FAILED(hr) )
+    if ( HasNativeTaskDialog() )
     {
     {
-        wxLogApiError( "TaskDialogIndirect", hr );
-        return wxID_CANCEL;
-    }
-
-    return MSWTranslateReturnCode( msAns );
-#else
-    wxFAIL_MSG( "Task dialogs are unavailable." );
-
-    return wxID_CANCEL;
-#endif // wxHAS_MSW_TASKDIALOG
-}
+        TaskDialogIndirect_t taskDialogIndirect = GetTaskDialogIndirectFunc();
+        wxCHECK_MSG( taskDialogIndirect, wxID_CANCEL, wxS("no task dialog?") );
 
 
+        WinStruct<TASKDIALOGCONFIG> tdc;
+        wxMSWTaskDialogConfig wxTdc( *this );
+        wxTdc.MSWCommonTaskDialogInit( tdc );
 
 
+        int msAns;
+        HRESULT hr = taskDialogIndirect( &tdc, &msAns, NULL, NULL );
+        if ( FAILED(hr) )
+        {
+            wxLogApiError( "TaskDialogIndirect", hr );
+            return wxID_CANCEL;
+        }
 
 
-int wxMessageDialog::ShowModal()
-{
-    if ( HasNativeTaskDialog() )
-        return ShowTaskDialog();
+        return MSWTranslateReturnCode( msAns );
+    }
+#endif // wxHAS_MSW_TASKDIALOG
 
     return ShowMessageBox();
 }
 
     return ShowMessageBox();
 }
@@ -758,19 +748,20 @@ wxCRIT_SECT_DECLARE(gs_csTaskDialogIndirect);
 
 TaskDialogIndirect_t wxMSWMessageDialog::GetTaskDialogIndirectFunc()
 {
 
 TaskDialogIndirect_t wxMSWMessageDialog::GetTaskDialogIndirectFunc()
 {
-    static TaskDialogIndirect_t s_TaskDialogIndirect = NULL;
+    // Initialize the function pointer to an invalid value different from NULL
+    // to avoid reloading comctl32.dll and trying to resolve it every time
+    // we're called if task dialog is not available (notice that this may
+    // happen even under Vista+ if we don't use comctl32.dll v6).
+    static const TaskDialogIndirect_t
+        INVALID_TASKDIALOG_FUNC = reinterpret_cast<TaskDialogIndirect_t>(-1);
+    static TaskDialogIndirect_t s_TaskDialogIndirect = INVALID_TASKDIALOG_FUNC;
 
     wxCRIT_SECT_LOCKER(lock, gs_csTaskDialogIndirect);
 
 
     wxCRIT_SECT_LOCKER(lock, gs_csTaskDialogIndirect);
 
-    if ( !s_TaskDialogIndirect )
+    if ( s_TaskDialogIndirect == INVALID_TASKDIALOG_FUNC )
     {
         wxLoadedDLL dllComCtl32("comctl32.dll");
         wxDL_INIT_FUNC(s_, TaskDialogIndirect, dllComCtl32);
     {
         wxLoadedDLL dllComCtl32("comctl32.dll");
         wxDL_INIT_FUNC(s_, TaskDialogIndirect, dllComCtl32);
-
-        // We must always succeed as this code is only executed under Vista and
-        // later which must have task dialog support.
-        wxASSERT_MSG( s_TaskDialogIndirect,
-                      "Task dialog support unexpectedly not available" );
     }
 
     return s_TaskDialogIndirect;
     }
 
     return s_TaskDialogIndirect;
@@ -781,10 +772,14 @@ TaskDialogIndirect_t wxMSWMessageDialog::GetTaskDialogIndirectFunc()
 bool wxMSWMessageDialog::HasNativeTaskDialog()
 {
 #ifdef wxHAS_MSW_TASKDIALOG
 bool wxMSWMessageDialog::HasNativeTaskDialog()
 {
 #ifdef wxHAS_MSW_TASKDIALOG
-    return wxGetWinVersion() >= wxWinVersion_6;
-#else
+    if ( wxGetWinVersion() >= wxWinVersion_6 )
+    {
+        if ( wxMSWMessageDialog::GetTaskDialogIndirectFunc() )
+            return true;
+    }
+#endif // wxHAS_MSW_TASKDIALOG
+
     return false;
     return false;
-#endif
 }
 
 int wxMSWMessageDialog::MSWTranslateReturnCode(int msAns)
 }
 
 int wxMSWMessageDialog::MSWTranslateReturnCode(int msAns)