]> git.ipfire.org Git - thirdparty/wireguard-apple.git/commitdiff
macOS: Tunnel edit view
authorRoopesh Chander <roop@roopc.net>
Sun, 6 Jan 2019 13:21:06 +0000 (18:51 +0530)
committerRoopesh Chander <roop@roopc.net>
Mon, 14 Jan 2019 09:22:33 +0000 (14:52 +0530)
Signed-off-by: Roopesh Chander <roop@roopc.net>
WireGuard/WireGuard.xcodeproj/project.pbxproj
WireGuard/WireGuard/Base.lproj/Localizable.strings
WireGuard/WireGuard/UI/macOS/View/KeyValueRow.swift
WireGuard/WireGuard/UI/macOS/ViewController/TunnelDetailTableViewController.swift
WireGuard/WireGuard/UI/macOS/ViewController/TunnelEditViewController.swift [new file with mode: 0644]

index b132fdd05f73410ba8990fe2d7df3ac16102d575..402fb297692381e6404f63b1dd53fab79f4066bb 100644 (file)
                6FBA104621D7EBFA0051C35F /* TunnelsListTableViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6FBA104521D7EBFA0051C35F /* TunnelsListTableViewController.swift */; };
                6FCD99AA21E0E14700BA4C82 /* NoTunnelsDetailViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6FCD99A821E0E0C700BA4C82 /* NoTunnelsDetailViewController.swift */; };
                6FCD99AF21E0EA1700BA4C82 /* ImportPanelPresenter.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6FCD99AE21E0EA1700BA4C82 /* ImportPanelPresenter.swift */; };
+               6FCD99B121E0EDA900BA4C82 /* TunnelEditViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6FCD99B021E0EDA900BA4C82 /* TunnelEditViewController.swift */; };
                6FDB3C3B21DCF47400A0C0BF /* TunnelDetailTableViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6FDB3C3A21DCF47400A0C0BF /* TunnelDetailTableViewController.swift */; };
                6FDB3C3C21DCF6BB00A0C0BF /* TunnelViewModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6F628C3C217F09E9003482A3 /* TunnelViewModel.swift */; };
                6FDEF7E421846C1A00D8FBF6 /* libwg-go.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 6FDEF7E321846C1A00D8FBF6 /* libwg-go.a */; };
                6FBA104521D7EBFA0051C35F /* TunnelsListTableViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TunnelsListTableViewController.swift; sourceTree = "<group>"; };
                6FCD99A821E0E0C700BA4C82 /* NoTunnelsDetailViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NoTunnelsDetailViewController.swift; sourceTree = "<group>"; };
                6FCD99AE21E0EA1700BA4C82 /* ImportPanelPresenter.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ImportPanelPresenter.swift; sourceTree = "<group>"; };
+               6FCD99B021E0EDA900BA4C82 /* TunnelEditViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TunnelEditViewController.swift; sourceTree = "<group>"; };
                6FDB3C3A21DCF47400A0C0BF /* TunnelDetailTableViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TunnelDetailTableViewController.swift; sourceTree = "<group>"; };
                6FDEF7E321846C1A00D8FBF6 /* libwg-go.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; path = "libwg-go.a"; sourceTree = BUILT_PRODUCTS_DIR; };
                6FDEF7E52185EFAF00D8FBF6 /* QRScanViewController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = QRScanViewController.swift; sourceTree = "<group>"; };
                                6F4DD16D21DBEA0700690EAE /* ManageTunnelsRootViewController.swift */,
                                6FDB3C3A21DCF47400A0C0BF /* TunnelDetailTableViewController.swift */,
                                6FCD99A821E0E0C700BA4C82 /* NoTunnelsDetailViewController.swift */,
+                               6FCD99B021E0EDA900BA4C82 /* TunnelEditViewController.swift */,
                        );
                        path = ViewController;
                        sourceTree = "<group>";
                                6F4DD16C21DA558F00690EAE /* NSTableView+Reuse.swift in Sources */,
                                6FB1BDD821D50F5300A991BF /* WireGuardResult.swift in Sources */,
                                6FB1BDD921D50F5300A991BF /* LocalizationHelper.swift in Sources */,
+                               6FCD99B121E0EDA900BA4C82 /* TunnelEditViewController.swift in Sources */,
                                6FB1BDCA21D50F1700A991BF /* x25519.c in Sources */,
                                6FB1BDCB21D50F1700A991BF /* Curve25519.swift in Sources */,
                                6FB1BDBB21D50F0200A991BF /* Localizable.strings in Sources */,
