About the project
I worked in a team of 5 for a software engineering project to morph a basic command line interface addressbook into a flashcard management application called Know-It-All. Know-It-All is designed to help medical students store, organise and share their learning material, integrated with a test session feature and scoring system to allow for a more efficient rote learning process.
My role was to design and implement the test session feature. The following sections illustrate this major feature in more detail.
Note the following icons and formatting used in this document:
This symbol indicates important information related to this section. |
test
: A grey highlight (called a mark-up) indicates that this is a command to be executed or a component, class
or object in the architecture of the application.
Information in a box like this represents additional useful information related to this section.
Summary of contributions
This section shows a summary of my coding, documentation, and other helpful contributions to the team project.
Major feature: I implemented the functionalities of a test session.
-
What it does: This allows users to begin and end a test session. While inside a test session, flashcard questions will be displayed, and student can input an answer or choose to reveal the answer before moving on to the next flashcard.
-
Justification: This feature is the main highlight of Know-It-All, as students use flashcards to test how much content they have memorised. Equipped with the user-friendly answer command that is missing in existing flashcard applications, Know-It-All provides a more engaging and interactive testing experience for the user.
-
Highlights: This feature modifies the existing UI to facilitate the addition of a new test session screen. It also has a heavy dependency on folder methods. Hence, this feature required an in-depth analysis of design alternatives, considering design patterns and principles as well as the user-friendliness of the commands. More details can be found under design considerations sections of Contributions to the Developer Guide. Implementation and writing tests were also tedious as many checks of the current state of the test session needs to be done to permit only certain commands and ban others.
Code contributed: [Collated code]
Other contributions:
-
Enhancements to features:
-
Wrote additional tests for new features to increase coverage from 79% to 81% (Pull requests #74)
-
Refactored existing status bar to display the current state of the user (whether user is in a test session, in a report display, in a folder or in home directory) instead of the previous last saved location and time. Corresponding tests are written as well. (Pull requests #162)
-
Updated UI colour scheme to enhance aesthetics and clarity of Know-It-All (Pull requests #162, #166, #174)
-
-
Documentation:
-
User guide: I updated the QuickStart section, added new features, remove previous addressbook features and modify existing commands (Pull requests #60, #59, #80, #106, #127)
-
Developer guide: I updated relevant sections related to addressbook to our Know-It-All flashcard context like Product scope and Non-Functional Requirements, some of its class diagrams and sequence diagrams, and added implementation for test session (Pull requests #80, #106)
-
About Us page: I collated and updated profiles for all members of the team. (Pull requests #6, #127)
-
-
Community:
-
PRs reviewed with non-trivial review comments: #65 (suggested another method of implementation), #46 (explained why Travis CI was failing)
-
Conducted manual testing, reported bugs and offered suggestions for our team: #119, #123, #124, #125, #134
-
Conducted manual testing and reported bugs for other teams in class: #170, #158, #165, #145
-
Contributions to the User Guide
We had to update the original addressbook User Guide with instructions for Know-It-All enhancements that we had added. The following is an excerpt from our updated Know-It-All User Guide, showing a few of the notable additions that I have made for the test session feature.
Command Format
-
Words in
UPPER_CASE
are the parameters to be supplied by you e.g. inaddfolder FOLDER_NAME
,FOLDER_NAME
is a parameter which can be something likeHuman Anatomy
. -
Items in square brackets are optional e.g
HINTS
inadd q/QUESTION a/ANSWER [h/HINTS]
.
Test Operations
After memorising the content of the flashcards, it is helpful to test how much information have been internalised and retained in a timed setting. The following commands show just how this can be done with the Test Session functionality of Know-It-All.
At the end of a successful test session, scores are final and you will not be able to perform an undo to restore the
previous states before the test session.
|
Test flashcards in a folder : test
You will enter a test session, where the display area enters a fullscreen and you will be presented flashcard questions and hints (if any) one by one. You should see a screen like the figure below.
Format: test
This command is only considered valid when inside the folder to be tested and is not already inside a test session. |
This command is invalid if the current folder is empty as there will be no flashcards to test. |
-
Hints will be presented along with the questions.
-
When presented with a question in a test session, you can either input an attempt or enter the command to reveal the answer.
-
For MCQ cards, the ordering of options will be randomized each time the flashcard is tested.
-
Internally, flashcards in a folder are queued to be displayed one by one in the order of lowest existing score to highest existing score.
-
The next flashcard will only be presented when the next command is carried out.
Examples:
-
test
Hint toggle on / off feature Coming in v2.0
If you are familiar with the content and feeling confident, simply toggle off hints during the test session. You can do it by specifying ‘-nohint’ at the end of the test command. Hint will not be displayed along with the question when the card is presented.
Format: test [-nohint]
Timer feature Coming in v2.0
If you are preparing for an exam that will require you to recall information quickly within the limited time given, this timer feature is just right for you! You will be given only 20 seconds to answer each question. If the 20 seconds is up before the question is answered, this attempt will be marked as wrong.
Format: test [-timer]
Keying in answer to a flashcard: ans
To reinforce learning and provide a more engaging experience with Know-It-All, you can input an answer for the currently displayed flashcard question. Know-It-All compares your attempt with the correct answer for that flashcard and tells you if you are right or wrong.
If the answer has been submitted successfully and it is correct, you will see the following page.
If the answer has been submitted successfully and it is wrong, you will see the following page.
Format: ans ANSWER
This command is only considered valid if a card question is currently being displayed in an active test session. |
-
Answer matching is case insensitive.
-
Answering a flashcard will increase the total number of attempts. If your answer is correct, this action will also increase the number of correct attempts.
-
To answer MCQ cards, enter the number of the option that you think is correct, rather than the option itself.
E.g.ans 1
rather thanans myanswer
Examples:
-
ans Mitochondrion
in response to the card question: What is the powerhouse of the cell? -
ans 2
in response to the card displayed below, choosing option 2 will give the right answer as the correct answer is 'Pigs'.
Contributions to the Developer Guide
Besides updating the original addressbook User Guide, Developer Guide has to be updated to Know-It-All context and features as well. To keep this section concise, I have included an excerpt from my contributions to the updated Know-It-All Developer Guide about the UI Component and the implementation details and design considerations for the test session feature.
UI component
API : Ui.java
UI
consists of a MainWindow
made up of many parts as seen above e.g.CommandBox
, ResultDisplay
, CardMainScreen
,
StatusBarFooter
, BrowserPanel
etc. All these parts, including the MainWindow
, inherit from the abstract UiPart
class.
Test Session feature
Overall Current Implementation
This big feature mainly involves UI
, Logic
and Model
components.
There are 3 main variables in ModelManager
introduced to keep track of the current state of the user in a test
session.
-
currentTestedCardFolder
-
The current card folder that the user is running a test session on (stored as an
ObservableList
of cards) . -
Set to null if user is not inside a test session
-
-
currentTestedCard
-
The current card the user is seeing in the test session, obtained from
currentTestedCardFolder
usingcurrentTestedCardIndex
. -
Set to null if user is not inside a test session
-
Related methods:
-
ModelManager#setCurrentTestedCard(Card card)
- setcurrentTestedCard
to the card specified. -
ModelManager#getCurrentTestedCard()
- returns thecurrentTestedCard
.
-
-
-
cardAlreadyAnswered
-
A boolean variable to indicate if the user has already executed a valid answer command for the current card.
-
Related methods:
-
ModelManager#setCardAsAnswered()
- setcardAlreadyAnswered
to true. -
ModelManager#setCardAsNotAnswered()
- setcardAlreadyAnswered
to false. -
ModelManager#isCardAlreadyAnswered()
- returns true if the current card has already been answered and false otherwise.
-
-
Overall Design Considerations
Aspect: Usage of an extra card variable to keep track of the current card in test session
-
Alternative 1 (current choice): Introduce another variable,
currentTestedCard
, to store the card to display in the test session.-
Pros: More reader friendly. Save time from accessing the list to get card at that index.
-
Cons: Extra space used.
-
-
Alternative 2: No introduction of
currentTestedCard
as using thecurrentTestedCardIndex
suffices. Every time a card is needed, can simply reference it usingcurrentTestedCardFolder#getIndex(currentTestedCardIndex)
.-
Pros: No need to store an extra variable so this method uses less space.
-
Cons: Not so reader friendly. Need to keep accessing the list using the index which can potentially lead to possible violation of the Law of Demeter where an object should only interact with objects that are closely related to it.
-
Evaluation:
We went with Alternative 1 since not a large amount of memory is taken up with just 1 extra card stored. As there will
be several references to the currentTestedCard
, it will be better to store them somewhere. Abiding by the Law
of Demeter, currentTestedCard
object will not be interacting with currentTestedCardFolder
, limiting its
knowledge of that object which is encouraged according to the Principle of Least Knowledge.
Test / End Command
Current Implementation
Model
The main logic for test
and end
command is carried out in ModelManager
with the following methods:
-
ModelManager#startTestSession()
- begins a test session on the current card folder user is in and implicitly sorts the cards in it. -
ModelManager#endTestSession()
- ends the current test session.
UI
To update the change in the UI to reflect that the user is a test session (app goes to full screen with question of the current card presented), the following methods are introduced.
-
MainWindow#handleStartTestSession(Card card)
- creates a newTestSession
page with the card specified and bring the page forward in front of the currentCardMainScreen
page. -
MainWindow#handleEndTestSession()
- deletes the currentTestSession
page and theCardMainScreen
page at the back is now presented to the user.
Example Usage of test command
To illustrate how the UI
, Model
and Logic
components interact, below is a walkthrough of a typical usage scenario of
the test command.
Component interactions for a test command is a sequence diagram that summarises Model
and Logic
interactions, namely steps 1 to 7.
Step 1. User is inside a folder and wants to begin a test session on the current folder by executing the command
test
.
Step 2. As with every command, the command parser reads the input and generates the relevant Command
object, in
this case a TestCommand
. The object is returned to the LogicManager
.
Step 3. The LogicManager
executes the TestCommand
, storing the result and then transferring control to the
Model component, with Model#getState()
to check that user is inside a folder and is not already in a test session.
(This is omitted from Component interactions for a test command for simplicity.)
If the user is not inside a folder, this test command would be rendered invalid. Step 4 would not proceed and an error message is displayed. |
Step 4. After checking user is in a folder, ModelManager#startTestSession()
method is invoked, which
does the following:
-
currentTestedCardFolder
is set to the current folder the user is in, by invokinggetCardList()
from the activeVersionedCardFolder
infolders
.If this folder is empty such that there is no card to present to the user, an EmptyCardFolderException
is thrown, to be caught inTestCommand
, which then throws aCommandException
to display an error message. -
The cards in this folder are sorted in ascending scores by invoking
sortFilteredCard(comparator)
, so that lowest score cards will be presented first to the user in a test session. -
ModelManager#setCurrentTestedCard(currentTestedCardIndex)
is then invoked to setcurrentTestedCard
to the first card in the folder ascurrentTestedCardIndex
is set to 0. -
state
inModel
is set toIN_TEST
to specify that user is in a test session from now onwards. -
No change to
cardAlreadyAnswered
as it is by default false.
Step 5. For TestCommand
to obtain the first card to present in the test session,
ModelManager#getCurrentTestedCard()
is invoked and the Card
, c
, is returned.
Step 6. With control now transferred back to the logic unit, TestCommand
creates a CommandResult
object, r
with the type START_TEST_SESSION
, and
set testSessionCard
in CommandResult
to c
obtained in Step 5.
Step 7. r
is returned to LogicManager
which then terminates and returns r
to the caller method.
Step 8. The caller method here is in MainWindow
. Control is now transferred to the UI component.
Step 9. MainWindow
sees that CommandResult
object r
has the type START_TEST_SESSION
. It invokes
MainWindow#handleStartTestSession(currentTestedCard)
to display the currentTestedCard
question and hints to the
user.
Design Considerations
Aspect: Way to execute a test/end command
-
Alternative 1 (current choice):
test
is executed when inside a folder. The user does not have to specify the folder index andtest
would just immediately display the first card in this current folder.-
Pros: The most logical way of carrying out a test session is when the user is in the folder that he or she wants to be tested on. Lesser dependency on entering and exiting folder methods.
-
Cons: Requires the extra step of entering the folder before it can test the folder. User may actually see the questions before the test session.
-
-
Alternative 2:
test
is executed when outside a folder, in the home directory. Test command would require a folder index, e.gtest 1
to test the first folder. Implementation of getting the card from the folder would rely on enter folder command as well.-
Pros: Fast way to enter test session from home directory
-
Cons: Not logical for
test
to be called from inside the home directory which should only allow folder operations.test
will then have to implicitly enter the folder to gain access to the cards in it in order to display them, creating a dependency between the test and enter folder commands. Similar issue will arise for the end test session command where user will need to implicitly exit the folder.
-
Evaluation: Overall, Alternative 1 is a better choice following the Single Level of Abstraction Principle(SLAP) where a function should not mix different levels of abstractions. We can then better achieve higher cohesion and lower coupling. Also, user being able to see the questions before the test session is not a big issue since the answer will not be shown unless user selects the card.
Use Cases
UC01 Test flashcards
MSS
-
Student is inside a folder and begins a test session.
-
System presents the question on the lowest-performing flashcard first.
-
Student inputs his/her answer.
-
System indicates whether student’s answer is correct or wrong and shows the answer of the flashcard.
-
Student navigates to next flashcard.
-
Repeat steps 2-4 until all the flashcards in the folder are tested.
Use case ends
Extensions
-
3a. Student doesn’t know the answer and wants to see the answer without attempting.
-
3a1. Student uses the reveal command.
-
3a2. Answer is displayed to the student.
-
Starting and ending a test session
-
Start a test session while inside a folder
-
Prerequisites: Enter a folder using the
cd
command. For example,cd 1
will enter the first folder. All the cards in the folder are listed. -
Test case:
test
Expected: Enters a test session, where the display area enters a fullscreen and the lowest scoring flashcard question and hints (if any) will be displayed first.In Test Session
is shown on the status message and status bar. -
Test case:
test
on an empty folder (this folder has no cards)
Expected: The errorThis command is not valid on an empty folder
is shown in the status message. Status bar remains the same (still in folder). -
Test case:
test
when not inside a folder (prerequisite not fulfilled, like being in the home directory, already in a test session or in report display)
Expected: The errorCommand can only be executed in folder
is shown in the status message. Status bar remains the same.
-
-
Ends a current test session
-
Prerequisites: Enter a test session by typing
test
when inside a folder. Display area enters fullscreen and lowest scoring flashcard question and hints are displayed. Tester can also be in any state in the test session -
Test case:
end
Expected: Ends the current test session, where the display area exits fullscreen and be back inside the folder.End Test Session
is shown on the status message and status bar shows that tester is back inside the folder. -
Test case:
end
when not inside a test or report (prerequisite not fulfilled, like being in the home directory or in a folder)
Expected: The errorThis command is not valid outside a test or report
is shown in the status message. Status bar remains the same.
-