X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/82eba82658182db222b56108a2f52e59e3f0b3d1..25e6a4a698b15d72874bd1dbf4d260163a60f005:/src/msw/display.cpp diff --git a/src/msw/display.cpp b/src/msw/display.cpp index 1fd815e37c..59367a8f7e 100644 --- a/src/msw/display.cpp +++ b/src/msw/display.cpp @@ -1,11 +1,12 @@ ///////////////////////////////////////////////////////////////////////////// -// Name: display.cpp +// Name: src/msw/display.cpp // Purpose: MSW Implementation of wxDisplay class // Author: Royce Mitchell III // Modified by: VZ (resolutions enumeration/change support, DirectDraw, ...) +// Ryan Norton (IsPrimary override) // Created: 06/21/02 // RCS-ID: $Id$ -// Copyright: (c) wxWindows team +// Copyright: (c) wxWidgets team // Licence: wxWindows licence ///////////////////////////////////////////////////////////////////////////// @@ -17,10 +18,6 @@ // headers // --------------------------------------------------------------------------- -#ifdef __GNUG__ - #pragma implementation "display.h" -#endif - // For compilers that support precompilation, includes "wx.h". #include "wx/wxprec.h" @@ -31,7 +28,9 @@ #if wxUSE_DISPLAY #ifndef WX_PRECOMP + #include "wx/app.h" #include "wx/dynarray.h" + #include "wx/frame.h" #endif #include "wx/dynload.h" @@ -53,7 +52,26 @@ #pragma warning(disable:4706) #endif -#include +// with mingw32, we must include windows.h first and it doesn't hurt with other +// compilers +#include "wx/msw/wrapwin.h" + +#ifndef __WXWINCE__ + #include + + // HMONITOR can be declared either in new enough windef.h or in multimon.h + // itself if _WIN32_WINNT < 0x0500, but the trouble is that we set + // _WIN32_WINNT to maximal possible value ourselves in wx/msw/wrapwin.h so + // that multimon.h doesn't define it but with old headers, neither does + // windef.h, in spite of _WIN32_WINNT value. Even more unfortunately, we + // can't directly test whether HMONITOR is defined or not in windef.h as + // it's not a macro but a typedef, so we test for an unrelated symbol which + // is only defined in winuser.h if WINVER >= 0x0500 + #if !defined(HMONITOR_DECLARED) && !defined(MNS_NOCHECK) + DECLARE_HANDLE(HMONITOR); + #define HMONITOR_DECLARED + #endif +#endif // !__WXWINCE__ #ifdef _MSC_VER #pragma warning(default:4706) @@ -166,10 +184,10 @@ static wxDisplayInfoArray *gs_displays = NULL; // ---------------------------------------------------------------------------- static BOOL CALLBACK wxmswMonitorEnumProc ( - HMONITOR hMonitor, // handle to display monitor - HDC hdcMonitor, // handle to monitor-appropriate device context (NULL) - LPRECT lprcMonitor, // pointer to monitor intersection rectangle - LPARAM dwData // data passed from EnumDisplayMonitors (unused) + HMONITOR hMonitor, // handle to display monitor + HDC WXUNUSED(hdcMonitor), // handle to monitor-appropriate device context + LPRECT lprcMonitor, // pointer to monitor intersection rectangle + LPARAM WXUNUSED(dwData) // data passed from EnumDisplayMonitors (unused) ) { wxDisplayInfo *info = new wxDisplayInfo(); @@ -193,9 +211,9 @@ static BOOL CALLBACK wxmswMonitorEnumProc ( BOOL PASCAL wxDDEnumExCallback(GUID *pGuid, - LPTSTR driverDescription, + LPTSTR WXUNUSED(driverDescription), LPTSTR driverName, - LPVOID lpContext, + LPVOID WXUNUSED(lpContext), HMONITOR hmon) { if ( pGuid ) @@ -214,11 +232,11 @@ wxDDEnumExCallback(GUID *pGuid, return true; } -HRESULT WINAPI wxDDEnumModesCallback(LPDDSURFACEDESC lpDDSurfaceDesc, +HRESULT WINAPI wxDDEnumModesCallback(LPDDSURFACEDESC lpDDSurfaceDesc, LPVOID lpContext) { // we need at least the mode size - static const int FLAGS_REQUIRED = DDSD_HEIGHT | DDSD_WIDTH; + static const DWORD FLAGS_REQUIRED = DDSD_HEIGHT | DDSD_WIDTH; if ( (lpDDSurfaceDesc->dwFlags & FLAGS_REQUIRED) == FLAGS_REQUIRED ) { wxArrayVideoModes * const modes = (wxArrayVideoModes *)lpContext; @@ -240,12 +258,16 @@ HRESULT WINAPI wxDDEnumModesCallback(LPDDSURFACEDESC lpDDSurfaceDesc, // initialize gs_displays using DirectX functions static bool DoInitDirectX() { +#if wxUSE_LOG // suppress the errors if ddraw.dll is not found wxLog::EnableLogging(false); +#endif wxDynamicLibrary dllDX(_T("ddraw.dll")); - wxLog::EnableLogging(true); +#if wxUSE_LOG + wxLog::EnableLogging(); +#endif if ( !dllDX.IsLoaded() ) return false; @@ -318,6 +340,7 @@ wxVideoMode ConvertToVideoMode(const DEVMODE& dm) dm.dmDisplayFrequency > 1 ? dm.dmDisplayFrequency : 0); } +#ifndef __WXWINCE__ // emulation of ChangeDisplaySettingsEx() for Win95 LONG WINAPI ChangeDisplaySettingsExForWin95(LPCTSTR WXUNUSED(lpszDeviceName), LPDEVMODE lpDevMode, @@ -327,6 +350,7 @@ LONG WINAPI ChangeDisplaySettingsExForWin95(LPCTSTR WXUNUSED(lpszDeviceName), { return ::ChangeDisplaySettings(lpDevMode, dwFlags); } +#endif // !__WXWINCE__ // ---------------------------------------------------------------------------- // wxDisplayModule @@ -371,10 +395,12 @@ size_t wxDisplayBase::GetCount() { InitDisplays(); - // I'm not sure if they really always return the same thing and if this is - // not true I'd like to know in which situation does it happen - wxASSERT_MSG( gs_displays->GetCount() == (size_t)::GetSystemMetrics(SM_CMONITORS), - _T("So how many displays does this system have?") ); + //RN: FIXME: This is wrong - the display info array should reload after every call + //to GetCount() - otherwise it will not be accurate. + //The user can change the number of displays in display properties/settings + //after GetCount or similar is called and really mess this up... + //wxASSERT_MSG( gs_displays->GetCount() == (size_t)::GetSystemMetrics(SM_CMONITORS), + // _T("So how many displays does this system have?") ); return gs_displays->GetCount(); } @@ -505,7 +531,11 @@ wxString wxDisplay::GetName() const wxZeroMemory(monInfo); monInfo.cbSize = sizeof(monInfo); - if ( !::GetMonitorInfo(dpyInfo.m_hmon, &monInfo) ) + // NB: Cast from MONITORINFOEX* to MONITORINFO* is done because + // Mingw headers - unlike the ones from Microsoft's Platform SDK - + // don't derive the former from the latter in C++ mode and so + // the pointer's type is not converted implicitly. + if ( !::GetMonitorInfo(dpyInfo.m_hmon, (LPMONITORINFO)&monInfo) ) { wxLogLastError(_T("GetMonitorInfo")); } @@ -534,12 +564,36 @@ wxString wxDisplay::GetNameForEnumSettings() const return name; } +// ---------------------------------------------------------------------------- +// determine if this is the primary display +// ---------------------------------------------------------------------------- + +bool wxDisplay::IsPrimary() const +{ + wxDisplayInfo& dpyInfo = (*gs_displays)[m_index]; + + MONITORINFOEX monInfo; + wxZeroMemory(monInfo); + monInfo.cbSize = sizeof(monInfo); + + // NB: Cast from MONITORINFOEX* to MONITORINFO* is done because + // Mingw headers - unlike the ones from Microsoft's Platform SDK - + // don't derive the former from the latter in C++ mode and so + // the pointer's type is not converted implicitly. + if ( !::GetMonitorInfo(dpyInfo.m_hmon, (LPMONITORINFO)&monInfo) ) + { + wxLogLastError(_T("GetMonitorInfo")); + } + + return (monInfo.dwFlags & MONITORINFOF_PRIMARY) == MONITORINFOF_PRIMARY; +} + // ---------------------------------------------------------------------------- // video modes enumeration // ---------------------------------------------------------------------------- wxArrayVideoModes -wxDisplay::DoGetModesDirectX(const wxVideoMode& modeMatch) const +wxDisplay::DoGetModesDirectX(const wxVideoMode& WXUNUSED(modeMatch)) const { wxArrayVideoModes modes; @@ -648,7 +702,7 @@ bool wxDisplay::DoChangeModeDirectX(const wxVideoMode& mode) return false; } - + return true; } @@ -690,7 +744,11 @@ bool wxDisplay::DoChangeModeWindows(const wxVideoMode& mode) pDevMode = &dm; +#ifdef __WXWINCE__ + flags = 0; +#else // !__WXWINCE__ flags = CDS_FULLSCREEN; +#endif // __WXWINCE__/!__WXWINCE__ } @@ -709,12 +767,14 @@ bool wxDisplay::DoChangeModeWindows(const wxVideoMode& mode) } //else: huh, no user32.dll?? +#ifndef __WXWINCE__ if ( !pfnChangeDisplaySettingsEx ) { // we must be under Win95 and so there is no multiple monitors // support anyhow pfnChangeDisplaySettingsEx = ChangeDisplaySettingsExForWin95; } +#endif // !__WXWINCE__ } // do change the mode @@ -729,6 +789,18 @@ bool wxDisplay::DoChangeModeWindows(const wxVideoMode& mode) { case DISP_CHANGE_SUCCESSFUL: // ok + { + // If we have a top-level, full-screen frame, emulate + // the DirectX behavior and resize it. This makes this + // API quite a bit easier to use. + wxWindow *winTop = wxTheApp->GetTopWindow(); + wxFrame *frameTop = wxDynamicCast(winTop, wxFrame); + if (frameTop && frameTop->IsFullScreen()) + { + wxVideoMode current = GetCurrentMode(); + frameTop->SetClientSize(current.w, current.h); + } + } return true; case DISP_CHANGE_BADMODE: