Patch: [#22524] Update Windows Recent Documents on Open/Save
[blender.git] / intern / ghost / intern / GHOST_DisplayManagerWin32.cpp
1 /**
2  * $Id$
3  * ***** BEGIN GPL LICENSE BLOCK *****
4  *
5  * This program is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU General Public License
7  * as published by the Free Software Foundation; either version 2
8  * of the License, or (at your option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program; if not, write to the Free Software Foundation,
17  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
18  *
19  * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
20  * All rights reserved.
21  *
22  * The Original Code is: all of this file.
23  *
24  * Contributor(s): none yet.
25  *
26  * ***** END GPL LICENSE BLOCK *****
27  */
28
29 /**
30
31  * $Id$
32  * Copyright (C) 2001 NaN Technologies B.V.
33  * @author      Maarten Gribnau
34  * @date        September 21, 2001
35  */
36
37 #include "GHOST_DisplayManagerWin32.h"
38 #include "GHOST_Debug.h"
39
40 // We do not support multiple monitors at the moment
41 #include <windows.h>
42 #define COMPILE_MULTIMON_STUBS
43 #ifndef FREE_WINDOWS
44 #include <multimon.h>
45 #endif
46
47
48 GHOST_DisplayManagerWin32::GHOST_DisplayManagerWin32(void)
49 {
50 }
51
52
53 GHOST_TSuccess GHOST_DisplayManagerWin32::getNumDisplays(GHOST_TUns8& numDisplays) const
54 {
55         // We do not support multiple monitors at the moment
56         numDisplays = ::GetSystemMetrics(SM_CMONITORS);
57         return numDisplays > 0 ? GHOST_kSuccess : GHOST_kFailure;
58 }
59
60
61 /*
62  * When you call EnumDisplaySettings with iModeNum set to zero, the operating system 
63  * initializes and caches information about the display device. When you call 
64  * EnumDisplaySettings with iModeNum set to a non-zero value, the function returns 
65  * the information that was cached the last time the function was called with iModeNum
66  * set to zero. 
67  */
68 GHOST_TSuccess GHOST_DisplayManagerWin32::getNumDisplaySettings(GHOST_TUns8 display, GHOST_TInt32& numSettings) const
69 {
70         GHOST_ASSERT((display==kMainDisplay), "GHOST_DisplayManagerWin32::getNumDisplaySettings(): only main displlay is supported");
71         numSettings = 0;
72         DEVMODE dm;
73         while (::EnumDisplaySettings(NULL, numSettings, &dm)) {
74                 numSettings++;
75         }
76         return GHOST_kSuccess;
77 }
78
79
80 GHOST_TSuccess GHOST_DisplayManagerWin32::getDisplaySetting(GHOST_TUns8 display, GHOST_TInt32 index, GHOST_DisplaySetting& setting) const
81 {
82         GHOST_ASSERT((display==kMainDisplay), "GHOST_DisplayManagerWin32::getDisplaySetting(): only main display is supported");
83         GHOST_TSuccess success;
84         DEVMODE dm;
85         if (::EnumDisplaySettings(NULL, index, &dm)) {
86 #ifdef GHOST_DEBUG
87                 printf("display mode: width=%d, height=%d, bpp=%d, frequency=%d\n", dm.dmPelsWidth, dm.dmPelsHeight, dm.dmBitsPerPel, dm.dmDisplayFrequency);
88 #endif // GHOST_DEBUG
89                 setting.xPixels         = dm.dmPelsWidth;
90                 setting.yPixels         = dm.dmPelsHeight;
91                 setting.bpp                     = dm.dmBitsPerPel;
92                 /* When you call the EnumDisplaySettings function, the dmDisplayFrequency member
93                  * may return with the value 0 or 1. These values represent the display hardware's
94                  * default refresh rate. This default rate is typically set by switches on a display 
95                  * card or computer motherboard, or by a configuration program that does not use 
96                  * Win32 display functions such as ChangeDisplaySettings. 
97                  */
98                 /* First, we tried to explicitly set the frequency to 60 if EnumDisplaySettings
99                  * returned 0 or 1 but this doesn't work since later on an exact match will
100                  * be searched. And this will never happen if we change it to 60. Now we rely
101                  * on the default h/w setting.
102                  */
103                 setting.frequency = dm.dmDisplayFrequency;
104                 success = GHOST_kSuccess;
105         }
106         else {
107                 success = GHOST_kFailure;
108         }
109         return success;
110 }
111
112
113 GHOST_TSuccess GHOST_DisplayManagerWin32::getCurrentDisplaySetting(GHOST_TUns8 display, GHOST_DisplaySetting& setting) const
114 {
115         GHOST_ASSERT((display==kMainDisplay), "GHOST_DisplayManagerWin32::getCurrentDisplaySetting(): only main display is supported");
116         return getDisplaySetting(kMainDisplay, ENUM_CURRENT_SETTINGS, setting);
117 }
118
119
120 GHOST_TSuccess GHOST_DisplayManagerWin32::setCurrentDisplaySetting(GHOST_TUns8 display, const GHOST_DisplaySetting& setting)
121 {
122         GHOST_ASSERT((display==kMainDisplay), "GHOST_DisplayManagerWin32::setCurrentDisplaySetting(): only main display is supported");
123
124         GHOST_DisplaySetting match;
125         findMatch(display, setting, match);
126         DEVMODE dm;
127         int i = 0;
128         while (::EnumDisplaySettings(NULL, i++, &dm)) {
129                 if ((dm.dmBitsPerPel == match.bpp) &&
130                         (dm.dmPelsWidth == match.xPixels) &&
131                         (dm.dmPelsHeight == match.yPixels) &&
132                         (dm.dmDisplayFrequency == match.frequency)) {
133                         break;
134                 }
135         }
136         /*
137         dm.dmBitsPerPel = match.bpp;
138         dm.dmPelsWidth = match.xPixels;
139         dm.dmPelsHeight = match.yPixels;
140         dm.dmDisplayFrequency = match.frequency;
141         dm.dmFields = DM_BITSPERPEL | DM_PELSWIDTH | DM_PELSHEIGHT | DM_DISPLAYFREQUENCY;
142         dm.dmSize = sizeof(DEVMODE);
143         dm.dmDriverExtra = 0;
144         */
145 #ifdef GHOST_DEBUG
146         printf("display change: Requested settings:\n");
147         printf("  dmBitsPerPel=%d\n", dm.dmBitsPerPel);
148         printf("  dmPelsWidth=%d\n", dm.dmPelsWidth);
149         printf("  dmPelsHeight=%d\n", dm.dmPelsHeight);
150         printf("  dmDisplayFrequency=%d\n", dm.dmDisplayFrequency);
151 #endif // GHOST_DEBUG
152
153         LONG status = ::ChangeDisplaySettings(&dm, CDS_FULLSCREEN);
154 #ifdef GHOST_DEBUG
155         switch (status)
156         {
157         case DISP_CHANGE_SUCCESSFUL:
158                 printf("display change: The settings change was successful.\n");
159                 break;
160         case DISP_CHANGE_RESTART:
161                 printf("display change: The computer must be restarted in order for the graphics mode to work.\n");
162                 break;
163         case DISP_CHANGE_BADFLAGS:
164                 printf("display change: An invalid set of flags was passed in.\n");
165                 break;
166         case DISP_CHANGE_BADPARAM:
167                 printf("display change: An invalid parameter was passed in. This can include an invalid flag or combination of flags.\n");
168                 break;
169         case DISP_CHANGE_FAILED:
170                 printf("display change: The display driver failed the specified graphics mode.\n");
171                 break;
172         case DISP_CHANGE_BADMODE:
173                 printf("display change: The graphics mode is not supported.\n");
174                 break;
175         case DISP_CHANGE_NOTUPDATED:
176                 printf("display change: Windows NT: Unable to write settings to the registry.\n");
177                 break;
178         default:
179                 printf("display change: Return value invalid\n");
180                 break;
181         }
182 #endif // GHOST_DEBUG
183         return status == DISP_CHANGE_SUCCESSFUL? GHOST_kSuccess : GHOST_kFailure;
184 }