macOS: Ability to remove multiple tunnels at a time

This commit is contained in:
Roopesh Chander 2019-03-10 20:02:19 +05:30
parent 8648f80877
commit 9c71d63254
3 changed files with 41 additions and 13 deletions

View File

@ -271,6 +271,7 @@
"macWindowTitleManageTunnels" = "Manage WireGuard Tunnels"; "macWindowTitleManageTunnels" = "Manage WireGuard Tunnels";
"macDeleteTunnelConfirmationAlertMessage (%@)" = "Are you sure you want to delete %@?"; "macDeleteTunnelConfirmationAlertMessage (%@)" = "Are you sure you want to delete %@?";
"macDeleteMultipleTunnelsConfirmationAlertMessage (%d)" = "Are you sure you want to delete %d tunnels?";
"macDeleteTunnelConfirmationAlertInfo" = "You cannot undo this action."; "macDeleteTunnelConfirmationAlertInfo" = "You cannot undo this action.";
"macDeleteTunnelConfirmationAlertButtonTitleDelete" = "Delete"; "macDeleteTunnelConfirmationAlertButtonTitleDelete" = "Delete";
"macDeleteTunnelConfirmationAlertButtonTitleCancel" = "Cancel"; "macDeleteTunnelConfirmationAlertButtonTitleCancel" = "Cancel";
@ -284,6 +285,8 @@
"macNameFieldExportZip" = "Export tunnels to"; "macNameFieldExportZip" = "Export tunnels to";
"macSheetButtonExportZip" = "Save"; "macSheetButtonExportZip" = "Save";
"macButtonDeleteTunnels (%d)" = "Delete %d tunnels";
// Mac detail/edit view fields // Mac detail/edit view fields
"macFieldKey (%@)" = "%@:"; "macFieldKey (%@)" = "%@:";

View File

