标签: 数字振动设置

利用Nvidia的API设置数字振动数值源码_显示器亮度、对比度等设置源码

开始是一位朋友有这个需求,他给了我一个英伟达官网的开发包,名字是:R410-developer.zip(诸位可以自己到英伟达官网下载),里面提供了一些示例,包含自定义分辨率、显示器颜色设置等,但是显示器色彩设置的例子一致没有跑通,而且我也没有找到哪个参数是可以设置数字振动值的,所以憋屈了很多天。但直到看到了一个 AHK 版本实现的设置工具通过代码发现,其实实现方法是通过 nvapi.dll 动态库导出的一个查询函数地址的方法,将指定接口导出来执行具体业务。在加上在 github 上搜索的各类示例,最终实现了这个功能,下面详细介绍实现步骤。 需要的方法和结构设置数字振动数值需要先通过 nvapi.dll 导出的 NvAPI_QueryInterface_t 方法获取 NvAPI_Initialize_t 方法来初始化 NvAPI。然后依次获取显示器句柄、获取当前显示器数字振动值、设置数字振动值的函数地址,他们的声明分别对应如下:12345678910// 查询在 nvapi.dll 中函数的地址方法函数声明typedef int*(*NvAPI_QueryInterface_t)(unsigned int offset);// 初始化 NvAPI 的方法typedef int(*NvAPI_Initialize_t)();// 根据 ID 枚举显示器句柄的方法typedef int(*NvAPI_EnumNvidiaDisplayHandle_t)(int thisEnum, int* pNvDispHandle);// 获取数字振动当前值typedef int(*NvAPI_GetDVCInfoEx_t)(int hNvDisplay, int outputId, NV_DISPLAY_DVC_INFO_EX* pDVCInfo);// 设置数字振动值typedef int(*NvAPI_SetDVCLevelEx_t)(int hNvDisplay, int outputId, NV_DISPLAY_DVC_INFO_EX* pDVCInfo); 其中设置和获取数字振动值需要一个结构体 NV_DISPLAY_DVC_INFO_EX,其声明如下:12345678typedef struct{ unsigned int version; // 结构体版本 int currentLevel; // 当前级别 int minLevel; // 最低级别 int maxLevel; // 最高级别 int defaultLevel; // 默认级别} NV_DISPLAY_DVC_INFO_EX, *PNV_DISPLAY_DVC_INFO_EX; 获取各个接口地址我们首先 Load nvapi.dll 然后得到 nvapi_QueryInterface 方法的地址,然后通过 nvapi_QueryInterface 方法查询另外一些接口的地址。如下所示:123456789101112131415161718192021222324bool NvController::Initialize(){ hModule = LoadLibraryW(TEXT("nvapi.dll")); if (hModule == nullptr) { std::cerr << "Failed to load nvapi.dll." << std::endl; return false; } NvAPI_QueryInterface = (NvAPI_QueryInterface_t)GetProcAddress(hModule, "nvapi_QueryInterface"); NvAPI_Initialize = (NvAPI_Initialize_t)(*NvAPI_QueryInterface)(_NvAPI_Initialize); NvAPI_EnumNvidiaDisplayHandle = (NvAPI_EnumNvidiaDisplayHandle_t)(*NvAPI_QueryInterface)(_NvAPI_EnumNvidiaDisplayHandle); NvAPI_GetDVCInfoEx = (NvAPI_GetDVCInfoEx_t)(*NvAPI_QueryInterface)(_NvAPI_GetDVCInfoEx); NvAPI_SetDVCLevelEx = (NvAPI_SetDVCLevelEx_t)(*NvAPI_QueryInterface)(_NvAPI_SetDVCLevelEx); _NvAPI_Status status = (_NvAPI_Status)(*NvAPI_Initialize)(); if (status != NVAPI_OK) { std::cerr << "NvAPI initialization failed." << std::endl; return false; } return true;} 其中以下划线开头的枚举名字是每个函数在 dll 中的对应地址,这些是写死的,如下所示:12345678enum NvAPIs{ _NvAPI_Initialize = 0x150E828, _NvAPI_EnumNvidiaDisplayHandle = 0x9ABDD40D, _NvAPI_GetAssociatedNvidiaDisplayName = 0x22A78B05, _NvAPI_GetDVCInfoEx = 0x0E45002D, _NvAPI_SetDVCLevelEx = 0x4A82C2B1}; 你可能会问,你怎么知道这些函数地址的?其实我也是搜索到的,也看了以前 NvAPI 老版本提供的代码,可以搜索到相关痕迹。点击查看此文件里面有完整的所有函数地址。 获取和设置数字振动得到了各个函数的地址,我们就可以设置数字振动值了,代码如下:12345678910111213141516171819202122232425bool NvController::SetDVCLevelEx(int nDisp, int level){ int NvDispHandle; if (EnumNvidiaDisplayHandle(nDisp, &NvDispHandle) != 0) { NV_DISPLAY_DVC_INFO_EX oldInfo = GetDvcInfoEx(nDisp); NV_DISPLAY_DVC_INFO_EX info; info.version = oldInfo.version; info.currentLevel = level; info.minLevel = oldInfo.minLevel; info.maxLevel = oldInfo.maxLevel; info.defaultLevel = oldInfo.defaultLevel; _NvAPI_Status status = (_NvAPI_Status)(*NvAPI_SetDVCLevelEx)(NvDispHandle, 0, &info); if (status != NVAPI_OK) { return false; } return true; } return false;} 我们首先获得用户传入的显示器编号所对应的句柄,然后根据这个句柄获取当前数字振动的数值,然后修改其 currentLevel 成员数值来设置数字振动效果。这样处理后就可以使用了。完整代码参考地址:https://github.com/nmgwddj/nvapi-example 转载自https://cloud.tencent.com/developer/article/13715644. 屏幕亮度,对比度获取和调节 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960bool set_screen_brightness(long val){ HWND hDesktopWnd = GetDesktopWindow(); HMONITOR hMonitor = MonitorFromWindow(hDesktopWnd, MONITOR_DEFAULTTOPRIMARY); DWORD cPhysicalMonitors = 0; if (!GetNumberOfPhysicalMonitorsFromHMONITOR(hMonitor, &cPhysicalMonitors)) return false; LPPHYSICAL_MONITOR pPhysicalMonitors = (LPPHYSICAL_MONITOR)malloc(cPhysicalMonitors* sizeof(PHYSICAL_MONITOR)); if (pPhysicalMonitors) { GetPhysicalMonitorsFromHMONITOR(hMonitor, cPhysicalMonitors, pPhysicalMonitors); //设置屏幕亮度 SetMonitorBrightness(pPhysicalMonitors->hPhysicalMonitor, val); //设置屏幕对比度 //SetMonitorContrast(pPhysicalMonitors->hPhysicalMonitor, val); // Close the monitor handles. DestroyPhysicalMonitors(cPhysicalMonitors, pPhysicalMonitors); // Free the array. free(pPhysicalMonitors); } return true;}long get_screen_brightness(){ long lret = -1; HWND hDesktopWnd = GetDesktopWindow(); HMONITOR hMonitor = MonitorFromWindow(hDesktopWnd, MONITOR_DEFAULTTOPRIMARY); DWORD dwMin = 0, dwMax = 0, dwCur = 0; DWORD cPhysicalMonitors = 0; if (!GetNumberOfPhysicalMonitorsFromHMONITOR(hMonitor, &cPhysicalMonitors)) return false; LPPHYSICAL_MONITOR pPhysicalMonitors = (LPPHYSICAL_MONITOR)malloc(cPhysicalMonitors* sizeof(PHYSICAL_MONITOR)); if (pPhysicalMonitors) { GetPhysicalMonitorsFromHMONITOR(hMonitor, cPhysicalMonitors, pPhysicalMonitors); //获取屏幕对比度 //if (GetMonitorContrast(pPhysicalMonitors->hPhysicalMonitor, &dwMin, &dwCur, &dwMax)) //获取屏幕亮度 if (GetMonitorBrightness(pPhysicalMonitors->hPhysicalMonitor, &dwMin, &dwCur, &dwMax)) { lret = dwCur; } //SetMonitorContrast(pPhysicalMonitors->hPhysicalMonitor, val); // Close the monitor handles. DestroyPhysicalMonitors(cPhysicalMonitors, pPhysicalMonitors); // Free the array. free(pPhysicalMonitors); } return lret;} 屏幕色彩灰度调节(Gamma调节)12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758// #pragma pack(push, 4)// typedef struct _tagD3dGammaramp_t// {// WORD red[256];// WORD green[256];// WORD blue[256];// }D3DGAMMARAMP, *LPD3DGAMMARAMP;// #pragma pack(pop)class CScreenDC{public: CScreenDC(){ m_hdc = GetDC(NULL); } ~CScreenDC(){ if (m_hdc) ReleaseDC(NULL, m_hdc); m_hdc = NULL; } operator HDC(){ return m_hdc; }private: HDC m_hdc;};bool set_screen_gray(long val){ //HDC的对比度 val = min(100, val); val = max(0, val); val = val*128.0 / 100; /* bright >=0 && bright <= 128 */ CScreenDC hScreenDc; D3DGAMMARAMP Ramp = { 0 }; BOOL bret = GetDeviceGammaRamp(hScreenDc, &Ramp); if (!bret) return false; for (int iIndex = 0; iIndex < 256; iIndex++) { //bright 为什么需要+128,因为当 bring < 128 的时候效果同bright = 0 Ramp.red[iIndex] = min(65535, iIndex * (val + 128)); Ramp.green[iIndex] = min(65535, iIndex * (val + 128)); Ramp.blue[iIndex] = min(65535, iIndex * (val + 128)); } bret = SetDeviceGammaRamp(hScreenDc, &Ramp); return bret ? true:false;}long get_screen_gray(){ CScreenDC hScreenDc; D3DGAMMARAMP Ramp = { 0 }; BOOL bret = GetDeviceGammaRamp(hScreenDc, &Ramp); if (!bret) return -1; long bright = Ramp.red[1] - 128; bright = bright * 100.0 / 128; bright = min(100, bright); bright = max(0, bright); return bright;} 鼠标移动速度调节123456789101112131415161718bool set_mousemove_speed(long val){ //其接收范围在1(最慢)和20(最快)之间的值。值为10是 val = min(20, val); val = max(1, val); BOOL bret = SystemParametersInfo(SPI_SETMOUSESPEED, 0, (LPVOID)val, SPIF_UPDATEINIFILE || SPIF_SENDCHANGE || SPIF_SENDWININICHANGE); if (!bret) return false; return true;}long get_mousemove_speed(){ int nSpeed = 0; BOOL bret = SystemParametersInfo(SPI_GETMOUSESPEED, 0, &nSpeed, 0); if (!bret) return -1; return nSpeed;} 鼠标双击速度调节1234567891011121314151617181920//方法1:SystemParametersInfo(SPI_SETDOUBLECLICKTIME....bool set_mousedbclick_speed(long val){ //最快200ms 最慢 900ms 间隔70ms //SPI_SETDOUBLECLICKTIME val = 550 - (val - 10) * 35; val = min(900, val); val = max(200, val); BOOL bret = SetDoubleClickTime(val); if (!bret) return false; return true;}UINT get_mousedbclick_speed(){ UINT ival = GetDoubleClickTime(); ival = (ival - 550) / 35 + 10; return ival;} 转自 https://blog.csdn.net/CAir2/article/details/103897288 华夏网盟的成品下载 链接:https://share.weiyun.com/GJUzRJLE 密码:6jaisr