library: Find tags for each track
This is each song's track number, play count, and anything else specific to a single file. After updating, save all the changed databases. Signed-off-by: Anna Schumaker <schumaker.anna@gmail.com>
This commit is contained in:
parent
846810fa2f
commit
e314248f10
|
@ -35,10 +35,11 @@ Library: (lib/library.cpp)
|
||||||
class library :: Album : public DatabaseEntry {
|
class library :: Album : public DatabaseEntry {
|
||||||
public:
|
public:
|
||||||
string name;
|
string name;
|
||||||
short year;
|
unsigned int year;
|
||||||
|
unsigned int artist_id;
|
||||||
};
|
};
|
||||||
|
|
||||||
File << year << name
|
File << artist_id << year << name
|
||||||
|
|
||||||
- Artist:
|
- Artist:
|
||||||
class library :: Artist : public DatabaseEntry {
|
class library :: Artist : public DatabaseEntry {
|
||||||
|
@ -68,15 +69,15 @@ Library: (lib/library.cpp)
|
||||||
- Track:
|
- Track:
|
||||||
class library :: Track : public DatabaseEntry {
|
class library :: Track : public DatabaseEntry {
|
||||||
public:
|
public:
|
||||||
|
unsigned int library_id;
|
||||||
unsigned int artist_id;
|
unsigned int artist_id;
|
||||||
unsigned int album_id;
|
unsigned int album_id;
|
||||||
unsigned int genre_id;
|
unsigned int genre_id;
|
||||||
unsigned int library_id;
|
|
||||||
|
|
||||||
short track;
|
unsigned int track;
|
||||||
short last_year;
|
unsigned int last_year;
|
||||||
short last_month;
|
unsigned int last_month;
|
||||||
short last_day;
|
unsigned int last_day;
|
||||||
unsigned int play_count;
|
unsigned int play_count;
|
||||||
unsigned int length;
|
unsigned int length;
|
||||||
|
|
||||||
|
@ -86,8 +87,8 @@ Library: (lib/library.cpp)
|
||||||
string filepath;
|
string filepath;
|
||||||
};
|
};
|
||||||
|
|
||||||
File << artist_id << album_id << genre_id << library_id << track << last_year
|
File << library_id << artist_id << album_id << genre_id << track << last_year
|
||||||
File << last_year << last_month << last_day << play_count << length << banned << endl
|
File << last_month << last_day << play_count << length << banned << endl
|
||||||
File << title << endl;
|
File << title << endl;
|
||||||
File << filepath << endl;
|
File << filepath << endl;
|
||||||
|
|
||||||
|
@ -158,4 +159,7 @@ Library: (lib/library.cpp)
|
||||||
#ifdef CONFIG_DEBUG
|
#ifdef CONFIG_DEBUG
|
||||||
void library :: print_db(DB_Type);
|
void library :: print_db(DB_Type);
|
||||||
Print the database corresponding to DB_Type
|
Print the database corresponding to DB_Type
|
||||||
|
|
||||||
|
void library :: reset();
|
||||||
|
Clear all databases, returning the library to an empty state.
|
||||||
endif /* CONFIG_DEBUG */
|
endif /* CONFIG_DEBUG */
|
||||||
|
|
|
@ -8,6 +8,7 @@
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|
||||||
#include <taglib/tag.h>
|
#include <taglib/tag.h>
|
||||||
|
#include <taglib/fileref.h>
|
||||||
|
|
||||||
namespace library
|
namespace library
|
||||||
{
|
{
|
||||||
|
@ -84,6 +85,38 @@ namespace library
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
class Track : public DatabaseEntry {
|
||||||
|
public:
|
||||||
|
unsigned int library_id;
|
||||||
|
unsigned int artist_id;
|
||||||
|
unsigned int album_id;
|
||||||
|
unsigned int genre_id;
|
||||||
|
|
||||||
|
unsigned int track;
|
||||||
|
unsigned int last_year;
|
||||||
|
unsigned int last_month;
|
||||||
|
unsigned int last_day;
|
||||||
|
unsigned int play_count;
|
||||||
|
unsigned int length;
|
||||||
|
|
||||||
|
bool banned;
|
||||||
|
std :: string title;
|
||||||
|
std :: string length_str;
|
||||||
|
std :: string filepath;
|
||||||
|
|
||||||
|
Track();
|
||||||
|
Track(TagLib :: Tag *, TagLib :: AudioProperties *,
|
||||||
|
unsigned int, unsigned int, unsigned int,
|
||||||
|
unsigned int, const std :: string &);
|
||||||
|
void read(File &);
|
||||||
|
void write(File &);
|
||||||
|
#ifdef CONFIG_DEBUG
|
||||||
|
void print();
|
||||||
|
#endif /* CONFIG_DEBUG */
|
||||||
|
bool operator==(const Track &);
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
void init();
|
void init();
|
||||||
bool add_path(const std::string &);
|
bool add_path(const std::string &);
|
||||||
void del_path(unsigned int);
|
void del_path(unsigned int);
|
||||||
|
|
|
@ -4,12 +4,12 @@
|
||||||
#include <library.h>
|
#include <library.h>
|
||||||
|
|
||||||
#include <glib.h>
|
#include <glib.h>
|
||||||
#include <taglib/fileref.h>
|
|
||||||
|
|
||||||
static Database<library :: Artist> artist_db("artist.db", DB_UNIQUE);
|
static Database<library :: Artist> artist_db("artist.db", DB_UNIQUE);
|
||||||
static Database<library :: Album> album_db("album.db", DB_UNIQUE);
|
static Database<library :: Album> album_db("album.db", DB_UNIQUE);
|
||||||
static Database<library :: Genre> genre_db("genre.db", DB_UNIQUE);
|
static Database<library :: Genre> genre_db("genre.db", DB_UNIQUE);
|
||||||
static Database<library :: Library> library_db("library.db", DB_NORMAL);
|
static Database<library :: Library> library_db("library.db", DB_NORMAL);
|
||||||
|
static Database<library :: Track> track_db("track.db", DB_UNIQUE);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@ -174,6 +174,67 @@ bool library :: Library :: operator==(library :: Library &rhs)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* library :: Track: Track tag information
|
||||||
|
*/
|
||||||
|
|
||||||
|
library :: Track :: Track()
|
||||||
|
: library_id(0), artist_id(0), album_id(0), genre_id(0)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
library :: Track :: Track(TagLib :: Tag *tag, TagLib :: AudioProperties *audio,
|
||||||
|
unsigned int lib, unsigned int artist, unsigned int album,
|
||||||
|
unsigned int genre, const std :: string &path)
|
||||||
|
: library_id(lib), artist_id(artist), album_id(album), genre_id(genre),
|
||||||
|
track(tag->track()), last_year(0), last_month(0), last_day(0),
|
||||||
|
play_count(0), length(audio->length()), banned(false),
|
||||||
|
title(tag->title().to8Bit(true))
|
||||||
|
{
|
||||||
|
filepath = path.substr(library_db[library_id].root_path.size() + 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
void library :: Track :: read(File &f)
|
||||||
|
{
|
||||||
|
f >> library_id >> artist_id >> album_id >> genre_id;
|
||||||
|
f >> track >> last_year >> last_month >> last_day;
|
||||||
|
f >> play_count >> length >> banned;
|
||||||
|
title = f.getline();
|
||||||
|
filepath = f.getline();
|
||||||
|
}
|
||||||
|
|
||||||
|
void library :: Track :: write(File &f)
|
||||||
|
{
|
||||||
|
f << library_id << " " << artist_id << " " << album_id << " " << genre_id;
|
||||||
|
f << " " << track << " " << last_year << " " << last_month << " " << last_day;
|
||||||
|
f << " " << play_count << " " << length << " " << banned << std :: endl;
|
||||||
|
f << title << std :: endl;
|
||||||
|
f << filepath;
|
||||||
|
}
|
||||||
|
|
||||||
|
#ifdef CONFIG_DEBUG
|
||||||
|
void library :: Track :: print()
|
||||||
|
{
|
||||||
|
:: print("%u. %s by %s from %s (%u)\n", track, title.c_str(),
|
||||||
|
artist_db[artist_id].name.c_str(),
|
||||||
|
album_db[album_id].name.c_str(), album_db[album_id].year);
|
||||||
|
:: print(" Genre: %s, Length: %u (seconds)\n",
|
||||||
|
genre_db[genre_id].name.c_str(), length);
|
||||||
|
:: print(" Play count: %u, last played %u/%u/%u\n", play_count,
|
||||||
|
last_day, last_month, last_year);
|
||||||
|
:: print(" %s", filepath.c_str());
|
||||||
|
}
|
||||||
|
#endif /* CONFIG_DEBUG */
|
||||||
|
|
||||||
|
bool library :: Track :: operator==(const library :: Track &rhs)
|
||||||
|
{
|
||||||
|
if (library_id == rhs.library_id)
|
||||||
|
return filepath == rhs.filepath;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Internal library functions
|
* Internal library functions
|
||||||
*/
|
*/
|
||||||
|
@ -182,8 +243,9 @@ static void do_update(unsigned int, const std :: string &);
|
||||||
static void read_tags(unsigned int lib_id, const std :: string &path)
|
static void read_tags(unsigned int lib_id, const std :: string &path)
|
||||||
{
|
{
|
||||||
TagLib :: Tag *tag;
|
TagLib :: Tag *tag;
|
||||||
TagLib :: FileRef ref(path.c_str());
|
TagLib :: AudioProperties *audio;
|
||||||
unsigned int artist_id;
|
TagLib :: FileRef ref(path.c_str(), true, TagLib :: AudioProperties :: Fast);
|
||||||
|
unsigned int artist_id, album_id, genre_id;
|
||||||
|
|
||||||
if (ref.isNull()) {
|
if (ref.isNull()) {
|
||||||
print("ERROR: Could not read tags for file %s", path.c_str());
|
print("ERROR: Could not read tags for file %s", path.c_str());
|
||||||
|
@ -191,9 +253,13 @@ static void read_tags(unsigned int lib_id, const std :: string &path)
|
||||||
}
|
}
|
||||||
|
|
||||||
tag = ref.tag();
|
tag = ref.tag();
|
||||||
|
audio = ref.audioProperties();
|
||||||
|
|
||||||
artist_id = artist_db.insert(tag);
|
artist_id = artist_db.insert(tag);
|
||||||
album_db.insert(library :: Album(tag, artist_id));
|
album_id = album_db.insert(library :: Album(tag, artist_id));
|
||||||
genre_db.insert(library :: Genre(tag));
|
genre_id = genre_db.insert(library :: Genre(tag));
|
||||||
|
track_db.insert(library :: Track(tag, audio, lib_id, artist_id,
|
||||||
|
album_id, genre_id, path));
|
||||||
}
|
}
|
||||||
|
|
||||||
static void process_path(unsigned int lib_id, const std :: string &dir,
|
static void process_path(unsigned int lib_id, const std :: string &dir,
|
||||||
|
@ -207,6 +273,14 @@ static void process_path(unsigned int lib_id, const std :: string &dir,
|
||||||
read_tags(lib_id, path);
|
read_tags(lib_id, path);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void save_all_dbs()
|
||||||
|
{
|
||||||
|
artist_db.save();
|
||||||
|
album_db.save();
|
||||||
|
genre_db.save();
|
||||||
|
track_db.save();
|
||||||
|
}
|
||||||
|
|
||||||
static void do_update(unsigned int lib_id, const std :: string &path)
|
static void do_update(unsigned int lib_id, const std :: string &path)
|
||||||
{
|
{
|
||||||
GDir *dir;
|
GDir *dir;
|
||||||
|
@ -219,6 +293,7 @@ static void do_update(unsigned int lib_id, const std :: string &path)
|
||||||
name = g_dir_read_name(dir);
|
name = g_dir_read_name(dir);
|
||||||
while (name != NULL) {
|
while (name != NULL) {
|
||||||
process_path(lib_id, path, name);
|
process_path(lib_id, path, name);
|
||||||
|
save_all_dbs();
|
||||||
name = g_dir_read_name(dir);
|
name = g_dir_read_name(dir);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -277,8 +352,8 @@ void library :: print_db(DB_Type type)
|
||||||
case DB_LIBRARY:
|
case DB_LIBRARY:
|
||||||
library_db.print();
|
library_db.print();
|
||||||
break;
|
break;
|
||||||
default:
|
case DB_TRACK:
|
||||||
break;
|
track_db.print();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -288,5 +363,6 @@ void library :: reset()
|
||||||
artist_db.clear();
|
artist_db.clear();
|
||||||
genre_db.clear();
|
genre_db.clear();
|
||||||
library_db.clear();
|
library_db.clear();
|
||||||
|
track_db.clear();
|
||||||
}
|
}
|
||||||
#endif /* CONFIG_DEBUG */
|
#endif /* CONFIG_DEBUG */
|
||||||
|
|
|
@ -44,7 +44,7 @@ function gen_tracks()
|
||||||
|
|
||||||
vorbiscomment -a -q -t "ARTIST=$artist" -t "ALBUM=$album" \
|
vorbiscomment -a -q -t "ARTIST=$artist" -t "ALBUM=$album" \
|
||||||
-t "GENRE=${genres[$album]}" -t "DATE=${dates[$album]}" \
|
-t "GENRE=${genres[$album]}" -t "DATE=${dates[$album]}" \
|
||||||
-t "TRACK=$i" -t "TITLE=$track" "tests/library/$OGG" \
|
-t "TRACKNUMBER=$i" -t "TITLE=$track" "tests/library/$OGG" \
|
||||||
"/tmp/$library/$artist/$album/$i - $track.ogg"
|
"/tmp/$library/$artist/$album/$i - $track.ogg"
|
||||||
done
|
done
|
||||||
}
|
}
|
||||||
|
|
|
@ -95,6 +95,8 @@ void test_4()
|
||||||
library :: print_db(library :: DB_ALBUM);
|
library :: print_db(library :: DB_ALBUM);
|
||||||
print("\n");
|
print("\n");
|
||||||
library :: print_db(library :: DB_GENRE);
|
library :: print_db(library :: DB_GENRE);
|
||||||
|
print("\n");
|
||||||
|
library :: print_db(library :: DB_TRACK);
|
||||||
}
|
}
|
||||||
|
|
||||||
int main(int argc, char **argv)
|
int main(int argc, char **argv)
|
||||||
|
|
Loading…
Reference in New Issue
Block a user