queue: Update design for queues

Signed-off-by: Anna Schumaker <anna@ocarinaproject.net>
This commit is contained in:
Anna Schumaker 2014-04-01 20:11:57 -04:00 committed by Anna Schumaker
parent a14f6145a5
commit 57fa16d289
1 changed files with 142 additions and 143 deletions

285
DESIGN
View File

@ -857,6 +857,148 @@ Track Tag:
Queue:
Queues are lists of songs that the user has requested to play. They
are the main interface for all music played by Ocarina.
- Flags:
enum queue_flag {
Q_ENABLED (1 << 0),
Q_RANDOM (1 << 1),
Q_REPEAT (1 << 2),
Q_NO_SORT (1 << 3),
};
- Sort info:
struct sort_info {
sort_t field;
bool ascending;
};
- Sorting:
Sorting is done using std::stable_sort() to make sure that orders won't
change unexpectedly. The default sort order is (SORT_ARTIST, true),
(SORT_YEAR, true), (SORT_TRACK, true).
- Queue:
class Queue {
private:
vector<Track *> _tracks;
list<sort_t> _sort_order;
unsigned int _cur;
unsigned int _flags;
unsigned int _length;
public:
Queue(unsigned int);
void read(File &);
void write(File &);
void set_flag(queue_flag);
void unset_flag(queue_flag);
bool has_flag(queue_flag);
unsigned int add(Track *);
void del(Track *);
void del(unsigned int);
void updated(Track *);
unsigned int size();
const std::string size_str();
const std::string length_str();
void sort(sort_t, bool, bool);
Track *next();
void track_selected(unsigned int);
};
File Format:
File << flags << tracks.size() << tracks[0] << tracks[1] << ... << tracks[N];
- API
Queue :: Queue(unsigned int flags);
Initialize a new queue with the appropriate flags set and with
default sorting.
Set _length = 0, _cur = 0.
void Queue :: read(File &f);
Read queue from file.
void Queue :: write(File &f);
Write queue to file.
void Queue :: set_flag(queue_flag f);
Set the appropriate flag.
void Queue :: unset_flag(queue_flag f);
Unset the appropriate flag.
bool Queue :: has_flag(queue_flag f);
Return true if the queue has the flag enabled and false
otherwise.
unsigned int Queue :: add(Track *track);
Add a new track to the tracks vector and return the index.
Increase length by the length of the track.
void Queue :: del(Track *track);
Remove all instances of the requested track from the queue.
void Queue :: del(unsigned int queue_id);
Remove the track at the given index from the queue.
void Queue :: updated(Track *track);
Find all indexes of the updated track and notify the UI that
it has changed.
unsigned int Queue :: size();
Return the number of tracks currently on the queue.
const std::string Queue :: size_str();
Return the number of tracks currently on the queue, in string
form.
const std::string Queue :: length_str();
Return the remaining length of the queue in a human-readable
format.
void Queue :: sort(sort_t field, bool ascending, bool reset);
Add a new sort field to the end of the sort order, then
resort the queue. If reset is set to true, clear the sorting
list before appending.
Track *Queue :: next();
Return the next track to play.
if (tracks.size() == 0)
return NULL;
if (flags & PL_RANDOM):
_cur += rand() % tracks.size();
else:
_cur += 1;
if (_cur >= tracks.size())
_cur -= tracks.size();
track = tracks[_cur];
if (!(flags & PL_REPEAT)):
del(_cur);
return track;
void Queue :: track_selected(unsigned int queue_id);
Set _cur to queue_id. If PQ_REPEAT is not set, remove the
track from the queue.
Library: (lib/library.cpp)
The library manages databases containing track information added by the
user. Ocarina 6 splits the library into multiple database tables for
@ -1002,149 +1144,6 @@ Playlists: (lib/playlist.cpp)
Playqueue: (lib/playqueue.cpp)
Playqueues are a list of songs that the user has requested to play.
- Flags:
enum playqueue_flags {
PQ_ENABLED (1 << 0),
PQ_RANDOM (1 << 1),
PQ_REPEAT (1 << 2),
};
- Sort order:
enum sort_t {
SORT_ARTIST_ASC = 1,
SORT_ARTIST_DESC = 2,
SORT_ALBUM_ASC = 3,
SORT_ALBUM_DESC = 4,
SORT_COUNT_ASC = 5,
SORT_COUNT_DESC = 6,
SORT_GENRE_ASC = 7,
SORT_GENRE_DESC = 8,
SORT_LENGTH_ASC = 9,
SORT_LENGTH_DESC = 10,
SORT_PLAYED_ASC = 11,
SORT_PLAYED_DESC = 12,
SORT_TITLE_ASC = 13,
SORT_TITLE_DESC = 14,
SORT_TRACK_ASC = 15,
SORT_TRACK_DESC = 16,
SORT_YEAR_ASC = 17,
SORT_YEAR_DESC = 18,
};
- Playqueue:
class Playqueue {
private:
vector<track_id> tracks;
list<sort_t> sort_order; /* default = { SORT_ARTIST_ASC,
SORT_YEAR_ASC,
SORT_TRACK_ASC };
unsigned int cur;
unsigned int flags;
unsigned int length;
public:
Playqueue(flags);
void write(File &);
void read(File &);
void set_flag(playqueue_flags);
void unset_flag(playqueue_flags);
const unsigned int get_flags();
string get_length();
unsigned int add(track_id);
unsigned int add_front(track_id);
void del(playqueue_id);
unsigned int size();
void reset_sort();
void add_sort(sort_t, bool);
void sort();
unsigned int next();
void reset_cur();
}
File << flags << tracks.size() << tracks[0] << tracks[1] << ... << tracks[N];
- API
Playqueue :: Playlist(unsigned int flags);
Create a new playqueue with the appropriate flags set.
sort_order = { (SORT_ARTIST, true), (SORT_YEAR, true),
(SORT_TRACK, true) };
unsigned int Playqueue :: add(unsigned int track_id);
unsigned int Playqueue :: add_front(unsigned int track_id);
Add a new track to the tracks vector and return the index. If
add_front is called, the track will be added to the front of
the playqueue (index = 0).
length += track.length.
void Playqueue :: del(unsigned int playqueue_id);
Erase tracks[playqueue_id] from the tracks vector.
length -= track.length.
void Playqueue :: del_track(unsigned int track_id);
Erase all tracks with track id track_id.
void Playqueue :: set_flag(playqueue_flags flag);
void Playqueue :: unset_flag(playqueue_flags flag);
Set or unset the given flag.
const unsigned int Playqueue :: get_flags();
Return the currently enabled flags.
song Playqueue :: get_length();
Convert the length variable into a string and return the result
to the caller.
unsigned int Playqueue :: size();
Return tracks.size();
void Playqueue :: write(File &);
void Playqueue :: read(File &);
Read or write the playqueue to the file.
void Playqueue :: reset_sort();
Reset the sort_order list to empty.
void Playqueue :: add_sort(sort_t type, bool ascending);
Add a new term to the sort order.
void Playqueue :: sort();
Perform a stable sort on the entire playqueue. Compare tracks
based on the sort_order list.
unsigned int Playqueue :: next();
Return the next track_id to play.
if (tracks.size() == 0)
throw -EEXIST;
if (flags & PL_RANDOM):
cur += rand() % tracks.size();
else:
cur += 1;
if (cur > = tracks.size())
cur -= tracks.size();
track = tracks[cur];
if (!(flags & PL_REPEAT)):
length -= track.length;
tracks.erase(cur);
return track;
void Playqueue :: reset_cur();
This function is intended to be used by the audio layer when
managing the recently played playqueue.
cur = 0;
Deck: (lib/deck.cpp)
The playqueue deck is used to hold the temporary playqueues created by
the user.