+void wxFileDialog::MSWOnSelChange(WXHWND hDlg)
+{
+ TCHAR buf[MAX_PATH];
+ LRESULT len = SendMessage(::GetParent(hDlg), CDM_GETFILEPATH,
+ MAX_PATH, reinterpret_cast<LPARAM>(buf));
+
+ if ( len > 0 )
+ m_currentlySelectedFilename = buf;
+ else
+ m_currentlySelectedFilename.clear();
+
+ if ( m_extraControl )
+ m_extraControl->UpdateWindowUI(wxUPDATE_UI_RECURSE);
+}
+
+// helper used below in ShowCommFileDialog(): style is used to determine
+// whether to show the "Save file" dialog (if it contains wxFD_SAVE bit) or
+// "Open file" one; returns true on success or false on failure in which case
+// err is filled with the CDERR_XXX constant
+static bool DoShowCommFileDialog(OPENFILENAME *of, long style, DWORD *err)
+{
+ if ( style & wxFD_SAVE ? GetSaveFileName(of) : GetOpenFileName(of) )
+ return true;
+
+ if ( err )
+ {
+#ifdef __WXWINCE__
+ // according to MSDN, CommDlgExtendedError() should work under CE as
+ // well but apparently in practice it doesn't (anybody has more
+ // details?)
+ *err = GetLastError();
+#else
+ *err = CommDlgExtendedError();
+#endif
+ }
+
+ return false;
+}
+
+// We want to use OPENFILENAME struct version 5 (Windows 2000/XP) but we don't
+// know if the OPENFILENAME declared in the currently used headers is a V5 or
+// V4 (smaller) one so we try to manually extend the struct in case it is the
+// old one.
+//
+// We don't do this on Windows CE nor under Win64, however, as there are no
+// compilers with old headers for these architectures
+#if defined(__WXWINCE__) || defined(__WIN64__)
+ typedef OPENFILENAME wxOPENFILENAME;
+
+ static const DWORD gs_ofStructSize = sizeof(OPENFILENAME);
+#else // !__WXWINCE__ || __WIN64__
+ #define wxTRY_SMALLER_OPENFILENAME
+
+ struct wxOPENFILENAME : public OPENFILENAME
+ {
+ // fields added in Windows 2000/XP comdlg32.dll version
+ void *pVoid;
+ DWORD dw1;
+ DWORD dw2;
+ };
+
+ // hardcoded sizeof(OPENFILENAME) in the Platform SDK: we have to do it
+ // because sizeof(OPENFILENAME) in the headers we use when compiling the
+ // library could be less if _WIN32_WINNT is not >= 0x500
+ static const DWORD wxOPENFILENAME_V5_SIZE = 88;
+
+ // this is hardcoded sizeof(OPENFILENAME_NT4) from Platform SDK
+ static const DWORD wxOPENFILENAME_V4_SIZE = 76;
+
+ // always try the new one first
+ static DWORD gs_ofStructSize = wxOPENFILENAME_V5_SIZE;
+#endif // __WXWINCE__ || __WIN64__/!...
+
+static bool ShowCommFileDialog(OPENFILENAME *of, long style)
+{
+ DWORD errCode;
+ bool success = DoShowCommFileDialog(of, style, &errCode);
+
+#ifdef wxTRY_SMALLER_OPENFILENAME
+ // the system might be too old to support the new version file dialog
+ // boxes, try with the old size
+ if ( !success && errCode == CDERR_STRUCTSIZE &&
+ of->lStructSize != wxOPENFILENAME_V4_SIZE )
+ {
+ of->lStructSize = wxOPENFILENAME_V4_SIZE;
+
+ success = DoShowCommFileDialog(of, style, &errCode);
+
+ if ( success || !errCode )
+ {
+ // use this struct size for subsequent dialogs
+ gs_ofStructSize = of->lStructSize;
+ }
+ }
+#endif // wxTRY_SMALLER_OPENFILENAME
+
+ if ( !success &&
+ // FNERR_INVALIDFILENAME is not defined under CE (besides we don't
+ // use CommDlgExtendedError() there anyhow)
+#ifndef __WXWINCE__
+ errCode == FNERR_INVALIDFILENAME &&
+#endif // !__WXWINCE__
+ of->lpstrFile[0] )
+ {
+ // this can happen if the default file name is invalid, try without it
+ // now
+ of->lpstrFile[0] = wxT('\0');
+ success = DoShowCommFileDialog(of, style, &errCode);
+ }
+
+ if ( !success )
+ {
+ // common dialog failed - why?
+ if ( errCode != 0 )
+ {
+ wxLogError(_("File dialog failed with error code %0lx."), errCode);
+ }
+ //else: it was just cancelled
+
+ return false;
+ }
+
+ return true;
+}
+
+#ifndef __WXWINCE__
+void wxFileDialog::MSWOnInitDialogHook(WXHWND hwnd)
+{
+ SetHWND(hwnd);
+
+ CreateExtraControl();
+
+ SetHWND(NULL);
+}
+#endif // __WXWINCE__
+