diff --git a/docs/AboutUs.md b/docs/AboutUs.md index e8817ee0bf71..aa805f3a4171 100644 --- a/docs/AboutUs.md +++ b/docs/AboutUs.md @@ -34,7 +34,7 @@ Component SME: UI * Other major contributions: * Initial gradle natty dependency configuration [[8360c0d](https://github.com/CS2103AUG2016-T14-C2/main/commit/8360c0d66fc55f36bed0d0e9d4c6b63186aeb590)] * Set up initial interface for undo/redo in Command classes and implement Logic-level undo/redo [[4dfafa0](https://github.com/CS2103AUG2016-T14-C2/main/commit/4dfafa07337f731959bcd7e267e0de9a093ae285)] - * All parsing related code for all commands [[Parser](../src/main/java/seedu/savvytasker/logic/parser)] + * Almost all parsing related code for all commands [[Parser](../src/main/java/seedu/savvytasker/logic/parser)] ----- diff --git a/docs/UserGuide.md b/docs/UserGuide.md index eb6fc76c9f68..a2594b5d230f 100644 --- a/docs/UserGuide.md +++ b/docs/UserGuide.md @@ -218,8 +218,8 @@ Format: `alias k/KEYWORD r/REPRESENTATION` > Parameters | Description > -------- | :-------- -> KEYWORD | Specifies the keyword that will be replaced when met in a command, must be a single word -> REPRESENTATION | Specifies the text that will replace the keyword +> KEYWORD | Specifies the keyword that will be replaced when met in a command, must be a single word. +> REPRESENTATION | Specifies the text that will replace the keyword. Cannot contain slashes. Examples: * `alias k/pjm r/Project Meeting`
diff --git a/src/main/java/seedu/savvytasker/MainApp.java b/src/main/java/seedu/savvytasker/MainApp.java index 787ff282cca2..878815f4a358 100644 --- a/src/main/java/seedu/savvytasker/MainApp.java +++ b/src/main/java/seedu/savvytasker/MainApp.java @@ -46,7 +46,7 @@ public class MainApp extends Application { protected Config config; protected UserPrefs userPrefs; protected static MainApp instance; - + public MainApp() {} @Override @@ -54,7 +54,7 @@ public void init() throws Exception { logger.info("=============================[ Initializing Savvy Tasker ]==========================="); super.init(); instance = this; - + config = initConfig(getApplicationParameter("config")); storage = new StorageManager(config.getSavvyTaskerFilePath(), config.getUserPrefsFilePath()); @@ -69,8 +69,9 @@ public void init() throws Exception { ui = new UiManager(logic, config, userPrefs); initEventsCenter(); + } - + private String getApplicationParameter(String parameterName){ Map applicationParameters = getParameters().getNamed(); return applicationParameters.get(parameterName); @@ -183,7 +184,7 @@ public void stop() { System.exit(0); } - //@@author A0139915W + //@@author A0138431L @Subscribe public void handleSavvyTaskerSaveLocationChangedEvent(DataSavingLocationChangedEvent dslce) { try { diff --git a/src/main/java/seedu/savvytasker/commons/core/Config.java b/src/main/java/seedu/savvytasker/commons/core/Config.java index 249cc84d3a8a..56b65d4bf159 100644 --- a/src/main/java/seedu/savvytasker/commons/core/Config.java +++ b/src/main/java/seedu/savvytasker/commons/core/Config.java @@ -17,7 +17,6 @@ public class Config { private String savvyTaskerFilePath = "data/savvytasker.xml"; private String savvyTaskerListName = "MyTaskList"; - public Config() { } @@ -61,7 +60,6 @@ public void setSavvyTaskerName(String savvyTaskerName) { this.savvyTaskerListName = savvyTaskerName; } - @Override public boolean equals(Object other) { if (other == this){ diff --git a/src/main/java/seedu/savvytasker/commons/events/storage/DataSavingLocationChangedEvent.java b/src/main/java/seedu/savvytasker/commons/events/storage/DataSavingLocationChangedEvent.java index 6e92df0cf402..1f5f384e1056 100644 --- a/src/main/java/seedu/savvytasker/commons/events/storage/DataSavingLocationChangedEvent.java +++ b/src/main/java/seedu/savvytasker/commons/events/storage/DataSavingLocationChangedEvent.java @@ -3,7 +3,7 @@ import seedu.savvytasker.commons.events.BaseEvent; import seedu.savvytasker.model.ReadOnlySavvyTasker; -//@@author A0139915W +//@@author A0138431L /** * Indicates a change in location of the storage */ diff --git a/src/main/java/seedu/savvytasker/commons/util/SmartDefaultDates.java b/src/main/java/seedu/savvytasker/commons/util/SmartDefaultDates.java index c7206ebdf7c7..5eeac6948a67 100644 --- a/src/main/java/seedu/savvytasker/commons/util/SmartDefaultDates.java +++ b/src/main/java/seedu/savvytasker/commons/util/SmartDefaultDates.java @@ -8,7 +8,6 @@ //@@author A0139915W /** * Helper functions for handling dates. - * @author A0139915W */ public class SmartDefaultDates { @@ -28,41 +27,37 @@ public SmartDefaultDates(InferredDate startDateTime, InferredDate endDateTime) { calendar = Calendar.getInstance(); today = Calendar.getInstance(); today.setTime(new Date()); - if (startDateTime == null && endDateTime == null) { - // dates not being supplied, nothing to parse - } else if (startDateTime == null && endDateTime != null) { + if (startDateTime == null && endDateTime != null) { // apply smart default for endDateTime only parseEnd(endDateTime); } else if (startDateTime != null && endDateTime == null) { // apply smart default for startDateTime only parseStart(startDateTime); - } else { + } else if (startDateTime != null && endDateTime != null) { parseStartAndEnd(startDateTime, endDateTime); } } /** - * Gets the smart default for end date + * Gets the smart defaults for end date. + * + * If the date is not supplied, the date will default to today. + * If the time is not supplied, the time will default to 2359:59 on the specified date. + * If both date and time are not supplied, the date returned will be null. * @param today the time now * @param endDateTime the end time to parse - * @return */ public Date getEnd(InferredDate endDateTime) { if (endDateTime == null) return null; calendar.setTime(endDateTime.getInferredDateTime()); if (endDateTime.isDateInferred() && endDateTime.isTimeInferred()) { - // user didn't specify anything // remove date field return null; } else if (endDateTime.isDateInferred()) { - // date not supplied - // defaults to today calendar.set(Calendar.DATE, today.get(Calendar.DATE)); calendar.set(Calendar.MONTH, today.get(Calendar.MONTH)); calendar.set(Calendar.YEAR, today.get(Calendar.YEAR)); } else if (endDateTime.isTimeInferred()) { - // time not supplied - // defaults to 2359 calendar.set(Calendar.HOUR_OF_DAY, 23); calendar.set(Calendar.MINUTE, 59); calendar.set(Calendar.SECOND, 59); @@ -97,7 +92,11 @@ private void parseEnd(InferredDate endDateTime) { /** - * Gets the smart default for start date + * Gets the smart default for start date. + * + * If the date is not supplied, the date will default to today. + * If the time is not supplied, the time will default to 0000:00 on the specified date. + * If both date and time are not supplied, the date returned will be null. * @param today the time now * @param startDateTime the start time to parse * @return @@ -110,14 +109,10 @@ public Date getStart(InferredDate startDateTime) { // remove date field return null; } else if (startDateTime.isDateInferred()) { - // date not supplied - // defaults to today calendar.set(Calendar.DATE, today.get(Calendar.DATE)); calendar.set(Calendar.MONTH, today.get(Calendar.MONTH)); calendar.set(Calendar.YEAR, today.get(Calendar.YEAR)); } else if (startDateTime.isTimeInferred()) { - // time not supplied - // defaults to 0000 calendar.set(Calendar.HOUR_OF_DAY, 0); calendar.set(Calendar.MINUTE, 0); calendar.set(Calendar.SECOND, 0); @@ -148,8 +143,12 @@ private void parseStart(InferredDate startDateTime) { /** * Sets the starting and ending date/time based on defaults for providing both - * start and end times + * start and end times. + * + * Note that this method has no restrictions on the starting and ending date/time. + * i.e. the starting time is later than the ending time. * @param startDateTime start time supplied + * @param endDateTime end time supplied */ private void parseStartAndEnd(InferredDate startDateTime, InferredDate endDateTime) { assert endDateTime.getInferredDateTime() != null; diff --git a/src/main/java/seedu/savvytasker/logic/Logic.java b/src/main/java/seedu/savvytasker/logic/Logic.java old mode 100644 new mode 100755 index bc55816f290a..1cf9b6cba531 --- a/src/main/java/seedu/savvytasker/logic/Logic.java +++ b/src/main/java/seedu/savvytasker/logic/Logic.java @@ -1,8 +1,10 @@ package seedu.savvytasker.logic; +import java.util.Date; + import javafx.collections.ObservableList; -import seedu.savvytasker.logic.commands.CommandResult; import seedu.savvytasker.model.alias.AliasSymbol; +import seedu.savvytasker.logic.commands.CommandResult; import seedu.savvytasker.model.task.ReadOnlyTask; /** @@ -18,10 +20,23 @@ public interface Logic { /** Returns the filtered list of tasks */ ObservableList getFilteredTaskList(); - + /** Returns the filtered list of alias symbol */ ObservableList getAliasSymbolList(); /** */ boolean canParseHeader(String keyword); + + /** Returns the list of tasks that are overdue */ + ObservableList getFilteredOverdueTasks(); + + /** Returns the list of floating tasks */ + ObservableList getFilteredFloatingTasks(); + + /** Returns the list of tasks on a specific day */ + ObservableList getFilteredDailyTasks(int i, Date date); + + /** Returns the list of tasks that occur after the selected week */ + ObservableList getFilteredUpcomingTasks(Date date); + } diff --git a/src/main/java/seedu/savvytasker/logic/LogicManager.java b/src/main/java/seedu/savvytasker/logic/LogicManager.java old mode 100644 new mode 100755 index 0225052f898d..b7c4231b2213 --- a/src/main/java/seedu/savvytasker/logic/LogicManager.java +++ b/src/main/java/seedu/savvytasker/logic/LogicManager.java @@ -1,13 +1,14 @@ package seedu.savvytasker.logic; +import java.util.Date; +import java.util.Deque; +import java.util.LinkedList; import java.util.List; -import java.util.Stack; import java.util.logging.Logger; import com.google.common.eventbus.Subscribe; import javafx.collections.ObservableList; -import seedu.savvytasker.MainApp; import seedu.savvytasker.commons.core.ComponentManager; import seedu.savvytasker.commons.core.EventsCenter; import seedu.savvytasker.commons.core.LogsCenter; @@ -37,26 +38,26 @@ import seedu.savvytasker.model.alias.AliasSymbol; import seedu.savvytasker.model.task.ReadOnlyTask; import seedu.savvytasker.storage.Storage; -import seedu.savvytasker.ui.Ui; /** * The main LogicManager of the app. */ public class LogicManager extends ComponentManager implements Logic { private final Logger logger = LogsCenter.getLogger(LogicManager.class); - + private final int MAX_UNDO_REDO_QUEUE_SIZE = 50; + private final Model model; private final Storage storage; private final MasterParser parser; - private final Stack undoStack; - private final Stack redoStack; + private final Deque undoDeque; + private final Deque redoDeque; public LogicManager(Model model, Storage storage) { this.model = model; this.storage = storage; this.parser = new MasterParser(); - this.undoStack = new Stack(); - this.redoStack = new Stack(); + this.undoDeque = new LinkedList(); + this.redoDeque = new LinkedList(); registerAllDefaultCommandParsers(); loadAllAliasSymbols(); @@ -89,23 +90,48 @@ else if (command.isRedo()){ } } else if (command.canUndo()){ - undoStack.push(command); - redoStack.clear(); + //@@author A0139916U + undoDeque.addLast(command); + if (undoDeque.size() > MAX_UNDO_REDO_QUEUE_SIZE) { + undoDeque.removeFirst(); + } + redoDeque.clear(); } //@@author return result; } - + //@@author A0139915W @Override public ObservableList getFilteredTaskList() { return model.getFilteredTaskList(); } - @Override public ObservableList getAliasSymbolList() { return parser.getAliasSymbolList(); + } + //@@author + + //@@author A0138431L + @Override + public ObservableList getFilteredOverdueTasks() { + return model.getFilteredOverdueTasks(); + } + + @Override + public ObservableList getFilteredFloatingTasks() { + return model.getFilteredFloatingTasks(); + } + + @Override + public ObservableList getFilteredDailyTasks(int i, Date date) { + return model.getFilteredDailyTasks(i, date); + } + + @Override + public ObservableList getFilteredUpcomingTasks(Date date) { + return model.getFilteredUpcomingTasks(date); } //@@author @@ -135,26 +161,34 @@ private void loadAllAliasSymbols() { } } + /** + * Undo last command and add it to the redo deque. + * @return true if undone successfully, false otherwise + */ private boolean undo() { boolean undone = false; - if (!undoStack.isEmpty()) { - Command command = undoStack.pop(); + if (!undoDeque.isEmpty()) { + Command command = undoDeque.removeLast(); command.undo(); - redoStack.push(command); + redoDeque.addLast(command); undone = true; } return undone; } + /** + * Redo last command and add it to undone deque. + * @return true if redone successfully, false otherwise + */ private boolean redo() { boolean redone = false; - if (!redoStack.isEmpty()) { - Command command = redoStack.pop(); + if (!redoDeque.isEmpty()) { + Command command = redoDeque.removeLast(); command.redo(); - undoStack.push(command); + undoDeque.addLast(command); redone = true; } diff --git a/src/main/java/seedu/savvytasker/logic/commands/AddCommand.java b/src/main/java/seedu/savvytasker/logic/commands/AddCommand.java index 83f6fc639954..faed3f637a21 100644 --- a/src/main/java/seedu/savvytasker/logic/commands/AddCommand.java +++ b/src/main/java/seedu/savvytasker/logic/commands/AddCommand.java @@ -97,11 +97,10 @@ public CommandResult execute() { addToListOfTasksAdded(tasksAdded.toArray(new Task[tasksAdded.size()])); } + // always >= 0 unless this is being run without UI. int targetIndex = getIndexOfTask(taskAdded); if (targetIndex >= 0) { EventsCenter.getInstance().post(new JumpToListRequestEvent(targetIndex)); - } else { - // GUI should never ever get here } return new CommandResult(String.format(MESSAGE_SUCCESS, toAdd)); } catch (InvalidDateException ex) { diff --git a/src/main/java/seedu/savvytasker/logic/commands/ClearCommand.java b/src/main/java/seedu/savvytasker/logic/commands/ClearCommand.java index e30b49e73b84..a59f2f1b0377 100644 --- a/src/main/java/seedu/savvytasker/logic/commands/ClearCommand.java +++ b/src/main/java/seedu/savvytasker/logic/commands/ClearCommand.java @@ -12,9 +12,6 @@ public class ClearCommand extends ModelRequiringCommand { public static final String MESSAGE_SUCCESS = "Savvy Tasker has been cleared!"; private ReadOnlySavvyTasker original; - - public ClearCommand() {} - @Override public CommandResult execute() { diff --git a/src/main/java/seedu/savvytasker/logic/commands/ExitCommand.java b/src/main/java/seedu/savvytasker/logic/commands/ExitCommand.java index 6e099ee4045f..c92f09110fa3 100644 --- a/src/main/java/seedu/savvytasker/logic/commands/ExitCommand.java +++ b/src/main/java/seedu/savvytasker/logic/commands/ExitCommand.java @@ -12,8 +12,6 @@ public class ExitCommand extends Command { public static final String MESSAGE_EXIT_ACKNOWLEDGEMENT = "Exiting Savvy Tasker as requested ..."; - public ExitCommand() {} - @Override public CommandResult execute() { EventsCenter.getInstance().post(new ExitAppRequestEvent()); diff --git a/src/main/java/seedu/savvytasker/logic/commands/FindCommand.java b/src/main/java/seedu/savvytasker/logic/commands/FindCommand.java index e9a4acac6b13..43b3b0d1ae63 100644 --- a/src/main/java/seedu/savvytasker/logic/commands/FindCommand.java +++ b/src/main/java/seedu/savvytasker/logic/commands/FindCommand.java @@ -5,7 +5,6 @@ /** * Finds and lists all persons in address book whose name contains any of the argument keywords. * Keyword matching is case sensitive. - * @author A0139915W */ public class FindCommand extends ModelRequiringCommand { diff --git a/src/main/java/seedu/savvytasker/logic/commands/HelpCommand.java b/src/main/java/seedu/savvytasker/logic/commands/HelpCommand.java index 15e2a40c1644..b9d73365693c 100644 --- a/src/main/java/seedu/savvytasker/logic/commands/HelpCommand.java +++ b/src/main/java/seedu/savvytasker/logic/commands/HelpCommand.java @@ -16,8 +16,6 @@ public class HelpCommand extends Command { public static final String SHOWING_HELP_MESSAGE = "Opened help window."; - public HelpCommand() {} - @Override public CommandResult execute() { EventsCenter.getInstance().post(new ShowHelpRequestEvent()); diff --git a/src/main/java/seedu/savvytasker/logic/commands/ListCommand.java b/src/main/java/seedu/savvytasker/logic/commands/ListCommand.java index f8c39d9032af..5c8f960bbb68 100644 --- a/src/main/java/seedu/savvytasker/logic/commands/ListCommand.java +++ b/src/main/java/seedu/savvytasker/logic/commands/ListCommand.java @@ -24,7 +24,6 @@ public class ListCommand extends ModelRequiringCommand { //@@author A0139915W /** * Creates the List command to list the specified tasks - * @author A0139915W * @param commandModel Arguments for the List command, must not be null */ public ListCommand(ListType listType) { @@ -43,9 +42,6 @@ public CommandResult execute() { // specifies to show the alias switch (_listType) { - case DueDate: - model.updateFilteredListToShowActiveSortedByDueDate(); - break; case PriorityLevel: model.updateFilteredListToShowActiveSortedByPriorityLevel(); break; @@ -55,10 +51,13 @@ public CommandResult execute() { case Alias: EventsCenter.getInstance().post(new ChangeListRequestEvent(DisplayedList.Alias)); break; - default: - // nothing to do + case DueDate: + // fall through. + default: // shows lists sorted by due date by default + model.updateFilteredListToShowActiveSortedByDueDate(); break; } + if (_listType != ListType.Alias) { EventsCenter.getInstance().post(new ChangeListRequestEvent(DisplayedList.Task)); return new CommandResult(getMessageForTaskListShownSummary(model.getFilteredTaskList().size())); diff --git a/src/main/java/seedu/savvytasker/logic/commands/ModifyCommand.java b/src/main/java/seedu/savvytasker/logic/commands/ModifyCommand.java index 02438849d7a4..1b5358706a60 100644 --- a/src/main/java/seedu/savvytasker/logic/commands/ModifyCommand.java +++ b/src/main/java/seedu/savvytasker/logic/commands/ModifyCommand.java @@ -29,7 +29,6 @@ public class ModifyCommand extends ModelRequiringCommand { public static final String MESSAGE_DUPLICATE_TASK = "This task already exists in the task list"; private Task originalTask; - private Task replacement; private final int index; private final String taskName; private final InferredDate startDateTime; @@ -73,7 +72,7 @@ public CommandResult execute() { } ReadOnlyTask taskToModify = lastShownList.get(index - 1); - replacement = new Task(taskToModify, taskName, startDateTime, + Task replacement = new Task(taskToModify, taskName, startDateTime, endDateTime, location, priority, recurringType, numberOfRecurrence, category, description); @@ -81,11 +80,11 @@ public CommandResult execute() { try { originalTask = (Task)taskToModify; Task taskModified = model.modifyTask(taskToModify, replacement); + + // GUI will always get index >= 0; int targetIndex = getIndexOfTask(taskModified); if (targetIndex >= 0) { EventsCenter.getInstance().post(new JumpToListRequestEvent(targetIndex)); - } else { - // GUI should never ever get here } } catch (TaskNotFoundException e) { assert false : "The target task cannot be missing"; diff --git a/src/main/java/seedu/savvytasker/logic/commands/RedoCommand.java b/src/main/java/seedu/savvytasker/logic/commands/RedoCommand.java index 765b3852c516..39721d6e3321 100644 --- a/src/main/java/seedu/savvytasker/logic/commands/RedoCommand.java +++ b/src/main/java/seedu/savvytasker/logic/commands/RedoCommand.java @@ -10,8 +10,6 @@ public class RedoCommand extends Command { public static final String MESSAGE_REDO_ACKNOWLEDGEMENT = "Last command redone"; - public RedoCommand() {} - @Override public CommandResult execute() { return new CommandResult(MESSAGE_REDO_ACKNOWLEDGEMENT); diff --git a/src/main/java/seedu/savvytasker/logic/commands/StorageCommand.java b/src/main/java/seedu/savvytasker/logic/commands/StorageCommand.java index 45df445e3f37..cc3172379958 100644 --- a/src/main/java/seedu/savvytasker/logic/commands/StorageCommand.java +++ b/src/main/java/seedu/savvytasker/logic/commands/StorageCommand.java @@ -4,6 +4,8 @@ import seedu.savvytasker.commons.events.storage.DataSavingLocationChangedEvent; import seedu.savvytasker.model.ReadOnlySavvyTasker; + +//@@author A0138431L /** * Changes the storage location of Savvy Tasker */ diff --git a/src/main/java/seedu/savvytasker/logic/commands/UndoCommand.java b/src/main/java/seedu/savvytasker/logic/commands/UndoCommand.java index ec905685594c..125e9305bebf 100644 --- a/src/main/java/seedu/savvytasker/logic/commands/UndoCommand.java +++ b/src/main/java/seedu/savvytasker/logic/commands/UndoCommand.java @@ -10,8 +10,6 @@ public class UndoCommand extends Command { public static final String MESSAGE_UNDO_ACKNOWLEDGEMENT = "Last command undone"; - public UndoCommand() {} - @Override public CommandResult execute() { return new CommandResult(MESSAGE_UNDO_ACKNOWLEDGEMENT); diff --git a/src/main/java/seedu/savvytasker/logic/parser/AddCommandParser.java b/src/main/java/seedu/savvytasker/logic/parser/AddCommandParser.java index 66dc288eeedf..afd504f48a72 100644 --- a/src/main/java/seedu/savvytasker/logic/parser/AddCommandParser.java +++ b/src/main/java/seedu/savvytasker/logic/parser/AddCommandParser.java @@ -1,4 +1,5 @@ //@@author A0139916U +// Please see CommandParser interface for documentation for many of the overridden methods package seedu.savvytasker.logic.parser; import java.util.regex.Matcher; diff --git a/src/main/java/seedu/savvytasker/logic/parser/AliasCommandParser.java b/src/main/java/seedu/savvytasker/logic/parser/AliasCommandParser.java index 2d5240d3534d..9166b8903414 100644 --- a/src/main/java/seedu/savvytasker/logic/parser/AliasCommandParser.java +++ b/src/main/java/seedu/savvytasker/logic/parser/AliasCommandParser.java @@ -53,9 +53,10 @@ public AliasCommand parse(String commandText) throws ParseException { private String parseRepresentation(String originalText) throws ParseException { String trimmedText = originalText.trim(); - if (trimmedText.isEmpty()) + if (trimmedText.isEmpty()) { throw new ParseException(trimmedText, "REPRESENTATION: Needs to be at least one character!"); - + } + return trimmedText; } diff --git a/src/main/java/seedu/savvytasker/logic/parser/DateParser.java b/src/main/java/seedu/savvytasker/logic/parser/DateParser.java index 66549fd40200..42ff9b2448d8 100644 --- a/src/main/java/seedu/savvytasker/logic/parser/DateParser.java +++ b/src/main/java/seedu/savvytasker/logic/parser/DateParser.java @@ -76,16 +76,16 @@ public InferredDate parseSingle(String input) throws ParseException { List dateGroups = this.nattyParser.parse(input); int totalDates = countDates(dateGroups); - if (totalDates == 0) + if (totalDates == 0) { throw new ParseException(input, "Failed to understand given date."); + } - if (totalDates > 1) + if (totalDates > 1) { throw new ParseException(input, "Too many dates entered."); + } DateGroup group = dateGroups.get(0); - - return new InferredDate( group.getDates().get(0), group.isDateInferred(), diff --git a/src/main/java/seedu/savvytasker/logic/parser/FindCommandParser.java b/src/main/java/seedu/savvytasker/logic/parser/FindCommandParser.java index 613378b1a794..d5c6867219b5 100644 --- a/src/main/java/seedu/savvytasker/logic/parser/FindCommandParser.java +++ b/src/main/java/seedu/savvytasker/logic/parser/FindCommandParser.java @@ -50,8 +50,9 @@ public FindCommand parse(String commandText) throws ParseException { //@@author private FindType parseFindType(String findTypeText) throws ParseException { - if (findTypeText == null) + if (findTypeText == null) { return null; + } String trimmedFindTypeText = findTypeText.trim(); try { @@ -67,12 +68,17 @@ private String[] parseKeywords(String keywordsBefore, String keywordsAfter) thro String[] keywordsArr1 = new String[0]; String[] keywordsArr2 = new String[0]; - if (!trimmedKeywordsBefore.isEmpty()) keywordsArr1 = trimmedKeywordsBefore.split("\\s+"); - if (!trimmedKeywordsAfter.isEmpty()) keywordsArr2 = trimmedKeywordsAfter.split("\\s+"); + if (!trimmedKeywordsBefore.isEmpty()) { + keywordsArr1 = trimmedKeywordsBefore.split("\\s+"); + } + if (!trimmedKeywordsAfter.isEmpty()) { + keywordsArr2 = trimmedKeywordsAfter.split("\\s+"); + } - if (keywordsArr1.length == 0 && keywordsArr2.length == 0) + if (keywordsArr1.length == 0 && keywordsArr2.length == 0) { throw new ParseException(trimmedKeywordsBefore + " ... " + trimmedKeywordsAfter, "KEYWORD: Need to specify at least one keyword!"); + } return concatArray(keywordsArr1, keywordsArr2); } diff --git a/src/main/java/seedu/savvytasker/logic/parser/IndexParser.java b/src/main/java/seedu/savvytasker/logic/parser/IndexParser.java index 3bdfebaea962..866ee418e60e 100644 --- a/src/main/java/seedu/savvytasker/logic/parser/IndexParser.java +++ b/src/main/java/seedu/savvytasker/logic/parser/IndexParser.java @@ -26,15 +26,17 @@ public int parseSingle(String indexText) throws ParseException { try { index = Integer.parseInt(trimmedIndexText); - if (index <= 0) + if (index <= 0) { parseError = true; + } } catch (NumberFormatException ex) { parseError = true; } - if (parseError) + if (parseError) { throw new ParseException(trimmedIndexText, "Must be a positive whole number."); - + } + return index; } @@ -66,9 +68,10 @@ public int[] parseMultiple(String indicesText) throws ParseException { parseError = true; } - if (parseError) + if (parseError) { throw new ParseException(trimmedIndicesText, INDEX_MUST_BE_POSITIVE); - + } + return indices; } } diff --git a/src/main/java/seedu/savvytasker/logic/parser/ListCommandParser.java b/src/main/java/seedu/savvytasker/logic/parser/ListCommandParser.java index ad2457b96f2f..f484abc8cb9c 100644 --- a/src/main/java/seedu/savvytasker/logic/parser/ListCommandParser.java +++ b/src/main/java/seedu/savvytasker/logic/parser/ListCommandParser.java @@ -42,8 +42,9 @@ public ListCommand parse(String commandText) throws ParseException { } private ListType parseListType(String listTypeText) throws ParseException { - if (listTypeText == null) + if (listTypeText == null) { return null; + } try { listTypeText = listTypeText.trim(); diff --git a/src/main/java/seedu/savvytasker/logic/parser/MasterParser.java b/src/main/java/seedu/savvytasker/logic/parser/MasterParser.java index 271cb564acd5..77ba0d698247 100644 --- a/src/main/java/seedu/savvytasker/logic/parser/MasterParser.java +++ b/src/main/java/seedu/savvytasker/logic/parser/MasterParser.java @@ -149,8 +149,9 @@ private String preprocessBody(String bodyText) { String spaces = matcher.group(2); // Preserves the amount of spaces as that may be what user wants AliasSymbol symbol = aliasingSymbols.get(keyword); - if (symbol != null) + if (symbol != null) { keyword = symbol.getRepresentation(); + } builder.append(keyword); builder.append(spaces); @@ -176,10 +177,12 @@ private String preprocessBody(String bodyText) { public boolean registerCommandParser(CommandParser commandParser) { assert commandParser != null; - if (commandParsers.containsKey(commandParser.getHeader())) + if (commandParsers.containsKey(commandParser.getHeader())) { return false; - if (aliasingSymbols.containsKey(commandParser.getHeader())) + } + if (aliasingSymbols.containsKey(commandParser.getHeader())) { return false; + } commandParsers.put(commandParser.getHeader(), commandParser); return true; @@ -219,10 +222,12 @@ public CommandParser unregisterCommandParser(String header) { public boolean addAliasSymbol(AliasSymbol symbol) { assert symbol != null; - if (aliasingSymbols.containsKey(symbol.getKeyword())) + if (aliasingSymbols.containsKey(symbol.getKeyword())) { return false; - if (isCommandParserRegistered(symbol.getKeyword())) + } + if (isCommandParserRegistered(symbol.getKeyword())) { return false; + } aliasList.add(symbol); aliasingSymbols.put(symbol.getKeyword(), symbol); diff --git a/src/main/java/seedu/savvytasker/logic/parser/TaskFieldParser.java b/src/main/java/seedu/savvytasker/logic/parser/TaskFieldParser.java index 361ad6944576..a15ace1d987a 100644 --- a/src/main/java/seedu/savvytasker/logic/parser/TaskFieldParser.java +++ b/src/main/java/seedu/savvytasker/logic/parser/TaskFieldParser.java @@ -9,7 +9,8 @@ /** * This class contains common parsing methods for parsing Task fields. * Each of the parse method takes in a string which can be null, and return - * the respective parsed object. + * the respective parsed object. If null is provided to each of the parse methods, + * null will be returned. */ public abstract class TaskFieldParser implements CommandParser { /* @@ -32,8 +33,9 @@ protected TaskFieldParser() { } protected String parseTaskName(String taskNameText) throws ParseException { - if (taskNameText == null) + if (taskNameText == null) { return null; + } return taskNameText.trim(); } @@ -46,9 +48,9 @@ protected InferredDate parseEndDate(String dateText) throws ParseException { } private InferredDate parseDate(String dateText, String errorField) throws ParseException { - if (dateText == null) + if (dateText == null) { return null; - + } String trimmedDateText = dateText.trim(); try { return dateParser.parseSingle(trimmedDateText); @@ -58,14 +60,16 @@ private InferredDate parseDate(String dateText, String errorField) throws ParseE } protected String parseLocation(String locationText) throws ParseException { - if (locationText == null) + if (locationText == null) { return null; + } return locationText.trim(); } protected PriorityLevel parsePriorityLevel(String priorityLevelText) throws ParseException { - if (priorityLevelText == null) + if (priorityLevelText == null) { return null; + } String trimmedPriorityLevelText = priorityLevelText.trim(); try { @@ -76,8 +80,9 @@ protected PriorityLevel parsePriorityLevel(String priorityLevelText) throws Pars } protected RecurrenceType parseRecurrenceType(String recurrenceTypeText) throws ParseException { - if (recurrenceTypeText == null) + if (recurrenceTypeText == null) { return null; + } String trimmedRecurrenceTypeText = recurrenceTypeText.trim(); try { @@ -88,8 +93,9 @@ protected RecurrenceType parseRecurrenceType(String recurrenceTypeText) throws P } protected Integer parseNumberOfRecurrence(String numRecurrenceText) throws ParseException { - if (numRecurrenceText == null) + if (numRecurrenceText == null) { return null; + } String trimmedNumRecurrenceText = numRecurrenceText.trim(); int numRecurrence = 0; @@ -97,27 +103,48 @@ protected Integer parseNumberOfRecurrence(String numRecurrenceText) throws Parse try { numRecurrence = Integer.parseInt(trimmedNumRecurrenceText); - if (numRecurrence < 0) + if (numRecurrence < 0) { parseError = true; + } } catch (NumberFormatException ex) { parseError = true; } - if (parseError) + if (parseError) { throw new ParseException(trimmedNumRecurrenceText, "NUMBER_OF_RECURRENCE: Must be a nonnegative whole number!"); + } return numRecurrence; } protected String parseCategory(String categoryText) throws ParseException { - if (categoryText == null) + if (categoryText == null) { return null; + } return categoryText.trim(); } protected String parseDescription(String descriptionText) throws ParseException { - if (descriptionText == null) + if (descriptionText == null) { return null; + } return descriptionText.trim(); } + //@@author + + //@@author A0138431L + public String parsefilePath(String filePathText) throws ParseException { + if (filePathText == null) { + return null; + } + return filePathText.trim(); + } + + public String parsefileName(String fileNameText) throws ParseException { + if (fileNameText == null) { + return null; + } + return fileNameText.trim(); + } + //@@author } diff --git a/src/main/java/seedu/savvytasker/model/ListType.java b/src/main/java/seedu/savvytasker/model/ListType.java index 2b7c9f244679..2e7fda37e229 100644 --- a/src/main/java/seedu/savvytasker/model/ListType.java +++ b/src/main/java/seedu/savvytasker/model/ListType.java @@ -32,8 +32,9 @@ public enum ListType { */ public static ListType valueOfIgnoreCase(String name) { for (ListType type : ListType.values()) { - if (type.toString().equalsIgnoreCase(name)) + if (type.toString().equalsIgnoreCase(name)) { return type; + } } throw new IllegalArgumentException("Unknown list type: " + name); diff --git a/src/main/java/seedu/savvytasker/model/Model.java b/src/main/java/seedu/savvytasker/model/Model.java index 4b081eb8ba34..bd52e32918b4 100644 --- a/src/main/java/seedu/savvytasker/model/Model.java +++ b/src/main/java/seedu/savvytasker/model/Model.java @@ -1,6 +1,7 @@ package seedu.savvytasker.model; import java.util.LinkedList; +import java.util.Date; import seedu.savvytasker.commons.core.UnmodifiableObservableList; import seedu.savvytasker.model.alias.AliasSymbol; @@ -80,4 +81,33 @@ public interface Model { /** Gets the number of aliases */ int getAliasSymbolCount(); + + //@@author A0138431L + /** Returns the filtered task list of overdue task as an {@code UnmodifiableObservableList} + * as of current date */ + UnmodifiableObservableList getFilteredOverdueTasks(); + + /** Returns the filtered task list of floating task as an {@code UnmodifiableObservableList} */ + UnmodifiableObservableList getFilteredFloatingTasks(); + + /** Returns the filtered task list of daily task as an {@code UnmodifiableObservableList} + * as of expected date */ + UnmodifiableObservableList getFilteredDailyTasks(int dayOfWeek, Date date); + + /** Returns the filtered task list of upcoming task as an {@code UnmodifiableObservableList} + * as of expected date */ + UnmodifiableObservableList getFilteredUpcomingTasks(Date date); + + /** Updates the filter of the filtered task list to show all overdue tasks */ + void updateFilteredListToShowOverdue(); + + /** Updates the filter of the filtered task list to show all floating tasks */ + void updateFilteredListToShowFloating(); + + /** Updates the filter of the filtered task list to show all tasks of the selected week*/ + void updateFilteredListToShowDaily(int i); + + /** Updates the filter of the filtered task list to show all upcoming tasks after the selected week*/ + void updateFilteredListToShowUpcoming(); + //@@author } diff --git a/src/main/java/seedu/savvytasker/model/ModelManager.java b/src/main/java/seedu/savvytasker/model/ModelManager.java old mode 100644 new mode 100755 index 1551a6608316..396e49ed67ed --- a/src/main/java/seedu/savvytasker/model/ModelManager.java +++ b/src/main/java/seedu/savvytasker/model/ModelManager.java @@ -1,7 +1,9 @@ package seedu.savvytasker.model; import java.util.Arrays; +import java.util.Calendar; import java.util.Comparator; +import java.util.Date; import java.util.HashSet; import java.util.Iterator; import java.util.LinkedList; @@ -9,6 +11,8 @@ import java.util.Set; import java.util.logging.Logger; +import org.apache.commons.lang.time.DateUtils; + import javafx.collections.transformation.FilteredList; import javafx.collections.transformation.SortedList; import seedu.savvytasker.commons.core.ComponentManager; @@ -31,69 +35,141 @@ * All changes to any model should be synchronized. */ public class ModelManager extends ComponentManager implements Model { - private static final Logger logger = LogsCenter.getLogger(ModelManager.class); - - //@@author A0139915W - private final SavvyTasker savvyTasker; - private final FilteredList filteredTasks; - private final SortedList sortedAndFilteredTasks; - - /** - * Initializes a ModelManager with the given SavvyTasker - * and its variables should not be null - */ - public ModelManager(SavvyTasker src) { - super(); - assert src != null; - - logger.fine("Initializing with savvy tasker: " + src); - - savvyTasker = new SavvyTasker(src); - filteredTasks = new FilteredList<>(savvyTasker.getTasks()); - sortedAndFilteredTasks = new SortedList<>(filteredTasks, new TaskSortedByDueDate()); - updateFilteredListToShowActive(); // shows only active tasks on start - } - - public ModelManager() { - this(new SavvyTasker()); - } - - public ModelManager(ReadOnlySavvyTasker initialData) { - savvyTasker = new SavvyTasker(initialData); - filteredTasks = new FilteredList<>(savvyTasker.getTasks()); - sortedAndFilteredTasks = new SortedList<>(filteredTasks, new TaskSortedByDueDate()); - updateFilteredListToShowActive(); // shows only active tasks on start - } - //@@author - - @Override - public void resetData(ReadOnlySavvyTasker newData) { - savvyTasker.resetData(newData); - indicateSavvyTaskerChanged(); - } - - @Override - public ReadOnlySavvyTasker getSavvyTasker() { - return savvyTasker; - } - - /** Raises an event to indicate the model has changed */ - private void indicateSavvyTaskerChanged() { - raise(new SavvyTaskerChangedEvent(savvyTasker)); - } - //@@author A0139916U - - private void indicateAliasSymbolAdded(AliasSymbol symbol) { - raise(new AliasSymbolChangedEvent(symbol, AliasSymbolChangedEvent.Action.Added)); - } - - private void indicateAliasSymbolRemoved(AliasSymbol symbol) { - raise(new AliasSymbolChangedEvent(symbol, AliasSymbolChangedEvent.Action.Removed)); - } - //@@author - - - //@@author A0139915W + private static final Logger logger = LogsCenter.getLogger(ModelManager.class); + Date onDate = new Date(); + Date firstDayOfSelectedWeek = new Date(); + + //@@author A0138431L + private final SavvyTasker savvyTasker; + private final FilteredList filteredTasks; + private final SortedList sortedAndFilteredTasks; + private final FilteredList filteredFloatingTasks; + private final SortedList sortedAndFilteredFloatingTasks; + private final FilteredList filteredOverdueTasks; + private final SortedList sortedAndFilteredOverdueTasks; + private final FilteredList filteredDay1Tasks; + private final SortedList sortedAndFilteredDay1Tasks; + private final FilteredList filteredDay2Tasks; + private final SortedList sortedAndFilteredDay2Tasks; + private final FilteredList filteredDay3Tasks; + private final SortedList sortedAndFilteredDay3Tasks; + private final FilteredList filteredDay4Tasks; + private final SortedList sortedAndFilteredDay4Tasks; + private final FilteredList filteredDay5Tasks; + private final SortedList sortedAndFilteredDay5Tasks; + private final FilteredList filteredDay6Tasks; + private final SortedList sortedAndFilteredDay6Tasks; + private final FilteredList filteredDay7Tasks; + private final SortedList sortedAndFilteredDay7Tasks; + private final FilteredList filteredUpcomingTasks; + private final SortedList sortedAndFilteredUpcomingTasks; + + /** + * Initializes a ModelManager with the given SavvyTasker + * and its variables should not be null + */ + public ModelManager(SavvyTasker src) { + super(); + assert src != null; + + logger.fine("Initializing with savvy tasker: " + src); + + savvyTasker = new SavvyTasker(src); + filteredTasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredTasks = new SortedList<>(filteredTasks, new TaskSortedByDefault()); + + filteredFloatingTasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredFloatingTasks = new SortedList<>(filteredFloatingTasks, new TaskSortedByDefault()); + + filteredOverdueTasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredOverdueTasks = new SortedList<>(filteredOverdueTasks, new TaskSortedByDefault()); + + filteredDay1Tasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredDay1Tasks = new SortedList<>(filteredDay1Tasks, new TaskSortedByDefault()); + filteredDay2Tasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredDay2Tasks = new SortedList<>(filteredDay2Tasks, new TaskSortedByDefault()); + filteredDay3Tasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredDay3Tasks = new SortedList<>(filteredDay3Tasks, new TaskSortedByDefault()); + filteredDay4Tasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredDay4Tasks = new SortedList<>(filteredDay4Tasks, new TaskSortedByDefault()); + filteredDay5Tasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredDay5Tasks = new SortedList<>(filteredDay5Tasks, new TaskSortedByDefault()); + filteredDay6Tasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredDay6Tasks = new SortedList<>(filteredDay6Tasks, new TaskSortedByDefault()); + filteredDay7Tasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredDay7Tasks = new SortedList<>(filteredDay7Tasks, new TaskSortedByDefault()); + + filteredUpcomingTasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredUpcomingTasks = new SortedList<>(filteredUpcomingTasks, new TaskSortedByDefault()); + + updateFilteredListToShowActive(); // shows only active tasks on start + } + + public ModelManager() { + this(new SavvyTasker()); + } + + public ModelManager(ReadOnlySavvyTasker initialData) { + savvyTasker = new SavvyTasker(initialData); + filteredTasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredTasks = new SortedList<>(filteredTasks, new TaskSortedByDefault()); + + filteredFloatingTasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredFloatingTasks = new SortedList<>(filteredFloatingTasks, new TaskSortedByDefault()); + + filteredOverdueTasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredOverdueTasks = new SortedList<>(filteredOverdueTasks, new TaskSortedByDefault()); + + filteredDay1Tasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredDay1Tasks = new SortedList<>(filteredDay1Tasks, new TaskSortedByDefault()); + filteredDay2Tasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredDay2Tasks = new SortedList<>(filteredDay2Tasks, new TaskSortedByDefault()); + filteredDay3Tasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredDay3Tasks = new SortedList<>(filteredDay3Tasks, new TaskSortedByDefault()); + filteredDay4Tasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredDay4Tasks = new SortedList<>(filteredDay4Tasks, new TaskSortedByDefault()); + filteredDay5Tasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredDay5Tasks = new SortedList<>(filteredDay5Tasks, new TaskSortedByDefault()); + filteredDay6Tasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredDay6Tasks = new SortedList<>(filteredDay6Tasks, new TaskSortedByDefault()); + filteredDay7Tasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredDay7Tasks = new SortedList<>(filteredDay7Tasks, new TaskSortedByDefault()); + + filteredUpcomingTasks = new FilteredList<>(savvyTasker.getTasks()); + sortedAndFilteredUpcomingTasks = new SortedList<>(filteredUpcomingTasks, new TaskSortedByDefault()); + + updateFilteredListToShowActive(); // shows only active tasks on start + } + //@@author + + @Override + public void resetData(ReadOnlySavvyTasker newData) { + savvyTasker.resetData(newData); + indicateSavvyTaskerChanged(); + } + + @Override + public ReadOnlySavvyTasker getSavvyTasker() { + return savvyTasker; + } + + /** Raises an event to indicate the model has changed */ + private void indicateSavvyTaskerChanged() { + raise(new SavvyTaskerChangedEvent(savvyTasker)); + } + //@@author A0139916U + + private void indicateAliasSymbolAdded(AliasSymbol symbol) { + raise(new AliasSymbolChangedEvent(symbol, AliasSymbolChangedEvent.Action.Added)); + } + + private void indicateAliasSymbolRemoved(AliasSymbol symbol) { + raise(new AliasSymbolChangedEvent(symbol, AliasSymbolChangedEvent.Action.Removed)); + } + //@@author + + + //@@author A0139915W @Override public synchronized Task deleteTask(ReadOnlyTask target) throws TaskNotFoundException { Task taskDeleted = savvyTasker.removeTask(target); @@ -124,8 +200,8 @@ public synchronized LinkedList addRecurringTask(Task recurringTask) throws return recurringTasks; } //@@author - - //@@author A0139916U + + //@@author A0139916U @Override public synchronized void addAliasSymbol(AliasSymbol symbol) throws DuplicateSymbolKeywordException { savvyTasker.addAliasSymbol(symbol); @@ -146,7 +222,7 @@ public int getAliasSymbolCount() { } //@@author - //=========== Filtered/Sorted Task List Accessors =============================================================== + //=========== Filtered/Sorted Task List Accessors =============================================================== //@@author A0139915W @Override @@ -168,52 +244,183 @@ public void updateFilteredListToShowActiveSortedByPriorityLevel() { public void updateFilteredListToShowActive() { updateFilteredTaskList(new PredicateExpression(new TaskIsActiveQualifier())); } - private void updateFilteredListToShowActive(Comparator comparator) { - updateFilteredTaskList( - new PredicateExpression(new TaskIsActiveQualifier()), - comparator); - } - - @Override - public void updateFilteredListToShowArchived() { - updateFilteredTaskList(new PredicateExpression(new TaskIsArchivedQualifier())); - } - - @Override - public void updateFilteredTaskList(FindType findType, String[] keywords) { - assert findType != null; - Qualifier qualifier = null; - switch (findType) - { - case Partial: - qualifier = new TaskNamePartialMatchQualifier(keywords); - break; - case Full: - qualifier = new TaskNameFullMatchQualifier(keywords); - break; - case Exact: - qualifier = new TaskNameExactMatchQualifier(keywords); - break; - case Category: - qualifier = new CategoryPartialMatchQualifier(keywords); - break; - default: - assert false; // should never get here. - } - updateFilteredTaskList(new PredicateExpression(qualifier)); - } - private void updateFilteredTaskList(Expression expression) { - updateFilteredTaskList(expression, new TaskSortedByDefault()); - } - - private void updateFilteredTaskList(Expression expression, Comparator comparator) { - filteredTasks.setPredicate(expression::satisfies); - sortedAndFilteredTasks.setComparator(comparator); - } - //@@author - - //========== Inner classes/interfaces used for filtering ================================================== + private void updateFilteredListToShowActive(Comparator comparator) { + updateFilteredTaskList( + new PredicateExpression(new TaskIsActiveQualifier()), + comparator); + } + + @Override + public void updateFilteredListToShowArchived() { + updateFilteredTaskList(new PredicateExpression(new TaskIsArchivedQualifier())); + } + + @Override + public void updateFilteredTaskList(FindType findType, String[] keywords) { + assert findType != null; + Qualifier qualifier = null; + switch (findType) + { + case Partial: + qualifier = new TaskNamePartialMatchQualifier(keywords); + break; + case Full: + qualifier = new TaskNameFullMatchQualifier(keywords); + break; + case Exact: + qualifier = new TaskNameExactMatchQualifier(keywords); + break; + case Category: + qualifier = new CategoryPartialMatchQualifier(keywords); + break; + default: + assert false; // should never get here. + break; + } + updateFilteredTaskList(new PredicateExpression(qualifier)); + } + + private void updateFilteredTaskList(Expression expression) { + updateFilteredTaskList(expression, new TaskSortedByDefault()); + } + + private void updateFilteredTaskList(Expression expression, Comparator comparator) { + filteredTasks.setPredicate(expression::satisfies); + sortedAndFilteredTasks.setComparator(comparator); + } + //@@author + + //@author A0138431L + //Get filtered task list according to date category + @Override + public UnmodifiableObservableList getFilteredOverdueTasks() { + updateFilteredListToShowOverdue(); + return new UnmodifiableObservableList(filteredOverdueTasks); + } + + @Override + public UnmodifiableObservableList getFilteredFloatingTasks() { + updateFilteredListToShowFloating(); + return new UnmodifiableObservableList(filteredFloatingTasks); + } + + @Override + public UnmodifiableObservableList getFilteredDailyTasks(int dayOfWeek, Date date) { + this.onDate = date; + updateFilteredListToShowDaily(dayOfWeek); + switch(dayOfWeek) { + case 0: + return new UnmodifiableObservableList(filteredDay1Tasks); + case 1: + return new UnmodifiableObservableList(filteredDay2Tasks); + case 2: + return new UnmodifiableObservableList(filteredDay3Tasks); + case 3: + return new UnmodifiableObservableList(filteredDay4Tasks); + case 4: + return new UnmodifiableObservableList(filteredDay5Tasks); + case 5: + return new UnmodifiableObservableList(filteredDay6Tasks); + case 6: + return new UnmodifiableObservableList(filteredDay7Tasks); + default: + return new UnmodifiableObservableList(filteredDay1Tasks); + } + } + + @Override + public UnmodifiableObservableList getFilteredUpcomingTasks(Date date) { + this.firstDayOfSelectedWeek = date; + updateFilteredListToShowUpcoming(); + return new UnmodifiableObservableList(filteredUpcomingTasks); + } + + //Binding isOverdue quantifier predicate to filtered list + @Override + public void updateFilteredListToShowOverdue() { + updateFilteredOverdueTaskList(new PredicateExpression(new TaskIsOverdueQualifier())); + } + + private void updateFilteredOverdueTaskList(Expression expression) { + updateFilteredOverdueTaskList(expression, new TaskSortedByDefault()); + } + + private void updateFilteredOverdueTaskList(Expression expression, Comparator comparator) { + filteredOverdueTasks.setPredicate(expression::satisfies); + sortedAndFilteredOverdueTasks.setComparator(comparator); + } + + //Binding isFloating quantifier predicate to filtered list + @Override + public void updateFilteredListToShowFloating() { + updateFilteredFloatingTaskList(new PredicateExpression(new TaskIsFloatingQualifier())); + } + + private void updateFilteredFloatingTaskList(Expression expression) { + updateFilteredFloatingTaskList(expression, new TaskSortedByDefault()); + } + + private void updateFilteredFloatingTaskList(Expression expression, Comparator comparator) { + filteredFloatingTasks.setPredicate(expression::satisfies); + sortedAndFilteredFloatingTasks.setComparator(comparator); + } + + //Binding isOnDate quantifier predicate to filtered list + @Override + public void updateFilteredListToShowDaily(int dayOfWeek) { + updateFilteredDailyTaskList(new PredicateExpression(new TaskIsOnDateQualifier()), dayOfWeek); + } + + private void updateFilteredDailyTaskList(Expression expression, int dayOfWeek) { + updateFilteredDailyTaskList(expression, new TaskSortedByDefault(), dayOfWeek); + } + + private void updateFilteredDailyTaskList(Expression expression, Comparator comparator, int dayOfWeek) { + switch(dayOfWeek) { + case 0: + filteredDay1Tasks.setPredicate(expression::satisfies); + sortedAndFilteredDay1Tasks.setComparator(comparator); + case 1: + filteredDay2Tasks.setPredicate(expression::satisfies); + sortedAndFilteredDay2Tasks.setComparator(comparator); + case 2: + filteredDay3Tasks.setPredicate(expression::satisfies); + sortedAndFilteredDay3Tasks.setComparator(comparator); + case 3: + filteredDay4Tasks.setPredicate(expression::satisfies); + sortedAndFilteredDay4Tasks.setComparator(comparator); + case 4: + filteredDay5Tasks.setPredicate(expression::satisfies); + sortedAndFilteredDay5Tasks.setComparator(comparator); + case 5: + filteredDay6Tasks.setPredicate(expression::satisfies); + sortedAndFilteredDay6Tasks.setComparator(comparator); + case 6: + filteredDay7Tasks.setPredicate(expression::satisfies); + sortedAndFilteredDay7Tasks.setComparator(comparator); + + } + } + + //Binding isUpcoming quantifier predicate to filtered list + @Override + public void updateFilteredListToShowUpcoming() { + updateFilteredUpcomingTaskList(new PredicateExpression(new TaskIsUpcomingQualifier())); + } + + private void updateFilteredUpcomingTaskList(Expression expression) { + updateFilteredUpcomingTaskList(expression, new TaskSortedByDefault()); + } + + private void updateFilteredUpcomingTaskList(Expression expression, Comparator comparator) { + filteredUpcomingTasks.setPredicate(expression::satisfies); + sortedAndFilteredUpcomingTasks.setComparator(comparator); + } + + //@@author + + //========== Inner classes/interfaces used for filtering ================================================== interface Expression { boolean satisfies(ReadOnlyTask task); @@ -259,7 +466,6 @@ default Set createSet(String[] keywords) { //@@author A0139915W /** * Qualifier matching a partial word from the set of keywords - * @author A0139915W */ private class CategoryPartialMatchQualifier implements Qualifier { private Set keyWordsToMatch; @@ -284,7 +490,6 @@ public String toString() { /** * Qualifier matching a partial word from the set of keywords - * @author A0139915W */ private class TaskNamePartialMatchQualifier implements Qualifier { private Set keyWordsToMatch; @@ -309,7 +514,6 @@ public String toString() { /** * Qualifier matching a full word from the set of keywords - * @author A0139915W */ private class TaskNameFullMatchQualifier implements Qualifier { private Set keyWordsToMatch; @@ -334,7 +538,6 @@ public String toString() { /** * Qualifier matching a exactly from the set of keywords - * @author A0139915W */ private class TaskNameExactMatchQualifier implements Qualifier { private Set keyWordsToMatch; @@ -378,14 +581,13 @@ public String toString() { /** * Qualifier for checking if {@link Task} is active. Tasks that are not archived are active. - * @author A0139915W * */ private class TaskIsActiveQualifier implements Qualifier { @Override public boolean run(ReadOnlyTask task) { - return task.isArchived() == false; + return !task.isArchived(); } @Override @@ -396,54 +598,268 @@ public String toString() { /** * Qualifier for checking if {@link Task} is archived - * @author A0139915W * */ private class TaskIsArchivedQualifier implements Qualifier { @Override public boolean run(ReadOnlyTask task) { - return task.isArchived() == true; + return task.isArchived(); } @Override public String toString() { return "isArchived=true"; } - } + }//@@author + + //@@author A0138431L + /** + * Qualifier for checking if {@link Task} is an overdue task + * + * A overdue task is a deadline or event task with end dateTime after current dateTime + * + * @return true if the task is overdue + * + */ + private class TaskIsOverdueQualifier implements Qualifier { + + @Override + public boolean run(ReadOnlyTask task) { + + Date today = new Date(); + + boolean isOverdue = false; + + if (task.getEndDateTime() != null) { + + Date endDateTime = task.getEndDateTime(); + + if (endDateTime.compareTo(today)<0 && task.isArchived() == false) { + + isOverdue = true; + } + + } + + return isOverdue; + + } + + @Override + public String toString() { + return "isOverdue=true"; + } + } + + /** + * Qualifier for checking if {@link Task} is a floating task + * + * A floating task do not have start or end time + * + * @return true if the task falls on the date specified. else return false + * + */ + private class TaskIsFloatingQualifier implements Qualifier { + + @Override + public boolean run(ReadOnlyTask task) { + + boolean isFloating = false; + + if(task.getStartDateTime() == null && task.getEndDateTime() == null && task.isArchived() == false) { + + isFloating = true; + + } + + return isFloating; + + } + + @Override + public String toString() { + return "isFloating=true"; + } + } + + /** + * Qualifier for checking if {@link Task} falls on the selected date + * + * Check whether the task is on the date specified (for deadline tasks) + * Check whether the date specified is within the range of date the task (for event tasks) + * Includes task that are completed. + * + * @return true if the task falls on the date specified. else return false + * + */ + private class TaskIsOnDateQualifier implements Qualifier { + + @Override + public boolean run(ReadOnlyTask task) { + + Date expectedDate = onDate; + + boolean isOnDate = false; + + //Archived Task + if(task.isArchived() == true){ + + isOnDate = false; + + } + //Deadline Task + else if(task.getStartDateTime() == null && task.getEndDateTime() != null) { + + Date endDateTime = task.getEndDateTime(); + + if (DateUtils.isSameDay(endDateTime, expectedDate)) { + + isOnDate = true; + + } + + } + //Event Task + else if(task.getStartDateTime() != null && task.getEndDateTime() != null) { + + Date startDateTime = task.getStartDateTime(); + Date endDateTime = task.getEndDateTime(); + + if (DateUtils.isSameDay(startDateTime, expectedDate)) { + + isOnDate = true; + + } else if (DateUtils.isSameDay(endDateTime, expectedDate)) { + + isOnDate = true; + + } else if (startDateTime.compareTo(expectedDate)<0 && expectedDate.compareTo(endDateTime)<0) { + + isOnDate = true; + + } + } + + return isOnDate; + } + + @Override + public String toString() { + return "isOnDate=true"; + } + } + + /** + * Qualifier for checking if {@link Task} task is upcoming + * + * A upcoming task is a task that will happen after the last day, 2359 of selected week + * + * @return true if the task is a upcoming task + * + */ + private class TaskIsUpcomingQualifier implements Qualifier { + + @Override + public boolean run(ReadOnlyTask task) { + + Date lastDateOfExpectedWeek = firstDayOfSelectedWeek; + + //convert date object to calendar object and add 7 days, last day of the selected week + Calendar calendarExpectedDate = Calendar.getInstance(); + calendarExpectedDate.setTime(lastDateOfExpectedWeek); + calendarExpectedDate.add(Calendar.DAY_OF_MONTH, 7); + calendarExpectedDate.set(Calendar.HOUR_OF_DAY,23); + calendarExpectedDate.set(Calendar.MINUTE,59); + calendarExpectedDate.set(Calendar.SECOND,59); + + //convert calendar object back to date object + lastDateOfExpectedWeek = calendarExpectedDate.getTime(); + + boolean isUpcoming = true; + + //Archived Task + if(task.isArchived() == true){ + + isUpcoming = false; + + } + + //Floating Task + else if(task.getStartDateTime() == null && task.getEndDateTime() == null) { + + isUpcoming = false; + + } + //Deadline Task + else if(task.getStartDateTime() == null && task.getEndDateTime() != null) { + + + if (task.getEndDateTime().compareTo(lastDateOfExpectedWeek)<0) { + + isUpcoming = false; + + } + + } + //Event Task + else { + + if (task.getStartDateTime().compareTo(lastDateOfExpectedWeek)<0) { + + isUpcoming = false; + + } + + } + + return isUpcoming; + } + + @Override + public String toString() { + return "isUpcoming=true"; + } + }//@@author - //========== Inner classes/interfaces used for sorting ================================================== + //@@author A0139915W + + //========== Inner classes/interfaces used for sorting ================================================== /** * Compares {@link Task} by their default field, id - * @author A0139915W - * */ private class TaskSortedByDefault implements Comparator { @Override public int compare(Task task1, Task task2) { - if (task1 == null && task2 == null) return 0; - else if (task1 == null) return 1; - else if (task2 == null) return -1; - else return task1.getId() - task2.getId(); + if (task1 == null && task2 == null) { + return 0; + } else if (task1 == null) { + return 1; + } else if (task2 == null) { + return -1; + } else { + return task1.getId() - task2.getId(); + } } } /** * Compares {@link Task} by their DueDate - * @author A0139915W - * */ private class TaskSortedByDueDate implements Comparator { @Override public int compare(Task task1, Task task2) { - if (task1 == null && task2 == null) return 0; - else if (task1 == null) return 1; - else if (task2 == null) return -1; - else { + if (task1 == null && task2 == null) { + return 0; + } else if (task1 == null) { + return 1; + } else if (task2 == null) { + return -1; + } else { // End dates can be nulls (floating tasks) // Check for existence of endDateTime before comparing if (task1.getEndDateTime() == null && @@ -463,8 +879,6 @@ public int compare(Task task1, Task task2) { /** * Compares {@link Task} by their PriorityLevel - * @author A0139915W - * */ private class TaskSortedByPriorityLevel implements Comparator { @@ -481,4 +895,4 @@ public int compare(Task task1, Task task2) { } //@@author -} +} \ No newline at end of file diff --git a/src/main/java/seedu/savvytasker/model/SavvyTasker.java b/src/main/java/seedu/savvytasker/model/SavvyTasker.java index 7b32afb8635f..f85f4307df2d 100644 --- a/src/main/java/seedu/savvytasker/model/SavvyTasker.java +++ b/src/main/java/seedu/savvytasker/model/SavvyTasker.java @@ -202,8 +202,10 @@ private Task setDatesForRecurringType(Task t, RecurrenceType recurringType, int } break; case None: + //fall through default: assert false; // should not come here + break; } t.setStartDateTime(startDate); t.setEndDateTime(endDate); diff --git a/src/main/java/seedu/savvytasker/model/task/FindType.java b/src/main/java/seedu/savvytasker/model/task/FindType.java index 49e69023a5f8..aab2e4e9b111 100644 --- a/src/main/java/seedu/savvytasker/model/task/FindType.java +++ b/src/main/java/seedu/savvytasker/model/task/FindType.java @@ -38,8 +38,9 @@ public enum FindType { */ public static FindType valueOfIgnoreCase(String name) { for (FindType type : FindType.values()) { - if (type.toString().equalsIgnoreCase(name)) + if (type.toString().equalsIgnoreCase(name)) { return type; + } } throw new IllegalArgumentException("Unknown find type: " + name); diff --git a/src/main/java/seedu/savvytasker/model/task/PriorityLevel.java b/src/main/java/seedu/savvytasker/model/task/PriorityLevel.java index 16db6b967ea6..836b8faeedfb 100644 --- a/src/main/java/seedu/savvytasker/model/task/PriorityLevel.java +++ b/src/main/java/seedu/savvytasker/model/task/PriorityLevel.java @@ -16,8 +16,9 @@ public enum PriorityLevel { */ public static PriorityLevel valueOfIgnoreCase(String name) { for (PriorityLevel type : PriorityLevel.values()) { - if (type.toString().equalsIgnoreCase(name)) + if (type.toString().equalsIgnoreCase(name)) { return type; + } } throw new IllegalArgumentException("Unknown priority level: " + name); diff --git a/src/main/java/seedu/savvytasker/model/task/ReadOnlyTask.java b/src/main/java/seedu/savvytasker/model/task/ReadOnlyTask.java index 9b4df673008c..a8648b5cfe9f 100644 --- a/src/main/java/seedu/savvytasker/model/task/ReadOnlyTask.java +++ b/src/main/java/seedu/savvytasker/model/task/ReadOnlyTask.java @@ -61,8 +61,10 @@ default String getAsText() { } if (getDescription() != null && !getDescription().isEmpty()) { builder.append(" Description: ") - . append(getDescription()); + .append(getDescription()); } + builder.append(" Archived: ") + .append(isArchived()); return builder.toString(); } @@ -100,8 +102,6 @@ default String getTextForUi() { .append(getDescription()) .append("\n"); } - builder.append(" Archived: ") - .append(isArchived()); return builder.toString(); } diff --git a/src/main/java/seedu/savvytasker/model/task/RecurrenceType.java b/src/main/java/seedu/savvytasker/model/task/RecurrenceType.java index 4d3fa8f4aca3..cb4e32e59f16 100644 --- a/src/main/java/seedu/savvytasker/model/task/RecurrenceType.java +++ b/src/main/java/seedu/savvytasker/model/task/RecurrenceType.java @@ -33,8 +33,9 @@ public enum RecurrenceType { */ public static RecurrenceType valueOfIgnoreCase(String name) { for (RecurrenceType type : RecurrenceType.values()) { - if (type.toString().equalsIgnoreCase(name)) + if (type.toString().equalsIgnoreCase(name)) { return type; + } } throw new IllegalArgumentException("Unknown recurrence type: " + name); diff --git a/src/main/java/seedu/savvytasker/model/task/Task.java b/src/main/java/seedu/savvytasker/model/task/Task.java index 593822c9bf31..361060f26140 100644 --- a/src/main/java/seedu/savvytasker/model/task/Task.java +++ b/src/main/java/seedu/savvytasker/model/task/Task.java @@ -134,10 +134,7 @@ public Task(ReadOnlyTask source, String taskName, InferredDate startDateTime, In } private void setStartDate(InferredDate inferredDate) { - if (inferredDate == null) { - // user didn't specify s/ - // keep existing start date - } else { + if (inferredDate != null) { if (inferredDate.isDateInferred() && inferredDate.isTimeInferred()) { // user specified s/ but with nothing tagged to it // remove existing start date @@ -152,10 +149,7 @@ private void setStartDate(InferredDate inferredDate) { } private void setEndDate(InferredDate inferredDate) { - if (inferredDate == null) { - // user didn't specify e/ - // keep existing end date - } else { + if (inferredDate != null) { if (inferredDate.isDateInferred() && inferredDate.isTimeInferred()) { // user specified e/ but with nothing tagged to it // remove existing end date @@ -279,8 +273,11 @@ public void setDescription(String description) { } public void setArchived(boolean isArchived) { - if (isArchived) mark(); - else unmark(); + if (isArchived) { + mark(); + } else { + unmark(); + } } /** diff --git a/src/main/java/seedu/savvytasker/model/task/TaskList.java b/src/main/java/seedu/savvytasker/model/task/TaskList.java index 6c68eab70ae7..2165115f7c17 100644 --- a/src/main/java/seedu/savvytasker/model/task/TaskList.java +++ b/src/main/java/seedu/savvytasker/model/task/TaskList.java @@ -17,6 +17,12 @@ */ public class TaskList implements Iterable { + private final ObservableList internalList = FXCollections.observableArrayList(); + private int nextId = 0; + private boolean isNextIdInitialized = false; + private int nextGroupId = 0; + private boolean isNextGroupIdInitialized = false; + /** * Signals that an operation would have violated the 'end time earlier than start time' property of the list. */ @@ -58,17 +64,6 @@ public static class TaskNotFoundException extends Exception { */ private static final long serialVersionUID = -7591982407764643511L; } - - private final ObservableList internalList = FXCollections.observableArrayList(); - private int nextId = 0; - private boolean isNextIdInitialized = false; - private int nextGroupId = 0; - private boolean isNextGroupIdInitialized = false; - - /** - * Constructs empty TaskList. - */ - public TaskList() {} /** * Gets the next available id for uniquely identifying a task in @@ -129,11 +124,8 @@ public boolean contains(ReadOnlyTask toCheck) { */ public boolean isValidStartEnd(ReadOnlyTask toCheck) { assert toCheck != null; - if (toCheck.getStartDateTime() != null && toCheck.getEndDateTime() != null && - toCheck.getStartDateTime().compareTo(toCheck.getEndDateTime()) >= 0) { - return false; - } - return true; + return toCheck.getStartDateTime() == null || toCheck.getEndDateTime() == null || + toCheck.getStartDateTime().compareTo(toCheck.getEndDateTime()) < 0; } /** diff --git a/src/main/java/seedu/savvytasker/storage/ConfigStorage.java b/src/main/java/seedu/savvytasker/storage/ConfigStorage.java new file mode 100644 index 000000000000..72ac5051173e --- /dev/null +++ b/src/main/java/seedu/savvytasker/storage/ConfigStorage.java @@ -0,0 +1,29 @@ +//@@author A0138431L +package seedu.savvytasker.storage; + +import java.io.IOException; +import java.util.Optional; + +import seedu.savvytasker.commons.core.Config; +import seedu.savvytasker.commons.exceptions.DataConversionException; + +/** + * Represents a storage for {@link seedu.savvytasker.commons.core.Config}. + */ +public interface ConfigStorage { + /** + * Returns Config data from storage. + * Returns {@code Optional.empty()} if storage file is not found. + * @throws DataConversionException if the data in storage is not in the expected format. + * @throws IOException if there was any problem when reading from the storage. + */ + Optional readConfigFile() throws DataConversionException, IOException; + + /** + * Saves the given {@link seedu.savvytasker.commons.core.Config} to the storage. + * @param config cannot be null. + * @throws IOException if there was any problem writing to the file. + */ + void saveConfigFile(Config config) throws IOException; + +} \ No newline at end of file diff --git a/src/main/java/seedu/savvytasker/storage/JsonConfigStorage.java b/src/main/java/seedu/savvytasker/storage/JsonConfigStorage.java new file mode 100644 index 000000000000..271de40c6e9b --- /dev/null +++ b/src/main/java/seedu/savvytasker/storage/JsonConfigStorage.java @@ -0,0 +1,90 @@ +//@@author A0138431L + +package seedu.savvytasker.storage; + +import java.io.File; +import java.io.IOException; +import java.util.Optional; +import java.util.logging.Logger; + +import seedu.savvytasker.commons.core.Config; +import seedu.savvytasker.commons.core.LogsCenter; +import seedu.savvytasker.commons.exceptions.DataConversionException; +import seedu.savvytasker.commons.util.FileUtil; + +/** + * A class to access Config stored in the hard disk as a json file + */ +public class JsonConfigStorage implements ConfigStorage { + + private static final Logger logger = LogsCenter.getLogger(JsonConfigStorage.class); + + private String filePath; + + public JsonConfigStorage(String filePath) { + + this.filePath = filePath; + } + + @Override + public Optional readConfigFile() throws DataConversionException, IOException { + + return readConfig(filePath); + } + + @Override + public void saveConfigFile(Config config) throws IOException { + + saveConfig(config, filePath); + } + + /** + * Similar to {@link #readConfigFile()} + * @param configFilePath location of the data. Cannot be null. + * @throws DataConversionException if the file format is not as expected. + */ + public Optional readConfig(String configFilePath) throws DataConversionException { + + assert configFilePath != null; + + File configFile = new File(configFilePath); + + if (!configFile.exists()) { + + logger.info("Config file " + configFile + " not found"); + + return Optional.empty(); + + } + + Config config; + + try { + + config = FileUtil.deserializeObjectFromJsonFile(configFile, Config.class); + + } catch (IOException e) { + + logger.warning("Error reading from config file " + configFile + ": " + e); + + throw new DataConversionException(e); + + } + + return Optional.of(config); + } + + /** + * Similar to {@link #saveConfigFile(Config)} + * @param configFilePath location of the data. Cannot be null. + */ + private void saveConfig(Config config, String configFilePath) throws IOException { + + assert config != null; + assert configFilePath != null; + assert !configFilePath.isEmpty(); + + FileUtil.serializeObjectToJsonFile(new File(configFilePath), config); + } + +} \ No newline at end of file diff --git a/src/main/java/seedu/savvytasker/storage/StorageManager.java b/src/main/java/seedu/savvytasker/storage/StorageManager.java index a9d463a690b4..5510e67eaef1 100644 --- a/src/main/java/seedu/savvytasker/storage/StorageManager.java +++ b/src/main/java/seedu/savvytasker/storage/StorageManager.java @@ -84,7 +84,7 @@ public void saveSavvyTasker(ReadOnlySavvyTasker savvyTasker, String filePath) th savvyTaskerStorage.saveSavvyTasker(savvyTasker, filePath); } - //@@author A0139915W + //@@author A0138431L @Override @Subscribe public void handleSavvyTaskerSaveLocationChangedEvent(DataSavingLocationChangedEvent dslce) { diff --git a/src/main/java/seedu/savvytasker/storage/XmlSerializableSavvyTasker.java b/src/main/java/seedu/savvytasker/storage/XmlSerializableSavvyTasker.java index da4e0a98cc93..0c9e71e69558 100644 --- a/src/main/java/seedu/savvytasker/storage/XmlSerializableSavvyTasker.java +++ b/src/main/java/seedu/savvytasker/storage/XmlSerializableSavvyTasker.java @@ -28,20 +28,19 @@ public class XmlSerializableSavvyTasker implements ReadOnlySavvyTasker { @XmlElement private List symbols; - { - tasks = new ArrayList<>(); - symbols = new ArrayList<>(); - } - /** * Empty constructor required for marshalling */ - public XmlSerializableSavvyTasker() {} + public XmlSerializableSavvyTasker() { + tasks = new ArrayList<>(); + symbols = new ArrayList<>(); + } /** * Conversion */ public XmlSerializableSavvyTasker(ReadOnlySavvyTasker src) { + this(); tasks.addAll(src.getReadOnlyListOfTasks().stream().map(XmlAdaptedTask::new).collect(Collectors.toList())); symbols.addAll(src.getReadOnlyListOfAliasSymbols().stream().map(XmlAdaptedAliasSymbol::new).collect(Collectors.toList())); } diff --git a/src/main/java/seedu/savvytasker/ui/AliasSymbolCard.java b/src/main/java/seedu/savvytasker/ui/AliasSymbolCard.java index 32d272f2be63..77ca5e554d54 100644 --- a/src/main/java/seedu/savvytasker/ui/AliasSymbolCard.java +++ b/src/main/java/seedu/savvytasker/ui/AliasSymbolCard.java @@ -22,10 +22,6 @@ public class AliasSymbolCard extends UiPart{ private AliasSymbol symbol; private int displayedIndex; - public AliasSymbolCard(){ - - } - public static AliasSymbolCard load(AliasSymbol symbol, int displayedIndex){ AliasSymbolCard card = new AliasSymbolCard(); card.symbol = symbol; diff --git a/src/main/java/seedu/savvytasker/ui/AliasSymbolListPanel.java b/src/main/java/seedu/savvytasker/ui/AliasSymbolListPanel.java index 001aa10b1c50..85f8949f1b1e 100644 --- a/src/main/java/seedu/savvytasker/ui/AliasSymbolListPanel.java +++ b/src/main/java/seedu/savvytasker/ui/AliasSymbolListPanel.java @@ -27,10 +27,6 @@ public class AliasSymbolListPanel extends UiPart { @FXML private ListView aliasSymbolListView; - public AliasSymbolListPanel() { - super(); - } - @Override public void setNode(Node node) { panel = (VBox) node; @@ -92,9 +88,6 @@ public void scrollTo(int index) { class AliasSymbolListViewCell extends ListCell { - public AliasSymbolListViewCell() { - } - @Override protected void updateItem(AliasSymbol symbol, boolean empty) { super.updateItem(symbol, empty); diff --git a/src/main/java/seedu/savvytasker/ui/CommandBox.java b/src/main/java/seedu/savvytasker/ui/CommandBox.java old mode 100644 new mode 100755 index 81d26932aee4..e2d5d3c086d3 --- a/src/main/java/seedu/savvytasker/ui/CommandBox.java +++ b/src/main/java/seedu/savvytasker/ui/CommandBox.java @@ -1,5 +1,8 @@ +//@@author A0138431L package seedu.savvytasker.ui; +import java.io.File; +import java.util.Stack; import java.util.logging.Logger; import com.google.common.eventbus.Subscribe; @@ -8,7 +11,12 @@ import javafx.scene.Node; import javafx.scene.control.SplitPane; import javafx.scene.control.TextField; +import javafx.scene.input.KeyCode; +import javafx.scene.input.KeyCodeCombination; +import javafx.scene.input.KeyCombination; +import javafx.scene.input.KeyEvent; import javafx.scene.layout.AnchorPane; +import javafx.stage.DirectoryChooser; import javafx.stage.Stage; import seedu.savvytasker.commons.core.LogsCenter; import seedu.savvytasker.commons.events.ui.IncorrectCommandAttemptedEvent; @@ -24,6 +32,10 @@ public class CommandBox extends UiPart { private AnchorPane commandPane; private ResultDisplay resultDisplay; String previousCommandTest; + + // stack to store commands history + private static Stack COMMAND_HISTORY_STACK = new Stack(); + private static Stack COMMAND_FUTURE_STACK = new Stack(); private Logic logic; @@ -72,7 +84,8 @@ public void setPlaceholder(AnchorPane pane) { private void handleCommandInputChanged() { //Take a copy of the command text previousCommandTest = commandTextField.getText(); - + + COMMAND_HISTORY_STACK.push(previousCommandTest); /* We assume the command is correct. If it is incorrect, the command box will be changed accordingly * in the event handling code {@link #handleIncorrectCommandAttempted} */ @@ -102,7 +115,7 @@ private void handleIncorrectCommandAttempted(IncorrectCommandAttemptedEvent even * Restores the command box text to the previously entered command */ private void restoreCommandText() { - commandTextField.setText(previousCommandTest); + commandTextField.setText(""); } /** @@ -112,4 +125,186 @@ private void setStyleToIndicateIncorrectCommand() { commandTextField.getStyleClass().add("error"); } + public Node getCommandTextField() { + return commandTextField; + } + + //==================== Keyboard Shortcuts Code ================================================================= + /** + * Key pressed handler for text box. + * + * @param keyEvent key event for the button that is being pressed. + */ + public void commandTextFieldOnKeyPressedHandler(KeyEvent keyEvent) { + + String userInput = commandTextField.getText().trim(); + + KeyCombination saveKey = new KeyCodeCombination(KeyCode.S, KeyCombination.META_DOWN); + KeyCombination undoKey = new KeyCodeCombination(KeyCode.Z, KeyCombination.META_DOWN); + KeyCombination redoKey = new KeyCodeCombination(KeyCode.Y, KeyCombination.META_DOWN); + KeyCombination helpKey = new KeyCodeCombination(KeyCode.H, KeyCombination.META_DOWN); + KeyCombination exitKey = new KeyCodeCombination(KeyCode.Q, KeyCombination.META_DOWN); + KeyCombination listKey = new KeyCodeCombination(KeyCode.L, KeyCombination.META_DOWN); + KeyCombination listArchivedKey = new KeyCodeCombination(KeyCode.A, KeyCombination.META_DOWN); + KeyCombination clearKey = new KeyCodeCombination(KeyCode.D, KeyCombination.META_DOWN); + + try { + + KeyCode keyCode = keyEvent.getCode(); + + if(saveKey.match(keyEvent)) { + + processSave(); + + }else if (keyCode == KeyCode.ESCAPE) { + + //close help dialog + //processEsc(); + + }else if (keyCode == KeyCode.UP) { + + processUp(userInput); + + } else if (keyCode == KeyCode.DOWN) { + + processDown(userInput); + + } else if (undoKey.match(keyEvent)) { + + executeCommand("undo"); + + } else if (redoKey.match(keyEvent)) { + + executeCommand("redo"); + + } else if (helpKey.match(keyEvent)) { + + executeCommand("help"); + + } else if (exitKey.match(keyEvent)) { + + executeCommand("exit"); + + } else if (listKey.match(keyEvent)) { + + executeCommand("list"); + + } else if (listArchivedKey.match(keyEvent)) { + + executeCommand("list t/Archived"); + + } else if (clearKey.match(keyEvent)) { + + executeCommand("clear"); + + } + + } catch (IllegalArgumentException e) { + + commandTextField.setText(""); + + COMMAND_HISTORY_STACK.add(userInput); + + this.logger.info("Illegal Argument has been entered."); + + } catch (Exception e) { + + e.printStackTrace(); + commandTextField.setText(""); + + this.logger.info("Illegal Argument has been entered."); + + } + + } + + /** + * Process the event that occurs after the user presses the ctrl-S button. + * + * @param userInput the command keyed in by the user. + */ + public void processSave() { + + //Execute the save command + DirectoryChooser directoryChooser = new DirectoryChooser(); + File selectedFile = directoryChooser.showDialog(primaryStage); + String filepath = selectedFile.getAbsolutePath(); + executeCommand("save " + filepath); + + } + + /** + * Process the event that occurs after the user presses the [ESC] button. + * + * @param userInput the command keyed in by the user. + + public void processEsc() { + + if (userInput.equals("") && isHelpViewVisible()) { + + hideHelpView(); + + } + + /** + * Process the event that occurs after the user presses the [UP] button. + * + * @param userInput the command keyed in by the user. + */ + public void processUp(String userInput) { + + if (!COMMAND_HISTORY_STACK.isEmpty()) { + + String previousCommand = COMMAND_HISTORY_STACK.pop(); + + if (!userInput.equals("")) { + + COMMAND_FUTURE_STACK.push(userInput); + + } + + commandTextField.setText(previousCommand); + + } + + commandTextField.positionCaret(commandTextField.getText().length()); + + } + + /** + * Process the event that occurs after the user presses the down button. + * + * @param userInput the command keyed in by the user. + */ + public void processDown(String userInput) { + + if (!COMMAND_FUTURE_STACK.isEmpty()) { + + String nextCommand = COMMAND_FUTURE_STACK.pop(); + + COMMAND_HISTORY_STACK.push(userInput); + commandTextField.setText(nextCommand); + + } else if (!userInput.equals("")) { + + COMMAND_HISTORY_STACK.push(userInput); + commandTextField.setText(""); + + } + + commandTextField.positionCaret(commandTextField.getText().length()); + + } + + /** + * Execute commands + * + * @param command to be executed + */ + public void executeCommand(String commandInput) { + CommandResult commandResult = logic.execute(commandInput); + resultDisplay.postMessage(commandResult.feedbackToUser); + logger.info("Result: " + commandResult.feedbackToUser); + } } + diff --git a/src/main/java/seedu/savvytasker/ui/DailyPanel.java b/src/main/java/seedu/savvytasker/ui/DailyPanel.java new file mode 100644 index 000000000000..d94c16d0f800 --- /dev/null +++ b/src/main/java/seedu/savvytasker/ui/DailyPanel.java @@ -0,0 +1,158 @@ +package seedu.savvytasker.ui; + +import java.text.SimpleDateFormat; +import java.util.Date; +import java.util.logging.Logger; + +import javafx.application.Platform; +import javafx.collections.ObservableList; +import javafx.fxml.FXML; +import javafx.scene.Node; +import javafx.scene.control.Label; +import javafx.scene.control.ListCell; +import javafx.scene.control.ListView; +import javafx.scene.control.SplitPane; +import javafx.scene.layout.AnchorPane; +import javafx.scene.layout.VBox; +import javafx.stage.Stage; +import seedu.savvytasker.commons.core.LogsCenter; +import seedu.savvytasker.commons.events.ui.TaskPanelSelectionChangedEvent; +import seedu.savvytasker.model.task.ReadOnlyTask; + +//@@author A0138431L + +/** + * Panel containing the list overdue task. + * @author A0138431L + * + */ +public class DailyPanel extends UiPart { + + private static String TODAY_TITLE = "Today"; + private static String TOMORROW_TITLE = "Tomorrow"; + private static String DAY_PATTERN = "EEEE"; + private static String DATE_PATTERN = "dd MMM yy"; + private static String DAY_DATE_FORMAT = "%1$s, %2$s"; + + private final Logger logger = LogsCenter.getLogger(TaskListPanel.class); + private static final String FXML = "DailyList.fxml"; + private VBox panel; + private AnchorPane placeHolderPane; + + @FXML + private Label dayHeader; + + @FXML + private ListView taskListView; + + public DailyPanel() { + super(); + } + + @Override + public void setNode(Node node) { + panel = (VBox) node; + } + + @Override + public String getFxmlPath() { + return FXML; + } + + @Override + public void setPlaceholder(AnchorPane pane) { + this.placeHolderPane = pane; + } + + public static DailyPanel load(Stage primaryStage, AnchorPane DailyListPlaceholder, + ObservableList taskList, int dayOfTheWeek, Date date) { + DailyPanel dailyPanel = + UiPartLoader.loadUiPart(primaryStage, DailyListPlaceholder, new DailyPanel()); + dailyPanel.configure(taskList, dayOfTheWeek, date); + return dailyPanel; + } + + private void configure(ObservableList taskList, int dayOfTheWeek, Date date) { + + String dateHeader = generateHeader(dayOfTheWeek, date); + setConnections(taskList, dateHeader); + addToPlaceholder(); + } + + private void setConnections(ObservableList taskList, String dateHeader) { + dayHeader.setText(dateHeader); + taskListView.setItems(taskList); + taskListView.setCellFactory(listView -> new TaskListViewCell()); + setEventHandlerForSelectionChangeEvent(); + } + + private void addToPlaceholder() { + SplitPane.setResizableWithParent(placeHolderPane, false); + placeHolderPane.getChildren().add(panel); + } + + private void setEventHandlerForSelectionChangeEvent() { + taskListView.getSelectionModel().selectedItemProperty().addListener((observable, oldValue, newValue) -> { + if (newValue != null) { + logger.fine("Selection in daily task list panel changed to : '" + newValue + "'"); + raise(new TaskPanelSelectionChangedEvent(newValue)); + } + }); + } + + public void scrollTo(int index) { + Platform.runLater(() -> { + taskListView.scrollTo(index); + taskListView.getSelectionModel().clearAndSelect(index); + }); + } + + private String generateHeader(int dayOfTheWeek, Date date) { + + SimpleDateFormat dayFormatter = new SimpleDateFormat(DAY_PATTERN); + SimpleDateFormat dateFormatter = new SimpleDateFormat(DATE_PATTERN); + + String day; + + switch (dayOfTheWeek) { + + case 0: + + day = TODAY_TITLE; + break; + + case 1: + + day = TOMORROW_TITLE; + break; + + default: + + day = dayFormatter.format(date); + break; + + } + String header = String.format(DAY_DATE_FORMAT, day, dateFormatter.format(date)); + + return header; + } + + class TaskListViewCell extends ListCell { + + public TaskListViewCell() { + } + + @Override + protected void updateItem(ReadOnlyTask task, boolean empty) { + super.updateItem(task, empty); + + if (empty || task == null) { + setGraphic(null); + setText(null); + } else { + setGraphic(TaskCard.load(task, getIndex() + 1).getLayout()); + } + } + } + +} diff --git a/src/main/java/seedu/savvytasker/ui/FloatingPanel.java b/src/main/java/seedu/savvytasker/ui/FloatingPanel.java new file mode 100644 index 000000000000..dd32e6abe677 --- /dev/null +++ b/src/main/java/seedu/savvytasker/ui/FloatingPanel.java @@ -0,0 +1,112 @@ +package seedu.savvytasker.ui; + +import java.util.logging.Logger; + +import javafx.application.Platform; +import javafx.collections.ObservableList; +import javafx.fxml.FXML; +import javafx.scene.Node; +import javafx.scene.control.ListCell; +import javafx.scene.control.ListView; +import javafx.scene.control.SplitPane; +import javafx.scene.layout.AnchorPane; +import javafx.scene.layout.VBox; +import javafx.stage.Stage; +import seedu.savvytasker.commons.core.LogsCenter; +import seedu.savvytasker.commons.events.ui.TaskPanelSelectionChangedEvent; +import seedu.savvytasker.model.task.ReadOnlyTask; + +//@@author A0138431L + +/** + * Panel containing the list floating task. + * @author A0138431L + * + */ +public class FloatingPanel extends UiPart { + private final Logger logger = LogsCenter.getLogger(TaskListPanel.class); + private static final String FXML = "FloatingList.fxml"; + private VBox panel; + private AnchorPane placeHolderPane; + + @FXML + private ListView taskListView; + + public FloatingPanel() { + super(); + } + + @Override + public void setNode(Node node) { + panel = (VBox) node; + } + + @Override + public String getFxmlPath() { + return FXML; + } + + @Override + public void setPlaceholder(AnchorPane pane) { + this.placeHolderPane = pane; + } + + public static FloatingPanel load(Stage primaryStage, AnchorPane floatingListPlaceholder, + ObservableList taskList) { + FloatingPanel floatingPanel = + UiPartLoader.loadUiPart(primaryStage, floatingListPlaceholder, new FloatingPanel()); + floatingPanel.configure(taskList); + return floatingPanel; + } + + private void configure(ObservableList taskList) { + setConnections(taskList); + addToPlaceholder(); + } + + private void setConnections(ObservableList taskList) { + taskListView.setItems(taskList); + taskListView.setCellFactory(listView -> new TaskListViewCell()); + setEventHandlerForSelectionChangeEvent(); + } + + private void addToPlaceholder() { + SplitPane.setResizableWithParent(placeHolderPane, false); + placeHolderPane.getChildren().add(panel); + } + + private void setEventHandlerForSelectionChangeEvent() { + taskListView.getSelectionModel().selectedItemProperty().addListener((observable, oldValue, newValue) -> { + if (newValue != null) { + logger.fine("Selection in floating task list panel changed to : '" + newValue + "'"); + raise(new TaskPanelSelectionChangedEvent(newValue)); + } + }); + } + + public void scrollTo(int index) { + Platform.runLater(() -> { + taskListView.scrollTo(index); + taskListView.getSelectionModel().clearAndSelect(index); + }); + } + + class TaskListViewCell extends ListCell { + + public TaskListViewCell() { + } + + @Override + protected void updateItem(ReadOnlyTask task, boolean empty) { + super.updateItem(task, empty); + + if (empty || task == null) { + setGraphic(null); + setText(null); + } else { + setGraphic(TaskCard.load(task, getIndex() + 1).getLayout()); + } + } + } + +} diff --git a/src/main/java/seedu/savvytasker/ui/HelpWindow.java b/src/main/java/seedu/savvytasker/ui/HelpWindow.java old mode 100644 new mode 100755 index 63df34b43afa..f98e4d5b0357 --- a/src/main/java/seedu/savvytasker/ui/HelpWindow.java +++ b/src/main/java/seedu/savvytasker/ui/HelpWindow.java @@ -59,4 +59,10 @@ private void configure(){ public void show() { dialogStage.showAndWait(); } + + public void hide() { + + dialogStage.hide(); + + } } diff --git a/src/main/java/seedu/savvytasker/ui/MainWindow.java b/src/main/java/seedu/savvytasker/ui/MainWindow.java old mode 100644 new mode 100755 index 1974651a4ecc..c1eb8c6a6c5f --- a/src/main/java/seedu/savvytasker/ui/MainWindow.java +++ b/src/main/java/seedu/savvytasker/ui/MainWindow.java @@ -1,5 +1,13 @@ +//@@author A0138431L + package seedu.savvytasker.ui; +import java.util.ArrayList; +import java.util.Calendar; +import java.util.Date; + +import com.google.common.eventbus.Subscribe; + import javafx.fxml.FXML; import javafx.scene.Node; import javafx.scene.Scene; @@ -8,8 +16,11 @@ import javafx.scene.layout.AnchorPane; import javafx.scene.layout.VBox; import javafx.stage.Stage; + import seedu.savvytasker.commons.core.Config; import seedu.savvytasker.commons.core.GuiSettings; +import seedu.savvytasker.commons.core.LogsCenter; +import seedu.savvytasker.commons.events.model.SavvyTaskerChangedEvent; import seedu.savvytasker.commons.events.ui.ExitAppRequestEvent; import seedu.savvytasker.logic.Logic; import seedu.savvytasker.model.UserPrefs; @@ -17,41 +28,63 @@ /** * The Main Window. Provides the basic application layout containing - * a menu bar and space where other JavaFX elements can be placed. + * a sorting and filtered list that display the result of the user command + * on the left and a week's view of the task + * + * The week's view contains 4 lists, namely the floating list, overdue list, + * days of the week list and upcoming list + * + * Floating list contains task without start and end dateTime + * Overdue list contains task with end date before current date + * Days of the week list contains task that falls on the respective day of the selected week + * Upcoming list contains task with start date after the last day of selected week + * + * @author A0138431L + * */ public class MainWindow extends UiPart { - private static final String ICON = "/images/address_book_32.png"; - private static final String FXML = "MainWindow.fxml"; - public static final int MIN_HEIGHT = 600; - public static final int MIN_WIDTH = 450; + private static final String ICON = "/images/address_book_32.png"; + private static final String FXML = "MainWindow.fxml"; + public static final int MIN_HEIGHT = 700; + public static final int MIN_WIDTH = 1150; - private Logic logic; + private Logic logic; + Date date = new Date(); + private static int DAYS_OF_WEEK = 7; - // Independent Ui parts residing in this Ui container - private BrowserPanel browserPanel; - private TaskListPanel taskListPanel; + // Independent Ui parts residing in this Ui container + //private BrowserPanel browserPanel; + private TaskListPanel taskListPanel; private AliasSymbolListPanel aliasSymbolListPanel; - private ResultDisplay resultDisplay; - private StatusBarFooter statusBarFooter; - private CommandBox commandBox; - private Config config; - private UserPrefs userPrefs; - - // Handles to elements of this Ui container - private VBox rootLayout; - private Scene scene; - - private String addressBookName; - - @FXML - private AnchorPane browserPlaceholder; - - @FXML - private AnchorPane commandBoxPlaceholder; - - @FXML - private MenuItem helpMenuItem; + private ResultDisplay resultDisplay; + private StatusBarFooter statusBarFooter; + private CommandBox commandBox; + private Config config; + private UserPrefs userPrefs; + @FXML + private FloatingPanel floatingPanel; + @FXML + private OverduePanel overduePanel; + @FXML + private DailyPanel dailyPanel; + @FXML + private UpcomingPanel upcomingPanel; + + // Handles to elements of this Ui container + private VBox rootLayout; + private Scene scene; + + private String addressBookName; + + @FXML + private AnchorPane browserPlaceholder; + + @FXML + private AnchorPane commandBoxPlaceholder; + + @FXML + private MenuItem helpMenuItem; @FXML private AnchorPane taskListPanelPlaceholder; @@ -59,72 +92,108 @@ public class MainWindow extends UiPart { @FXML private AnchorPane aliasSymbolListPanelPlaceholder; - @FXML - private AnchorPane resultDisplayPlaceholder; + @FXML + private AnchorPane resultDisplayPlaceholder; + + @FXML + private AnchorPane statusbarPlaceholder; - @FXML - private AnchorPane statusbarPlaceholder; - @FXML private VBox listPanel; - public MainWindow() { - super(); - } - - @Override - public void setNode(Node node) { - rootLayout = (VBox) node; - } - - @Override - public String getFxmlPath() { - return FXML; - } - - public static MainWindow load(Stage primaryStage, Config config, UserPrefs prefs, Logic logic) { - - MainWindow mainWindow = UiPartLoader.loadUiPart(primaryStage, new MainWindow()); - mainWindow.configure(config.getAppTitle(), config.getSavvyTaskerListName(), config, prefs, logic); - return mainWindow; - } - - private void configure(String appTitle, String addressBookName, Config config, UserPrefs prefs, - Logic logic) { - - //Set dependencies - this.logic = logic; - this.addressBookName = addressBookName; - this.config = config; - this.userPrefs = prefs; - - //Configure the UI - setTitle(appTitle); - setIcon(ICON); - setWindowMinSize(); - setWindowDefaultSize(prefs); - scene = new Scene(rootLayout); - primaryStage.setScene(scene); - - setAccelerators(); - } - - private void setAccelerators() { - helpMenuItem.setAccelerator(KeyCombination.valueOf("F1")); - } - - void fillInnerParts() { - browserPanel = BrowserPanel.load(browserPlaceholder); + @FXML + private AnchorPane floatingPanelPlaceholder; + + @FXML + private AnchorPane overduePanelPlaceholder; + + @FXML + private AnchorPane day1PanelPlaceholder; + @FXML + private AnchorPane day2PanelPlaceholder; + @FXML + private AnchorPane day3PanelPlaceholder; + @FXML + private AnchorPane day4PanelPlaceholder; + @FXML + private AnchorPane day5PanelPlaceholder; + @FXML + private AnchorPane day6PanelPlaceholder; + @FXML + private AnchorPane day7PanelPlaceholder; + + @FXML + private AnchorPane upcomingPanelPlaceholder; + + public MainWindow() { + super(); + } + + @Override + public void setNode(Node node) { + rootLayout = (VBox) node; + } + + @Override + public String getFxmlPath() { + return FXML; + } + + public static MainWindow load(Stage primaryStage, Config config, UserPrefs prefs, Logic logic) { + + MainWindow mainWindow = UiPartLoader.loadUiPart(primaryStage, new MainWindow()); + mainWindow.configure(config.getAppTitle(), config.getSavvyTaskerListName(), config, prefs, logic); + return mainWindow; + } + + private void configure(String appTitle, String addressBookName, Config config, UserPrefs prefs, + Logic logic) { + + //Set dependencies + this.logic = logic; + this.addressBookName = addressBookName; + this.config = config; + this.userPrefs = prefs; + registerAsAnEventHandler(this); + + //Configure the UI + setTitle(appTitle); + setIcon(ICON); + setWindowMinSize(); + setWindowDefaultSize(prefs); + scene = new Scene(rootLayout); + primaryStage.setScene(scene); + + } + + void fillInnerParts() { + //browserPanel = BrowserPanel.load(browserPlaceholder); taskListPanel = TaskListPanel.load(primaryStage, getTaskListPlaceholder(), logic.getFilteredTaskList()); aliasSymbolListPanel = AliasSymbolListPanel.load(primaryStage, getAliasSymbolPlaceholder(), logic.getAliasSymbolList()); setDefaultView(); - resultDisplay = ResultDisplay.load(primaryStage, getResultDisplayPlaceholder()); - statusBarFooter = StatusBarFooter.load(primaryStage, getStatusbarPlaceholder(), config.getSavvyTaskerFilePath()); - commandBox = CommandBox.load(primaryStage, getCommandBoxPlaceholder(), resultDisplay, logic); - } - - /** + + resultDisplay = ResultDisplay.load(primaryStage, getResultDisplayPlaceholder()); + statusBarFooter = StatusBarFooter.load(primaryStage, getStatusbarPlaceholder(), config.getSavvyTaskerFilePath()); + commandBox = CommandBox.load(primaryStage, getCommandBoxPlaceholder(), resultDisplay, logic); + commandBox.getCommandTextField().requestFocus(); + floatingPanel = FloatingPanel.load(primaryStage, getFloatingPanelPlaceholder(), logic.getFilteredFloatingTasks()); + overduePanel = OverduePanel.load(primaryStage, getOverduePanelPlaceholder(), logic.getFilteredOverdueTasks()); + loadDailyPanel(); + upcomingPanel = UpcomingPanel.load(primaryStage, getUpcomingPanelPlaceholder(), logic.getFilteredUpcomingTasks(date)); + } + + private void loadDailyPanel() { + for (int i = 0; i < DAYS_OF_WEEK; i++) { + Date onDate = new Date(); + onDate.setTime(date.getTime()); + onDate = addDay(i, onDate); + dailyPanel = DailyPanel.load(primaryStage, getDailyPanelPlaceholder(i), + logic.getFilteredDailyTasks(i, onDate), i, onDate); + } + } + + /** * Removes all the children in the taskPanel VBox * Shows the default list, which is the list of tasks */ @@ -152,17 +221,17 @@ private VBox getListPanel() { return listPanel; } - private AnchorPane getCommandBoxPlaceholder() { - return commandBoxPlaceholder; - } + private AnchorPane getCommandBoxPlaceholder() { + return commandBoxPlaceholder; + } - private AnchorPane getStatusbarPlaceholder() { - return statusbarPlaceholder; - } + private AnchorPane getStatusbarPlaceholder() { + return statusbarPlaceholder; + } - private AnchorPane getResultDisplayPlaceholder() { - return resultDisplayPlaceholder; - } + private AnchorPane getResultDisplayPlaceholder() { + return resultDisplayPlaceholder; + } public AnchorPane getTaskListPlaceholder() { return taskListPanelPlaceholder; @@ -172,6 +241,71 @@ public AnchorPane getAliasSymbolPlaceholder() { return aliasSymbolListPanelPlaceholder; } + private AnchorPane getFloatingPanelPlaceholder() { + return floatingPanelPlaceholder; + } + + private AnchorPane getOverduePanelPlaceholder() { + return overduePanelPlaceholder; + } + + private AnchorPane getDailyPanelPlaceholder(int index) { + + switch(index) { + + case 0: + + return day1PanelPlaceholder; + + case 1: + + return day2PanelPlaceholder; + + case 2: + + return day3PanelPlaceholder; + + case 3: + + return day4PanelPlaceholder; + + case 4: + + return day5PanelPlaceholder; + + case 5: + + return day6PanelPlaceholder; + + case 6: + + return day7PanelPlaceholder; + + default: + + return day1PanelPlaceholder; + } + + } + + private AnchorPane getUpcomingPanelPlaceholder() { + return upcomingPanelPlaceholder; + } + + private Date addDay(int i, Date date) { + + //convert date object to calendar object and add 1 days + Calendar calendarExpectedDate = Calendar.getInstance(); + calendarExpectedDate.setTime(date); + + calendarExpectedDate.add(Calendar.DATE, i); + + //convert calendar object back to date object + date = calendarExpectedDate.getTime(); + + return date; + } + public void hide() { primaryStage.hide(); } @@ -180,10 +314,10 @@ private void setTitle(String appTitle) { primaryStage.setTitle(appTitle); } - /** - * Sets the default size based on user preferences. - */ - protected void setWindowDefaultSize(UserPrefs prefs) { + /** + * Sets the default size based on user preferences. + */ + protected void setWindowDefaultSize(UserPrefs prefs) { primaryStage.setHeight(prefs.getGuiSettings().getWindowHeight()); primaryStage.setWidth(prefs.getGuiSettings().getWindowWidth()); if (prefs.getGuiSettings().getWindowCoordinates() != null) { @@ -198,11 +332,11 @@ private void setWindowMinSize() { } /** - * Returns the current size and the position of the main Window. - */ + * Returns the current size and the position of the main Window. + */ public GuiSettings getCurrentGuiSetting() { return new GuiSettings(primaryStage.getWidth(), primaryStage.getHeight(), - (int) primaryStage.getX(), (int) primaryStage.getY()); + (int) primaryStage.getX(), (int) primaryStage.getY()); } @FXML @@ -210,14 +344,19 @@ public void handleHelp() { HelpWindow helpWindow = HelpWindow.load(primaryStage); helpWindow.show(); } + + public void hideHelp() { + HelpWindow helpWindow = HelpWindow.load(primaryStage); + helpWindow.hide(); + } - public void show() { - primaryStage.show(); + public void show() { + primaryStage.show(); } /** - * Closes the application. - */ + * Closes the application. + */ @FXML private void handleExit() { raise(new ExitAppRequestEvent()); @@ -231,11 +370,18 @@ public TaskListPanel getTaskListPanel() { return this.taskListPanel; } - public void loadPersonPage(ReadOnlyTask task) { - browserPanel.loadPersonPage(task); + + public void loadPersonPage(ReadOnlyTask task) { + //browserPanel.loadPersonPage(task); + } + + public void releaseResources() { + //browserPanel.freeResources(); } - public void releaseResources() { - browserPanel.freeResources(); + @Subscribe + public void handleSavvyTaskerChangedEvent(SavvyTaskerChangedEvent stce) { + loadDailyPanel(); } -} + +} \ No newline at end of file diff --git a/src/main/java/seedu/savvytasker/ui/OverduePanel.java b/src/main/java/seedu/savvytasker/ui/OverduePanel.java new file mode 100644 index 000000000000..b4eba1935b7d --- /dev/null +++ b/src/main/java/seedu/savvytasker/ui/OverduePanel.java @@ -0,0 +1,112 @@ +package seedu.savvytasker.ui; + +import java.util.logging.Logger; + +import javafx.application.Platform; +import javafx.collections.ObservableList; +import javafx.fxml.FXML; +import javafx.scene.Node; +import javafx.scene.control.ListCell; +import javafx.scene.control.ListView; +import javafx.scene.control.SplitPane; +import javafx.scene.layout.AnchorPane; +import javafx.scene.layout.VBox; +import javafx.stage.Stage; +import seedu.savvytasker.commons.core.LogsCenter; +import seedu.savvytasker.commons.events.ui.TaskPanelSelectionChangedEvent; +import seedu.savvytasker.model.task.ReadOnlyTask; + +//@@author A0138431L + +/** +* Panel containing the list overdue task. +* @author A0138431L +* +*/ +public class OverduePanel extends UiPart { + private final Logger logger = LogsCenter.getLogger(TaskListPanel.class); + private static final String FXML = "OverdueList.fxml"; + private VBox panel; + private AnchorPane placeHolderPane; + + @FXML + private ListView taskListView; + + public OverduePanel() { + super(); + } + + @Override + public void setNode(Node node) { + panel = (VBox) node; + } + + @Override + public String getFxmlPath() { + return FXML; + } + + @Override + public void setPlaceholder(AnchorPane pane) { + this.placeHolderPane = pane; + } + + public static OverduePanel load(Stage primaryStage, AnchorPane overdueListPlaceholder, + ObservableList taskList) { + OverduePanel oveduePanel = + UiPartLoader.loadUiPart(primaryStage, overdueListPlaceholder, new OverduePanel()); + oveduePanel.configure(taskList); + return oveduePanel; + } + + private void configure(ObservableList taskList) { + setConnections(taskList); + addToPlaceholder(); + } + + private void setConnections(ObservableList taskList) { + taskListView.setItems(taskList); + taskListView.setCellFactory(listView -> new TaskListViewCell()); + setEventHandlerForSelectionChangeEvent(); + } + + private void addToPlaceholder() { + SplitPane.setResizableWithParent(placeHolderPane, false); + placeHolderPane.getChildren().add(panel); + } + + private void setEventHandlerForSelectionChangeEvent() { + taskListView.getSelectionModel().selectedItemProperty().addListener((observable, oldValue, newValue) -> { + if (newValue != null) { + logger.fine("Selection in overdue task list panel changed to : '" + newValue + "'"); + raise(new TaskPanelSelectionChangedEvent(newValue)); + } + }); + } + + public void scrollTo(int index) { + Platform.runLater(() -> { + taskListView.scrollTo(index); + taskListView.getSelectionModel().clearAndSelect(index); + }); + } + + class TaskListViewCell extends ListCell { + + public TaskListViewCell() { + } + + @Override + protected void updateItem(ReadOnlyTask task, boolean empty) { + super.updateItem(task, empty); + + if (empty || task == null) { + setGraphic(null); + setText(null); + } else { + setGraphic(TaskCard.load(task, getIndex() + 1).getLayout()); + } + } + } + +} diff --git a/src/main/java/seedu/savvytasker/ui/ResultDisplay.java b/src/main/java/seedu/savvytasker/ui/ResultDisplay.java index 8f7dce90e194..ca5b0396047b 100644 --- a/src/main/java/seedu/savvytasker/ui/ResultDisplay.java +++ b/src/main/java/seedu/savvytasker/ui/ResultDisplay.java @@ -37,6 +37,7 @@ public void configure() { resultDisplayArea.getStyleClass().add(STATUS_BAR_STYLE_SHEET); resultDisplayArea.setText(""); resultDisplayArea.textProperty().bind(displayed); + resultDisplayArea.setStyle("-fx-text-fill: white;"); FxViewUtil.applyAnchorBoundaryParameters(resultDisplayArea, 0.0, 0.0, 0.0, 0.0); mainPane.getChildren().add(resultDisplayArea); FxViewUtil.applyAnchorBoundaryParameters(mainPane, 0.0, 0.0, 0.0, 0.0); diff --git a/src/main/java/seedu/savvytasker/ui/StatusBarFooter.java b/src/main/java/seedu/savvytasker/ui/StatusBarFooter.java index 482171f30520..0b1df76eea51 100644 --- a/src/main/java/seedu/savvytasker/ui/StatusBarFooter.java +++ b/src/main/java/seedu/savvytasker/ui/StatusBarFooter.java @@ -92,7 +92,7 @@ public String getFxmlPath() { return FXML; } - //@@author A0139915W + //@@author A0138431L @Subscribe public void handleSavvyTaskerSaveLocationChangedEvent(DataSavingLocationChangedEvent dslce) { setSaveLocation(dslce.newPath); diff --git a/src/main/java/seedu/savvytasker/ui/TaskCard.java b/src/main/java/seedu/savvytasker/ui/TaskCard.java index 5d3512c8b5de..d978f9229316 100644 --- a/src/main/java/seedu/savvytasker/ui/TaskCard.java +++ b/src/main/java/seedu/savvytasker/ui/TaskCard.java @@ -9,6 +9,10 @@ public class TaskCard extends UiPart{ private static final String FXML = "TaskListCard.fxml"; + + public static final String LOW_PRIORITY_BACKGROUND = "-fx-background-color:#CEFFDC"; + public static final String MEDIUM_PRIORITY_BACKGROUND = "-fx-background-color:#FFFED8"; + public static final String HIGH_PRIORITY_BACKGROUND = "-fx-background-color:#FF8180"; @FXML private HBox cardPane; @@ -22,10 +26,6 @@ public class TaskCard extends UiPart{ private ReadOnlyTask task; private int displayedIndex; - public TaskCard(){ - - } - public static TaskCard load(ReadOnlyTask task, int displayedIndex){ TaskCard card = new TaskCard(); card.task = task; @@ -38,12 +38,32 @@ public void initialize() { taskName.setText(task.getTaskName()); id.setText(displayedIndex + ". "); details.setText(task.getTextForUi()); + setCardBackground(); } public HBox getLayout() { return cardPane; } - + + private void setCardBackground() { + + if (task.getPriority().toString().equals("High")) { + + cardPane.setStyle(HIGH_PRIORITY_BACKGROUND); + + } else if (task.getPriority().toString().equals("Medium")) { + + cardPane.setStyle(MEDIUM_PRIORITY_BACKGROUND); + + } else if (task.getPriority().toString().equals("Low")) { + + cardPane.setStyle(LOW_PRIORITY_BACKGROUND); + + } + + } + + @Override public void setNode(Node node) { cardPane = (HBox)node; diff --git a/src/main/java/seedu/savvytasker/ui/TaskListPanel.java b/src/main/java/seedu/savvytasker/ui/TaskListPanel.java index f90ea46f78fd..56b053ec13b1 100644 --- a/src/main/java/seedu/savvytasker/ui/TaskListPanel.java +++ b/src/main/java/seedu/savvytasker/ui/TaskListPanel.java @@ -28,10 +28,6 @@ public class TaskListPanel extends UiPart { @FXML private ListView taskListView; - public TaskListPanel() { - super(); - } - @Override public void setNode(Node node) { panel = (VBox) node; @@ -93,9 +89,6 @@ public void scrollTo(int index) { class TaskListViewCell extends ListCell { - public TaskListViewCell() { - } - @Override protected void updateItem(ReadOnlyTask task, boolean empty) { super.updateItem(task, empty); diff --git a/src/main/java/seedu/savvytasker/ui/UpcomingPanel.java b/src/main/java/seedu/savvytasker/ui/UpcomingPanel.java new file mode 100644 index 000000000000..6c374a4410d7 --- /dev/null +++ b/src/main/java/seedu/savvytasker/ui/UpcomingPanel.java @@ -0,0 +1,112 @@ +package seedu.savvytasker.ui; + +import java.util.logging.Logger; + +import javafx.application.Platform; +import javafx.collections.ObservableList; +import javafx.fxml.FXML; +import javafx.scene.Node; +import javafx.scene.control.ListCell; +import javafx.scene.control.ListView; +import javafx.scene.control.SplitPane; +import javafx.scene.layout.AnchorPane; +import javafx.scene.layout.VBox; +import javafx.stage.Stage; +import seedu.savvytasker.commons.core.LogsCenter; +import seedu.savvytasker.commons.events.ui.TaskPanelSelectionChangedEvent; +import seedu.savvytasker.model.task.ReadOnlyTask; + +//@@author A0138431L + +/** +* Panel containing the list overdue task. +* @author A0138431L +* +*/ +public class UpcomingPanel extends UiPart { + private final Logger logger = LogsCenter.getLogger(TaskListPanel.class); + private static final String FXML = "UpcomingList.fxml"; + private VBox panel; + private AnchorPane placeHolderPane; + + @FXML + private ListView taskListView; + + public UpcomingPanel() { + super(); + } + + @Override + public void setNode(Node node) { + panel = (VBox) node; + } + + @Override + public String getFxmlPath() { + return FXML; + } + + @Override + public void setPlaceholder(AnchorPane pane) { + this.placeHolderPane = pane; + } + + public static UpcomingPanel load(Stage primaryStage, AnchorPane UpcomingListPlaceholder, + ObservableList taskList) { + UpcomingPanel upcomingPanel = + UiPartLoader.loadUiPart(primaryStage, UpcomingListPlaceholder, new UpcomingPanel()); + upcomingPanel.configure(taskList); + return upcomingPanel; + } + + private void configure(ObservableList taskList) { + setConnections(taskList); + addToPlaceholder(); + } + + private void setConnections(ObservableList taskList) { + taskListView.setItems(taskList); + taskListView.setCellFactory(listView -> new TaskListViewCell()); + setEventHandlerForSelectionChangeEvent(); + } + + private void addToPlaceholder() { + SplitPane.setResizableWithParent(placeHolderPane, false); + placeHolderPane.getChildren().add(panel); + } + + private void setEventHandlerForSelectionChangeEvent() { + taskListView.getSelectionModel().selectedItemProperty().addListener((observable, oldValue, newValue) -> { + if (newValue != null) { + logger.fine("Selection in upcoming task list panel changed to : '" + newValue + "'"); + raise(new TaskPanelSelectionChangedEvent(newValue)); + } + }); + } + + public void scrollTo(int index) { + Platform.runLater(() -> { + taskListView.scrollTo(index); + taskListView.getSelectionModel().clearAndSelect(index); + }); + } + + class TaskListViewCell extends ListCell { + + public TaskListViewCell() { + } + + @Override + protected void updateItem(ReadOnlyTask task, boolean empty) { + super.updateItem(task, empty); + + if (empty || task == null) { + setGraphic(null); + setText(null); + } else { + setGraphic(TaskCard.load(task, getIndex() + 1).getLayout()); + } + } + } + +} diff --git a/src/main/resources/view/CommandBox.fxml b/src/main/resources/view/CommandBox.fxml index d2267909fd5c..1b27d75c643b 100644 --- a/src/main/resources/view/CommandBox.fxml +++ b/src/main/resources/view/CommandBox.fxml @@ -1,9 +1,8 @@ - - - - + + + + diff --git a/src/main/resources/view/DailyList.fxml b/src/main/resources/view/DailyList.fxml new file mode 100644 index 000000000000..0ad3c5149b13 --- /dev/null +++ b/src/main/resources/view/DailyList.fxml @@ -0,0 +1,18 @@ + + + + + + + + + + + + + + + + diff --git a/src/main/resources/view/DarkTheme.css b/src/main/resources/view/DarkTheme.css old mode 100644 new mode 100755 index 8043b344253a..1efb0b72e305 --- a/src/main/resources/view/DarkTheme.css +++ b/src/main/resources/view/DarkTheme.css @@ -122,7 +122,11 @@ } .result-display { - -fx-background-color: #ffffff; + -fx-background-color: transparent; +} + +.result-display .content { + -fx-background-color: #383838; } .result-display .label { @@ -285,4 +289,187 @@ #filterField, #personListPanel, #personWebpage { -fx-effect: innershadow(gaussian, black, 10, 0, 0, 0); +} + +#taskListView { + -fx-background-color: transparent; +} +/*------------------------------------------ OverduePanel Styling ------------------------------------------*/ + +.overdue-scrollpane, .overdue-panel { + -fx-background-color:#DCFFFD; +} + +.overdue-scrollpane > .scroll-bar:horizontal .thumb, +.overdue-scrollpane > .scroll-bar:vertical .thumb { + -fx-background-color:#99534D; +} + +.overdue-panel .title, .overdue-panel .taskname { + -fx-text-fill:#000000; +} + +.overdue-panel .subtitle, .overdue-panel .timestamp { + -fx-text-fill:#B26059; +} + +/*------------------------------------------ FloatingPanel Styling ------------------------------------------*/ + +.floating-scrollpane, .floating-panel { + -fx-background-color:#ACEDFF; +} + +.floating-scrollpane { + -fx-border-radius: 15px; +} + +.floating-scrollpane > .scroll-bar:horizontal .thumb, +.floating-scrollpane > .scroll-bar:vertical .thumb { + -fx-background-color:#406C7F; +} + +.floating-panel .title, .floating-panel .taskname { + -fx-text-fill:#000000; +} + +.floating-panel .subtitle, .floating-panel .timestamp { + -fx-text-fill:#5997BS2; +} + +/*------------------------------------------ DailyPanel Styling ------------------------------------------*/ + +.daily-scrollpane, .daily-panel { + -fx-background-color:#99D3FF; +} + +.daily-scrollpane > .scroll-bar:horizontal .thumb, +.daily-scrollpane > .scroll-bar:vertical .thumb { + -fx-background-color:#7E7E45; +} + +.daily-panel .title, .daily-panel .taskname { + -fx-text-fill:#5D5D33; +} + +.daily-panel .subtitle, .daily-panel .timestamp { + -fx-text-fill:#B2B262; +} + +/*------------------------------------------ UpcomingPanel Styling ------------------------------------------*/ +.upcoming-scrollpane, .upcoming-panel { + -fx-background-color:#D1E0FF; +} + +.upcoming-scrollpane > .scroll-bar:horizontal .thumb, +.upcoming-scrollpane > .scroll-bar:vertical .thumb { + -fx-background-color:#657E47; +} + +.upcoming-panel .check-box > .box { + -fx-border-color:#657E47; +} + +.upcoming-panel .check-box { + -fx-font-family:'Helvetica'; + -fx-text-fill:#485A33; + -fx-font-size:10; + -fx-font-weight:bold; +} + +.upcoming-panel .title, .upcoming-panel .taskname { + -fx-text-fill:#485A33; +} + +.upcoming-panel .subtitle, .upcoming-panel .timestamp { + -fx-text-fill:#8EB264; +} + +/*------------------------------------------ ArchivedPanel Styling ------------------------------------------*/ + +.archived-panel .title { + -fx-font-family:'Helvetica Condensed'; + -fx-font-size:24; + -fx-font-weight:normal; +} + +.archived-panel .taskname, .archived-panel .timestamp { + -fx-text-fill:#FFFFFF; +} + +/*------------------------------------------ SearchPanel Styling ------------------------------------------*/ + +.search-view-title { + -fx-font-family:'Helvetica Condensed'; + -fx-font-size:24; + -fx-font-weight:normal; +} + +.search-panel .title { + -fx-font-family:'Helvetica Condensed'; + -fx-font-size:20; + -fx-font-weight:normal; +} + +.search-panel .check-box { + -fx-font-family:'Helvetica'; + -fx-text-fill:#FFFFFF; + -fx-font-size:10; + -fx-font-weight:bold; +} + +.search-panel .taskname, .search-panel .timestamp { + -fx-text-fill:#FFFFFF; +} + +/*------------------------------------------ HelpPanel Styling ------------------------------------------*/ + +.help-panel .title { + -fx-font-family:'Helvetica Bold'; + -fx-font-size:48; + -fx-font-weight:normal; +} + +.help-panel .subtitle { + -fx-font-family:'Helvetica'; + -fx-font-size:13; + -fx-font-weight:bold; +} + +.overlay-scrollpane, .overlay-scrollpane > .viewport { + -fx-background-color:transparent; +} + +.scroll-pane > .scroll-bar:horizontal, +.scroll-pane > .scroll-bar:vertical { + -fx-background-color:transparent; + -fx-background-radius:2em; + -fx-border-radius:2em; +} + +.scorll-pane > .scroll-bar:horizontal .track, +.scroll-pane > .scroll-bar:vertical .track { + -fx-background-color:transparent; + -fx-background-radius:0em; + -fx-border-color:transparent; + -fx-border-radius:2em; +} + +.scroll-pane > .scroll-bar:horizontal .thumb, +.scroll-pane > .scroll-bar:vertical .thumb { + -fx-background-insets:4, 5, 6; + -fx-background-radius:2em; + -fx-border-radius:2em; +} + +.scroll-pane > .scroll-bar > .increment-button, +.scroll-pane > .scroll-bar > .decrement-button { + -fx-background-color:transparent; + -fx-background-radius:0em; + -fx-padding:0 0 10 0; +} + +.scroll-pane > .scroll-bar > .increment-button > .increment-arrow, +.scroll-pane > .scroll-bar > .decrement-button > .decrement-arrow { + -fx-shape:" "; + -fx-padding:0; } \ No newline at end of file diff --git a/src/main/resources/view/FloatingList.fxml b/src/main/resources/view/FloatingList.fxml new file mode 100644 index 000000000000..8d58ccc772b8 --- /dev/null +++ b/src/main/resources/view/FloatingList.fxml @@ -0,0 +1,23 @@ + + + + + + + + + + + + + + + + + + + diff --git a/src/main/resources/view/MainWindow.fxml b/src/main/resources/view/MainWindow.fxml old mode 100644 new mode 100755 index e2567ee9ad65..9c39bab158f1 --- a/src/main/resources/view/MainWindow.fxml +++ b/src/main/resources/view/MainWindow.fxml @@ -1,55 +1,130 @@ - - - - + + + + + + + + + + - - - - - - - - - - - - - - - + + + + + + - + + + + - - - - - - + - + - + - + - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/main/resources/view/OverdueList.fxml b/src/main/resources/view/OverdueList.fxml new file mode 100644 index 000000000000..ab5ca805ad79 --- /dev/null +++ b/src/main/resources/view/OverdueList.fxml @@ -0,0 +1,23 @@ + + + + + + + + + + + + + + + + + + + diff --git a/src/main/resources/view/PersonListCard.fxml b/src/main/resources/view/PersonListCard.fxml new file mode 100755 index 000000000000..9953ce588beb --- /dev/null +++ b/src/main/resources/view/PersonListCard.fxml @@ -0,0 +1,42 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/main/resources/view/PersonListPanel.fxml b/src/main/resources/view/PersonListPanel.fxml new file mode 100755 index 000000000000..aa9c30ae99eb --- /dev/null +++ b/src/main/resources/view/PersonListPanel.fxml @@ -0,0 +1,14 @@ + + + + + + + + + + + + + + diff --git a/src/main/resources/view/TaskListCard.fxml b/src/main/resources/view/TaskListCard.fxml old mode 100644 new mode 100755 index 2df104257f29..987e7b0ec451 --- a/src/main/resources/view/TaskListCard.fxml +++ b/src/main/resources/view/TaskListCard.fxml @@ -12,7 +12,7 @@ - + diff --git a/src/main/resources/view/UpcomingList.fxml b/src/main/resources/view/UpcomingList.fxml new file mode 100644 index 000000000000..8cd68484bb65 --- /dev/null +++ b/src/main/resources/view/UpcomingList.fxml @@ -0,0 +1,23 @@ + + + + + + + + + + + + + + + + + + + diff --git a/src/test/java/guitests/AddCommandTest.java b/src/test/java/guitests/AddCommandTest.java index becd062d5121..ae4fc28569d2 100644 --- a/src/test/java/guitests/AddCommandTest.java +++ b/src/test/java/guitests/AddCommandTest.java @@ -20,6 +20,9 @@ //@@author A0139915W public class AddCommandTest extends SavvyTaskerGuiTest { + private DateFormat formatter = DateFormat.getDateInstance(DateFormat.MEDIUM, Locale.getDefault()); + private SimpleDateFormat format = new SimpleDateFormat("dd/MM/yyyy"); + @Test public void add() { //add one task @@ -61,8 +64,7 @@ private void assertAddSuccess(TestTask taskToAdd, TestTask... currentList) { TestTask[] expectedList = TestUtil.addTasksToList(currentList, taskToAdd); assertTrue(taskListPanel.isListMatching(expectedList)); } - - private DateFormat formatter = DateFormat.getDateInstance(DateFormat.MEDIUM, Locale.getDefault()); + private String getLocaleDateString(Date date) { try { return formatter.format(date); @@ -72,7 +74,6 @@ private String getLocaleDateString(Date date) { return null; } - private SimpleDateFormat format = new SimpleDateFormat("dd/MM/yyyy"); private Date getDate(String ddmmyyyy) { try { return format.parse(ddmmyyyy); diff --git a/src/test/java/guitests/CommandBoxTest.java b/src/test/java/guitests/CommandBoxTest.java index dbd8b655d036..ef2111d47438 100644 --- a/src/test/java/guitests/CommandBoxTest.java +++ b/src/test/java/guitests/CommandBoxTest.java @@ -13,9 +13,9 @@ public void commandBox_commandSucceeds_textCleared() { } @Test - public void commandBox_commandFails_textStays(){ + public void commandBox_commandFails_textClears(){ commandBox.runCommand("invalid command"); - assertEquals(commandBox.getCommandInput(), "invalid command"); + assertEquals(commandBox.getCommandInput(), ""); //TODO: confirm the text box color turns to red } diff --git a/src/test/java/guitests/DeleteCommandTest.java b/src/test/java/guitests/DeleteCommandTest.java index 7dfe77dbc734..bb0f13f9b730 100644 --- a/src/test/java/guitests/DeleteCommandTest.java +++ b/src/test/java/guitests/DeleteCommandTest.java @@ -17,11 +17,9 @@ public void delete() { //delete the first in the list TestTask[] currentList = td.getTypicalTasks(); int targetIndex = 1; - assertDeleteSuccess(targetIndex, currentList); //delete the last in the list - currentList = TestUtil.removeTaskFromList(currentList, targetIndex); targetIndex = currentList.length; assertDeleteSuccess(targetIndex, currentList); diff --git a/src/test/java/guitests/HelpWindowTest.java b/src/test/java/guitests/HelpWindowTest.java index 988156dd3dec..0b84c09ceb78 100644 --- a/src/test/java/guitests/HelpWindowTest.java +++ b/src/test/java/guitests/HelpWindowTest.java @@ -12,9 +12,11 @@ public void openHelpWindow() { taskListPanel.clickOnListView(); - assertHelpWindowOpen(mainMenu.openHelpWindowUsingAccelerator()); + // Feature removed + //assertHelpWindowOpen(mainMenu.openHelpWindowUsingAccelerator()); - assertHelpWindowOpen(mainMenu.openHelpWindowUsingMenu()); + // Feature removed + //assertHelpWindowOpen(mainMenu.openHelpWindowUsingMenu()); assertHelpWindowOpen(commandBox.runHelpCommand()); diff --git a/src/test/java/guitests/ModifyCommandTest.java b/src/test/java/guitests/ModifyCommandTest.java index fddc833fe95e..a57ed8f57d2d 100644 --- a/src/test/java/guitests/ModifyCommandTest.java +++ b/src/test/java/guitests/ModifyCommandTest.java @@ -18,6 +18,9 @@ //@@author A0139915W public class ModifyCommandTest extends SavvyTaskerGuiTest { + private DateFormat formatter = DateFormat.getDateInstance(DateFormat.MEDIUM, Locale.getDefault()); + private SimpleDateFormat format = new SimpleDateFormat("dd/MM/yyyy"); + @Test public void add() { //modify task @@ -60,7 +63,6 @@ private void assertModifySuccess(String command, TestTask taskToModify, TestTask assertTrue(taskListPanel.isListMatching(expectedList)); } - private DateFormat formatter = DateFormat.getDateInstance(DateFormat.MEDIUM, Locale.getDefault()); private String getLocaleDateString(Date date) { try { return formatter.format(date); @@ -70,7 +72,6 @@ private String getLocaleDateString(Date date) { return null; } - private SimpleDateFormat format = new SimpleDateFormat("dd/MM/yyyy"); private Date getDate(String ddmmyyyy) { try { return format.parse(ddmmyyyy); diff --git a/src/test/java/guitests/RedoCommandTest.java b/src/test/java/guitests/RedoCommandTest.java new file mode 100644 index 000000000000..00a77efc1dbc --- /dev/null +++ b/src/test/java/guitests/RedoCommandTest.java @@ -0,0 +1,152 @@ +//@@author A0097627N +package guitests; + +import guitests.guihandles.TaskCardHandle; + +import org.junit.Test; + +import seedu.savvytasker.logic.commands.UndoCommand; +import seedu.savvytasker.logic.commands.RedoCommand; +import seedu.savvytasker.logic.commands.HelpCommand; +import seedu.savvytasker.testutil.TestTask; +import seedu.savvytasker.testutil.TestUtil; + +import static org.junit.Assert.assertTrue; +import static seedu.savvytasker.commons.core.Messages.MESSAGE_UNKNOWN_COMMAND; +import static seedu.savvytasker.logic.commands.RedoCommand.MESSAGE_REDO_ACKNOWLEDGEMENT; + +public class RedoCommandTest extends SavvyTaskerGuiTest { + + TestTask[] expectedList = td.getTypicalTasks(); + TestTask[] currentList = td.getTypicalTasks(); + TestTask firstTaskToAdd = td.happy; + TestTask secondTaskToAdd = td.haloween; + TestTask pjmTaskToAdd = td.pjm; + TestTask projectMeetingTaskToAdd = td.projectMeeting; + + @Test + // redo one add command + public void redoAddTest() { + expectedList = TestUtil.addTasksToList(currentList, firstTaskToAdd); + commandBox.runCommand(firstTaskToAdd.getAddCommand()); + commandBox.runCommand("undo"); + commandBox.runCommand("redo"); + assertTrue(taskListPanel.isListMatching(expectedList)); + assertResultMessage(MESSAGE_REDO_ACKNOWLEDGEMENT); + } + + @Test + // redo a delete command + public void redoDeleteTest() { + expectedList = TestUtil.removeTaskFromList(currentList, 1); + commandBox.runCommand("delete 1"); + commandBox.runCommand("undo"); + commandBox.runCommand("redo"); + assertTrue(taskListPanel.isListMatching(expectedList)); + assertResultMessage(MESSAGE_REDO_ACKNOWLEDGEMENT); + } + + @Test + // redo clear command + public void redoClearTest() { + commandBox.runCommand("clear"); + commandBox.runCommand("undo"); + commandBox.runCommand("redo"); + assertListSize(0); + assertResultMessage(MESSAGE_REDO_ACKNOWLEDGEMENT); + } + + @Test + // redo alias command + public void redoAliasTest() { + expectedList = td.getTypicalTasks(); + expectedList = TestUtil.addTasksToList(expectedList, projectMeetingTaskToAdd); + commandBox.runCommand("alias k/pjm r/Project Meeting"); + commandBox.runCommand("undo"); + commandBox.runCommand("redo"); + assertResultMessage(MESSAGE_REDO_ACKNOWLEDGEMENT); + commandBox.runCommand(pjmTaskToAdd.getAddCommand()); + assertTrue(taskListPanel.isListMatching(expectedList)); + } + + @Test + // redo unalias command + public void redoUnaliasTest() { + expectedList = TestUtil.addTasksToList(currentList, pjmTaskToAdd); + commandBox.runCommand("alias k/pjm r/Project Meeting"); + commandBox.runCommand("unalias pjm"); + commandBox.runCommand("undo"); + commandBox.runCommand("redo"); + assertResultMessage(MESSAGE_REDO_ACKNOWLEDGEMENT); + commandBox.runCommand(pjmTaskToAdd.getAddCommand()); + assertTrue(taskListPanel.isListMatching(expectedList)); + } + + // redo two add commands + @Test + public void redoTwoAddTest() { + expectedList = TestUtil.addTasksToList(currentList, firstTaskToAdd); + expectedList = TestUtil.addTasksToList(expectedList, secondTaskToAdd); + commandBox.runCommand(firstTaskToAdd.getAddCommand()); + commandBox.runCommand(secondTaskToAdd.getAddCommand()); + commandBox.runCommand("undo"); + commandBox.runCommand("undo"); + commandBox.runCommand("redo"); + commandBox.runCommand("redo"); + assertTrue(taskListPanel.isListMatching(expectedList)); + assertResultMessage(MESSAGE_REDO_ACKNOWLEDGEMENT); + } + + // redo two delete commands + @Test + public void redoTwoDeleteTest() { + expectedList = TestUtil.removeTaskFromList(currentList, 1); + expectedList = TestUtil.removeTaskFromList(expectedList, 1); + commandBox.runCommand("delete 1"); + commandBox.runCommand("delete 1"); + commandBox.runCommand("undo"); + commandBox.runCommand("undo"); + commandBox.runCommand("redo"); + commandBox.runCommand("redo"); + assertTrue(taskListPanel.isListMatching(expectedList)); + assertResultMessage(MESSAGE_REDO_ACKNOWLEDGEMENT); + } + + // redo a delete command followed by an add command + @Test + public void redoDeleteAddTest() { + expectedList = TestUtil.addTasksToList(currentList, firstTaskToAdd); + expectedList = TestUtil.removeTaskFromList(expectedList, 1); + commandBox.runCommand(firstTaskToAdd.getAddCommand()); + commandBox.runCommand("delete 1"); + commandBox.runCommand("undo"); + commandBox.runCommand("undo"); + commandBox.runCommand("redo"); + commandBox.runCommand("redo"); + assertTrue(taskListPanel.isListMatching(expectedList)); + assertResultMessage(MESSAGE_REDO_ACKNOWLEDGEMENT); + } + + // redo an add command followed by a delete command + @Test + public void redoAddDeleteTest() { + expectedList = TestUtil.removeTaskFromList(currentList, 1); + expectedList = TestUtil.addTasksToList(expectedList, firstTaskToAdd); + commandBox.runCommand("delete 1"); + commandBox.runCommand(firstTaskToAdd.getAddCommand()); + commandBox.runCommand("undo"); + commandBox.runCommand("undo"); + commandBox.runCommand("redo"); + commandBox.runCommand("redo"); + assertTrue(taskListPanel.isListMatching(expectedList)); + assertResultMessage(MESSAGE_REDO_ACKNOWLEDGEMENT); + } + + // invalid command + @Test + public void invalidTest() { + commandBox.runCommand("redos"); + assertResultMessage("Input: redos\n" + String.format(MESSAGE_UNKNOWN_COMMAND, HelpCommand.MESSAGE_USAGE)); + } +} +//@@author \ No newline at end of file diff --git a/src/test/java/guitests/UndoCommandTest.java b/src/test/java/guitests/UndoCommandTest.java new file mode 100644 index 000000000000..813c06479a81 --- /dev/null +++ b/src/test/java/guitests/UndoCommandTest.java @@ -0,0 +1,145 @@ +//@@author A0097627N +package guitests; + +import guitests.guihandles.TaskCardHandle; + +import org.junit.Test; + +import seedu.savvytasker.logic.commands.UndoCommand; +import seedu.savvytasker.logic.commands.HelpCommand; +import seedu.savvytasker.testutil.TestTask; +import seedu.savvytasker.testutil.TestUtil; + +import static org.junit.Assert.assertTrue; +import static seedu.savvytasker.commons.core.Messages.MESSAGE_UNKNOWN_COMMAND; +import static seedu.savvytasker.logic.commands.UndoCommand.MESSAGE_UNDO_ACKNOWLEDGEMENT; + +public class UndoCommandTest extends SavvyTaskerGuiTest { + + TestTask[] expectedList = td.getTypicalTasks(); + TestTask[] currentList = td.getTypicalTasks(); + TestTask firstTaskToAdd = td.happy; + TestTask secondTaskToAdd = td.haloween; + TestTask pjmTaskToAdd = td.pjm; + TestTask projectMeetingTaskToAdd = td.projectMeeting; + + @Test + // undo one add command + public void undoAddTest() { + expectedList = td.getTypicalTasks(); + commandBox.runCommand(firstTaskToAdd.getAddCommand()); + commandBox.runCommand("undo"); + assertTrue(taskListPanel.isListMatching(expectedList)); + assertResultMessage(MESSAGE_UNDO_ACKNOWLEDGEMENT); + } + + @Test + // undo a delete command + public void undoDeleteTest() { + expectedList = td.getTypicalTasks(); + commandBox.runCommand("delete 1"); + commandBox.runCommand("undo"); + assertTrue(taskListPanel.isListMatching(expectedList)); + assertResultMessage(MESSAGE_UNDO_ACKNOWLEDGEMENT); + } + + @Test + // undo clear command + public void undoClearTest() { + expectedList = td.getTypicalTasks(); + commandBox.runCommand("clear"); + commandBox.runCommand("undo"); + assertTrue(taskListPanel.isListMatching(expectedList)); + assertResultMessage(MESSAGE_UNDO_ACKNOWLEDGEMENT); + } + + @Test + // undo alias command + public void undoAliasTest() { + expectedList = td.getTypicalTasks(); + expectedList = TestUtil.addTasksToList(expectedList, pjmTaskToAdd); + commandBox.runCommand("alias k/pjm r/Project Meeting"); + commandBox.runCommand("undo"); + assertResultMessage(MESSAGE_UNDO_ACKNOWLEDGEMENT); + commandBox.runCommand(pjmTaskToAdd.getAddCommand()); + assertTrue(taskListPanel.isListMatching(expectedList)); + } + + @Test + // undo unalias command + public void undoUnaliasTest() { + expectedList = TestUtil.addTasksToList(currentList, projectMeetingTaskToAdd); + commandBox.runCommand("alias k/pjm r/Project Meeting"); + commandBox.runCommand("unalias pjm"); + commandBox.runCommand("undo"); + assertResultMessage(MESSAGE_UNDO_ACKNOWLEDGEMENT); + commandBox.runCommand(pjmTaskToAdd.getAddCommand()); + assertTrue(taskListPanel.isListMatching(expectedList)); + } + + // undo mark command + @Test + public void undoMarkTest() { + expectedList = td.getTypicalTasks(); + commandBox.runCommand("mark 1"); + commandBox.runCommand("undo"); + assertTrue(taskListPanel.isListMatching(expectedList)); + assertResultMessage(MESSAGE_UNDO_ACKNOWLEDGEMENT); + } + + // undo two add commands + @Test + public void undoTwoAddTest() { + expectedList = td.getTypicalTasks(); + commandBox.runCommand(firstTaskToAdd.getAddCommand()); + commandBox.runCommand(secondTaskToAdd.getAddCommand()); + commandBox.runCommand("undo"); + commandBox.runCommand("undo"); + assertTrue(taskListPanel.isListMatching(expectedList)); + assertResultMessage(MESSAGE_UNDO_ACKNOWLEDGEMENT); + } + + // undo two delete commands + @Test + public void undoTwoDeleteTest() { + expectedList = td.getTypicalTasks(); + commandBox.runCommand("delete 1"); + commandBox.runCommand("delete 1"); + commandBox.runCommand("undo"); + commandBox.runCommand("undo"); + assertTrue(taskListPanel.isListMatching(expectedList)); + assertResultMessage(MESSAGE_UNDO_ACKNOWLEDGEMENT); + } + + // undo a delete command followed by an add command + @Test + public void undoDeleteAddTest() { + expectedList = td.getTypicalTasks(); + commandBox.runCommand(firstTaskToAdd.getAddCommand()); + commandBox.runCommand("delete 1"); + commandBox.runCommand("undo"); + commandBox.runCommand("undo"); + assertTrue(taskListPanel.isListMatching(expectedList)); + assertResultMessage(MESSAGE_UNDO_ACKNOWLEDGEMENT); + } + + // undo an add command followed by a delete command + @Test + public void undoAddDeleteTest() { + expectedList = td.getTypicalTasks(); + commandBox.runCommand("delete 1"); + commandBox.runCommand(firstTaskToAdd.getAddCommand()); + commandBox.runCommand("undo"); + commandBox.runCommand("undo"); + assertTrue(taskListPanel.isListMatching(expectedList)); + assertResultMessage(MESSAGE_UNDO_ACKNOWLEDGEMENT); + } + + // invalid command + @Test + public void invalidTest() { + commandBox.runCommand("undos"); + assertResultMessage("Input: undos\n" + String.format(MESSAGE_UNKNOWN_COMMAND, HelpCommand.MESSAGE_USAGE)); + } +} +// @@author diff --git a/src/test/java/seedu/savvytasker/commons/util/SmartDefaultDatesTest.java b/src/test/java/seedu/savvytasker/commons/util/SmartDefaultDatesTest.java index 6fe7ca6fc358..d8598a8eecf2 100644 --- a/src/test/java/seedu/savvytasker/commons/util/SmartDefaultDatesTest.java +++ b/src/test/java/seedu/savvytasker/commons/util/SmartDefaultDatesTest.java @@ -15,6 +15,8 @@ //@@author A0139915W public class SmartDefaultDatesTest { + private SimpleDateFormat format = new SimpleDateFormat("dd/MM/yyyy HHmmss"); + @Test public void smartDefaultDates_parseStart() { DateParser dateParser = new DateParser(); @@ -29,10 +31,9 @@ public void smartDefaultDates_parseStart() { SmartDefaultDates sdd = new SmartDefaultDates(inferredStart, inferredEnd); // specifying only start date, assumed to on the given date at 12am // and to end on the given date at 2359:59 - Date expectedStartTime = getDate("31/12/2016 000000"); - Date expectedEndTime = getDate("31/12/2016 235959"); - assertEquals(expectedStartTime, sdd.getStartDate()); - assertEquals(expectedEndTime, sdd.getEndDate()); + assertStartEndEquals( + getDate("31/12/2016 000000"), getDate("31/12/2016 235959"), + sdd.getStartDate(), sdd.getEndDate()); SimpleDateFormat sdf = new SimpleDateFormat("dd/MM/yyyy"); Date today = today(0, 0); @@ -45,10 +46,9 @@ public void smartDefaultDates_parseStart() { sdd = new SmartDefaultDates(inferredStart, inferredEnd); // specifying only start time, assumed to start today at the given time // and to end today 2359:59 - expectedStartTime = getDate(sdf.format(today) + " 150000"); - expectedEndTime = getDate(sdf.format(today) + " 235959"); - assertEquals(expectedStartTime, sdd.getStartDate()); - assertEquals(expectedEndTime, sdd.getEndDate()); + assertStartEndEquals( + getDate(sdf.format(today) + " 150000"), getDate(sdf.format(today) + " 235959"), + sdd.getStartDate(), sdd.getEndDate()); } @Test @@ -67,10 +67,9 @@ public void smartDefaultDates_parseEnd() { SmartDefaultDates sdd = new SmartDefaultDates(inferredStart, inferredEnd); // specified only the end date, assumed to start today at 12am // and to end on the given date at 2359:59 - Date expectedStartTime = getDate(sdf.format(today) + " 000000"); - Date expectedEndTime = getDate("31/12/2016 235959"); - assertEquals(expectedStartTime, sdd.getStartDate()); - assertEquals(expectedEndTime, sdd.getEndDate()); + assertStartEndEquals( + getDate(sdf.format(today) + " 000000"), getDate("31/12/2016 235959"), + sdd.getStartDate(), sdd.getEndDate()); try { //use MM-dd-yyyy @@ -81,10 +80,9 @@ public void smartDefaultDates_parseEnd() { sdd = new SmartDefaultDates(inferredStart, inferredEnd); // specified only the end time, assumed to start today at 12am // and to end at the given time today - expectedStartTime = getDate(sdf.format(today) + " 000000"); - expectedEndTime = getDate(sdf.format(today) + " 150000"); - assertEquals(expectedStartTime, sdd.getStartDate()); - assertEquals(expectedEndTime, sdd.getEndDate()); + assertStartEndEquals( + getDate(sdf.format(today) + " 000000"), getDate(sdf.format(today) + " 150000"), + sdd.getStartDate(), sdd.getEndDate()); try { @@ -96,10 +94,9 @@ public void smartDefaultDates_parseEnd() { sdd = new SmartDefaultDates(inferredStart, inferredEnd); // specified only the end date in the past, start date will be null // and to end on the given date at 2359:59 - expectedStartTime = null; - expectedEndTime = getDate("31/12/2000 235959"); - assertEquals(expectedStartTime, sdd.getStartDate()); - assertEquals(expectedEndTime, sdd.getEndDate()); + assertStartEndEquals( + null, getDate("31/12/2000 235959"), + sdd.getStartDate(), sdd.getEndDate()); } @Test @@ -126,10 +123,9 @@ public void smartDefaultDates_parseStartEnd() { // no time supplied for start and end // start defaults to 0000 // end defaults to 2359:59 - Date expectedStartTime = getDate("31/12/2016 000000"); - Date expectedEndTime = getDate("31/12/2016 235959"); - assertEquals(expectedStartTime, sdd.getStartDate()); - assertEquals(expectedEndTime, sdd.getEndDate()); + assertStartEndEquals( + getDate("31/12/2016 000000"), getDate("31/12/2016 235959"), + sdd.getStartDate(), sdd.getEndDate()); inferredStart = null; inferredEnd = null; @@ -145,10 +141,9 @@ public void smartDefaultDates_parseStartEnd() { // start defaults to 0000 // end defaults to 2359:59 // no restrictions imposed on end time earlier than start time - expectedStartTime = getDate("31/12/2016 000000"); - expectedEndTime = getDate("30/12/2016 235959"); - assertEquals(expectedStartTime, sdd.getStartDate()); - assertEquals(expectedEndTime, sdd.getEndDate()); + assertStartEndEquals( + getDate("31/12/2016 000000"), getDate("30/12/2016 235959"), + sdd.getStartDate(), sdd.getEndDate()); inferredStart = null; inferredEnd = null; @@ -162,10 +157,9 @@ public void smartDefaultDates_parseStartEnd() { sdd = new SmartDefaultDates(inferredStart, inferredEnd); // no date supplied for start and end // start and end defaults to the given time today - expectedStartTime = getDate(sdf.format(today) + " 100000"); - expectedEndTime = getDate(sdf.format(today) + " 220000"); - assertEquals(expectedStartTime, sdd.getStartDate()); - assertEquals(expectedEndTime, sdd.getEndDate()); + assertStartEndEquals( + getDate(sdf.format(today) + " 100000"), getDate(sdf.format(today) + " 220000"), + sdd.getStartDate(), sdd.getEndDate()); inferredStart = null; inferredEnd = null; @@ -180,10 +174,9 @@ public void smartDefaultDates_parseStartEnd() { // no date supplied for start and end, end time ends before start time // start and end defaults to the given time today // no restrictions imposed on end time being earlier - expectedStartTime = getDate(sdf.format(today) + " 220000"); - expectedEndTime = getDate(sdf.format(today) + " 100000"); - assertEquals(expectedStartTime, sdd.getStartDate()); - assertEquals(expectedEndTime, sdd.getEndDate()); + assertStartEndEquals( + getDate(sdf.format(today) + " 220000"), getDate(sdf.format(today) + " 100000"), + sdd.getStartDate(), sdd.getEndDate()); } @Test @@ -194,10 +187,8 @@ public void smartDefaultDates_defaultParse() { SmartDefaultDates sdd = new SmartDefaultDates(null, null); Date actualStart = sdd.getStart(dateParser.new InferredDate(new Date(), true, true)); Date actualEnd = sdd.getEnd(dateParser.new InferredDate(new Date(), true, true)); - Date expectedStart = null; - Date expectedEnd = null; - assertEquals(expectedStart, actualStart); - assertEquals(expectedEnd, actualEnd); + assertStartEndEquals(null, null, + actualStart, actualEnd); try { //use MM-dd-yyyy @@ -206,10 +197,9 @@ public void smartDefaultDates_defaultParse() { } catch (ParseException e) { assert false; //won't get here } - expectedStart = getDate(sdf.format(today) + " 220000"); - expectedEnd = getDate(sdf.format(today) + " 100000"); - assertEquals(expectedStart, actualStart); - assertEquals(expectedEnd, actualEnd); + assertStartEndEquals( + getDate(sdf.format(today) + " 220000"), getDate(sdf.format(today) + " 100000"), + actualStart, actualEnd); try { //use MM-dd-yyyy @@ -218,13 +208,16 @@ public void smartDefaultDates_defaultParse() { } catch (ParseException e) { assert false; //won't get here } - expectedStart = getDate("31/12/2016 000000"); - expectedEnd = getDate("31/12/2016 235959"); + assertStartEndEquals(getDate("31/12/2016 000000"), getDate("31/12/2016 235959"), + actualStart, actualEnd); + } + + private void assertStartEndEquals(Date expectedStart, Date expectedEnd, + Date actualStart, Date actualEnd) { assertEquals(expectedStart, actualStart); assertEquals(expectedEnd, actualEnd); } - private SimpleDateFormat format = new SimpleDateFormat("dd/MM/yyyy HHmmss"); private Date getDate(String ddmmyyyy) { try { return format.parse(ddmmyyyy); diff --git a/src/test/java/seedu/savvytasker/logic/LogicManagerTest.java b/src/test/java/seedu/savvytasker/logic/LogicManagerTest.java index 9b59af423a5e..a5682f25e361 100644 --- a/src/test/java/seedu/savvytasker/logic/LogicManagerTest.java +++ b/src/test/java/seedu/savvytasker/logic/LogicManagerTest.java @@ -3,7 +3,6 @@ import com.google.common.eventbus.Subscribe; import seedu.savvytasker.commons.core.EventsCenter; -import seedu.savvytasker.commons.core.Messages; import seedu.savvytasker.commons.core.UnmodifiableObservableList; import seedu.savvytasker.commons.events.model.SavvyTaskerChangedEvent; import seedu.savvytasker.commons.events.ui.JumpToListRequestEvent; @@ -49,7 +48,7 @@ public class LogicManagerTest { //These are for checking the correctness of the events raised private ReadOnlySavvyTasker latestSavedSavvyTasker; private boolean helpShown; - private int targetedJumpIndex; + //private int targetedJumpIndex; @Subscribe private void handleLocalModelChangedEvent(SavvyTaskerChangedEvent stce) { @@ -63,7 +62,7 @@ private void handleShowHelpRequestEvent(ShowHelpRequestEvent she) { @Subscribe private void handleJumpToListRequestEvent(JumpToListRequestEvent je) { - targetedJumpIndex = je.targetIndex; + //targetedJumpIndex = je.targetIndex; } @Before @@ -76,7 +75,7 @@ public void setup() { latestSavedSavvyTasker = new SavvyTasker(model.getSavvyTasker()); // last saved assumed to be up to date before. helpShown = false; - targetedJumpIndex = -1; // non yet + //targetedJumpIndex = -1; // non yet } @After @@ -196,12 +195,12 @@ private void assertIncorrectIndexFormatBehaviorForCommand(String commandWord, St // the following commands outputs a different expected message dealing with // invalid indices. - expectedMessage = "Input: delete -1\n" + String.format(Messages.MESSAGE_INVALID_COMMAND_FORMAT, DeleteCommand.COMMAND_FORMAT) + ": " + IndexParser.INDEX_MUST_BE_POSITIVE; - assertCommandBehavior(commandWord + " -1", expectedMessage); //index should be unsigned - expectedMessage = "Input: delete 0\n" + String.format(Messages.MESSAGE_INVALID_COMMAND_FORMAT, DeleteCommand.COMMAND_FORMAT) + ": " + IndexParser.INDEX_MUST_BE_POSITIVE; - assertCommandBehavior(commandWord + " 0", expectedMessage); //index cannot be 0 - expectedMessage = "Input: delete not_a_number\n" + String.format(Messages.MESSAGE_INVALID_COMMAND_FORMAT, DeleteCommand.COMMAND_FORMAT) + ": " + IndexParser.INDEX_MUST_BE_POSITIVE; - assertCommandBehavior(commandWord + " not_a_number", expectedMessage); + String newExpectedMessage = "Input: delete -1\n" + String.format(MESSAGE_INVALID_COMMAND_FORMAT, DeleteCommand.COMMAND_FORMAT) + ": " + IndexParser.INDEX_MUST_BE_POSITIVE; + assertCommandBehavior(commandWord + " -1", newExpectedMessage); //index should be unsigned + newExpectedMessage = "Input: delete 0\n" + String.format(MESSAGE_INVALID_COMMAND_FORMAT, DeleteCommand.COMMAND_FORMAT) + ": " + IndexParser.INDEX_MUST_BE_POSITIVE; + assertCommandBehavior(commandWord + " 0", newExpectedMessage); //index cannot be 0 + newExpectedMessage = "Input: delete not_a_number\n" + String.format(MESSAGE_INVALID_COMMAND_FORMAT, DeleteCommand.COMMAND_FORMAT) + ": " + IndexParser.INDEX_MUST_BE_POSITIVE; + assertCommandBehavior(commandWord + " not_a_number", newExpectedMessage); } /** diff --git a/src/test/java/seedu/savvytasker/testutil/TestUtil.java b/src/test/java/seedu/savvytasker/testutil/TestUtil.java index 348a28c5e37b..3ced67abe8ab 100644 --- a/src/test/java/seedu/savvytasker/testutil/TestUtil.java +++ b/src/test/java/seedu/savvytasker/testutil/TestUtil.java @@ -38,7 +38,11 @@ * A utility class for test cases. */ public class TestUtil { - + /** + * Folder used for temp files created during testing. Ignored by Git. + */ + public static String SANDBOX_FOLDER = FileUtil.getPath("./src/test/data/sandbox/"); + public static final Task[] sampleTaskData = getSampleTaskData(); public static String LS = System.lineSeparator(); public static void assertThrows(Class expected, Runnable executable) { @@ -56,13 +60,7 @@ public static void assertThrows(Class expected, Runnable ex String.format("Expected %s to be thrown, but nothing was thrown.", expected.getName())); } - /** - * Folder used for temp files created during testing. Ignored by Git. - */ - public static String SANDBOX_FOLDER = FileUtil.getPath("./src/test/data/sandbox/"); - //@@author A0139915W - public static final Task[] sampleTaskData = getSampleTaskData(); private static Task[] getSampleTaskData() { return new Task[]{ diff --git a/src/test/java/seedu/savvytasker/testutil/TypicalTestTasks.java b/src/test/java/seedu/savvytasker/testutil/TypicalTestTasks.java index 31f80cda0527..bfff6d3faa63 100644 --- a/src/test/java/seedu/savvytasker/testutil/TypicalTestTasks.java +++ b/src/test/java/seedu/savvytasker/testutil/TypicalTestTasks.java @@ -16,7 +16,7 @@ public class TypicalTestTasks { public TestTask highPriority, medPriority, lowPriority, furthestDue, - nearerDue, notSoNearerDue, earliestDue, longDue, happy, haloween; + nearerDue, notSoNearerDue, earliestDue, longDue, happy, haloween, pjm, projectMeeting; private SimpleDateFormat format = new SimpleDateFormat("dd/MM/yyyy"); public TypicalTestTasks() { @@ -41,6 +41,8 @@ public TypicalTestTasks() { //Manually added happy = new TaskBuilder().withId(9).withTaskName("Happy Task").build(); haloween = new TaskBuilder().withId(10).withTaskName("Haloween Task").build(); + pjm = new TaskBuilder().withId(11).withTaskName("pjm").build(); + projectMeeting = new TaskBuilder().withId(12).withTaskName("Project Meeting").build(); } catch (IllegalValueException e) { e.printStackTrace(); assert false : "not possible";