]> repos.lx-s.de Git - winmute.git/commitdiff
Fixed Display Suspend Detection. Added Notifications.
authorAlexander Steinhöfer <alexander@steinhoefer.net>
Thu, 7 Apr 2022 14:34:47 +0000 (16:34 +0200)
committerAlexander Steinhöfer <alexander@steinhoefer.net>
Thu, 7 Apr 2022 14:34:47 +0000 (16:34 +0200)
WinMute/MuteControl.cpp
WinMute/MuteControl.h
WinMute/TrayIcon.cpp
WinMute/TrayIcon.h
WinMute/WinMute.cpp
WinMute/WinMute.h
WinMute/WinMute.rc
WinMute/common.h
WinMute/resource.h

index af2b9156c2474d6d155f919f8843459a2c83707d..6c46fdaf39108e6fa08e3a7677a9b604675234f6 100644 (file)
@@ -48,6 +48,7 @@ enum MuteType {
 };
 
 MuteControl::MuteControl()
+   : trayIcon_(nullptr), notificationsEnabled_(false), displayWasOffOnce_(false)
 {
    MuteConfig initMuteConf;
    initMuteConf.active = false;
@@ -61,12 +62,13 @@ MuteControl::~MuteControl()
 {
 }
 
-bool MuteControl::Init(HWND hParent)
+bool MuteControl::Init(HWND hParent, const TrayIcon *trayIcon)
 {
    winAudio_ = std::make_unique<VistaAudio>();
    if (!winAudio_->Init(hParent)) {
       return false;
    }
+   trayIcon_ = trayIcon;
    return true;
 }
 
@@ -92,6 +94,18 @@ void MuteControl::SaveMuteStatus()
    }
 }
 
+void MuteControl::ShowNotification(const tstring& title, const tstring& text)
+{
+   if (notificationsEnabled_ && trayIcon_ != nullptr) {
+      trayIcon_->ShowPopup(title, text);
+   }
+}
+
+void MuteControl::SetNotifications(bool enable)
+{
+   notificationsEnabled_ = enable;
+}
+
 void MuteControl::RestoreVolume()
 {
    WMLog& log = WMLog::GetInstance();
@@ -109,6 +123,9 @@ void MuteControl::RestoreVolume()
    }
    if (restore) {
       log.Write(_T("Restoring previous mute state"));
+      ShowNotification(
+         _T("Volume restored"),
+         _T("All endpoints have been restored to their previous configuration"));
       winAudio_->RestoreMuteStatus();
    }
 }
@@ -200,6 +217,9 @@ void MuteControl::NotifyRestoreCondition(int type, bool active)
       muteConfig_[type].active = active;
       if (muteConfig_[type].shouldMute) {
          WMLog::GetInstance().Write(_T("Muting workstation"));
+         ShowNotification(
+            _T("Muting workstation"),
+            _T("All endpoints have been muted"));
          winAudio_->SetMute(true);
       }
    } else {
@@ -231,9 +251,12 @@ void MuteControl::NotifyRemoteSession(bool active)
 
 void MuteControl::NotifyDisplayStandby(bool active)
 {
-   WMLog::GetInstance().Write(_T("Mute Event: Display Standby {}"),
-                              active ? _T("start") : _T("stop"));
-   NotifyRestoreCondition(MuteTypeDisplayStandby, active);
+   if (displayWasOffOnce_ || active) {
+      WMLog::GetInstance().Write(_T("Mute Event: Display Standby {}"),
+                                 active ? _T("start") : _T("stop"));
+      NotifyRestoreCondition(MuteTypeDisplayStandby, active);
+      displayWasOffOnce_ = true;
+   }
 }
 
 void MuteControl::NotifyLogout()
index 4e62a1dc028e44832eba49109a5c1335801e8600..1d1f5733d6c187ca7bfdffd3ca62558698afff4e 100644 (file)
@@ -42,7 +42,10 @@ public:
    MuteControl(const MuteControl&) = delete;
    MuteControl& operator=(const MuteControl&) = delete;
 
-   bool Init(HWND hParent);
+   bool Init(HWND hParent, const TrayIcon* trayIcon);
+
+
+   void SetNotifications(bool enable);
 
    void SetMute(bool mute);
 
@@ -85,10 +88,16 @@ private:
    };
    std::vector<MuteConfig> muteConfig_;
    bool restoreVolume_;
