From ac7e408d26a6f6765e0aac535e849257f879a83a Mon Sep 17 00:00:00 2001 From: Matthew Malensek Date: Sun, 8 Mar 2015 23:55:44 -0600 Subject: [PATCH] Move display enumeration functionality to DisplayManager --- 3RVX/3RVX.cpp | 8 +-- 3RVX/3RVX.vcxproj | 3 +- 3RVX/3RVX.vcxproj.filters | 9 ++- 3RVX/{Monitor.cpp => DisplayManager.cpp} | 43 +++++------ 3RVX/DisplayManager.h | 25 +++++++ 3RVX/Monitor.h | 53 +++++++++++--- 3RVX/OSD/EjectOSD.cpp | 4 +- 3RVX/OSD/EjectOSD.h | 2 +- 3RVX/OSD/OSD.cpp | 92 +++++++++++++----------- 3RVX/OSD/OSD.h | 12 ++-- 3RVX/OSD/VolumeOSD.cpp | 4 +- 3RVX/OSD/VolumeOSD.h | 2 +- SettingsUI/Display.cpp | 4 +- SettingsUI/SettingsUI.vcxproj | 3 +- SettingsUI/SettingsUI.vcxproj.filters | 9 ++- 15 files changed, 174 insertions(+), 99 deletions(-) rename 3RVX/{Monitor.cpp => DisplayManager.cpp} (62%) create mode 100644 3RVX/DisplayManager.h diff --git a/3RVX/3RVX.cpp b/3RVX/3RVX.cpp index c103473b..5c564a95 100644 --- a/3RVX/3RVX.cpp +++ b/3RVX/3RVX.cpp @@ -7,12 +7,12 @@ #include #include "3RVX.h" -#include "OSD\EjectOSD.h" -#include "OSD\VolumeOSD.h" +#include "DisplayManager.h" #include "HotkeyInfo.h" #include "HotkeyManager.h" #include "Logger.h" -#include "Monitor.h" +#include "OSD\EjectOSD.h" +#include "OSD\VolumeOSD.h" #include "Settings.h" #include "SkinManager.h" @@ -117,7 +117,7 @@ void init() { SkinManager::Instance()->LoadSkin(settings->SkinXML()); /* TODO: Detect monitor changes, update this map, and reload/reorg OSDs */ - Monitor::UpdateMonitorMap(); + DisplayManager::UpdateMonitorMap(); /* OSDs */ eOSD = new EjectOSD(); diff --git a/3RVX/3RVX.vcxproj b/3RVX/3RVX.vcxproj index 4d0644f7..aea89e0d 100644 --- a/3RVX/3RVX.vcxproj +++ b/3RVX/3RVX.vcxproj @@ -81,6 +81,7 @@ + @@ -124,6 +125,7 @@ + @@ -141,7 +143,6 @@ - diff --git a/3RVX/3RVX.vcxproj.filters b/3RVX/3RVX.vcxproj.filters index aaa93706..07db8df2 100644 --- a/3RVX/3RVX.vcxproj.filters +++ b/3RVX/3RVX.vcxproj.filters @@ -141,6 +141,9 @@ Header Files + + Header Files + @@ -182,9 +185,6 @@ Source Files - - Source Files - Source Files @@ -245,6 +245,9 @@ Source Files + + Source Files + diff --git a/3RVX/Monitor.cpp b/3RVX/DisplayManager.cpp similarity index 62% rename from 3RVX/Monitor.cpp rename to 3RVX/DisplayManager.cpp index 6b08050f..c567b7d6 100644 --- a/3RVX/Monitor.cpp +++ b/3RVX/DisplayManager.cpp @@ -1,38 +1,48 @@ -#include "Monitor.h" +#include "DisplayManager.h" -static std::unordered_map monitorMap; +static std::unordered_map monitorMap; -HMONITOR Monitor::Primary() { +std::unordered_map &DisplayManager::MonitorMap() { + return monitorMap; +} + +void DisplayManager::UpdateMonitorMap() { + monitorMap.clear(); + EnumDisplayMonitors(NULL, NULL, &MonitorEnumProc, NULL); +} + +Monitor DisplayManager::Primary() { /* The Primary or 'Main' monitor is at (0, 0). */ const POINT p = { 0, 0 }; HMONITOR monitor = MonitorFromPoint(p, MONITOR_DEFAULTTOPRIMARY); - return monitor; + MONITORINFO mInfo = Info(monitor); + return Monitor(L"Primary", mInfo.rcMonitor); } -const int Monitor::Width(HMONITOR monitor) { +const int DisplayManager::Width(HMONITOR monitor) { MONITORINFO mInfo = Info(monitor); RECT mDims = mInfo.rcMonitor; return mDims.right - mDims.left; } -const int Monitor::Height(HMONITOR monitor) { +const int DisplayManager::Height(HMONITOR monitor) { MONITORINFO mInfo = Info(monitor); RECT mDims = mInfo.rcMonitor; return mDims.bottom - mDims.top; } -RECT Monitor::Rect(HMONITOR monitor) { +RECT DisplayManager::Rect(HMONITOR monitor) { return Info(monitor).rcMonitor; } -MONITORINFO Monitor::Info(HMONITOR monitor) { +MONITORINFO DisplayManager::Info(HMONITOR monitor) { MONITORINFO mInfo = {}; mInfo.cbSize = sizeof(MONITORINFO); GetMonitorInfo(monitor, &mInfo); return mInfo; } -std::list Monitor::ListAllDevices() { +std::list DisplayManager::ListAllDevices() { std::list devs; DISPLAY_DEVICE dev = {}; dev.cb = sizeof(DISPLAY_DEVICE); @@ -44,25 +54,16 @@ std::list Monitor::ListAllDevices() { return devs; } -std::unordered_map Monitor::MonitorMap() { - return monitorMap; -} - -void Monitor::UpdateMonitorMap() { - EnumDisplayMonitors(NULL, NULL, &MonitorEnumProc, NULL); -} - -BOOL CALLBACK Monitor::MonitorEnumProc( +BOOL CALLBACK DisplayManager::MonitorEnumProc( HMONITOR hMonitor, HDC hdcMonitor, LPRECT lprcMonitor, LPARAM dwData) { - monitorMap.clear(); - MONITORINFOEX mInfo = {}; mInfo.cbSize = sizeof(MONITORINFOEX); GetMonitorInfo(hMonitor, &mInfo); std::wstring monitorName = std::wstring(mInfo.szDevice); - monitorMap[monitorName] = hMonitor; + Monitor mon(monitorName, mInfo.rcMonitor); + monitorMap[monitorName] = mon; return TRUE; } \ No newline at end of file diff --git a/3RVX/DisplayManager.h b/3RVX/DisplayManager.h new file mode 100644 index 00000000..9ced608e --- /dev/null +++ b/3RVX/DisplayManager.h @@ -0,0 +1,25 @@ +#pragma once +#include +#include +#include +#include +#include + +#include "Monitor.h" + +class DisplayManager { +public: + static std::unordered_map &MonitorMap(); + static void UpdateMonitorMap(); + static Monitor Primary(); + static std::list ListAllDevices(); + +private: + static MONITORINFO Info(HMONITOR monitor); + static const int Width(HMONITOR monitor); + static const int Height(HMONITOR monitor); + static RECT Rect(HMONITOR monitor); + + static BOOL CALLBACK MonitorEnumProc( + HMONITOR hMonitor, HDC hdcMonitor, LPRECT lprcMonitor, LPARAM dwData); +}; \ No newline at end of file diff --git a/3RVX/Monitor.h b/3RVX/Monitor.h index b3f3d5a5..69cbd3ee 100644 --- a/3RVX/Monitor.h +++ b/3RVX/Monitor.h @@ -1,3 +1,5 @@ +#pragma once + #include #include #include @@ -5,17 +7,48 @@ class Monitor { public: - static HMONITOR Primary(); - static MONITORINFO Info(HMONITOR monitor); - static const int Width(HMONITOR monitor); - static const int Height(HMONITOR monitor); - static RECT Rect(HMONITOR monitor); - static std::list ListAllDevices(); + Monitor() { + + } + + Monitor(std::wstring name, int x, int y, int width, int height) : + _name(name), + _x(x), + _y(y), + _width(width), + _height(height) { + + } + + Monitor(std::wstring name, RECT rect) : + _name(name), + _x(rect.left), + _y(rect.top), + _width(rect.right - rect.left), + _height(rect.bottom - rect.top) { + + } + + int X() { + return _x; + } + + int Y() { + return _y; + } + + int Width() { + return _width; + } - static void UpdateMonitorMap(); - static std::unordered_map MonitorMap(); + int Height() { + return _height; + } private: - static BOOL CALLBACK MonitorEnumProc( - HMONITOR hMonitor, HDC hdcMonitor, LPRECT lprcMonitor, LPARAM dwData); + std::wstring _name; + int _x; + int _y; + int _width; + int _height; }; \ No newline at end of file diff --git a/3RVX/OSD/EjectOSD.cpp b/3RVX/OSD/EjectOSD.cpp index 5e1cd6b9..1f7f93f0 100644 --- a/3RVX/OSD/EjectOSD.cpp +++ b/3RVX/OSD/EjectOSD.cpp @@ -26,7 +26,7 @@ _mWnd(L"3RVX-EjectOSD", L"3RVX-EjectOSD") { _mWnd.Update(); _mWnd.VisibleDuration(Settings::Instance()->HideDelay()); - UpdateWindowPositions(MonitorHandles()); + UpdateWindowPositions(ActiveMonitors()); } EjectOSD::~EjectOSD() { @@ -36,7 +36,7 @@ void EjectOSD::Hide() { _mWnd.Hide(false); } -void EjectOSD::UpdateWindowPositions(std::vector monitors) { +void EjectOSD::UpdateWindowPositions(std::vector monitors) { PositionWindow(monitors[0], _mWnd); } diff --git a/3RVX/OSD/EjectOSD.h b/3RVX/OSD/EjectOSD.h index f682b9f9..89511155 100644 --- a/3RVX/OSD/EjectOSD.h +++ b/3RVX/OSD/EjectOSD.h @@ -14,7 +14,7 @@ class EjectOSD : public OSD { private: MeterWnd _mWnd; - virtual void UpdateWindowPositions(std::vector monitors); + virtual void UpdateWindowPositions(std::vector monitors); virtual LRESULT WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam); diff --git a/3RVX/OSD/OSD.cpp b/3RVX/OSD/OSD.cpp index 175997b8..d554727e 100644 --- a/3RVX/OSD/OSD.cpp +++ b/3RVX/OSD/OSD.cpp @@ -3,6 +3,7 @@ #include #include "..\3RVX.h" +#include "..\DisplayManager.h" #include "..\HotkeyInfo.h" #include "..\Monitor.h" @@ -47,25 +48,29 @@ void OSD::HideOthers(OSDType except = All) { SendMessage(_masterWnd, WM_3RVX_CONTROL, MSG_HIDEOSD, except); } -std::vector OSD::MonitorHandles() { - std::vector monitors; +std::vector OSD::ActiveMonitors() { + std::vector monitors; std::wstring monitorStr = Settings::Instance()->Monitor(); if (monitorStr == L"") { /* Primary Monitor */ - monitors.push_back(Monitor::Primary()); + monitors.push_back(DisplayManager::Primary()); CLOG(L"Monitor: (Primary)"); } else if (monitorStr == L"*") { /* All Monitors */ - std::unordered_map map = Monitor::MonitorMap(); + std::unordered_map map + = DisplayManager::MonitorMap(); + for (auto it = map.begin(); it != map.end(); ++it) { CLOG(L"Monitor: %s", it->first.c_str()); monitors.push_back(it->second); } } else { /* Specific Monitor */ - std::unordered_map map = Monitor::MonitorMap(); + std::unordered_map map + = DisplayManager::MonitorMap(); + for (auto it = map.begin(); it != map.end(); ++it) { if (monitorStr == it->first) { CLOG(L"Monitor: %s", it->first.c_str()); @@ -78,7 +83,7 @@ std::vector OSD::MonitorHandles() { return monitors; } -void OSD::PositionWindow(HMONITOR monitor, MeterWnd &mWnd) { +void OSD::PositionWindow(Monitor monitor, MeterWnd &mWnd) { Settings::OSDPos pos = Settings::Instance()->OSDPosition(); if (pos == Settings::OSDPos::Custom) { @@ -89,6 +94,32 @@ void OSD::PositionWindow(HMONITOR monitor, MeterWnd &mWnd) { return; } + int offset = Settings::Instance()->OSDEdgeOffset(); + + /* Edge cases ;-) */ + switch (pos) { + case Settings::TopLeft: + mWnd.X(monitor.X() + offset); + mWnd.Y(monitor.Y() + offset); + return; + + case Settings::TopRight: + mWnd.X(monitor.X() + monitor.Width() - mWnd.Width() - offset); + mWnd.Y(monitor.Y() + offset); + return; + + case Settings::BottomLeft: + mWnd.X(monitor.X() + offset); + mWnd.Y(monitor.Y() + monitor.Height() - mWnd.Height() - offset); + return; + + case Settings::BottomRight: + mWnd.X(monitor.X() + monitor.Width() - mWnd.Width() - offset); + mWnd.Y(monitor.Y() + monitor.Height() - mWnd.Height() - offset); + return; + } + + /* Center */ CenterWindowX(monitor, mWnd); CenterWindowY(monitor, mWnd); if (pos == Settings::OSDPos::Center) { @@ -96,57 +127,32 @@ void OSD::PositionWindow(HMONITOR monitor, MeterWnd &mWnd) { } /* We're centered. Now adjust based on top, bottom, left, or right: */ - const int mWidth = Monitor::Width(monitor); - const int mHeight = Monitor::Height(monitor); - int offset = Settings::Instance()->OSDEdgeOffset(); switch (pos) { case Settings::Top: - mWnd.Y(offset); - break; + mWnd.Y(monitor.Y() + offset); + return; case Settings::Bottom: - mWnd.Y(mHeight - mWnd.Height() - offset); - break; + mWnd.Y(monitor.Y() + monitor.Height() - mWnd.Height() - offset); + return; case Settings::Left: - mWnd.X(offset); - break; + mWnd.X(monitor.X() + offset); + return; case Settings::Right: - mWnd.X(mWidth - mWnd.Width() - offset); - break; - - case Settings::TopLeft: - mWnd.X(offset); - mWnd.Y(offset); - break; - - case Settings::TopRight: - mWnd.X(mWidth - mWnd.Width() - offset); - mWnd.Y(offset); - break; - - case Settings::BottomLeft: - mWnd.X(offset); - mWnd.Y(mHeight - mWnd.Height() - offset); - break; - - case Settings::BottomRight: - mWnd.X(mWidth - mWnd.Width() - offset); - mWnd.Y(mHeight - mWnd.Height() - offset); - break; + mWnd.X(monitor.X() + monitor.Width() - mWnd.Width() - offset); + return; } } -void OSD::CenterWindowX(HMONITOR monitor, MeterWnd &mWnd) { - const int mWidth = Monitor::Width(monitor); - mWnd.X(mWidth / 2 - mWnd.Width() / 2); +void OSD::CenterWindowX(Monitor monitor, MeterWnd &mWnd) { + mWnd.X(monitor.X() + monitor.Width() / 2 - mWnd.Width() / 2); } -void OSD::CenterWindowY(HMONITOR monitor, MeterWnd &mWnd) { - const int mHeight = Monitor::Height(monitor); - mWnd.Y(mHeight / 2 - mWnd.Height() / 2); +void OSD::CenterWindowY(Monitor monitor, MeterWnd &mWnd) { + mWnd.Y(monitor.Y() + monitor.Height() / 2 - mWnd.Height() / 2); } void OSD::ProcessHotkeys(HotkeyInfo &hki) { diff --git a/3RVX/OSD/OSD.h b/3RVX/OSD/OSD.h index 5f5f769c..054c2c42 100644 --- a/3RVX/OSD/OSD.h +++ b/3RVX/OSD/OSD.h @@ -6,6 +6,8 @@ #include "..\Settings.h" #include "OSDType.h" +class Monitor; + class OSD { public: OSD(std::wstring className, HINSTANCE hInstance = NULL); @@ -20,11 +22,11 @@ class OSD { void HideOthers(OSDType except); - virtual void UpdateWindowPositions(std::vector monitors) = 0; - std::vector MonitorHandles(); - void PositionWindow(HMONITOR monitor, MeterWnd &mWnd); - void CenterWindowX(HMONITOR monitor, MeterWnd &mWnd); - void CenterWindowY(HMONITOR monitor, MeterWnd &mWnd); + virtual void UpdateWindowPositions(std::vector monitors) = 0; + std::vector ActiveMonitors(); + void PositionWindow(Monitor monitor, MeterWnd &mWnd); + void CenterWindowX(Monitor monitor, MeterWnd &mWnd); + void CenterWindowY(Monitor monitor, MeterWnd &mWnd); static LRESULT CALLBACK StaticWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam); diff --git a/3RVX/OSD/VolumeOSD.cpp b/3RVX/OSD/VolumeOSD.cpp index 04fac683..1c394cca 100644 --- a/3RVX/OSD/VolumeOSD.cpp +++ b/3RVX/OSD/VolumeOSD.cpp @@ -143,7 +143,7 @@ void VolumeOSD::LoadSkin() { } _muteWnd.Update(); - UpdateWindowPositions(MonitorHandles()); + UpdateWindowPositions(ActiveMonitors()); /* Set up notification icon */ if (settings->NotifyIconEnabled()) { @@ -242,7 +242,7 @@ void VolumeOSD::ProcessHotkeys(HotkeyInfo &hki) { } } -void VolumeOSD::UpdateWindowPositions(std::vector monitors) { +void VolumeOSD::UpdateWindowPositions(std::vector monitors) { PositionWindow(monitors[0], _mWnd); PositionWindow(monitors[0], _muteWnd); } diff --git a/3RVX/OSD/VolumeOSD.h b/3RVX/OSD/VolumeOSD.h index 10bc0c95..06817326 100644 --- a/3RVX/OSD/VolumeOSD.h +++ b/3RVX/OSD/VolumeOSD.h @@ -52,7 +52,7 @@ class VolumeOSD : public OSD, MeterCallbackReceiver { void UpdateDeviceMenu(); void UnMute(); - virtual void UpdateWindowPositions(std::vector monitors); + virtual void UpdateWindowPositions(std::vector monitors); virtual LRESULT WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam); diff --git a/SettingsUI/Display.cpp b/SettingsUI/Display.cpp index a414b1e7..7b05342b 100644 --- a/SettingsUI/Display.cpp +++ b/SettingsUI/Display.cpp @@ -3,7 +3,7 @@ #include "Display.h" #include "afxdialogex.h" -#include "Monitor.h" +#include "DisplayManager.h" #include "Settings.h" #define MIN_EDGE -65535 @@ -124,7 +124,7 @@ BOOL Display::OnInitDialog() { _monitor.AddString(L"Primary Monitor"); _monitor.AddString(L"All Monitors"); - std::list devices = Monitor::ListAllDevices(); + std::list devices = DisplayManager::ListAllDevices(); for (DISPLAY_DEVICE dev : devices) { std::wstring devString(dev.DeviceName); _monitor.AddString(devString.c_str()); diff --git a/SettingsUI/SettingsUI.vcxproj b/SettingsUI/SettingsUI.vcxproj index 747fa164..82b172f6 100644 --- a/SettingsUI/SettingsUI.vcxproj +++ b/SettingsUI/SettingsUI.vcxproj @@ -114,6 +114,7 @@ + @@ -136,10 +137,10 @@ + - diff --git a/SettingsUI/SettingsUI.vcxproj.filters b/SettingsUI/SettingsUI.vcxproj.filters index 081a764a..4a47f842 100644 --- a/SettingsUI/SettingsUI.vcxproj.filters +++ b/SettingsUI/SettingsUI.vcxproj.filters @@ -78,6 +78,9 @@ Header Files + + Header Files + @@ -113,9 +116,6 @@ Source Files - - Source Files - Source Files @@ -134,6 +134,9 @@ Source Files + + Source Files +