Как использовать функции GetMonitorCapabilities и GetMonitorBrightness
Я пытаюсь настроить яркость монитора программно. После небольшого исследования я придумал это ссылке, и написал следующий код (в основном копипаст с других ссылок, которые ведут меня).
#include "Windows.h"
#include "WinUser.h"
#include "PhysicalMonitorEnumerationAPI.h"
#include "HighLevelMonitorConfigurationAPI.h"
#include <strsafe.h>
void ShowError(LPTSTR lpszFunction);
int main()
{
HMONITOR hMonitor = NULL;
DWORD cPhysicalMonitors;
LPPHYSICAL_MONITOR pPhysicalMonitors = NULL;
HWND hWnd = GetDesktopWindow();
// Get the monitor handle.
hMonitor = MonitorFromWindow(hWnd, MONITOR_DEFAULTTOPRIMARY);
// Get the number of physical monitors.
BOOL bSuccess = GetNumberOfPhysicalMonitorsFromHMONITOR(hMonitor, &cPhysicalMonitors);
if (bSuccess)
{
// Allocate the array of PHYSICAL_MONITOR structures.
pPhysicalMonitors = (LPPHYSICAL_MONITOR)malloc(cPhysicalMonitors* sizeof(PHYSICAL_MONITOR));
if (pPhysicalMonitors != NULL)
{
// Get the array.
bSuccess = GetPhysicalMonitorsFromHMONITOR( hMonitor, cPhysicalMonitors, pPhysicalMonitors);
// Get physical monitor handle.
HANDLE hPhysicalMonitor = pPhysicalMonitors[0].hPhysicalMonitor;
LPDWORD pdwMinimumBrightness = NULL;
LPDWORD pdwCurrentBrightness = NULL;
LPDWORD pdwMaximumBrightness = NULL;
bSuccess = GetMonitorBrightness(hPhysicalMonitor, pdwMinimumBrightness, pdwCurrentBrightness, pdwMaximumBrightness);
if (bSuccess == FALSE)
{
ShowError(TEXT("GetMonitorBrightness"));
}
// Close the monitor handles.
bSuccess = DestroyPhysicalMonitors(cPhysicalMonitors, pPhysicalMonitors);
// Free the array.
free(pPhysicalMonitors);
}
}
return 0;
}
void ShowError(LPTSTR lpszFunction)
{
// Retrieve the system error message for the last-error code
LPVOID lpMsgBuf;
LPVOID lpDisplayBuf;
DWORD dw = GetLastError();
FormatMessage(
FORMAT_MESSAGE_ALLOCATE_BUFFER |
FORMAT_MESSAGE_FROM_SYSTEM |
FORMAT_MESSAGE_IGNORE_INSERTS,
NULL,
dw,
MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
(LPTSTR) &lpMsgBuf,
0, NULL );
// Display the error message and exit the process
lpDisplayBuf = (LPVOID)LocalAlloc(LMEM_ZEROINIT,
(lstrlen((LPCTSTR)lpMsgBuf) + lstrlen((LPCTSTR)lpszFunction) + 40) * sizeof(TCHAR));
StringCchPrintf((LPTSTR)lpDisplayBuf,
LocalSize(lpDisplayBuf) / sizeof(TCHAR),
TEXT("%s failed with error %d: %s"),
lpszFunction, dw, lpMsgBuf);
MessageBox(NULL, (LPCTSTR)lpDisplayBuf, TEXT("Error"), MB_OK);
LocalFree(lpMsgBuf);
LocalFree(lpDisplayBuf);
}
этот код аварийно завершает работу при выполнении этой строки:
bSuccess = GetMonitorBrightness(hPhysicalMonitor, pdwMinimumBrightness, pdwCurrentBrightness, pdwMaximumBrightness);
согласно документации, эта функция может не поддерживаться.
если эта функция поддерживается, функция GetMonitorCapabilities возвращает флаг MC_CAPS_BRIGHTNESS.
Итак, чтобы проверить это, я добавляю следующий блок в свой код, непосредственно перед вызовом GetMonitorBrightness
.
LPDWORD pdwMonitorCapabilities = NULL;
LPDWORD pdwSupportedColorTemperatures = NULL;
bSuccess = GetMonitorCapabilities(hPhysicalMonitor, pdwMonitorCapabilities, pdwSupportedColorTemperatures);
if (bSuccess == FALSE)
{
ShowError(TEXT("GetMonitorCapabilities"));
}
к сожалению, после того, как я добавил этот блок, я получил следующую ошибку:
опять же, по данным документация, GetMonitorCapabilities
сбой функции, если монитор не поддерживает DDC / CI.
затем я проверил, если мой монитор поддерживает DDC / CI и выяснил, что это так. Кроме того, когда я вручную отключаю поддержку DDC/CI из настроек монитора, предыдущее сообщение об ошибке переключается на следующее, поэтому теперь я уверен мой монитор имеет поддержку DDC/CI.
Я чувствую, что я делаю все правильно, но, видимо, я не. Короче говоря,GetMonitorCapabilities
функция не работает с сообщением об ошибке, которое я не могу дать никакого значения, и получает разбитый.
Примечания:
мой монитор Dell U2713H.
Я на 64 бит Windows 7.
Я использую компилятор Microsoft Visual C++ 12.0 (x86)
1 ответов
ваши звонки в GetMonitorBrightness()
и GetMonitorCapabilities()
ошибаетесь. Вы передаете нулевые указатели, но они ожидают указателей на фактическое DWORD
вместо переменных:
DWORD dwMinimumBrightness = 0;
DWORD dwCurrentBrightness = 0;
DWORD dwMaximumBrightness = 0;
bSuccess = GetMonitorBrightness(hPhysicalMonitor, &dwMinimumBrightness, &dwCurrentBrightness, &dwMaximumBrightness);
DWORD dwMonitorCapabilities = 0;
DWORD dwSupportedColorTemperatures = 0;
bSuccess = GetMonitorCapabilities(hPhysicalMonitor, &dwMonitorCapabilities, &dwSupportedColorTemperatures);