来自GetMonitorInfo和GetDeviceCaps的第二台显示器的宽度和高度不正确

时间:2015-05-08 07:17:00

标签: winapi jsctypes

我想要左上角x,y和右下角x,y。并计算显示器的宽度和高度。

我的辅助显示器是1920x1080,如我的显示设置屏幕截图所示:

我以两种方式获取显示器尺寸。下面的代码是js-ctypes但我简化了所有的错误检查和其他ctypes的东西,并试图让它看起来像c。但这是一个winapi问题而不是ctypes,因此我没有用它来标记这个主题。

第一种方法:

cPoint = POINT();
GetCursorPos(&cPoint);


cMon = MonitorFromPoint(cPoint, MONITOR_DEFAULTTONEAREST);


cMonInfo = MONITORINFOEX();
cMonInfo.cbSize = MONITORINFOEX.size;
GetMonitorInfo(cMon, &cMonInfo);

lpszDriver = null;
lpszDevice = cMonInfo.szDevice;

xTopLeft = cMonInfo.rcMonitor.left;
yTopLeft = cMonInfo.rcMonitor.top;
nWidth = cMonInfo.rcMonitor.right - xTopLeft;
nHeight = cMonInfo.rcMonitor.bottom - yTopLeft;

这给了我一个以下的矩形:

_RECT(-1920, -1080, -640, -360)

右 - 左给出1280 做底部 - 顶部给出720

尺寸肯定是错误的。应该是1920的宽度和1080的高度。

然后我尝试第二种方法:

hdcScreen = CreateDC(lpszDriver, lpszDevice, null, null);
nWidth = GetDeviceCaps(hdcScreen, HORZRES);
nHeight = GetDeviceCaps(hdcScreen, VERTRES);

这给了我同样的东西,宽度为1280,高度为720.我的头脑很难受!我如何获得1920x1080?

这个方法为我的主显示器提供了正确的尺寸,所以我很困惑。

修改

我刚刚尝试了第三种方法,但问题仍然存在:

var jsMonitorEnumProc = function(hMonitor, hdcMonitor, lprcMonitor, dwData) {
    xTopLeft = lprcMonitor.contents.left;
    yTopLeft = lprcMonitor.contents.top;
    nWidth = lprcMonitor.contents.right - xTopLeft;
    nHeight = lprcMonitor.contents.bottom - yTopLeft;

    return true;
}
EnumDisplayMonitors(null, null, jsMonitorEnumProc, 0);

这给了我以下内容:

_RECT(0, 0, 1280, 1024)
_RECT(-1920, -1080, -640, -360)

第一个是我的主显示器,我们看到做底部 - 顶部给出1280,右 - 左给出1024,这是正确的我的主显示器是1280 x 1024。

但第二台显示器的高度为-360 - -1080,高度为720,宽度为640 - - 1920。我正在使用它来截取所有监视器的屏幕截图,第二个监视器将被截断。

1 个答案:

答案 0 :(得分:0)

在Win 8.1 64bit上的非dpi识别应用32位Firefox中,我可以使用大小为220的DISPLAY_DEVICE结构使用EnumDisplaySettings来获得正确的尺寸。

JS-ctypes的:

            // start - get all monitor resolutions
            var iDevNum = -1;
            while (true) {
                iDevNum++;
                var lpDisplayDevice = ostypes.TYPE.DISPLAY_DEVICE();
                lpDisplayDevice.cb = ostypes.TYPE.DISPLAY_DEVICE.size;
                var rez_EnumDisplayDevices = ostypes.API('EnumDisplayDevices')(null, iDevNum, lpDisplayDevice.address(), 0);
                //console.info('rez_EnumDisplayDevices:', rez_EnumDisplayDevices.toString(), uneval(rez_EnumDisplayDevices), cutils.jscGetDeepest(rez_EnumDisplayDevices));

                if (cutils.jscEqual(rez_EnumDisplayDevices, 0)) { // ctypes.winLastError != 0
                    // iDevNum is greater than the largest device index.
                    break;
                }

                console.info('lpDisplayDevice.DeviceName:', lpDisplayDevice.DeviceName.readString()); // "\\.\DISPLAY1" till "\\.\DISPLAY4"

                if (lpDisplayDevice.StateFlags & ostypes.CONST.DISPLAY_DEVICE_ATTACHED_TO_DESKTOP) {
                    console.log('is monitor');

                    var dm = ostypes.TYPE.DEVMODE(); // SIZEOF_DEVMODE = 148
                    console.info('dm.size:', ostypes.TYPE.DEVMODE.size);
                    //dm.dmFields = ostypes.CONST.DM_PELSWIDTH;
                    //dm.dmSize = ostypes.TYPE.DEVMODE.size;

                    console.log('iDevNum:', iDevNum, lpDisplayDevice.DeviceName.readString());
                    var rez_EnumDisplaySettings = ostypes.API('EnumDisplaySettings')(lpDisplayDevice.DeviceName, ostypes.CONST.ENUM_CURRENT_SETTINGS, dm.address());
                    //console.info('rez_EnumDisplaySettings:', rez_EnumDisplaySettings.toString(), uneval(rez_EnumDisplaySettings), cutils.jscGetDeepest(rez_EnumDisplaySettings));
                    //console.info('dm:', dm.toString());

                    collMonInfos.push({
                        x: parseInt(cutils.jscGetDeepest(dm.u.dmPosition.x)),
                        y: parseInt(cutils.jscGetDeepest(dm.u.dmPosition.y)),
                        w: parseInt(cutils.jscGetDeepest(dm.dmPelsWidth)),
                        h: parseInt(cutils.jscGetDeepest(dm.dmPelsHeight)),
                        screenshot: null, // for winnt, each collMonInfos entry has screenshot data
                        otherInfo: {
                            nBPP: parseInt(cutils.jscGetDeepest(dm.dmBitsPerPel)),
                            lpszDriver: null,
                            lpszDevice: lpDisplayDevice.DeviceName
                        }
                    });
                }
            }
            // end - get all monitor resolutions