]> git.ipfire.org Git - thirdparty/wireguard-apple.git/commitdiff
macOS: Different status bar icon looks for different states
authorRoopesh Chander <roop@roopc.net>
Tue, 15 Jan 2019 19:30:42 +0000 (01:00 +0530)
committerRoopesh Chander <roop@roopc.net>
Tue, 15 Jan 2019 19:56:10 +0000 (01:26 +0530)
- Looks dimmed when no tunnel is active
- Looks normal when a tunnel is active
- Animates when a tunnel is activating

Signed-off-by: Roopesh Chander <roop@roopc.net>
28 files changed:
WireGuard/WireGuard.xcodeproj/project.pbxproj
WireGuard/WireGuard/Tunnel/TunnelsManager.swift
WireGuard/WireGuard/UI/macOS/AppDelegate.swift
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIcon.imageset/Contents.json [moved from WireGuard/WireGuard/UI/macOS/Assets.xcassets/WireGuardMacStatusBarIcon.imageset/Contents.json with 57% similarity]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIcon.imageset/StatusBarIcon@1x.png [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIcon.imageset/StatusBarIcon@2x.png [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIcon.imageset/StatusBarIcon@3x.png [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDimmed.imageset/Contents.json [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDimmed.imageset/StatusBarIconDimmed@1x.png [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDimmed.imageset/StatusBarIconDimmed@2x.png [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDimmed.imageset/StatusBarIconDimmed@3x.png [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot1.imageset/Contents.json [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot1.imageset/StatusBarIconDot1@1x.png [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot1.imageset/StatusBarIconDot1@2x.png [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot1.imageset/StatusBarIconDot1@3x.png [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot2.imageset/Contents.json [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot2.imageset/StatusBarIconDot2@1x.png [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot2.imageset/StatusBarIconDot2@2x.png [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot2.imageset/StatusBarIconDot2@3x.png [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot3.imageset/Contents.json [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot3.imageset/StatusBarIconDot3@1x.png [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot3.imageset/StatusBarIconDot3@2x.png [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot3.imageset/StatusBarIconDot3@3x.png [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/WireGuardMacStatusBarIcon.imageset/WireGuardMacStatusBarIcon@1x.png [deleted file]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/WireGuardMacStatusBarIcon.imageset/WireGuardMacStatusBarIcon@2x.png [deleted file]
WireGuard/WireGuard/UI/macOS/Assets.xcassets/WireGuardMacStatusBarIcon.imageset/WireGuardMacStatusBarIcon@3x.png [deleted file]
WireGuard/WireGuard/UI/macOS/StatusItemController.swift [new file with mode: 0644]
WireGuard/WireGuard/UI/macOS/StatusMenu.swift

index a5119b65164f14b40171eabe4b2423c2b885c234..b6b1c32bda8ba85362673ce4a0579a339e2ca378 100644 (file)
@@ -54,6 +54,7 @@
                6F7774EF21722D97006A79B3 /* TunnelsManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6F7774EE21722D97006A79B3 /* TunnelsManager.swift */; };
                6F7774F321774263006A79B3 /* TunnelEditTableViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6F7774F221774263006A79B3 /* TunnelEditTableViewController.swift */; };
                6F7F7E5F21C7D74B00527607 /* TunnelErrors.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6F7F7E5E21C7D74B00527607 /* TunnelErrors.swift */; };
+               6F89E17A21EDEB0E00C97BB9 /* StatusItemController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6F89E17921EDEB0E00C97BB9 /* StatusItemController.swift */; };
                6F919EC3218A2AE90023B400 /* ErrorPresenter.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6F919EC2218A2AE90023B400 /* ErrorPresenter.swift */; };
                6F919ED9218C65C50023B400 /* wireguard_doc_logo_22x29.png in Resources */ = {isa = PBXBuildFile; fileRef = 6F919ED5218C65C50023B400 /* wireguard_doc_logo_22x29.png */; };
                6F919EDA218C65C50023B400 /* wireguard_doc_logo_44x58.png in Resources */ = {isa = PBXBuildFile; fileRef = 6F919ED6218C65C50023B400 /* wireguard_doc_logo_44x58.png */; };
                6F7774EE21722D97006A79B3 /* TunnelsManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TunnelsManager.swift; sourceTree = "<group>"; };
                6F7774F221774263006A79B3 /* TunnelEditTableViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TunnelEditTableViewController.swift; sourceTree = "<group>"; };
                6F7F7E5E21C7D74B00527607 /* TunnelErrors.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TunnelErrors.swift; sourceTree = "<group>"; };
+               6F89E17921EDEB0E00C97BB9 /* StatusItemController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = StatusItemController.swift; sourceTree = "<group>"; };
                6F919EC2218A2AE90023B400 /* ErrorPresenter.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ErrorPresenter.swift; sourceTree = "<group>"; };
                6F919ED5218C65C50023B400 /* wireguard_doc_logo_22x29.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = wireguard_doc_logo_22x29.png; sourceTree = "<group>"; };
                6F919ED6218C65C50023B400 /* wireguard_doc_logo_44x58.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = wireguard_doc_logo_44x58.png; sourceTree = "<group>"; };
                                6FBA104421D7EA750051C35F /* ViewController */,
                                6FBA101321D613F30051C35F /* Application.swift */,
                                6FB1BD5F21D2607A00A991BF /* AppDelegate.swift */,
+                               6F89E17921EDEB0E00C97BB9 /* StatusItemController.swift */,
                                6FBA101621D655340051C35F /* StatusMenu.swift */,
                                6FBA104121D6BC210051C35F /* ErrorPresenter.swift */,
                                6FCD99AE21E0EA1700BA4C82 /* ImportPanelPresenter.swift */,
                                6FB1BDBC21D50F0200A991BF /* ringlogger.c in Sources */,
                                6FB1BDBD21D50F0200A991BF /* ringlogger.h in Sources */,
                                6FBA103F21D6B6FF0051C35F /* TunnelImporter.swift in Sources */,
+                               6F89E17A21EDEB0E00C97BB9 /* StatusItemController.swift in Sources */,
                                6F4DD16B21DA558800690EAE /* TunnelListRow.swift in Sources */,
                                5F52D0BF21E3788900283CEA /* NSColor+Hex.swift in Sources */,
                                6FB1BDBE21D50F0200A991BF /* Logger.swift in Sources */,
index 4476c4a0d1e065bc8db9619d944036ee8669453e..1b3cc50fc63b86a806f1fd6211279917ee6a7908 100644 (file)
@@ -222,6 +222,10 @@ class TunnelsManager {
         return tunnels.first { $0.name == tunnelName }
     }
 
+    func waitingTunnel() -> TunnelContainer? {
+        return tunnels.first { $0.status == .waiting }
+    }
+
     func startActivation(of tunnel: TunnelContainer) {
         guard tunnels.contains(tunnel) else { return } // Ensure it's not deleted
         guard tunnel.status == .inactive else {
index a08f9dc0ed38650cbfb3c631435c10ee75ed13a7..3f089875c9c13d2e00f4fa586830f7f16103d407 100644 (file)
@@ -6,7 +6,8 @@ import Cocoa
 @NSApplicationMain
 class AppDelegate: NSObject, NSApplicationDelegate {
 
-    var statusItem: NSStatusItem?
+    var statusItemController: StatusItemController?
+    var currentTunnelStatusObserver: AnyObject?
 
     func applicationDidFinishLaunching(_ aNotification: Notification) {
         Logger.configureGlobal(withFilePath: FileManager.appLogFileURL?.path)
@@ -19,21 +20,19 @@ class AppDelegate: NSObject, NSApplicationDelegate {
             }
 
             let tunnelsManager: TunnelsManager = result.value!
+            let statusItemController = StatusItemController()
+
             let statusMenu = StatusMenu(tunnelsManager: tunnelsManager)
-            self.statusItem = createStatusBarItem(with: statusMenu)
+
+            statusItemController.statusItem.menu = statusMenu
+            statusItemController.currentTunnel = statusMenu.currentTunnel
+            self.currentTunnelStatusObserver = statusMenu.observe(\.currentTunnel) { statusMenu, _ in
+                statusItemController.currentTunnel = statusMenu.currentTunnel
+            }
+            self.statusItemController = statusItemController
 
             tunnelsManager.tunnelsListDelegate = statusMenu
             tunnelsManager.activationDelegate = statusMenu
         }
     }
 }
-
-func createStatusBarItem(with statusMenu: StatusMenu) -> NSStatusItem {
-    let statusItem = NSStatusBar.system.statusItem(withLength: NSStatusItem.squareLength)
-    if let statusBarImage = NSImage(named: "WireGuardMacStatusBarIcon") {
-        statusBarImage.isTemplate = true
-        statusItem.button?.image = statusBarImage
-    }
-    statusItem.menu = statusMenu
-    return statusItem
-}
similarity index 57%
rename from WireGuard/WireGuard/UI/macOS/Assets.xcassets/WireGuardMacStatusBarIcon.imageset/Contents.json
rename to WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIcon.imageset/Contents.json
index 2adee86995772794695f0879f118b80d45ba37ae..c878d79c8459f06d83692ffd795adfcccbc950d3 100644 (file)
@@ -2,22 +2,25 @@
   "images" : [
     {
       "idiom" : "universal",
-      "filename" : "WireGuardMacStatusBarIcon@1x.png",
+      "filename" : "StatusBarIcon@1x.png",
       "scale" : "1x"
     },
     {
       "idiom" : "universal",
-      "filename" : "WireGuardMacStatusBarIcon@2x.png",
+      "filename" : "StatusBarIcon@2x.png",
       "scale" : "2x"
     },
     {
       "idiom" : "universal",
-      "filename" : "WireGuardMacStatusBarIcon@3x.png",
+      "filename" : "StatusBarIcon@3x.png",
       "scale" : "3x"
     }
   ],
   "info" : {
     "version" : 1,
     "author" : "xcode"
+  },
+  "properties" : {
+    "template-rendering-intent" : "template"
   }
 }
\ No newline at end of file
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIcon.imageset/StatusBarIcon@1x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIcon.imageset/StatusBarIcon@1x.png
new file mode 100644 (file)
index 0000000..c0a43e7
Binary files /dev/null and b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIcon.imageset/StatusBarIcon@1x.png differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIcon.imageset/StatusBarIcon@2x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIcon.imageset/StatusBarIcon@2x.png
new file mode 100644 (file)
index 0000000..2057c31
Binary files /dev/null and b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIcon.imageset/StatusBarIcon@2x.png differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIcon.imageset/StatusBarIcon@3x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIcon.imageset/StatusBarIcon@3x.png
new file mode 100644 (file)
index 0000000..60cc363
Binary files /dev/null and b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIcon.imageset/StatusBarIcon@3x.png differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDimmed.imageset/Contents.json b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDimmed.imageset/Contents.json
new file mode 100644 (file)
index 0000000..aeb8a8e
--- /dev/null
@@ -0,0 +1,26 @@
+{
+  "images" : [
+    {
+      "idiom" : "universal",
+      "filename" : "StatusBarIconDimmed@1x.png",
+      "scale" : "1x"
+    },
+    {
+      "idiom" : "universal",
+      "filename" : "StatusBarIconDimmed@2x.png",
+      "scale" : "2x"
+    },
+    {
+      "idiom" : "universal",
+      "filename" : "StatusBarIconDimmed@3x.png",
+      "scale" : "3x"
+    }
+  ],
+  "info" : {
+    "version" : 1,
+    "author" : "xcode"
+  },
+  "properties" : {
+    "template-rendering-intent" : "template"
+  }
+}
\ No newline at end of file
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDimmed.imageset/StatusBarIconDimmed@1x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDimmed.imageset/StatusBarIconDimmed@1x.png
new file mode 100644 (file)
index 0000000..fb9d8f7
Binary files /dev/null and b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDimmed.imageset/StatusBarIconDimmed@1x.png differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDimmed.imageset/StatusBarIconDimmed@2x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDimmed.imageset/StatusBarIconDimmed@2x.png
new file mode 100644 (file)
index 0000000..2f4e613
Binary files /dev/null and b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDimmed.imageset/StatusBarIconDimmed@2x.png differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDimmed.imageset/StatusBarIconDimmed@3x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDimmed.imageset/StatusBarIconDimmed@3x.png
new file mode 100644 (file)
index 0000000..cc5ead9
Binary files /dev/null and b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDimmed.imageset/StatusBarIconDimmed@3x.png differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot1.imageset/Contents.json b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot1.imageset/Contents.json
new file mode 100644 (file)
index 0000000..0024a60
--- /dev/null
@@ -0,0 +1,26 @@
+{
+  "images" : [
+    {
+      "idiom" : "universal",
+      "filename" : "StatusBarIconDot1@1x.png",
+      "scale" : "1x"
+    },
+    {
+      "idiom" : "universal",
+      "filename" : "StatusBarIconDot1@2x.png",
+      "scale" : "2x"
+    },
+    {
+      "idiom" : "universal",
+      "filename" : "StatusBarIconDot1@3x.png",
+      "scale" : "3x"
+    }
+  ],
+  "info" : {
+    "version" : 1,
+    "author" : "xcode"
+  },
+  "properties" : {
+    "template-rendering-intent" : "template"
+  }
+}
\ No newline at end of file
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot1.imageset/StatusBarIconDot1@1x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot1.imageset/StatusBarIconDot1@1x.png
new file mode 100644 (file)
index 0000000..bbbe0c3
Binary files /dev/null and b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot1.imageset/StatusBarIconDot1@1x.png differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot1.imageset/StatusBarIconDot1@2x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot1.imageset/StatusBarIconDot1@2x.png
new file mode 100644 (file)
index 0000000..01b5eb3
Binary files /dev/null and b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot1.imageset/StatusBarIconDot1@2x.png differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot1.imageset/StatusBarIconDot1@3x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot1.imageset/StatusBarIconDot1@3x.png
new file mode 100644 (file)
index 0000000..76afa15
Binary files /dev/null and b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot1.imageset/StatusBarIconDot1@3x.png differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot2.imageset/Contents.json b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot2.imageset/Contents.json
new file mode 100644 (file)
index 0000000..8b61c0e
--- /dev/null
@@ -0,0 +1,26 @@
+{
+  "images" : [
+    {
+      "idiom" : "universal",
+      "filename" : "StatusBarIconDot2@1x.png",
+      "scale" : "1x"
+    },
+    {
+      "idiom" : "universal",
+      "filename" : "StatusBarIconDot2@2x.png",
+      "scale" : "2x"
+    },
+    {
+      "idiom" : "universal",
+      "filename" : "StatusBarIconDot2@3x.png",
+      "scale" : "3x"
+    }
+  ],
+  "info" : {
+    "version" : 1,
+    "author" : "xcode"
+  },
+  "properties" : {
+    "template-rendering-intent" : "template"
+  }
+}
\ No newline at end of file
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot2.imageset/StatusBarIconDot2@1x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot2.imageset/StatusBarIconDot2@1x.png
new file mode 100644 (file)
index 0000000..a16143f
Binary files /dev/null and b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot2.imageset/StatusBarIconDot2@1x.png differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot2.imageset/StatusBarIconDot2@2x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot2.imageset/StatusBarIconDot2@2x.png
new file mode 100644 (file)
index 0000000..ce00482
Binary files /dev/null and b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot2.imageset/StatusBarIconDot2@2x.png differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot2.imageset/StatusBarIconDot2@3x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot2.imageset/StatusBarIconDot2@3x.png
new file mode 100644 (file)
index 0000000..82640f7
Binary files /dev/null and b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot2.imageset/StatusBarIconDot2@3x.png differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot3.imageset/Contents.json b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot3.imageset/Contents.json
new file mode 100644 (file)
index 0000000..96da519
--- /dev/null
@@ -0,0 +1,26 @@
+{
+  "images" : [
+    {
+      "idiom" : "universal",
+      "filename" : "StatusBarIconDot3@1x.png",
+      "scale" : "1x"
+    },
+    {
+      "idiom" : "universal",
+      "filename" : "StatusBarIconDot3@2x.png",
+      "scale" : "2x"
+    },
+    {
+      "idiom" : "universal",
+      "filename" : "StatusBarIconDot3@3x.png",
+      "scale" : "3x"
+    }
+  ],
+  "info" : {
+    "version" : 1,
+    "author" : "xcode"
+  },
+  "properties" : {
+    "template-rendering-intent" : "template"
+  }
+}
\ No newline at end of file
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot3.imageset/StatusBarIconDot3@1x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot3.imageset/StatusBarIconDot3@1x.png
new file mode 100644 (file)
index 0000000..80e221b
Binary files /dev/null and b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot3.imageset/StatusBarIconDot3@1x.png differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot3.imageset/StatusBarIconDot3@2x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot3.imageset/StatusBarIconDot3@2x.png
new file mode 100644 (file)
index 0000000..663f92b
Binary files /dev/null and b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot3.imageset/StatusBarIconDot3@2x.png differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot3.imageset/StatusBarIconDot3@3x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot3.imageset/StatusBarIconDot3@3x.png
new file mode 100644 (file)
index 0000000..10e43d9
Binary files /dev/null and b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/StatusBarIconDot3.imageset/StatusBarIconDot3@3x.png differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/WireGuardMacStatusBarIcon.imageset/WireGuardMacStatusBarIcon@1x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/WireGuardMacStatusBarIcon.imageset/WireGuardMacStatusBarIcon@1x.png
deleted file mode 100644 (file)
index 1a7d77c..0000000
Binary files a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/WireGuardMacStatusBarIcon.imageset/WireGuardMacStatusBarIcon@1x.png and /dev/null differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/WireGuardMacStatusBarIcon.imageset/WireGuardMacStatusBarIcon@2x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/WireGuardMacStatusBarIcon.imageset/WireGuardMacStatusBarIcon@2x.png
deleted file mode 100644 (file)
index 66c49c1..0000000
Binary files a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/WireGuardMacStatusBarIcon.imageset/WireGuardMacStatusBarIcon@2x.png and /dev/null differ
diff --git a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/WireGuardMacStatusBarIcon.imageset/WireGuardMacStatusBarIcon@3x.png b/WireGuard/WireGuard/UI/macOS/Assets.xcassets/WireGuardMacStatusBarIcon.imageset/WireGuardMacStatusBarIcon@3x.png
deleted file mode 100644 (file)
index e1bcc35..0000000
Binary files a/WireGuard/WireGuard/UI/macOS/Assets.xcassets/WireGuardMacStatusBarIcon.imageset/WireGuardMacStatusBarIcon@3x.png and /dev/null differ
diff --git a/WireGuard/WireGuard/UI/macOS/StatusItemController.swift b/WireGuard/WireGuard/UI/macOS/StatusItemController.swift
new file mode 100644 (file)
index 0000000..2568c15
--- /dev/null
@@ -0,0 +1,66 @@
+// SPDX-License-Identifier: MIT
+// Copyright © 2018-2019 WireGuard LLC. All Rights Reserved.
+
+import Cocoa
+
+class StatusItemController {
+    var currentTunnel: TunnelContainer? {
+        didSet {
+            updateStatusItemImage()
+        }
+    }
+
+    let statusItem = NSStatusBar.system.statusItem(withLength: NSStatusItem.squareLength)
+    private let statusBarImageWhenActive = NSImage(named: "StatusBarIcon")!
+    private let statusBarImageWhenInactive = NSImage(named: "StatusBarIconDimmed")!
+
+    private let animationImages = [
+        NSImage(named: "StatusBarIconDot1")!,
+        NSImage(named: "StatusBarIconDot2")!,
+        NSImage(named: "StatusBarIconDot3")!
+    ]
+    private var animationImageIndex: Int = 0
+    private var animationTimer: Timer?
+
+    init() {
+        updateStatusItemImage()
+    }
+
+    func updateStatusItemImage() {
+        guard let currentTunnel = currentTunnel else {
+            stopActivatingAnimation()
+            statusItem.button?.image = statusBarImageWhenInactive
+            return
+        }
+        switch currentTunnel.status {
+        case .inactive:
+            stopActivatingAnimation()
+            statusItem.button?.image = statusBarImageWhenInactive
+        case .active:
+            stopActivatingAnimation()
+            statusItem.button?.image = statusBarImageWhenActive
+        case .activating, .waiting, .reasserting, .restarting:
+            startActivatingAnimation()
+        case .deactivating:
+            break
+        }
+    }
+
+    func startActivatingAnimation() {
+        guard animationTimer == nil else { return }
+        let timer = Timer(timeInterval: 0.3, repeats: true) { [weak self] _ in
+            guard let self = self else { return }
+            self.statusItem.button?.image = self.animationImages[self.animationImageIndex]
+            self.animationImageIndex = (self.animationImageIndex + 1) % self.animationImages.count
+        }
+        RunLoop.main.add(timer, forMode: .default)
+        animationTimer = timer
+    }
+
+    func stopActivatingAnimation() {
+        guard let timer = self.animationTimer else { return }
+        timer.invalidate()
+        animationTimer = nil
+        animationImageIndex = 0
+    }
+}
index 78e71ba7d1adcafb9673ef13db7c1af0b19f87df..a2f02d8cc1c3bc2524f5c9af765ad3c92d47ef9d 100644 (file)
@@ -13,6 +13,8 @@ class StatusMenu: NSMenu {
     var firstTunnelMenuItemIndex = 0
     var numberOfTunnelMenuItems = 0
 
+    @objc dynamic var currentTunnel: TunnelContainer?
+
     var manageTunnelsRootVC: ManageTunnelsRootViewController?
     lazy var manageTunnelsWindow: NSWindow = {
         manageTunnelsRootVC = ManageTunnelsRootViewController(tunnelsManager: tunnelsManager)
@@ -30,7 +32,11 @@ class StatusMenu: NSMenu {
         addStatusMenuItems()
         addItem(NSMenuItem.separator())
         for index in 0 ..< tunnelsManager.numberOfTunnels() {
-            let isUpdated = updateStatusMenuItems(with: tunnelsManager.tunnel(at: index), ignoreInactive: true)
+            let tunnel = tunnelsManager.tunnel(at: index)
+            if tunnel.status != .inactive {
+                currentTunnel = tunnel
+            }
+            let isUpdated = updateStatusMenuItems(with: tunnel, ignoreInactive: true)
             if isUpdated {
                 break
             }
@@ -176,6 +182,13 @@ extension StatusMenu {
         updateTunnelMenuItem(menuItem)
         let statusObservationToken = tunnel.observe(\.status) { [weak self] tunnel, _ in
             updateTunnelMenuItem(menuItem)
+            if tunnel.status == .deactivating || tunnel.status == .inactive {
+                if self?.currentTunnel == tunnel {
+                    self?.currentTunnel = self?.tunnelsManager.waitingTunnel()
+                }
+            } else {
+                self?.currentTunnel = tunnel
+            }
             self?.updateStatusMenuItems(with: tunnel, ignoreInactive: false)
         }
         tunnelStatusObservers.insert(statusObservationToken, at: tunnelIndex)