From bc39cd81c14f742e525fcfbb754e1cf4e489d1de Mon Sep 17 00:00:00 2001 From: Antonio Ribeiro Date: Mon, 20 Apr 2020 23:00:33 +0100 Subject: [PATCH] Manual task form now has autocomplete (#41) --- Timetracker/Base.lproj/Main.storyboard | 72 ++++++++++++++-------- Timetracker/ManualTaskViewController.swift | 56 +++++++++++++++-- 2 files changed, 96 insertions(+), 32 deletions(-) diff --git a/Timetracker/Base.lproj/Main.storyboard b/Timetracker/Base.lproj/Main.storyboard index 0e1985645..f1e60c42f 100644 --- a/Timetracker/Base.lproj/Main.storyboard +++ b/Timetracker/Base.lproj/Main.storyboard @@ -762,12 +762,11 @@ - + - - - + + @@ -783,9 +782,8 @@ - - - + + @@ -801,9 +799,8 @@ - - - + + @@ -814,17 +811,11 @@ + + + - - - - - - - - - @@ -874,9 +865,8 @@ - - + + + + + + + + + + + + + + + + + + + + + + + + - diff --git a/Timetracker/ManualTaskViewController.swift b/Timetracker/ManualTaskViewController.swift index 5235d2915..7327306bc 100644 --- a/Timetracker/ManualTaskViewController.swift +++ b/Timetracker/ManualTaskViewController.swift @@ -9,16 +9,19 @@ import Foundation import Cocoa -class ManualTaskViewController: NSViewController { +class ManualTaskViewController: NSViewController, NSComboBoxDataSource { @IBOutlet var hodsPopup: NSPopUpButton! @IBOutlet var projectsPopup: NSPopUpButton! @IBOutlet var clientsPopup: NSPopUpButton! @IBOutlet var taskEnd: NSDatePicker! @IBOutlet var taskStart: NSDatePicker! - @IBOutlet var taskName: NSTextField! + @IBOutlet weak var taskComboBox: NSComboBox! + + var selectedProjectsTaskNames: [String]? weak var editingTask: Task? + var onDismiss: (() -> Void)? fileprivate var selectedHod: HeadOfDevelopment? { @@ -46,7 +49,7 @@ class ManualTaskViewController: NSViewController { taskStart.dateValue = task.startTime! as Date taskEnd.dateValue = task.endTime! as Date - taskName.stringValue = task.title! + taskComboBox.stringValue = task.title! let taskProject = task.project! let taskClient = taskProject.client! @@ -64,6 +67,13 @@ class ManualTaskViewController: NSViewController { taskEnd.minDate = taskStart.dateValue taskStart.maxDate = Date() taskEnd.maxDate = Date() + + self.taskComboBox.usesDataSource = true + self.taskComboBox.completes = true + self.taskComboBox.dataSource = self + + populateTasks() + } fileprivate func populateClients(_ defaultSelected: String?, withDefaultProject defaultProject: String?) { @@ -110,16 +120,20 @@ class ManualTaskViewController: NSViewController { populateProjects(nil) } + @IBAction func projectChanged(_ sender: Any) { + populateTasks() + } + @IBAction func cancelClicked(_ sender: NSButton) { self.dismiss(self) } @IBAction func saveClicked(_ sender: NSButton) { - if let selectedProject = self.selectedProject, taskName.stringValue.count > 0 { + if let selectedProject = self.selectedProject, taskComboBox.stringValue.count > 0 { if let task = editingTask { - task.title = taskName.stringValue + task.title = taskComboBox.stringValue task.startTime = taskStart.dateValue task.endTime = taskEnd.dateValue task.project = selectedProject @@ -135,7 +149,7 @@ class ManualTaskViewController: NSViewController { } else { if TaskProviderManager.instance.saveTaskInProject(selectedProject, - withTitle: taskName.stringValue, + withTitle: taskComboBox.stringValue, startingAt: taskStart.dateValue, finishingAt: taskEnd.dateValue) { dismiss(self) @@ -157,4 +171,34 @@ class ManualTaskViewController: NSViewController { @IBAction func endDateChanged(_ sender: NSDatePicker) { self.taskStart.maxDate = sender.dateValue } + + fileprivate func populateTasks() { + + self.selectedProjectsTaskNames = selectedProject?.distinctTasksNames + + taskComboBox.reloadData() + + if taskComboBox.numberOfItems > 0 { + taskComboBox.selectItem(at: 0) + } + + } + + func numberOfItems(in comboBox: NSComboBox) -> Int { + return self.selectedProjectsTaskNames?.count ?? 0 + } + + func comboBox(_ comboBox: NSComboBox, objectValueForItemAt index: Int) -> Any? { + return self.selectedProjectsTaskNames![index] + } + + func comboBox(_ comboBox: NSComboBox, completedString string: String) -> String? { + return self.selectedProjectsTaskNames?.filter({ (taskTitle) -> Bool in + return taskTitle.starts(with: string) + }).first + } + + func comboBox(_ comboBox: NSComboBox, indexOfItemWithStringValue string: String) -> Int { + return self.selectedProjectsTaskNames?.firstIndex(of: string) ?? NSNotFound + } }