@ -77,10 +77,27 @@ class ManageTunnelsRootViewController: NSViewController {
} }
extension ManageTunnelsRootViewController: TunnelsListTableViewControllerDelegate { extension ManageTunnelsRootViewController: TunnelsListTableViewControllerDelegate {
func tunnelSelected(tunnel: TunnelContainer) { func tunnelsSelected(tunnelIndices: [Int]) {
let tunnelDetailVC = TunnelDetailTableViewController(tunnelsManager: tunnelsManager, tunnel: tunnel) assert(!tunnelIndices.isEmpty)
setTunnelDetailContentVC(tunnelDetailVC) if tunnelIndices.count == 1 {
self.tunnelDetailVC = tunnelDetailVC let tunnel = tunnelsManager.tunnel(at: tunnelIndices.first!)
let tunnelDetailVC = TunnelDetailTableViewController(tunnelsManager: tunnelsManager, tunnel: tunnel)
setTunnelDetailContentVC(tunnelDetailVC)
self.tunnelDetailVC = tunnelDetailVC
} else if tunnelIndices.count > 1 {
let multiSelectionVC: ButtonedDetailViewController
if let buttonedDetailVC = tunnelDetailContentVC as? ButtonedDetailViewController {
multiSelectionVC = buttonedDetailVC
} else {
multiSelectionVC = ButtonedDetailViewController()
}
multiSelectionVC.setButtonTitle(tr(format: "macButtonDeleteTunnels (%d)", tunnelIndices.count))
multiSelectionVC.onButtonClicked = { [weak tunnelsListVC] in
tunnelsListVC?.handleRemoveTunnelAction()
}
setTunnelDetailContentVC(multiSelectionVC)
self.tunnelDetailVC = nil
}
} }
func tunnelsListEmpty() { func tunnelsListEmpty() {

View File

@ -4,7 +4,7 @@
import Cocoa import Cocoa
protocol TunnelsListTableViewControllerDelegate: class { protocol TunnelsListTableViewControllerDelegate: class {
func tunnelSelected(tunnel: TunnelContainer) func tunnelsSelected(tunnelIndices: [Int])
func tunnelsListEmpty() func tunnelsListEmpty()
} }
@ -18,6 +18,7 @@ class TunnelsListTableViewController: NSViewController {
tableView.addTableColumn(NSTableColumn(identifier: NSUserInterfaceItemIdentifier("TunnelsList"))) tableView.addTableColumn(NSTableColumn(identifier: NSUserInterfaceItemIdentifier("TunnelsList")))
tableView.headerView = nil tableView.headerView = nil
tableView.rowSizeStyle = .medium tableView.rowSizeStyle = .medium
tableView.allowsMultipleSelection = true
return tableView return tableView
}() }()
@ -158,18 +159,24 @@ class TunnelsListTableViewController: NSViewController {
@objc func handleRemoveTunnelAction() { @objc func handleRemoveTunnelAction() {
guard let window = view.window else { return } guard let window = view.window else { return }
let selectedTunnelIndex = tableView.selectedRow let selectedTunnelIndices = tableView.selectedRowIndexes.sorted()
guard selectedTunnelIndex >= 0 && selectedTunnelIndex < tunnelsManager.numberOfTunnels() else { return } let selectedTunnels = selectedTunnelIndices.compactMap { tunnelIndex in
let selectedTunnel = tunnelsManager.tunnel(at: selectedTunnelIndex) tunnelIndex >= 0 && tunnelIndex < tunnelsManager.numberOfTunnels() ? tunnelsManager.tunnel(at: tunnelIndex) : nil
}
guard !selectedTunnels.isEmpty else { return }
let alert = NSAlert() let alert = NSAlert()
alert.messageText = tr(format: "macDeleteTunnelConfirmationAlertMessage (%@)", selectedTunnel.name) if selectedTunnels.count == 1 {
alert.messageText = tr(format: "macDeleteTunnelConfirmationAlertMessage (%@)", selectedTunnels.first!.name)
} else {
alert.messageText = tr(format: "macDeleteMultipleTunnelsConfirmationAlertMessage (%d)", selectedTunnels.count)
}
alert.informativeText = tr("macDeleteTunnelConfirmationAlertInfo") alert.informativeText = tr("macDeleteTunnelConfirmationAlertInfo")
alert.addButton(withTitle: tr("macDeleteTunnelConfirmationAlertButtonTitleDelete")) alert.addButton(withTitle: tr("macDeleteTunnelConfirmationAlertButtonTitleDelete"))
alert.addButton(withTitle: tr("macDeleteTunnelConfirmationAlertButtonTitleCancel")) alert.addButton(withTitle: tr("macDeleteTunnelConfirmationAlertButtonTitleCancel"))
alert.beginSheetModal(for: window) { [weak self] response in alert.beginSheetModal(for: window) { [weak self] response in
guard response == .alertFirstButtonReturn else { return } guard response == .alertFirstButtonReturn else { return }
self?.removeButton.isEnabled = false self?.removeButton.isEnabled = false
self?.tunnelsManager.remove(tunnel: selectedTunnel) { [weak self] error in self?.tunnelsManager.removeMultiple(tunnels: selectedTunnels) { [weak self] error in
guard let self = self else { return } guard let self = self else { return }
defer { self.removeButton.isEnabled = true } defer { self.removeButton.isEnabled = true }
if let error = error { if let error = error {
@ -309,9 +316,10 @@ extension TunnelsListTableViewController: NSTableViewDelegate {
} }
func tableViewSelectionDidChange(_ notification: Notification) { func tableViewSelectionDidChange(_ notification: Notification) {
guard tableView.selectedRow >= 0 else { return } let selectedTunnelIndices = tableView.selectedRowIndexes.sorted()
let selectedTunnel = tunnelsManager.tunnel(at: tableView.selectedRow) if !selectedTunnelIndices.isEmpty {
delegate?.tunnelSelected(tunnel: selectedTunnel) delegate?.tunnelsSelected(tunnelIndices: tableView.selectedRowIndexes.sorted())
}
} }
} }