原理
SetDeviceGammaRamp
API函数位于 Gdi32.ll
中,接收一个 256*3 RGB
值的数组。
增加这个数组中的值会使屏幕更亮,而减少这些值会使屏幕变暗。
可以通过增加或减少的红/绿/蓝成分的值来显示影响。例如:在所有RGB值中增加蓝色分量将增加整个显示的蓝色。
下面的类封装调用 GetDeviceGammaRamp
和 SetDeviceGammaRamp
,并设置屏幕的亮度,提供 setbrightness
功能。
GammaRamp.h
#ifndef GAMMARAMP_H_
#define GAMMARAMP_H_
/*
CGammaRamp class
Encapsulates the Gamma Ramp API and changes the brightness of
the entire screen.
Written by Nir Sofer.
http://www.nirsoft.net
*/
class CGammaRamp
{
protected:
HMODULE hGDI32;
HDC hScreenDC;
typedef BOOL (WINAPI *Type_GetDeviceGammaRamp)(HDC hDC, LPVOID lpRamp);
typedef BOOL (WINAPI *Type_SetDeviceGammaRamp)(HDC hDC, LPVOID lpRamp);
Type_GetDeviceGammaRamp pGetDeviceGammaRamp;
Type_SetDeviceGammaRamp pSetDeviceGammaRamp;
public:
CGammaRamp();
~CGammaRamp();
BOOL LoadLibrary();
void FreeLibrary();
BOOL LoadLibraryIfNeeded();
BOOL SetDeviceGammaRamp(HDC hDC, LPVOID lpRamp);
BOOL GetDeviceGammaRamp(HDC hDC, LPVOID lpRamp);
BOOL SetBrightness(HDC hDC, WORD wBrightness);
};
#endif//#ifndef GAMMARAMP_H_
GammaRamp.cpp
#include <windows.h>
#include "gammaramp.h"
/*
CGammaRamp class
Encapsulates the Gamma Ramp API and changes the brightness of
the entire screen.
Written by Nir Sofer.
http://www.nirsoft.net
*/
CGammaRamp::CGammaRamp()
{
//Initialize all variables.
hGDI32 = NULL;
hScreenDC = NULL;
pGetDeviceGammaRamp = NULL;
pSetDeviceGammaRamp = NULL;
}
CGammaRamp::~CGammaRamp()
{
FreeLibrary();
}
BOOL CGammaRamp::LoadLibrary()
{
BOOL bReturn = FALSE;
FreeLibrary();
//Load the GDI library.
hGDI32 = ::LoadLibrary("gdi32.dll");
if (hGDI32 != NULL)
{
//Get the addresses of GetDeviceGammaRamp and SetDeviceGammaRamp API functions.
pGetDeviceGammaRamp = (Type_GetDeviceGammaRamp)GetProcAddress(hGDI32, "GetDeviceGammaRamp");
pSetDeviceGammaRamp = (Type_SetDeviceGammaRamp)GetProcAddress(hGDI32, "SetDeviceGammaRamp");
//Return TRUE only if these functions exist.
if (pGetDeviceGammaRamp == NULL || pSetDeviceGammaRamp == NULL)
{
FreeLibrary();
}
else
{
bReturn = TRUE;
}
}
return bReturn;
}
void CGammaRamp::FreeLibrary()
{
//Free the GDI library.
if (hGDI32 != NULL)
{
::FreeLibrary(hGDI32);
hGDI32 = NULL;
}
}
BOOL CGammaRamp::LoadLibraryIfNeeded()
{
BOOL bReturn = FALSE;
if (hGDI32 == NULL)
{
LoadLibrary();
}
if (pGetDeviceGammaRamp != NULL && pSetDeviceGammaRamp != NULL)
{
bReturn = TRUE;
}
return bReturn;
}
BOOL CGammaRamp::SetDeviceGammaRamp(HDC hDC, LPVOID lpRamp)
{
//Call to SetDeviceGammaRamp only if this function is successfully loaded.
if (LoadLibraryIfNeeded())
{
return pSetDeviceGammaRamp(hDC, lpRamp);
}
else
{
return FALSE;
}
}
BOOL CGammaRamp::GetDeviceGammaRamp(HDC hDC, LPVOID lpRamp)
{
//Call to GetDeviceGammaRamp only if this function is successfully loaded.
if (LoadLibraryIfNeeded())
{
return pGetDeviceGammaRamp(hDC, lpRamp);
}
else
{
return FALSE;
}
}
BOOL CGammaRamp::SetBrightness(HDC hDC, WORD wBrightness)
{
/*
Changes the brightness of the entire screen.
This function may not work properly in some video cards.
The wBrightness value should be a number between 0 and 255.
128 = Regular brightness
above 128 = brighter
below 128 = darker
If hDC is NULL, SetBrightness automatically load and release
the display device context for you.
*/
BOOL bReturn = FALSE;
HDC hGammaDC = hDC;
//Load the display device context of the entire screen if hDC is NULL.
if (hDC == NULL)
hGammaDC = GetDC(NULL);
if (hGammaDC != NULL)
{
//Generate the 256-colors array for the specified wBrightness value.
WORD GammaArray[3][256];
for (int iIndex = 0; iIndex < 256; iIndex++)
{
int iArrayValue = iIndex * (wBrightness + 128);
if (iArrayValue > 65535)
{
iArrayValue = 65535;
}
GammaArray[0][iIndex] =
GammaArray[1][iIndex] =
GammaArray[2][iIndex] = (WORD)iArrayValue;
}
//Set the GammaArray values into the display device context.
bReturn = SetDeviceGammaRamp(hGammaDC, GammaArray);
}
if (hDC == NULL)
{
ReleaseDC(NULL, hGammaDC);
}
return bReturn;
}
用法
#include <Windows.h>
#include "gammaramp.h"
int WINAPI WinMain(
HINSTANCE hInstance, // handle to current instance
HINSTANCE hPrevInstance, // handle to previous instance
LPSTR lpCmdLine, // command line
int nCmdShow // show state
)
{
//Example for changing the brightness with CGammaRamp class:
//Be aware that this exmaple may not work properly in all Video cards.
CGammaRamp GammaRamp;
//Make the screen darker:
GammaRamp.SetBrightness(NULL, 64);
//Wait 3 seconds:
Sleep(3000);
//Return back to normal:
GammaRamp.SetBrightness(NULL, 128);
return 0;
}
资料
Changing the screen brightness programmingly - By using the Gamma Ramp API
OωO 这个是调整伽马值,不同显示器有不同的伽马校对,不能乱调。