index ecbc087ea75fdbb402bf5d5df5c5cf120b44efbb..8cae3963a5427749389e0a493b6c680b83130086 100644 (file)
 
 "macButtonImportTunnels" = "Import tunnel(s) from file";
 
-// Mac detail view fields
+// Mac detail/edit view fields
 
-"macDetailFieldKey (%@)" = "%@:";
+"macFieldKey (%@)" = "%@:";
 
 // Mac status display
 
 "macStatus (%@)" = "Status: %@";
+
+// Mac editing config
+
+"macEditDiscard" = "Discard";
+"macEditSave" = "Save";
index 4e9fa7d39b9e1e9f276981f465776b35f026ff84..cdf682cd257b8b7b9607081ad2d38c0640bb1455 100644 (file)
@@ -3,7 +3,7 @@
 
 import Cocoa
 
-class KeyValueRow: NSView {
+class EditableKeyValueRow: NSView {
     let keyLabel: NSTextField = {
         let keyLabel = NSTextField()
         keyLabel.isEditable = false
@@ -18,12 +18,9 @@ class KeyValueRow: NSView {
 
     let valueLabel: NSTextField = {
         let valueLabel = NSTextField()
-        valueLabel.isEditable = false
         valueLabel.isSelectable = true
-        valueLabel.isBordered = false
         valueLabel.maximumNumberOfLines = 1
         valueLabel.lineBreakMode = .byTruncatingTail
-        valueLabel.backgroundColor = .clear
         return valueLabel
     }()
 
@@ -46,6 +43,11 @@ class KeyValueRow: NSView {
         }
     }
 
+    override var intrinsicContentSize: NSSize {
+        let height = max(keyLabel.intrinsicContentSize.height, valueLabel.intrinsicContentSize.height)
+        return NSSize(width: NSView.noIntrinsicMetric, height: height)
+    }
+
     init() {
         super.init(frame: CGRect.zero)
 
@@ -74,3 +76,16 @@ class KeyValueRow: NSView {
         isKeyInBold = false
     }
 }
+
+class KeyValueRow: EditableKeyValueRow {
+    override init() {
+        super.init()
+        valueLabel.isEditable = false
+        valueLabel.isBordered = false
+        valueLabel.backgroundColor = .clear
+    }
+
+    required init?(coder decoder: NSCoder) {
+        fatalError("init(coder:) has not been implemented")
+    }
+}
index 8e7db43438b5aa83187d707c350537a639a36b9b..9e84e120d9099fd8b1add8833ba4f74691dad1ea 100644 (file)
@@ -191,7 +191,8 @@ class TunnelDetailTableViewController: NSViewController {
     }
 
     @objc func editButtonClicked() {
-        print("editButtonClicked")
+        let tunnelEditVC = TunnelEditViewController(tunnelsManager: tunnelsManager, tunnel: tunnel)
+        presentAsSheet(tunnelEditVC)
     }
 
     @objc func statusCheckboxToggled(sender: AnyObject?) {
@@ -217,14 +218,14 @@ extension TunnelDetailTableViewController: NSTableViewDelegate {
         case .interfaceFieldRow(let field):
             let cell: KeyValueRow = tableView.dequeueReusableCell()
             let localizedKeyString = modelRow.isTitleRow() ? modelRow.localizedSectionKeyString() : field.localizedUIString
-            cell.key = tr(format: "macDetailFieldKey (%@)", localizedKeyString)
+            cell.key = tr(format: "macFieldKey (%@)", localizedKeyString)
             cell.value = tunnelViewModel.interfaceData[field]
             cell.isKeyInBold = modelRow.isTitleRow()
             return cell
         case .peerFieldRow(let peerData, let field):
             let cell: KeyValueRow = tableView.dequeueReusableCell()
             let localizedKeyString = modelRow.isTitleRow() ? modelRow.localizedSectionKeyString() : field.localizedUIString
-            cell.key = tr(format: "macDetailFieldKey (%@)", localizedKeyString)
+            cell.key = tr(format: "macFieldKey (%@)", localizedKeyString)
             cell.value = peerData[field]
             cell.isKeyInBold = modelRow.isTitleRow()
             return cell
diff --git a/WireGuard/WireGuard/UI/macOS/ViewController/TunnelEditViewController.swift b/WireGuard/WireGuard/UI/macOS/ViewController/TunnelEditViewController.swift
new file mode 100644 (file)
index 0000000..52b80f6
--- /dev/null
@@ -0,0 +1,125 @@
+// SPDX-License-Identifier: MIT
+// Copyright © 2018 WireGuard LLC. All Rights Reserved.
+
+import Cocoa
+
+class TunnelEditViewController: NSViewController {
+
+    let nameRow: EditableKeyValueRow = {
+        let nameRow = EditableKeyValueRow()
+        nameRow.key = tr(format: "macFieldKey (%@)", TunnelViewModel.InterfaceField.name.localizedUIString)
+        return nameRow
+    }()
+
+    let publicKeyRow: KeyValueRow = {
+        let publicKeyRow = KeyValueRow()
+        publicKeyRow.key = tr(format: "macFieldKey (%@)", TunnelViewModel.InterfaceField.publicKey.localizedUIString)
+        return publicKeyRow
+    }()
+
+    let textView: NSTextView = {
+        let textView = NSTextView()
+        let minWidth: CGFloat = 120
+        let minHeight: CGFloat = 60
+        textView.minSize = NSSize(width: 0, height: minHeight)
+        textView.maxSize = NSSize(width: CGFloat.greatestFiniteMagnitude, height: CGFloat.greatestFiniteMagnitude)
+        textView.autoresizingMask = .width
+        textView.isHorizontallyResizable = true
+        if let textContainer = textView.textContainer {
+            textContainer.size = NSSize(width: minWidth, height: CGFloat.greatestFiniteMagnitude)
+            textContainer.widthTracksTextView = true
+        }
+        NSLayoutConstraint.activate([
+            textView.widthAnchor.constraint(greaterThanOrEqualToConstant: minWidth),
+            textView.heightAnchor.constraint(greaterThanOrEqualToConstant: minHeight)
+        ])
+        return textView
+    }()
+
+    let scrollView: NSScrollView = {
+        let scrollView = NSScrollView()
+        scrollView.hasVerticalScroller = true
+        scrollView.borderType = .bezelBorder
+        return scrollView
+    }()
+
+    let discardButton: NSButton = {
+        let button = NSButton()
+        button.title = tr("macEditDiscard")
+        button.setButtonType(.momentaryPushIn)
+        button.bezelStyle = .rounded
+        return button
+    }()
+
+    let saveButton: NSButton = {
+        let button = NSButton()
+        button.title = tr("macEditSave")
+        button.setButtonType(.momentaryPushIn)
+        button.bezelStyle = .rounded
+        return button
+    }()
+
+    let tunnelsManager: TunnelsManager
+    let tunnel: TunnelContainer?
+
+    init(tunnelsManager: TunnelsManager, tunnel: TunnelContainer?) {
+        self.tunnelsManager = tunnelsManager
+        self.tunnel = tunnel
+        super.init(nibName: nil, bundle: nil)
+    }
+
+    required init?(coder: NSCoder) {
+        fatalError("init(coder:) has not been implemented")
+    }
+
+    override func loadView() {
+        if let tunnel = tunnel, let tunnelConfiguration = tunnel.tunnelConfiguration {
+            nameRow.value = tunnel.name
+            publicKeyRow.value = tunnelConfiguration.interface.publicKey.base64EncodedString()
+            textView.string = tunnelConfiguration.asWgQuickConfig()
+        }
+
+        scrollView.documentView = textView
+
+        saveButton.target = self
+        saveButton.action = #selector(saveButtonClicked)
+
+        discardButton.target = self
+        discardButton.action = #selector(discardButtonClicked)
+
+        let margin: CGFloat = 20
+        let internalSpacing: CGFloat = 10
+
+        let editorStackView = NSStackView(views: [nameRow, publicKeyRow, scrollView])
+        editorStackView.orientation = .vertical
+        editorStackView.setHuggingPriority(.defaultHigh, for: .horizontal)
+        editorStackView.spacing = internalSpacing
+
+        let buttonRowStackView = NSStackView()
+        buttonRowStackView.setViews([discardButton, saveButton], in: .trailing)
+        buttonRowStackView.orientation = .horizontal
+        buttonRowStackView.spacing = internalSpacing
+
+        let containerView = NSStackView(views: [editorStackView, buttonRowStackView])
+        containerView.orientation = .vertical
+        containerView.edgeInsets = NSEdgeInsets(top: margin, left: margin, bottom: margin, right: margin)
+        containerView.setHuggingPriority(.defaultHigh, for: .horizontal)
+        containerView.spacing = internalSpacing
+
+        NSLayoutConstraint.activate([
+            containerView.widthAnchor.constraint(greaterThanOrEqualToConstant: 180),
+            containerView.heightAnchor.constraint(greaterThanOrEqualToConstant: 240)
+        ])
+        containerView.frame = NSRect(x: 0, y: 0, width: 480, height: 320)
+
+        self.view = containerView
+    }
+
+    @objc func saveButtonClicked() {
+        print("saveButtonClicked")
+    }
+
+    @objc func discardButtonClicked() {
+        dismiss(self)
+    }
+}