Programmatically change display resolution






3.69/5 (6 votes)
Programmatically change display resolution from console using API call.
Introduction
Recently, on a local forum, someone asked about how to programmatically change the display resolution from a console application (he wanted to place that in a .bat file for gaming). 20 minutes later, I sent him the sources to compile, and it seems to worK OK until now. So I imagined that this little code snippet can prove useful to others.
User: How it works
This is a console application, expecting two arguments, the desired width and height. There are no assumptions or defaults, just a simple input check and the conversions to int.
C:\>chscrres 1024 768
C:\>chscrres 1280 1024
Developer: How it works
- The list of devices is enumerated in a structure called
DDList
. The structure is handled by the functionsDDList_Build
(constructs the list),DDList_Clean
(frees the list), andDDList_Pop
(extracts the first item from the list). The implementation uses a simple linked list and theEnumDisplayDevices
API to retrieve the display devices, using theDISPLAY_DEVICE_ATTACHED_TO_DESKTOP
mask. You can also use other masks as well depending on what you need. - After the list is built, the first device is extracted from the list, if any. Depending on the number of devices and/or additional conditions, you may want to impose, rewrite the
DDList_Pop
call (or implement aDDList_PopEx
to pass additional data) to get to the desiredDISPLAY_DEVICE
structure fromDDList
. - Finally, we change the resolution for the extracted device. First, the
DEVMODE
structure is retrieved using a call toEnumDisplaySettingsEx
; the existingDEVMODE
'sdmPelsWidth
/dmPelsHeight
are compared against the values passed in the command line, and, if at least one is different, theDEVMODE
structure is updated with the new width and height andChangeDisplaySettingsEx
is called to update the device.
struct DDList {
DISPLAY_DEVICE Device;
struct DDList *Next;
};
If ChangeDisplaySettingsEx
returned DISP_CHANGE_SUCCESSFUL
, then the system is informed about the display change using:
// broadcast change to system
SendMessage(HWND_BROADCAST, WM_DISPLAYCHANGE,
(WPARAM)(deviceMode.dmBitsPerPel),
MAKELPARAM(newWidth, newHeight));
(Although I tested this on XP, 2000, and NT4, there is absolutely no guarantees that this will work. I don't want to be sued for display damage. Try out and see.)