diff --git a/docs/UserGuide.md b/docs/UserGuide.md index 55633b395f1..1b1969d196f 100644 --- a/docs/UserGuide.md +++ b/docs/UserGuide.md @@ -264,7 +264,7 @@ You can create a group in your contact list. You can delete a group in your contact list. -**Format:** `delete n/GROUP_NAME` +**Format:** `delete g/GROUP_NAME` **Acceptable values:** @@ -285,6 +285,28 @@ You can delete a group in your contact list. +### Adding remarks to a group `remark` +You can add remarks to a group in your contact list. + + +**Format:** `remark g/GROUP_NAME r/REMARK` + + +**Acceptable values:** +- `GROUP_NAME` must be alphanumeric and cannot be blank. +- `GROUP_NAME` must be an existing group in the contact list. +- `REMARK` must be alphanumeric. + +**Example(s):** +- `remark g/CS2103T r/quiz tomorrow` + This adds the remark "quiz tomorrow" to the existing "CS2103T" group in your contact list. + + +**Potential errors(s):** +- Incorrect format (e.g. no prefix): +- The group you entered does not exist in your contact list: + + ### Finding a group `find` You can find a group in your contact list. This allows you to view the group's members and remarks. @@ -303,7 +325,7 @@ You can find a group in your contact list. This allows you to view the group's m **Potential error(s):** -- Incorrect format (e.g., no prefix): +- Incorrect format (e.g. no prefix): - The group you are trying to find does not exist in your contact list: @@ -554,17 +576,19 @@ You list meeting time for your groups. You can find a meeting time slot for your group where everyone is available. -**Format:** `findfreetime g/GROUP_NAME` +**Format:** `findfreetime g/GROUP_NAME d/DURATION` - Provide the full name of the group using the `g/` prefix. +- Provide the duration of the meeting using the `d/` prefix. **Acceptable values:** - `GROUP_NAME` must be alphanumeric. +- `DURATION` must be an integer representing the meeting duration in minutes. **Example(s):** -- `findfreetime g/CS2100` - This finds a common meeting time for your CS2100 group. +- `findfreetime g/CS2100 d/60` + This finds a common meeting time of 60 minutes for your CS2100 group. Insert Image diff --git a/src/main/java/seedu/address/logic/commands/AddCommand.java b/src/main/java/seedu/address/logic/commands/AddCommand.java index 398519a740c..9ae4e6a17c0 100644 --- a/src/main/java/seedu/address/logic/commands/AddCommand.java +++ b/src/main/java/seedu/address/logic/commands/AddCommand.java @@ -33,8 +33,10 @@ public class AddCommand extends Command { public static final String MESSAGE_SUCCESS = "New person added: %1$s"; public static final String MESSAGE_DUPLICATE_PERSON = "%1$s is already in the contact list"; - public static final String MESSAGE_DUPLICATE_EMAIL = "This email: %1$s already belongs to some one in the contact list"; - public static final String MESSAGE_DUPLICATE_PHONE = "This phone number: %1$s belongs to some one in the contact list"; + public static final String MESSAGE_DUPLICATE_EMAIL = "This email: %1$s already belongs to some " + + "one in the contact list"; + public static final String MESSAGE_DUPLICATE_PHONE = "This phone number: %1$s belongs to some one " + + "in the contact list"; private final Person toAdd; diff --git a/src/main/java/seedu/address/logic/commands/AddGroupMeetingTimeCommand.java b/src/main/java/seedu/address/logic/commands/AddGroupMeetingTimeCommand.java index 159fca0fe22..f462f173a78 100644 --- a/src/main/java/seedu/address/logic/commands/AddGroupMeetingTimeCommand.java +++ b/src/main/java/seedu/address/logic/commands/AddGroupMeetingTimeCommand.java @@ -21,7 +21,7 @@ public class AddGroupMeetingTimeCommand extends Command { + PREFIX_FREETIME + "MEETING_TIME \n" + "Example: " + COMMAND_WORD + " " + PREFIX_GROUPTAG + "CS2103T " - + PREFIX_FREETIME + "mon 1200 - mon 1400 ;tue 1000 - wed 1600"; + + PREFIX_FREETIME + "mon 1200 - mon 1400 " + PREFIX_FREETIME + "wed 1000 - wed 1600"; public static final String MESSAGE_NO_GROUP_WITH_NAME_FOUND = "No group with such name found.\n" + "Please provide the group's full name as in the existing contact list."; diff --git a/src/main/java/seedu/address/logic/commands/FindFreeTimeCommand.java b/src/main/java/seedu/address/logic/commands/FindFreeTimeCommand.java index d126d906087..f8c4174f039 100644 --- a/src/main/java/seedu/address/logic/commands/FindFreeTimeCommand.java +++ b/src/main/java/seedu/address/logic/commands/FindFreeTimeCommand.java @@ -19,84 +19,84 @@ */ public class FindFreeTimeCommand extends Command { - public static final String COMMAND_WORD = "findfreetime"; - - public static final String MESSAGE_USAGE = COMMAND_WORD + ": Finds a free time slot given a group and duration \n" + - "Parameters: " + PREFIX_GROUPTAG + "GROUPNAME " + PREFIX_DURATION + "DURATION"; - - public static final String MESSAGE_DURATION_USAGE = "Enter Duration in minutes"; - - - public static final String MESSAGE_NOT_ALL_FREE = "%s has not input their free time yet\n"; - - public static final String MESSAGE_SUCCESS = "These are the available timeslots \n"; - public static final String MESSAGE_INTERVAL_DISPLAY = "%d. %s\n"; - - private final String groupName; - private final Duration duration; - - - /** - * Creates an AddCommand to add the specified {@code Person} - */ - public FindFreeTimeCommand(String groupName, Duration duration) { - requireNonNull(groupName); - requireNonNull(duration); - this.groupName = groupName; - this.duration = duration; - } - - @Override - public CommandResult execute(Model model) throws CommandException { - // 3 steps - // find group, if group exists check everybody input time, use find free time algo - requireNonNull(model); - Group g; - // br stores message - StringBuilder br = new StringBuilder(); - int intervalCounter = 1; - try { - g = model.findGroup(groupName); - } catch (GroupNotFoundException e) { - throw new CommandException(e.getMessage()); - } - - // check everybody input time, modify br should somebody not key in their free time - g.areAllFree(br, MESSAGE_NOT_ALL_FREE); - if (br.length() != 0) { - throw new CommandException(br.toString()); - } - - // use algorithm to findFreeTime() - TimeIntervalList freeTime = g.findFreeTime(duration); - freeTime.getMessage(br, MESSAGE_INTERVAL_DISPLAY); - - return new CommandResult(MESSAGE_SUCCESS + br.toString()); - } - - @Override - public boolean equals(Object other) { - if (other == this) { - return true; - } - - // instanceof handles nulls - if (!(other instanceof GroupPersonCommand)) { - return false; - } - - GroupPersonCommand otherGroupPersonCommand = (GroupPersonCommand) other; - // to check - return this.equals(otherGroupPersonCommand); - - } - - // to fix - @Override - public java.lang.String toString() { - return new ToStringBuilder(this) - .add("toAddToGroup", "") - .toString(); - } + public static final String COMMAND_WORD = "findfreetime"; + + public static final String MESSAGE_USAGE = COMMAND_WORD + ": Finds a free time slot given a group and duration \n" + + "Parameters: " + PREFIX_GROUPTAG + "GROUPNAME " + PREFIX_DURATION + "DURATION"; + + public static final String MESSAGE_DURATION_USAGE = "Enter Duration in minutes"; + + + public static final String MESSAGE_NOT_ALL_FREE = "%s has not input their free time yet\n"; + + public static final String MESSAGE_SUCCESS = "These are the available timeslots \n"; + public static final String MESSAGE_INTERVAL_DISPLAY = "%d. %s\n"; + + private final String groupName; + private final Duration duration; + + + /** + * Creates an AddCommand to add the specified {@code Person} + */ + public FindFreeTimeCommand(String groupName, Duration duration) { + requireNonNull(groupName); + requireNonNull(duration); + this.groupName = groupName; + this.duration = duration; + } + + @Override + public CommandResult execute(Model model) throws CommandException { + // 3 steps + // find group, if group exists check everybody input time, use find free time algo + requireNonNull(model); + Group g; + // br stores message + StringBuilder br = new StringBuilder(); + int intervalCounter = 1; + try { + g = model.findGroup(groupName); + } catch (GroupNotFoundException e) { + throw new CommandException(e.getMessage()); + } + + // check everybody input time, modify br should somebody not key in their free time + g.areAllFree(br, MESSAGE_NOT_ALL_FREE); + if (br.length() != 0) { + throw new CommandException(br.toString()); + } + + // use algorithm to findFreeTime() + TimeIntervalList freeTime = g.findFreeTime(duration); + freeTime.getMessage(br, MESSAGE_INTERVAL_DISPLAY); + + return new CommandResult(MESSAGE_SUCCESS + br.toString()); + } + + @Override + public boolean equals(Object other) { + if (other == this) { + return true; + } + + // instanceof handles nulls + if (!(other instanceof GroupPersonCommand)) { + return false; + } + + GroupPersonCommand otherGroupPersonCommand = (GroupPersonCommand) other; + // to check + return this.equals(otherGroupPersonCommand); + + } + + // to fix + @Override + public java.lang.String toString() { + return new ToStringBuilder(this) + .add("toAddToGroup", "") + .toString(); + } } diff --git a/src/main/java/seedu/address/logic/parser/AddTimeCommandParser.java b/src/main/java/seedu/address/logic/parser/AddTimeCommandParser.java index 384c8f3f691..37268f5d53a 100644 --- a/src/main/java/seedu/address/logic/parser/AddTimeCommandParser.java +++ b/src/main/java/seedu/address/logic/parser/AddTimeCommandParser.java @@ -1,7 +1,6 @@ package seedu.address.logic.parser; import static seedu.address.logic.Messages.MESSAGE_INVALID_COMMAND_FORMAT; -import static seedu.address.logic.parser.CliSyntax.PREFIX_ENDINTERVAL; import static seedu.address.logic.parser.CliSyntax.PREFIX_FREETIME; import static seedu.address.logic.parser.CliSyntax.PREFIX_NAME; @@ -13,7 +12,9 @@ import seedu.address.model.TimeInterval; import seedu.address.model.person.Name; - +/** + * Parses input arguments and creates a new AddTimeCommand object + */ public class AddTimeCommandParser implements Parser { @Override diff --git a/src/main/java/seedu/address/logic/parser/DeleteTimeCommandParser.java b/src/main/java/seedu/address/logic/parser/DeleteTimeCommandParser.java index b56d413ab85..307d5f52d62 100644 --- a/src/main/java/seedu/address/logic/parser/DeleteTimeCommandParser.java +++ b/src/main/java/seedu/address/logic/parser/DeleteTimeCommandParser.java @@ -12,7 +12,7 @@ import static seedu.address.logic.Messages.MESSAGE_INVALID_COMMAND_FORMAT; import static seedu.address.logic.parser.CliSyntax.*; -public class DeleteTimeCommandParser implements Parser{ +public class DeleteTimeCommandParser implements Parser { /** * Parses the given {@code String} of arguments in the context of the DeleteTimeCommand @@ -22,20 +22,21 @@ public DeleteTimeCommand parse(String args) throws ParseException { String trimmedArgs = args.trim(); if (trimmedArgs.isEmpty()) { throw new ParseException( - String.format(MESSAGE_INVALID_COMMAND_FORMAT, DeleteTimeCommand.MESSAGE_USAGE)); + String.format(MESSAGE_INVALID_COMMAND_FORMAT, DeleteTimeCommand.MESSAGE_USAGE)); } ArgumentMultimap argMultimap = - ArgumentTokenizer.tokenize(args, PREFIX_NAME, PREFIX_GROUPTAG, PREFIX_FREETIME); + ArgumentTokenizer.tokenize(args, PREFIX_NAME, PREFIX_GROUPTAG, PREFIX_FREETIME); - if (!arePrefixesPresent(argMultimap, PREFIX_FREETIME)|| !argMultimap.getPreamble().isEmpty()) { + if (!arePrefixesPresent(argMultimap, PREFIX_FREETIME) || !argMultimap.getPreamble().isEmpty()) { throw new ParseException(String.format(MESSAGE_INVALID_COMMAND_FORMAT, DeleteTimeCommand.MESSAGE_USAGE)); } argMultimap.verifyNoDuplicatePrefixesFor(PREFIX_NAME, PREFIX_GROUPTAG); ArrayList timeInterval = ParserUtil.parseInterval(argMultimap.getAllValues(PREFIX_FREETIME)); if ((arePrefixesPresent(argMultimap, PREFIX_NAME) && arePrefixesPresent(argMultimap, PREFIX_GROUPTAG))) { - throw new ParseException(String.format(DeleteCommand.MESSAGE_TWO_PARAMETERS, DeleteTimeCommand.MESSAGE_USAGE)); + throw new ParseException( + String.format(DeleteCommand.MESSAGE_TWO_PARAMETERS, DeleteTimeCommand.MESSAGE_USAGE)); } if (arePrefixesPresent(argMultimap, PREFIX_NAME)) { Name name = ParserUtil.parseName(argMultimap.getValue(PREFIX_NAME).get()); diff --git a/src/main/java/seedu/address/logic/parser/FindFreeTimeCommandParser.java b/src/main/java/seedu/address/logic/parser/FindFreeTimeCommandParser.java index 43727b755b2..78075636b64 100644 --- a/src/main/java/seedu/address/logic/parser/FindFreeTimeCommandParser.java +++ b/src/main/java/seedu/address/logic/parser/FindFreeTimeCommandParser.java @@ -15,60 +15,63 @@ */ public class FindFreeTimeCommandParser implements Parser { - /** - * Parses the given {@code String} of arguments in the context of the FindFreeTimeCommand - * and returns an FindFreeTimeCommand object for execution. - * @throws ParseException if the user input does not conform the expected format - */ + /** + * Parses the given {@code String} of arguments in the context of the FindFreeTimeCommand + * and returns an FindFreeTimeCommand object for execution. + * + * @throws ParseException if the user input does not conform the expected format + */ - public FindFreeTimeCommand parse(String args) throws ParseException { - String trimmedArgs = args.trim(); - if (trimmedArgs.isEmpty()) { - throw new ParseException( - String.format(MESSAGE_INVALID_COMMAND_FORMAT, FindFreeTimeCommand.MESSAGE_USAGE)); - } + public FindFreeTimeCommand parse(String args) throws ParseException { + String trimmedArgs = args.trim(); + if (trimmedArgs.isEmpty()) { + throw new ParseException( + String.format(MESSAGE_INVALID_COMMAND_FORMAT, FindFreeTimeCommand.MESSAGE_USAGE)); + } // return new FindCommand(new NameContainsKeywordsPredicate(Arrays.asList(nameKeywords))); - ArgumentMultimap argMultimap = - ArgumentTokenizer.tokenize(args, PREFIX_DURATION, PREFIX_GROUPTAG); + ArgumentMultimap argMultimap = + ArgumentTokenizer.tokenize(args, PREFIX_DURATION, PREFIX_GROUPTAG); - if (!arePrefixesPresent(argMultimap, PREFIX_DURATION, PREFIX_GROUPTAG) || !argMultimap.getPreamble().isEmpty()) { - throw new ParseException(String.format(MESSAGE_INVALID_COMMAND_FORMAT, FindFreeTimeCommand.MESSAGE_USAGE)); - } - String groupName = argMultimap.getValue(PREFIX_GROUPTAG).get(); - String durationName = argMultimap.getValue(PREFIX_DURATION).get(); - int duration = 0; + if (!arePrefixesPresent(argMultimap, PREFIX_DURATION, PREFIX_GROUPTAG) || + !argMultimap.getPreamble().isEmpty()) { + throw new ParseException(String.format(MESSAGE_INVALID_COMMAND_FORMAT, FindFreeTimeCommand.MESSAGE_USAGE)); + } + String groupName = argMultimap.getValue(PREFIX_GROUPTAG).get(); + String durationName = argMultimap.getValue(PREFIX_DURATION).get(); + int duration = 0; - try { - duration = Integer.parseInt(durationName); - if (duration == 0) { - throw new IllegalArgumentException("You can't have a meeting without specifying a duration"); - } - if (duration < 0) { - throw new IllegalArgumentException("Duration specified is less than 0"); - } - // there are 10079 mins from mon 0000 to sun 1159 - if (duration > 10079) { - throw new IllegalArgumentException(String.format("The value you entered, %d is beyond the time you have in a week", duration)); - } - } catch (NumberFormatException e) { - throw new ParseException( - String.format(MESSAGE_INVALID_COMMAND_FORMAT, FindFreeTimeCommand.MESSAGE_DURATION_USAGE)); - } catch (IllegalArgumentException i) { - throw new ParseException( - String.format(MESSAGE_INVALID_COMMAND_FORMAT, i.getMessage())); - } - // 0 is duration placeholder, should not enter this line if duration is 0 - return new FindFreeTimeCommand(groupName, new Duration(duration)); - } + try { + duration = Integer.parseInt(durationName); + if (duration == 0) { + throw new IllegalArgumentException("You can't have a meeting without specifying a duration"); + } + if (duration < 0) { + throw new IllegalArgumentException("Duration specified is less than 0"); + } + // there are 10079 mins from mon 0000 to sun 1159 + if (duration > 10079) { + throw new IllegalArgumentException( + String.format("The value you entered, %d is beyond the time you have in a week", duration)); + } + } catch (NumberFormatException e) { + throw new ParseException( + String.format(MESSAGE_INVALID_COMMAND_FORMAT, FindFreeTimeCommand.MESSAGE_DURATION_USAGE)); + } catch (IllegalArgumentException i) { + throw new ParseException( + String.format(MESSAGE_INVALID_COMMAND_FORMAT, i.getMessage())); + } + // 0 is duration placeholder, should not enter this line if duration is 0 + return new FindFreeTimeCommand(groupName, new Duration(duration)); + } - /** - * Returns true if none of the prefixes contains empty {@code Optional} values in the given - * {@code ArgumentMultimap}. - */ - private static boolean arePrefixesPresent(ArgumentMultimap argumentMultimap, Prefix... prefixes) { - return Stream.of(prefixes).allMatch(prefix -> argumentMultimap.getValue(prefix).isPresent()); - } + /** + * Returns true if none of the prefixes contains empty {@code Optional} values in the given + * {@code ArgumentMultimap}. + */ + private static boolean arePrefixesPresent(ArgumentMultimap argumentMultimap, Prefix... prefixes) { + return Stream.of(prefixes).allMatch(prefix -> argumentMultimap.getValue(prefix).isPresent()); + } } diff --git a/src/main/java/seedu/address/model/Duration.java b/src/main/java/seedu/address/model/Duration.java index dc934d4ba30..62516c68cad 100644 --- a/src/main/java/seedu/address/model/Duration.java +++ b/src/main/java/seedu/address/model/Duration.java @@ -2,13 +2,14 @@ public class Duration { - private int duration; - public Duration(int duration) { - this.duration = duration; - } - - public int getDurationInMin() { - return this.duration; - } + private final int duration; + + public Duration(int duration) { + this.duration = duration; + } + + public int getDurationInMin() { + return this.duration; + } } diff --git a/src/main/java/seedu/address/model/FreeTime.java b/src/main/java/seedu/address/model/FreeTime.java index c03f182cfeb..1b58dc4f4b8 100644 --- a/src/main/java/seedu/address/model/FreeTime.java +++ b/src/main/java/seedu/address/model/FreeTime.java @@ -12,7 +12,7 @@ public class FreeTime implements Iterable { private final ObservableList internalList = FXCollections.observableArrayList(); private final ObservableList internalUnmodifiableList = - FXCollections.unmodifiableObservableList(internalList); + FXCollections.unmodifiableObservableList(internalList); public void addTime(TimeInterval timeInterval) { internalList.add(timeInterval); @@ -33,6 +33,7 @@ public void addTime(ArrayList timeIntervals) { /** * Check whether no time is stored + * * @return boolean representing whether no time is stored */ public boolean isEmpty() { @@ -42,12 +43,13 @@ public boolean isEmpty() { /** * Generate String representing list of intervals - * @param br StringBuilder to store message + * + * @param br StringBuilder to store message * @param format specify Message format */ public void getMessage(StringBuilder br, String format) { int intervalCount = 1; - for (TimeInterval t: this.internalList) { + for (TimeInterval t : this.internalList) { br.append(br.append(String.format(format, intervalCount, t.toString()))); intervalCount++; } diff --git a/src/main/java/seedu/address/model/Time.java b/src/main/java/seedu/address/model/Time.java index fa26a43deb6..287aecc9aea 100644 --- a/src/main/java/seedu/address/model/Time.java +++ b/src/main/java/seedu/address/model/Time.java @@ -6,6 +6,9 @@ import java.time.LocalTime; import java.time.format.DateTimeFormatter; +/** + * A class represent a time object + */ public class Time { public static final String MESSAGE_CONSTRAINTS = "The format of a time should be: mon 1200,\n" @@ -76,6 +79,11 @@ public boolean equals(Object object) { } } + /** + * Converts string to DayOfWeek object + * @param day In String + * @return day in DayOfWeek object + */ public static DayOfWeek decodeDay(String day) { day = day.toLowerCase(); if (DayOfWeek.MONDAY.toString().toLowerCase().contains(day)) { diff --git a/src/main/java/seedu/address/model/TimeInterval.java b/src/main/java/seedu/address/model/TimeInterval.java index e9c1f88b929..1e64660796f 100644 --- a/src/main/java/seedu/address/model/TimeInterval.java +++ b/src/main/java/seedu/address/model/TimeInterval.java @@ -1,15 +1,14 @@ package seedu.address.model; -import static java.util.Objects.requireNonNull; + import static seedu.address.logic.parser.CliSyntax.PREFIX_FREETIME; import java.time.DayOfWeek; import java.util.ArrayList; -import seedu.address.logic.parser.ParserUtil; - -import javax.xml.stream.FactoryConfigurationError; - +/** + * A class representing a time interval object + */ public class TimeInterval { public static final String MESSAGE_CONSTRAINTS_SYNTAX = "The format of an interval should be: mon 1200 - tue 1400"; @@ -17,8 +16,8 @@ public class TimeInterval { public static final String MESSAGE_CONSTRAINTS_LOGIC = "Your end time cannot be before your start time "; public static final String MESSAGE_CONSTRAINTS_OVERLAP = "No overlap is allowed in your interval. \n " - + PREFIX_FREETIME + "mon 1200 - mon 1600 " + PREFIX_FREETIME + "mon 1400 - mon 1800 is not allowed. " + - "Write it as mon 1200 - mon 1800"; + + PREFIX_FREETIME + "mon 1200 - mon 1600 " + PREFIX_FREETIME + "mon 1400 - mon 1800 is not allowed. " + + "Write it as mon 1200 - mon 1800"; public static final String VALIDATION_REGEX = ".* .* - .* .*"; @@ -27,8 +26,9 @@ public class TimeInterval { /** * TimeInterval constructor. + * * @param start The start time of the interval. - * @param end The end time of the interval. + * @param end The end time of the interval. */ public TimeInterval(Time start, Time end) { this.start = start; @@ -37,6 +37,7 @@ public TimeInterval(Time start, Time end) { /** * Returns true if the timeInterval overlaps with one another. + * * @param intervals ArrayList of TimeIntervals. * @return Returns true if the timeInterval overlaps with one another. */ @@ -45,7 +46,8 @@ public static boolean isTimeIntervalOverlap(ArrayList intervals) { for (int j = i + 1; j < intervals.size(); j++) { int startComparison = intervals.get(i).compareStart(intervals.get(j)); int endComparison = intervals.get(i).compareEnd(intervals.get(j)); - boolean noClash = ((startComparison < 0 && endComparison < 0)|| (startComparison > 0 && endComparison > 0)); + boolean noClash = ((startComparison < 0 && endComparison < 0) + || (startComparison > 0 && endComparison > 0)); if ((startComparison == 0 && endComparison == 0) || !noClash) { return true; } @@ -57,6 +59,7 @@ public static boolean isTimeIntervalOverlap(ArrayList intervals) { /** * Check whether an interval overlaps another interval in any way * Interval overlapping at start and end points not considered as overlap does not form interval + * * @param t * @return */ @@ -76,6 +79,7 @@ public boolean isTimeIntervalOverlapWithTimeInterval(TimeInterval t) { /** * Check if Intervals are equal in terms of time representation and not exact object comparison + * * @param otherInterval that we are comparing to * @return boolean whether otherInterval is equal in terms of time representation */ @@ -95,6 +99,7 @@ public static TimeInterval getMinEnd(TimeInterval first, TimeInterval second) { /** * Create new time interval with MaxStart and MinEnd + * * @param otherInterval * @return */ @@ -105,6 +110,7 @@ public TimeInterval getIntersect(TimeInterval otherInterval) { /** * Check if time interval can accomodate for a given duration * Whether duration can fit in interval + * * @param duration of meeting in consideration * @return boolean whether meeting is permissible */ @@ -119,6 +125,7 @@ public boolean allows(Duration duration) { /** * Returns true if the interval string is in right format. + * * @param timeInterval The timeInterval to be checked. * @return Returns true if the interval string is in right format. */ @@ -128,17 +135,23 @@ public static boolean isValidTimeIntervalSyntax(String timeInterval) { /** * Returns true if start time is less than end time. + * * @param start Start time. - * @param end End time. + * @param end End time. * @return Returns true if start time is less than end time. */ public static boolean isValidTimeIntervalLogic(Time start, Time end) { return start.compareTo(end) <= -1; } + /** + * Checks if timeInterval clashes with otherTime + */ public boolean isClash(TimeInterval otherTime) { - boolean isBefore = this.start.compareTo(otherTime.start) < 0 && this.end.compareTo(otherTime.end) < 0 && this.end.compareTo(otherTime.start) < 0; - boolean isAfter = this.start.compareTo(otherTime.start) > 0 && this.end.compareTo(otherTime.end) > 0 && this.start.compareTo(otherTime.end) > 0; + boolean isBefore = this.start.compareTo(otherTime.start) < 0 && this.end.compareTo(otherTime.end) < 0 + && this.end.compareTo(otherTime.start) < 0; + boolean isAfter = this.start.compareTo(otherTime.start) > 0 && this.end.compareTo(otherTime.end) > 0 + && this.start.compareTo(otherTime.end) > 0; return !(isBefore || isAfter); } @@ -156,6 +169,7 @@ public DayOfWeek getStartTimeDay() { /** * Gets the start time of the interval + * * @return Start time */ public Time getStart() { @@ -164,6 +178,7 @@ public Time getStart() { /** * Gets the end time of the interval + * * @return end time */ public Time getEnd() { diff --git a/src/main/java/seedu/address/model/TimeIntervalList.java b/src/main/java/seedu/address/model/TimeIntervalList.java index e23ec944029..11e234e271f 100644 --- a/src/main/java/seedu/address/model/TimeIntervalList.java +++ b/src/main/java/seedu/address/model/TimeIntervalList.java @@ -7,8 +7,12 @@ import javafx.collections.FXCollections; import javafx.collections.ObservableList; + import seedu.address.logic.commands.exceptions.CommandException; +/** + * Class representing the list of time intervals + */ public class TimeIntervalList implements Iterable { private final ObservableList internalList = FXCollections.observableArrayList(); @@ -20,18 +24,16 @@ public void addTime(TimeInterval timeInterval) { } /** - * Converts the internal list to streams. + * Adds time to the current TimeInterval list * - * @return Internal list into streams. + * @param timeIntervals ArrayList of timeIntervals + * @return the status after adding the time */ - public Stream toStream() { - return internalList.stream(); - } - - public String addTime(ArrayList timeIntervals) throws CommandException{ + public String addTime(ArrayList timeIntervals) { boolean isPass = false; boolean isFail = false; - StringBuilder errorMessage = new StringBuilder("There is a clash in these input timings with your existing timings:\n"); + StringBuilder errorMessage = new StringBuilder("There is a clash in these input timings with " + + "your existing timings:\n"); StringBuilder passMessage = new StringBuilder("These times have been added:\n"); for (TimeInterval interval : timeIntervals) { if (isTimeIntervalOverlap(interval)) { @@ -53,6 +55,19 @@ public String addTime(ArrayList timeIntervals) throws CommandExcep } } + /** + * Converts the internal list to streams. + * + * @return Internal list into streams. + */ + public Stream toStream() { + return internalList.stream(); + } + + /** + * Adds all the timeInterval in to current timeInterval list + * @param timeIntervalList TimeIntervalList to be added + */ public void addAll(TimeIntervalList timeIntervalList) { for (TimeInterval timeInterval : timeIntervalList) { this.internalList.add(timeInterval); @@ -86,6 +101,7 @@ public String deleteTime(ArrayList timeIntervals) throws CommandEx /** * Checks whether timeInterval contains the time + * * @param timeInterval The time Interval to check * @return Whether time interval is in list */ @@ -95,6 +111,7 @@ public boolean hasTime(TimeInterval timeInterval) { /** * Removes free time from list + * * @param timeInterval The time interval to remove */ public void removeTime(TimeInterval timeInterval) { @@ -103,6 +120,7 @@ public void removeTime(TimeInterval timeInterval) { /** * Checks if time interval overlaps with internal list + * * @param interval The time iunterval to check * @return Whether time interval overlaps with internal list */ @@ -115,9 +133,11 @@ public boolean isTimeIntervalOverlap(TimeInterval interval) { return false; } -///////////////////// + ///////////////////// + /** * Check whether no time is stored + * * @return boolean representing whether no time is stored */ public boolean isEmpty() { @@ -127,12 +147,13 @@ public boolean isEmpty() { /** * Generate String representing list of intervals - * @param br StringBuilder to store message + * + * @param br StringBuilder to store message * @param format specify Message format */ public void getMessage(StringBuilder br, String format) { int intervalCount = 1; - for (TimeInterval t: this.internalList) { + for (TimeInterval t : this.internalList) { br.append(String.format(format, intervalCount, t.toString())); intervalCount++; } @@ -141,12 +162,13 @@ public void getMessage(StringBuilder br, String format) { /** * Filter a TimeIntervalList to contain only intervals that fit the duration + * * @param duration represent time in minutes * @return TimeIntervalList with duration greater than duration specified */ public TimeIntervalList fitDuration(Duration duration) { TimeIntervalList personTime = new TimeIntervalList(); - for (TimeInterval interval: internalList) { + for (TimeInterval interval : internalList) { if (interval.allows(duration)) { personTime.addTime(interval); } diff --git a/src/main/java/seedu/address/model/group/Group.java b/src/main/java/seedu/address/model/group/Group.java index 493388223c6..350a4176791 100644 --- a/src/main/java/seedu/address/model/group/Group.java +++ b/src/main/java/seedu/address/model/group/Group.java @@ -65,7 +65,8 @@ public Group(String groupName, GroupRemark groupRemark, List listOfGroup /** * Name field, listOfGroupMates and timeIntervalList must be present and not null. */ - public Group(String groupName, GroupRemark groupRemark, List listOfGroupMates, TimeIntervalList timeIntervalList) { + public Group(String groupName, GroupRemark groupRemark, List listOfGroupMates, + TimeIntervalList timeIntervalList) { requireNonNull(groupName); requireNonNull(listOfGroupMates); requireNonNull(timeIntervalList); @@ -82,6 +83,7 @@ public String getGroupName() { public TimeIntervalList getTimeIntervalList() { return timeIntervalList; } + /** * Converts the internal list to streams. * @@ -170,11 +172,12 @@ public void setGroupRemark(GroupRemark groupRemark) { /** * Modify StringBuilder to display message should any groupMate not input their free time - * @param br StringBuilder + * + * @param br StringBuilder * @param format Format specifier */ public void areAllFree(StringBuilder br, String format) { - for (Person p: this.listOfGroupMates) { + for (Person p : this.listOfGroupMates) { if (p.isNotFree()) { br.append(String.format(format, p.getName().fullName)); } @@ -184,6 +187,7 @@ public void areAllFree(StringBuilder br, String format) { /** * Compare each person in group to get overlap * Accumulate the result + * * @param duration represent duration in minutes * @return TimeInterval that can fit duration specified */ @@ -205,25 +209,26 @@ public TimeIntervalList findFreeTime(Duration duration) throws CommandException } for (int i = 0; i < listOfGroupMates.size(); i++) { - if (i + 1 == listOfGroupMates.size()) { - break; - } - Person firstPerson = listOfGroupMates.get(i); - Person secondPerson = listOfGroupMates.get(i + 1); - TimeIntervalList first = firstPerson.getTime(); - TimeIntervalList second = secondPerson.getTime(); - // uninitialised freeTime e.g. first and second person in group - if (freeTime.isEmpty()) { - freeTime = first.findOverlap(second, duration); - } else { - freeTime = freeTime.findOverlap(second, duration); - } + if (i + 1 == listOfGroupMates.size()) { + break; + } + Person firstPerson = listOfGroupMates.get(i); + Person secondPerson = listOfGroupMates.get(i + 1); + TimeIntervalList first = firstPerson.getTime(); + TimeIntervalList second = secondPerson.getTime(); + // uninitialised freeTime e.g. first and second person in group + if (freeTime.isEmpty()) { + freeTime = first.findOverlap(second, duration); + } else { + freeTime = freeTime.findOverlap(second, duration); + } } return freeTime; } /** * Adds a single time interval to the group + * * @param toAddTime time interval to add */ public void addTime(TimeInterval toAddTime) throws CommandException { @@ -232,6 +237,7 @@ public void addTime(TimeInterval toAddTime) throws CommandException { /** * Adds a list of free time to the group + * * @param toAddTime List of time intervals to add * @throws CommandException When there is a clash in timings within the list */ @@ -241,6 +247,7 @@ public String addTime(ArrayList toAddTime) throws CommandException /** * Checks if the group has the time interval + * * @param timeInterval time interval to check * @return result of check */ @@ -252,7 +259,9 @@ public TimeIntervalList getTime() { return this.timeIntervalList; } - public String deleteTime(ArrayList toDeleteTime) throws CommandException { return this.timeIntervalList.deleteTime(toDeleteTime);} + public String deleteTime(ArrayList toDeleteTime) throws CommandException { + return this.timeIntervalList.deleteTime(toDeleteTime); + } @Override public boolean equals(Object group) { @@ -272,8 +281,8 @@ public boolean equals(Object group) { @Override public String toString() { return new ToStringBuilder(this) - .add("Group name", groupName) - .toString(); + .add("Group name", groupName) + .toString(); } public int size() { diff --git a/src/main/java/seedu/address/model/person/Person.java b/src/main/java/seedu/address/model/person/Person.java index c505c8d5ac0..df43d9bc889 100644 --- a/src/main/java/seedu/address/model/person/Person.java +++ b/src/main/java/seedu/address/model/person/Person.java @@ -8,8 +8,8 @@ import seedu.address.commons.util.ToStringBuilder; import seedu.address.logic.commands.exceptions.CommandException; -import seedu.address.model.TimeIntervalList; import seedu.address.model.TimeInterval; +import seedu.address.model.TimeIntervalList; import seedu.address.model.group.Group; import seedu.address.model.group.GroupList; @@ -117,13 +117,6 @@ public boolean isSamePerson(Person otherPerson) { return isSameName(otherPerson); } - public boolean isSameGroups(Person otherPerson) { - if (otherPerson == this) { - return true; - } - return otherPerson != null && otherPerson.getGroups().equals(this.getGroups()); - } - /** * Returns true if both persons have the same name. * This defines a weaker notion of equality between two persons. diff --git a/src/main/java/seedu/address/model/person/UniquePersonList.java b/src/main/java/seedu/address/model/person/UniquePersonList.java index c408725bfc4..91448794c58 100644 --- a/src/main/java/seedu/address/model/person/UniquePersonList.java +++ b/src/main/java/seedu/address/model/person/UniquePersonList.java @@ -9,7 +9,6 @@ import javafx.collections.FXCollections; import javafx.collections.ObservableList; import seedu.address.logic.Messages; -import seedu.address.logic.commands.UngroupPersonCommand; import seedu.address.logic.commands.exceptions.CommandException; import seedu.address.model.person.exceptions.DuplicatePersonException; import seedu.address.model.person.exceptions.PersonNotFoundException; @@ -40,18 +39,22 @@ public boolean contains(Person toCheck) { return internalList.stream().anyMatch(toCheck::isSamePerson); } + /** + * Returns true if the list contains an equivalent email as the given argument. + */ public boolean containsEmail(Person toCheck) { requireNonNull(toCheck); return internalList.stream().anyMatch(toCheck::isSameEmail); } + + /** + * Returns true if the list contains an equivalent phonenumber as the given argument. + */ public boolean containsPhoneNumber(Person toCheck) { requireNonNull(toCheck); return internalList.stream().anyMatch(toCheck::isSamePhone); } - - - /** * Adds a person to the list. * The person must not already exist in the list. @@ -81,6 +84,19 @@ public void setPersons(UniquePersonList replacement) { internalList.setAll(replacement.internalList); } + /** + * Replaces the contents of this list with {@code persons}. + * {@code persons} must not contain duplicate persons. + */ + public void setPersons(List persons) { + requireAllNonNull(persons); + if (!personsAreUnique(persons)) { + throw new DuplicatePersonException(); + } + + internalList.setAll(persons); + } + /** * Replaces the person {@code target} in the list with {@code editedPerson}. * {@code target} must exist in the list. @@ -102,18 +118,6 @@ && contains(editedPerson)) { internalList.set(index, editedPerson); } - /** - * Replaces the contents of this list with {@code persons}. - * {@code persons} must not contain duplicate persons. - */ - public void setPersons(List persons) { - requireAllNonNull(persons); - if (!personsAreUnique(persons)) { - throw new DuplicatePersonException(); - } - - internalList.setAll(persons); - } /** * Returns the backing list as an unmodifiable {@code ObservableList}. diff --git a/src/main/java/seedu/address/ui/Calendar.java b/src/main/java/seedu/address/ui/Calendar.java index fd704d81afb..3fd7cb9ef64 100644 --- a/src/main/java/seedu/address/ui/Calendar.java +++ b/src/main/java/seedu/address/ui/Calendar.java @@ -1,7 +1,5 @@ package seedu.address.ui; -import java.net.URL; -import java.util.ArrayList; import javafx.collections.FXCollections; import javafx.collections.ListChangeListener; import javafx.collections.ObservableList; @@ -9,10 +7,11 @@ import javafx.scene.control.ListCell; import javafx.scene.control.ListView; import javafx.scene.layout.Region; -import seedu.address.model.TimeInterval; import seedu.address.model.group.Group; -import seedu.address.model.person.Person; +/** + * The UI component that is responsible for the calendar. + */ public class Calendar extends UiPart { private static final String FXML = "CalendarList.fxml"; @@ -29,6 +28,9 @@ public class Calendar extends UiPart { @FXML private ListView> dayListView; + /** + * Creates a {@code Calendar with tasks} with the given {@code groupList}. + */ public Calendar(ObservableList groupList) { super(FXML); this.groupList = groupList; diff --git a/src/main/java/seedu/address/ui/DayCard.java b/src/main/java/seedu/address/ui/DayCard.java index 468dea10ec9..32a651b097c 100644 --- a/src/main/java/seedu/address/ui/DayCard.java +++ b/src/main/java/seedu/address/ui/DayCard.java @@ -1,7 +1,7 @@ package seedu.address.ui; -import java.awt.Font; import java.time.DayOfWeek; + import javafx.collections.ObservableList; import javafx.fxml.FXML; import javafx.scene.control.Label; @@ -9,8 +9,10 @@ import javafx.scene.control.ListView; import javafx.scene.layout.HBox; import javafx.scene.layout.Region; -import seedu.address.model.person.Person; +/** + * The UI component that is responsible for each day in the calendar + */ public class DayCard extends UiPart { private static final String FXML = "DayCard.fxml"; @@ -24,15 +26,18 @@ public class DayCard extends UiPart { @FXML private ListView eachDayTaskList; + /** + * Creates a {@code DayCard in the calendar} with the given {@code dayTaskList} and index to display day. + */ public DayCard(ObservableList dayTaskList, int dayIndex) { super(FXML); this.dayTaskList = dayTaskList; day.setText(DayOfWeek.of(dayIndex).toString().substring(0, 3)); eachDayTaskList.setItems(dayTaskList); - eachDayTaskList.setCellFactory(listview -> new eachDayTaskListCell()); + eachDayTaskList.setCellFactory(listview -> new EachDayTaskListCell()); } - class eachDayTaskListCell extends ListCell { + class EachDayTaskListCell extends ListCell { @Override protected void updateItem(GroupTimeContainer task, boolean empty) { super.updateItem(task, empty); diff --git a/src/main/java/seedu/address/ui/EachDayTaskLine.java b/src/main/java/seedu/address/ui/EachDayTaskLine.java index 29cfefc7b67..677b0358602 100644 --- a/src/main/java/seedu/address/ui/EachDayTaskLine.java +++ b/src/main/java/seedu/address/ui/EachDayTaskLine.java @@ -6,6 +6,9 @@ import javafx.scene.layout.HBox; import javafx.scene.layout.Region; +/** + * The UI component that is responsible for each line in each day task list + */ public class EachDayTaskLine extends UiPart { private static final String FXML = "GroupTaskCell.fxml"; @@ -15,14 +18,17 @@ public class EachDayTaskLine extends UiPart { @FXML private Label dot; @FXML - private Label group_in_sch; + private Label groupInSch; @FXML private Label taskLine; + /** + * Creates a {@code line of group name and meeting time} with the given {@code task}. + */ public EachDayTaskLine(GroupTimeContainer task) { super(FXML); this.task = task; - group_in_sch.setText(task.getGroup().getGroupName()); + groupInSch.setText(task.getGroup().getGroupName()); taskLine.setText(task.getTimeInterval().toString()); } diff --git a/src/main/java/seedu/address/ui/GroupTimeContainer.java b/src/main/java/seedu/address/ui/GroupTimeContainer.java index 0a18d3f11c0..fcf49911693 100644 --- a/src/main/java/seedu/address/ui/GroupTimeContainer.java +++ b/src/main/java/seedu/address/ui/GroupTimeContainer.java @@ -3,11 +3,17 @@ import seedu.address.model.TimeInterval; import seedu.address.model.group.Group; +/** + * A helper class to create a object that contains a group and a single timeInterval + */ public class GroupTimeContainer { private final Group group; private final TimeInterval timeInterval; + /** + * Constructor for GroupTimeContainer + */ public GroupTimeContainer(Group group, TimeInterval timeInterval) { this.group = group; this.timeInterval = timeInterval; @@ -31,8 +37,8 @@ public boolean equals(Object other) { return false; } GroupTimeContainer otherGrpTimeContainer = (GroupTimeContainer) other; - return this.group.equals(otherGrpTimeContainer.group) && - this.timeInterval.equals(otherGrpTimeContainer.timeInterval); + return this.group.equals(otherGrpTimeContainer.group) + && this.timeInterval.equals(otherGrpTimeContainer.timeInterval); } } diff --git a/src/main/java/seedu/address/ui/HelpWindow.java b/src/main/java/seedu/address/ui/HelpWindow.java index dc7a8c1821e..1483d590600 100644 --- a/src/main/java/seedu/address/ui/HelpWindow.java +++ b/src/main/java/seedu/address/ui/HelpWindow.java @@ -15,7 +15,7 @@ */ public class HelpWindow extends UiPart { - public static final String USERGUIDE_URL = "https://raw.githubusercontent.com/AY2324S1-CS2103T-T10-3/tp/master/docs/UserGuide.md"; + public static final String USERGUIDE_URL = "https://ay2324s1-cs2103t-t10-3.github.io/tp/UserGuide.html"; public static final String HELP_MESSAGE = "Refer to the user guide: " + USERGUIDE_URL; private static final Logger logger = LogsCenter.getLogger(HelpWindow.class); diff --git a/src/main/java/seedu/address/ui/PersonCard.java b/src/main/java/seedu/address/ui/PersonCard.java index a3ff541363a..da3130f748c 100644 --- a/src/main/java/seedu/address/ui/PersonCard.java +++ b/src/main/java/seedu/address/ui/PersonCard.java @@ -42,7 +42,7 @@ public class PersonCard extends UiPart { @FXML private FlowPane groups; @FXML - private FlowPane free_time; + private FlowPane freeTime; /** * Creates a {@code PersonCode} with the given {@code Person} and index to display. @@ -58,6 +58,7 @@ public PersonCard(Person person, int displayedIndex) { .toStream() .sorted(Comparator.comparing(Group::getGroupName)) .forEach(group -> groups.getChildren().add(new Label(group.getGroupName()))); - person.getTime().iterator().forEachRemaining(interval -> free_time.getChildren().add(new Label(interval.toString()))); + person.getTime().iterator().forEachRemaining(interval -> + freeTime.getChildren().add(new Label(interval.toString()))); } } diff --git a/src/main/resources/view/DarkTheme.css b/src/main/resources/view/DarkTheme.css index 0a3171db7fb..93b62389186 100644 --- a/src/main/resources/view/DarkTheme.css +++ b/src/main/resources/view/DarkTheme.css @@ -326,12 +326,12 @@ -fx-font-size: 11; } -#free_time { +#freeTime { -fx-hgap: 7; -fx-vgap: 3; } -#free_time .label { +#freeTime .label { -fx-text-fill: white; -fx-background-color: #B488E1; -fx-padding: 1 3 1 3; @@ -357,7 +357,7 @@ -fx-background-color: transparent; } -#group_in_sch { +#groupInSch { -fx-text-fill: white; -fx-background-color: #E18888; -fx-padding: 1 3 1 3; diff --git a/src/main/resources/view/GroupTaskCell.fxml b/src/main/resources/view/GroupTaskCell.fxml index d1ce6faf94c..0af188a9ee9 100644 --- a/src/main/resources/view/GroupTaskCell.fxml +++ b/src/main/resources/view/GroupTaskCell.fxml @@ -9,7 +9,7 @@ - +