+   bool notificationsEnabled_;
    std::unique_ptr<WinAudio> winAudio_;
 
+   bool displayWasOffOnce_; // Since a power message is sent right after registering
+                            // We skip the first "was on" message
+
+   const TrayIcon* trayIcon_;
+
    void NotifyRestoreCondition(int type, bool active);
    void SaveMuteStatus();
    void RestoreVolume();
-
+   void ShowNotification(const tstring& title, const tstring& text);
 };
index dfbaa786dbb043c455ba6bc22eff1e623545da5e..443ea60c900b84590e503b8f1fb5e790137e935b 100644 (file)
@@ -39,14 +39,14 @@ TrayIcon::TrayIcon() :
 }
 
 TrayIcon::TrayIcon(HWND hWnd, UINT trayID, HICON hIcon,
-   const std::wstring& tooltip, bool show) :
+                   const tstring& tooltip, bool show) :
    iconVisible_(false)
 {
    Init(hWnd, trayID, hIcon, tooltip, show);
 }
 
 void TrayIcon::Init(HWND hWnd, UINT trayID, HICON hIcon,
-   const std::wstring& tooltip, bool show)
+                    const tstring& tooltip, bool show)
 {
    if (!hIcon) {
       hIcon_ = LoadIcon(0, IDI_APPLICATION);
@@ -115,7 +115,7 @@ void TrayIcon::ChangeIcon(HICON hNewIcon)
    return;
 }
 
-void TrayIcon::ChangeText(const std::wstring& tooltip)
+void TrayIcon::ChangeText(const tstring& tooltip)
 {
    tooltip_ = tooltip;
 
@@ -123,9 +123,7 @@ void TrayIcon::ChangeText(const std::wstring& tooltip)
       ChangeText();
 }
 
-void TrayIcon::ShowPopup(
-   const std::wstring& title,
-   const std::wstring& text)
+void TrayIcon::ShowPopup(const tstring& title, const tstring& text) const
 {
    NOTIFYICONDATA tnid;
    tnid.cbSize = sizeof(NOTIFYICONDATA);
@@ -135,8 +133,8 @@ void TrayIcon::ShowPopup(
    tnid.dwInfoFlags = NIIF_INFO | NIIF_NOSOUND | NIIF_LARGE_ICON
       | NIIF_RESPECT_QUIET_TIME;
    tnid.uTimeout = 10 * 1000;
-   wcscpy_s(tnid.szInfoTitle, sizeof(tnid.szInfoTitle) / sizeof(TCHAR), title.c_str());
-   wcscpy_s(tnid.szInfo, sizeof(tnid.szInfo) / sizeof(TCHAR), text.c_str());
+   StringCchCopy(tnid.szInfoTitle, ARRAY_SIZE(tnid.szInfoTitle), title.c_str());
+   StringCchCopy(tnid.szInfo, ARRAY_SIZE(tnid.szInfo), text.c_str());
 
    Shell_NotifyIcon(NIM_MODIFY, &tnid);
 }
@@ -160,9 +158,7 @@ bool TrayIcon::AddNotifyIcon()
    tnid.hIcon = hIcon_;
    tnid.uCallbackMessage = WM_TRAYICON;
 
-   if (SUCCEEDED(StringCchCopy(tnid.szTip,
-      sizeof(tnid.szTip) / sizeof(TCHAR),
-      tooltip_.c_str()))) {
+   if (SUCCEEDED(StringCchCopy(tnid.szTip, ARRAY_SIZE(tnid.szTip), tooltip_.c_str()))) {
       return Shell_NotifyIcon(NIM_ADD, &tnid) != 0;
    }
    return false;
@@ -188,9 +184,7 @@ bool TrayIcon::ChangeText()
    tnid.uID = trayID_;
    tnid.uFlags = NIF_TIP;
 
-   if (SUCCEEDED(StringCchCopy(tnid.szTip,
-      sizeof(tnid.szTip) / sizeof(TCHAR),
-      tooltip_.c_str()))) {
+   if (SUCCEEDED(StringCchCopy(tnid.szTip, ARRAY_SIZE(tnid.szTip), tooltip_.c_str()))) {
       return Shell_NotifyIcon(NIM_MODIFY, &tnid) != 0;
    }
    return false;
index f8db69c79a4e849daa7560ad68a097cff7eec924..7304306883c34b24f81399bb8d4be7e8c2c39b70 100644 (file)
@@ -40,17 +40,17 @@ POSSIBILITY OF SUCH DAMAGE.
 class TrayIcon {
 public:
    TrayIcon();
-   TrayIcon(HWND hWnd, UINT trayID, HICON hIcon, const std::wstring& tooltip,
+   TrayIcon(HWND hWnd, UINT trayID, HICON hIcon, const tstring& tooltip,
       bool show);
    ~TrayIcon();
-   void Init(HWND hWnd, UINT trayID, HICON hIcon, const std::wstring& tooltip,
+   void Init(HWND hWnd, UINT trayID, HICON hIcon, const tstring& tooltip,
       bool show);
    void Hide();
    void Show();
    bool IsShown() const { return iconVisible_; }
    void ChangeIcon(HICON hNewIcon);
-   void ChangeText(const std::wstring& tooltip);
-   void ShowPopup(const std::wstring& title, const std::wstring& text);
+   void ChangeText(const tstring& tooltip);
+   void ShowPopup(const tstring& title, const tstring& text) const;
 
 private:
    void DestroyTrayIcon();
@@ -62,5 +62,5 @@ private:
    UINT trayID_;
    HICON hIcon_;
    HWND hWnd_;
-   std::wstring tooltip_;
+   tstring tooltip_;
 };
index 636a4e1cc0a1d1cc092b4ca7db77df6757a7b18e..81a4882529c37b03abc014e8c1816e0191b0947d 100644 (file)
@@ -156,10 +156,9 @@ bool WinMute::InitAudio()
       return false;
    }
 
-   if (!muteCtrl_.Init(hWnd_)) {
+   if (!muteCtrl_.Init(hWnd_, &trayIcon_)) {
       return false;
    }
-   
 
    return true;
 }
@@ -192,8 +191,11 @@ bool WinMute::Init()
 
    hAppIcon_ = LoadIcon(hglobInstance, MAKEINTRESOURCE(IDI_APP));
 
-   if (!settings_.Init() ||
-       !LoadDefaults()) {
+   if (!InitAudio()) {
+      return false;
+   }
+
+   if (!settings_.Init() || !LoadDefaults()) {
       return false;
    }
 
@@ -210,10 +212,6 @@ bool WinMute::Init()
       return false;
    }
 
-   if (!InitAudio()) {
-      return false;
-   }
-
    if (!scrnSaverNoti_.Init()) {
       return false;
    }
@@ -229,6 +227,11 @@ bool WinMute::Init()
       return false;
    }
 
+   if (!RegisterPowerSettingNotification(hWnd_, &GUID_CONSOLE_DISPLAY_STATE, 0)) {
+      PrintWindowsError(_T("RegisterPowerSettingNotification"));
+      return false;
+   }
+
    bool isDarkMode = true;
    IsDarkMode(isDarkMode);
    hTrayIcon_ = LoadIcon(
@@ -258,6 +261,10 @@ bool WinMute::LoadDefaults()
    muteCtrl_.SetMuteOnSuspend(!!settings_.QueryValue(SettingsKey::MUTE_ON_SUSPEND, 0));
    muteCtrl_.SetMuteOnShutdown(!!settings_.QueryValue(SettingsKey::MUTE_ON_SHUTDOWN, 0));
 
+   muteCtrl_.SetNotifications(settings_.QueryValue(SettingsKey::NOTIFICATIONS_ENABLED, 0) != 0);
+
+   muteConfig_.showNotifications =
+      settings_.QueryValue(SettingsKey::NOTIFICATIONS_ENABLED, 0) != 0;
    muteConfig_.quietHours.enabled =
       settings_.QueryValue(SettingsKey::QUIETHOURS_ENABLE, 0) != 0;
    muteConfig_.quietHours.forceUnmute =
@@ -308,14 +315,18 @@ LRESULT CALLBACK WinMute::WindowProc(
       case ID_TRAYMENU_EXIT:
          SendMessage(hWnd, WM_CLOSE, 0, 0);
          break;
-      case ID_TRAYMENU_SETTINGS:
+      case ID_TRAYMENU_SETTINGS: {
          DialogBoxParam(
             hglobInstance,
             MAKEINTRESOURCE(IDD_SETTINGS),
             hWnd_,
             SettingsDlgProc,
             reinterpret_cast<LPARAM>(&settings_));
+         bool notifications = settings_.QueryValue(SettingsKey::NOTIFICATIONS_ENABLED, 0) != 0;
+         muteConfig_.showNotifications = notifications;
+         muteCtrl_.SetNotifications(notifications);
          break;
+      }
       case ID_TRAYMENU_MUTE: {
          bool state = false;
          ToggleMenuCheck(ID_TRAYMENU_MUTE, &state);
@@ -348,6 +359,13 @@ LRESULT CALLBACK WinMute::WindowProc(
          }
          break;
       }
+      case ID_TRAYMENU_SCREENSUSPEND: {
+         bool checked = false;
+         ToggleMenuCheck(ID_TRAYMENU_SCREENSUSPEND, &checked);
+         muteCtrl_.SetMuteOnDisplayStandby(checked);
+         settings_.SetValue(SettingsKey::MUTE_ON_DISPLAYSTANDBY, checked);
+         break;
+      }
       case ID_TRAYMENU_MUTEONSHUTDOWN: {
          bool checked = false;
          ToggleMenuCheck(ID_TRAYMENU_MUTEONSHUTDOWN, &checked);
@@ -420,7 +438,7 @@ LRESULT CALLBACK WinMute::WindowProc(
             }
          }
       }
-      break;
+      return TRUE;
    case WM_QUERYENDSESSION:
       if (lParam == 0) { // Shutdown
          muteCtrl_.NotifyShutdown();
index 0db8eefa024b380dd629603bc84305a4ef696e42..03f85f94397dc5d0ef394bc47fd5a082a41d708f 100644 (file)
@@ -61,16 +61,7 @@ private:
 
    struct MuteConfig {
       MuteConfig();
-      /*struct {
-         bool onLock;
-         bool onScreensaver;
-      } withRestore;
-      bool restoreAudio;
-      struct {
-         bool onLogoff;
-         bool onShutdown;
-         bool onSuspend;
-      } noRestore;*/
+      bool showNotifications;
       struct {
          bool enabled;
          bool forceUnmute;
index df113888805f861ede1357d8db53a6e96d1d6368..0831b5cbc091c3d68e5060243c8f0030d8e45191 100644 (file)
@@ -76,9 +76,10 @@ STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD
 FONT 8, "MS Shell Dlg", 400, 0, 0x1
 BEGIN
     CONTROL         "Start WinMute on system startup",IDC_RUNONSTARTUP,
-                    "Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,15,132,26
-    CONTROL         "Enable Logging",IDC_ENABLELOGGING,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,61,101,21
-    CONTROL         "Show notifications",IDC_SHOWNOTIFICATIONS,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,39,86,21
+                    "Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,15,187,26
+    CONTROL         "Enable Logging",IDC_ENABLELOGGING,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,61,187,21
+    CONTROL         "Show mute event notifications",IDC_SHOWNOTIFICATIONS,
+                    "Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,39,187,21
     PUSHBUTTON      "Open Log File...",IDC_OPENLOG,22,82,58,15
 END
 
@@ -244,6 +245,7 @@ BEGIN
         MENUITEM "Mute when...",                40003, INACTIVE
         MENUITEM "... Workstation is locked",   ID_TRAYMENU_MUTEONLOCK, CHECKED
         MENUITEM "... Screensaver starts",      ID_TRAYMENU_MUTEONSCREENSAVER, CHECKED
+        MENUITEM "... Screen turns off",        ID_TRAYMENU_SCREENSUSPEND, CHECKED
         MENUITEM SEPARATOR
         MENUITEM "Restore previous volume afterwards", ID_TRAYMENU_RESTOREAUDIO, CHECKED
         MENUITEM SEPARATOR
@@ -267,8 +269,8 @@ END
 //
 
 VS_VERSION_INFO VERSIONINFO
- FILEVERSION 1,7,0,0
- PRODUCTVERSION 1,7,0,0
+ FILEVERSION 1,9,9,9
+ PRODUCTVERSION 1,9,9,9
  FILEFLAGSMASK 0x3fL
 #ifdef _DEBUG
  FILEFLAGS 0x1L
@@ -285,23 +287,23 @@ BEGIN
         BEGIN
             VALUE "CompanyName", "LX-Systems"
             VALUE "FileDescription", "WinMute"
-            VALUE "FileVersion", "1.7.0.0"
+            VALUE "FileVersion", "1.9.9.9"
             VALUE "InternalName", "WinMute.exe"
             VALUE "LegalCopyright", "Copyright (C) 2022, Alexander Steinhöfer"
             VALUE "OriginalFilename", "WinMute.exe"
             VALUE "ProductName", "WinMute"
-            VALUE "ProductVersion", "1.7.0.0"
+            VALUE "ProductVersion", "1.9.9.9"
         END
         BLOCK "040704b0"
         BEGIN
             VALUE "CompanyName", "LX-Systems"
             VALUE "FileDescription", "WinMute"
-            VALUE "FileVersion", "1.7.0.0"
+            VALUE "FileVersion", "1.9.9.9"
             VALUE "InternalName", "WinMute.exe"
             VALUE "LegalCopyright", "Copyright (C) 2022, Alexander Steinhöfer"
             VALUE "OriginalFilename", "WinMute.exe"
             VALUE "ProductName", "WinMute"
-            VALUE "ProductVersion", "1.7.0.0"
+            VALUE "ProductVersion", "1.9.9.9"
         END
     END
     BLOCK "VarFileInfo"
index 7b52dcc860d459c890fa639f2a90696f80043191..0ab3349e2347efcf62453ff8acad4d2502651af1 100644 (file)
@@ -103,3 +103,5 @@ inline void SafeRelease(Interface * *ppInterfaceToRelease)
       (*ppInterfaceToRelease) = nullptr;
    }
 }
+
+#define ARRAY_SIZE(arr) ((sizeof(arr)) / (sizeof(arr[0])))
index 2473a9c521a47f1c7b85c35eaefc9116debb342f..8e77249bd5a0a4db213b65fe0d5ba8a549bc2907 100644 (file)
 #define ID_TRAYMENU_MUTE                40023
 #define ID_TRAYMENU_MUTEONLOCK          40024
 #define ID_TRAYMENU_SETTINGS            40025
+#define ID_TRAYMENU_SCREENTURNSOFF      40026
+#define ID_TRAYMENU_SCREENSUSPEND       40027
 
 // Next default values for new objects
 // 
 #ifdef APSTUDIO_INVOKED
 #ifndef APSTUDIO_READONLY_SYMBOLS
 #define _APS_NEXT_RESOURCE_VALUE        123
-#define _APS_NEXT_COMMAND_VALUE         40026
+#define _APS_NEXT_COMMAND_VALUE         40028
 #define _APS_NEXT_CONTROL_VALUE         1021
 #define _APS_NEXT_SYMED_VALUE           101
 #endif