From 0e1e3c6342e4b513b4596f6df8e6a8b62ebce1c3 Mon Sep 17 00:00:00 2001 From: unK Date: Tue, 9 Sep 2008 16:49:22 +0200 Subject: [PATCH] a lot of code clean-ups, remove song info screen --- src/Makefile.am | 8 +- src/helpers.cpp | 317 +---------------------------------------- src/helpers.h | 19 +-- src/lyrics.cpp | 2 +- src/misc.h | 3 +- src/mpdpp.h | 1 + src/ncmpcpp.cpp | 234 ++++++++++++++++-------------- src/ncmpcpp.h | 31 ++-- src/search_engine.cpp | 195 +++++++++++++++++++++++++ src/search_engine.h | 32 +++++ src/song.cpp | 29 +--- src/song.h | 3 +- src/status_checker.cpp | 45 +++--- src/status_checker.h | 2 +- src/tag_editor.cpp | 138 ++++++++++++++++++ src/tag_editor.h | 45 ++++++ 16 files changed, 604 insertions(+), 500 deletions(-) create mode 100644 src/search_engine.cpp create mode 100644 src/search_engine.h create mode 100644 src/tag_editor.cpp create mode 100644 src/tag_editor.h diff --git a/src/Makefile.am b/src/Makefile.am index e0cbb217..274c399c 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -1,12 +1,12 @@ bin_PROGRAMS = ncmpcpp ncmpcpp_SOURCES = color_parser.cpp helpers.cpp libmpdclient.c lyrics.cpp \ - menu.cpp misc.cpp mpdpp.cpp ncmpcpp.cpp scrollpad.cpp settings.cpp song.cpp \ - status_checker.cpp window.cpp + menu.cpp misc.cpp mpdpp.cpp ncmpcpp.cpp scrollpad.cpp search_engine.cpp \ + settings.cpp song.cpp status_checker.cpp tag_editor.cpp window.cpp # set the include path found by configure INCLUDES= $(all_includes) # the library search path. ncmpcpp_LDFLAGS = $(all_libraries) -noinst_HEADERS = helpers.h lyrics.h menu.h mpdpp.h scrollpad.h settings.h \ - song.h status_checker.h window.h +noinst_HEADERS = helpers.h lyrics.h menu.h mpdpp.h scrollpad.h search_engine.h \ + settings.h song.h status_checker.h tag_editor.h window.h diff --git a/src/helpers.cpp b/src/helpers.cpp index 80de044f..43cfd6fe 100644 --- a/src/helpers.cpp +++ b/src/helpers.cpp @@ -18,8 +18,8 @@ * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * ***************************************************************************/ +#include #include "helpers.h" -#include "settings.h" extern MPDConnection *Mpd; @@ -27,21 +27,14 @@ extern ncmpcpp_config Config; extern Menu *mPlaylist; extern Menu *mBrowser; -extern Menu *mTagEditor; -extern Menu *mSearcher; -extern Menu *mPlaylistEditor; - extern Window *wFooter; extern NcmpcppScreen current_screen; -extern Song edited_song; -extern Song searched_song; - -extern int block_statusbar_update_delay; +extern int lock_statusbar_delay; extern int browsed_dir_scroll_begin; -extern time_t block_delay; +extern time_t time_of_statusbar_lock; extern string browsed_dir; @@ -50,9 +43,9 @@ extern bool block_progressbar_update; extern bool block_statusbar_update; extern bool search_case_sensitive; -extern bool search_mode_match; +extern bool search_match_to_pattern; -extern bool redraw_me; +extern bool redraw_screen; extern string EMPTY_TAG; extern string UNKNOWN_ARTIST; @@ -61,8 +54,6 @@ extern string UNKNOWN_ALBUM; bool CaseInsensitiveSorting::operator()(string a, string b) { - //a = Window::OmitBBCodes(a); - //b = Window::OmitBBCodes(b); transform(a.begin(), a.end(), a.begin(), tolower); transform(b.begin(), b.end(), b.begin(), tolower); return a < b; @@ -132,25 +123,6 @@ void UpdateSongList(Menu *menu) menu->Refresh(); } -void UpdateFoundList(const SongList &v) -{ - int i = search_engine_static_option; - bool bold = 0; - for (SongList::const_iterator it = v.begin(); it != v.end(); it++, i++) - { - for (int j = 0; j < mPlaylist->Size(); j++) - { - if (mPlaylist->at(j).GetHash() == (*it)->GetHash()) - { - bold = 1; - break; - } - } - mSearcher->BoldOption(i, bold); - bold = 0; - } -} - string DisplayKeys(int *key, int size) { bool backspace = 1; @@ -225,33 +197,6 @@ void WindowTitle(const string &status) printf("\033]0;%s\7",status.c_str()); } -string FindSharedDir(Menu *menu) -{ - SongList list; - for (int i = 0; i < menu->Size(); i++) - list.push_back(&menu->at(i)); - return FindSharedDir(list); -} - -string FindSharedDir(const SongList &v) -{ - string result; - if (!v.empty()) - { - result = v.front()->GetFile(); - for (SongList::const_iterator it = v.begin()+1; it != v.end(); it++) - { - int i = 1; - while (result.substr(0, i) == (*it)->GetFile().substr(0, i)) - i++; - result = result.substr(0, i); - } - int slash = result.find_last_of("/"); - result = slash != string::npos ? result.substr(0, slash) : "/"; - } - return result; -} - string TotalPlaylistLength() { const int MINUTE = 60; @@ -305,31 +250,6 @@ string TotalPlaylistLength() return result; } -string DisplayTag(const Song &s, void *data) -{ - switch (static_cast *>(data)->GetChoice()) - { - case 0: - return s.GetTitle(); - case 1: - return s.GetArtist(); - case 2: - return s.GetAlbum(); - case 3: - return s.GetYear(); - case 4: - return s.GetTrack(); - case 5: - return s.GetGenre(); - case 6: - return s.GetComment(); - case 8: - return s.GetShortFilename(); - default: - return ""; - } -} - string DisplayItem(const Item &item, void *) { switch (item.type) @@ -773,158 +693,12 @@ string DisplaySong(const Song &s, void *s_template) return result; } -void PrepareSearchEngine(Song &s) -{ - s.Clear(); - mSearcher->Clear(); - mSearcher->Reset(); - mSearcher->AddOption("[.b]Filename:[/b] " + s.GetShortFilename()); - mSearcher->AddOption("[.b]Title:[/b] " + s.GetTitle()); - mSearcher->AddOption("[.b]Artist:[/b] " + s.GetArtist()); - mSearcher->AddOption("[.b]Album:[/b] " + s.GetAlbum()); - mSearcher->AddOption("[.b]Year:[/b] " + s.GetYear()); - mSearcher->AddOption("[.b]Track:[/b] " + s.GetTrack()); - mSearcher->AddOption("[.b]Genre:[/b] " + s.GetGenre()); - mSearcher->AddOption("[.b]Comment:[/b] " + s.GetComment()); - mSearcher->AddSeparator(); - mSearcher->AddOption("[.b]Search mode:[/b] " + (search_mode_match ? search_mode_one : search_mode_two)); - mSearcher->AddOption("[.b]Case sensitive:[/b] " + (string)(search_case_sensitive ? "Yes" : "No")); - mSearcher->AddSeparator(); - mSearcher->AddOption("Search"); - mSearcher->AddOption("Reset"); -} - -void Search(SongList &result, Song &s) -{ - FreeSongList(result); - - if (s.Empty()) - return; - - SongList list; - Mpd->GetDirectoryRecursive("/", list); - - bool found = 1; - - s.GetEmptyFields(1); - - if (!search_case_sensitive) - { - string t; - t = s.GetShortFilename(); - transform(t.begin(), t.end(), t.begin(), tolower); - s.SetShortFilename(t); - - t = s.GetTitle(); - transform(t.begin(), t.end(), t.begin(), tolower); - s.SetTitle(t); - - t = s.GetArtist(); - transform(t.begin(), t.end(), t.begin(), tolower); - s.SetArtist(t); - - t = s.GetAlbum(); - transform(t.begin(), t.end(), t.begin(), tolower); - s.SetAlbum(t); - - t = s.GetGenre(); - transform(t.begin(), t.end(), t.begin(), tolower); - s.SetGenre(t); - - t = s.GetComment(); - transform(t.begin(), t.end(), t.begin(), tolower); - s.SetComment(t); - } - - for (SongList::const_iterator it = list.begin(); it != list.end(); it++) - { - Song copy = **it; - - if (!search_case_sensitive) - { - string t; - t = copy.GetShortFilename(); - transform(t.begin(), t.end(), t.begin(), tolower); - copy.SetShortFilename(t); - - t = copy.GetTitle(); - transform(t.begin(), t.end(), t.begin(), tolower); - copy.SetTitle(t); - - t = copy.GetArtist(); - transform(t.begin(), t.end(), t.begin(), tolower); - copy.SetArtist(t); - - t = copy.GetAlbum(); - transform(t.begin(), t.end(), t.begin(), tolower); - copy.SetAlbum(t); - - t = copy.GetGenre(); - transform(t.begin(), t.end(), t.begin(), tolower); - copy.SetGenre(t); - - t = copy.GetComment(); - transform(t.begin(), t.end(), t.begin(), tolower); - copy.SetComment(t); - } - - if (search_mode_match) - { - if (found && !s.GetShortFilename().empty()) - found = copy.GetShortFilename().find(s.GetShortFilename()) != string::npos; - if (found && !s.GetTitle().empty()) - found = copy.GetTitle().find(s.GetTitle()) != string::npos; - if (found && !s.GetArtist().empty()) - found = copy.GetArtist().find(s.GetArtist()) != string::npos; - if (found && !s.GetAlbum().empty()) - found = copy.GetAlbum().find(s.GetAlbum()) != string::npos; - if (found && !s.GetYear().empty()) - found = StrToInt(copy.GetYear()) == StrToInt(s.GetYear()) && StrToInt(s.GetYear()); - if (found && !s.GetTrack().empty()) - found = StrToInt(copy.GetTrack()) == StrToInt(s.GetTrack()) && StrToInt(s.GetTrack()); - if (found && !s.GetGenre().empty()) - found = copy.GetGenre().find(s.GetGenre()) != string::npos; - if (found && !s.GetComment().empty()) - found = copy.GetComment().find(s.GetComment()) != string::npos; - } - else - { - if (found && !s.GetShortFilename().empty()) - found = copy.GetShortFilename() == s.GetShortFilename(); - if (found && !s.GetTitle().empty()) - found = copy.GetTitle() == s.GetTitle(); - if (found && !s.GetArtist().empty()) - found = copy.GetArtist() == s.GetArtist(); - if (found && !s.GetAlbum().empty()) - found = copy.GetAlbum() == s.GetAlbum(); - if (found && !s.GetYear().empty()) - found = StrToInt(copy.GetYear()) == StrToInt(s.GetYear()) && StrToInt(s.GetYear()); - if (found && !s.GetTrack().empty()) - found = StrToInt(copy.GetTrack()) == StrToInt(s.GetTrack()) && StrToInt(s.GetTrack()); - if (found && !s.GetGenre().empty()) - found = copy.GetGenre() == s.GetGenre(); - if (found && !s.GetComment().empty()) - found = copy.GetComment() == s.GetComment(); - } - - if (found) - { - Song *ss = new Song(**it); - result.push_back(ss); - } - - found = 1; - } - FreeSongList(list); - s.GetEmptyFields(0); -} - void ShowMessage(const string &message, int delay) { if (messages_allowed) { - block_delay = time(NULL); - block_statusbar_update_delay = delay; + time_of_statusbar_lock = time(NULL); + lock_statusbar_delay = delay; if (Config.statusbar_visibility) block_statusbar_update = 1; else @@ -935,83 +709,6 @@ void ShowMessage(const string &message, int delay) } } -#ifdef HAVE_TAGLIB_H -bool WriteTags(Song &s) -{ - string path_to_file = Config.mpd_music_dir + "/" + s.GetFile(); - TagLib::FileRef f(path_to_file.c_str()); - if (!f.isNull()) - { - s.GetEmptyFields(1); - f.tag()->setTitle(TO_WSTRING(s.GetTitle())); - f.tag()->setArtist(TO_WSTRING(s.GetArtist())); - f.tag()->setAlbum(TO_WSTRING(s.GetAlbum())); - f.tag()->setYear(StrToInt(s.GetYear())); - f.tag()->setTrack(StrToInt(s.GetTrack())); - f.tag()->setGenre(TO_WSTRING(s.GetGenre())); - f.tag()->setComment(TO_WSTRING(s.GetComment())); - s.GetEmptyFields(0); - f.save(); - return true; - } - else - return false; -} -#endif // HAVE_TAGLIB_H - -bool GetSongInfo(Song &s) -{ - string path_to_file = Config.mpd_music_dir + "/" + s.GetFile(); - -# ifdef HAVE_TAGLIB_H - TagLib::FileRef f(path_to_file.c_str()); - if (f.isNull()) - return false; - s.SetComment(f.tag()->comment().to8Bit(UNICODE)); -# endif - - mTagEditor->Clear(); - mTagEditor->Reset(); - - mTagEditor->AddStaticOption("[.b][.white]Song name: [/white][.green][/b]" + s.GetShortFilename() + "[/green]"); - mTagEditor->AddStaticOption("[.b][.white]Location in DB: [/white][.green][/b]" + s.GetDirectory() + "[/green]"); - mTagEditor->AddStaticOption(""); - mTagEditor->AddStaticOption("[.b][.white]Length: [/white][.green][/b]" + s.GetLength() + "[/green]"); -# ifdef HAVE_TAGLIB_H - mTagEditor->AddStaticOption("[.b][.white]Bitrate: [/white][.green][/b]" + IntoStr(f.audioProperties()->bitrate()) + " kbps[/green]"); - mTagEditor->AddStaticOption("[.b][.white]Sample rate: [/white][.green][/b]" + IntoStr(f.audioProperties()->sampleRate()) + " Hz[/green]"); - mTagEditor->AddStaticOption("[.b][.white]Channels: [/white][.green][/b]" + (string)(f.audioProperties()->channels() == 1 ? "Mono" : "Stereo") + "[/green]"); -# endif - - mTagEditor->AddSeparator(); - -# ifdef HAVE_TAGLIB_H - mTagEditor->AddOption("[.b]Title:[/b] " + s.GetTitle()); - mTagEditor->AddOption("[.b]Artist:[/b] " + s.GetArtist()); - mTagEditor->AddOption("[.b]Album:[/b] " + s.GetAlbum()); - mTagEditor->AddOption("[.b]Year:[/b] " + s.GetYear()); - mTagEditor->AddOption("[.b]Track:[/b] " + s.GetTrack()); - mTagEditor->AddOption("[.b]Genre:[/b] " + s.GetGenre()); - mTagEditor->AddOption("[.b]Comment:[/b] " + s.GetComment()); - mTagEditor->AddSeparator(); - mTagEditor->AddOption("Save"); - mTagEditor->AddOption("Cancel"); -# else - mTagEditor->AddStaticOption("[.b]Title:[/b] " + s.GetTitle()); - mTagEditor->AddStaticOption("[.b]Artist:[/b] " + s.GetArtist()); - mTagEditor->AddStaticOption("[.b]Album:[/b] " + s.GetAlbum()); - mTagEditor->AddStaticOption("[.b]Year:[/b] " + s.GetYear()); - mTagEditor->AddStaticOption("[.b]Track:[/b] " + s.GetTrack()); - mTagEditor->AddStaticOption("[.b]Genre:[/b] " + s.GetGenre()); - mTagEditor->AddStaticOption("[.b]Comment:[/b] " + s.GetComment()); - mTagEditor->AddSeparator(); - mTagEditor->AddOption("Back"); -# endif - - edited_song = s; - return true; -} - void GetDirectory(string dir, string subdir) { int highlightme = -1; diff --git a/src/helpers.h b/src/helpers.h index eca9981e..c381ac43 100644 --- a/src/helpers.h +++ b/src/helpers.h @@ -21,12 +21,9 @@ #ifndef HAVE_HELPERS_H #define HAVE_HELPERS_H -#include - -#include "ncmpcpp.h" #include "mpdpp.h" +#include "ncmpcpp.h" #include "settings.h" -#include "song.h" extern ncmpcpp_config Config; @@ -38,31 +35,23 @@ class CaseInsensitiveSorting bool operator()(const Item &, const Item &); }; +bool SortSongsByTrack(Song *, Song *); + void UpdateItemList(Menu *); void UpdateSongList(Menu *); -void UpdateFoundList(const SongList &); string DisplayKeys(int *, int = 2); bool Keypressed(int, const int *); -bool SortSongsByTrack(Song *, Song *); void WindowTitle(const string &); -string FindSharedDir(Menu *); -string FindSharedDir(const SongList &); + string TotalPlaylistLength(); -string DisplayTag(const Song &, void *); string DisplayItem(const Item &, void * = NULL); string DisplayColumns(string); string DisplaySongInColumns(const Song &, void *); string DisplaySong(const Song &, void * = &Config.song_list_format); void ShowMessage(const string &, int = Config.message_delay_time); void GetDirectory(string, string = "/"); -#ifdef HAVE_TAGLIB_H -bool WriteTags(Song &); -#endif -bool GetSongInfo(Song &); -void PrepareSearchEngine(Song &s); -void Search(SongList &, Song &); #endif diff --git a/src/lyrics.cpp b/src/lyrics.cpp index f1cad4d8..c15cbcf3 100644 --- a/src/lyrics.cpp +++ b/src/lyrics.cpp @@ -18,8 +18,8 @@ * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * ***************************************************************************/ -#include "lyrics.h" #include +#include "lyrics.h" const string lyrics_folder = home_folder + "/" + ".lyrics"; diff --git a/src/misc.h b/src/misc.h index 807de097..6ca72f1c 100644 --- a/src/misc.h +++ b/src/misc.h @@ -37,4 +37,5 @@ string IntoStr(double, int); string ShowTime(int); -#endif \ No newline at end of file +#endif + diff --git a/src/mpdpp.h b/src/mpdpp.h index ed754e98..fba6e84b 100644 --- a/src/mpdpp.h +++ b/src/mpdpp.h @@ -21,6 +21,7 @@ #ifndef HAVE_MPDPP_H #define HAVE_MPDPP_H +#include "libmpdclient.h" #include "ncmpcpp.h" #include "song.h" diff --git a/src/ncmpcpp.cpp b/src/ncmpcpp.cpp index 844b1bc9..34cfabe5 100644 --- a/src/ncmpcpp.cpp +++ b/src/ncmpcpp.cpp @@ -18,13 +18,16 @@ * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * ***************************************************************************/ -#include "ncmpcpp.h" #include "mpdpp.h" -#include "status_checker.h" +#include "ncmpcpp.h" + #include "helpers.h" +#include "lyrics.h" +#include "search_engine.h" #include "settings.h" #include "song.h" -#include "lyrics.h" +#include "status_checker.h" +#include "tag_editor.h" #define LOCK_STATUSBAR \ if (Config.statusbar_visibility) \ @@ -35,7 +38,7 @@ #define UNLOCK_STATUSBAR \ allow_statusbar_unblock = 1; \ - if (block_statusbar_update_delay < 0) \ + if (lock_statusbar_delay < 0) \ { \ if (Config.statusbar_visibility) \ block_statusbar_update = 0; \ @@ -44,31 +47,23 @@ } #define REFRESH_MEDIA_LIBRARY_SCREEN \ - mLibArtists->Display(redraw_me); \ + mLibArtists->Display(redraw_screen); \ mvvline(main_start_y, lib_albums_start_x-1, 0, main_height); \ - mLibAlbums->Display(redraw_me); \ + mLibAlbums->Display(redraw_screen); \ mvvline(main_start_y, lib_songs_start_x-1, 0, main_height); \ - mLibSongs->Display(redraw_me) + mLibSongs->Display(redraw_screen) #define REFRESH_PLAYLIST_EDITOR_SCREEN \ - mPlaylistList->Display(redraw_me); \ + mPlaylistList->Display(redraw_screen); \ mvvline(main_start_y, lib_albums_start_x-1, 0, main_height); \ - mPlaylistEditor->Display(redraw_me) + mPlaylistEditor->Display(redraw_screen) #define REFRESH_ALBUM_EDITOR_SCREEN \ - mEditorAlbums->Display(redraw_me); \ + mEditorAlbums->Display(redraw_screen); \ mvvline(main_start_y, lib_albums_start_x-1, 0, main_height); \ - mEditorTagTypes->Display(redraw_me); \ + mEditorTagTypes->Display(redraw_screen); \ mvvline(main_start_y, lib_songs_start_x-1, 0, main_height); \ - mEditorTags->Display(redraw_me) - -#ifdef HAVE_TAGLIB_H - const string tag_screen = "Tag editor"; - const string tag_screen_keydesc = "Edit song's tags/playlist's name\n"; -#else - const string tag_screen = "Tag info"; - const string tag_screen_keydesc = "Show song's tags/edit playlist's name\n"; -#endif + mEditorTags->Display(redraw_screen) ncmpcpp_config Config; ncmpcpp_keys Key; @@ -85,16 +80,18 @@ Window *wPrev = 0; Menu *mPlaylist; Menu *mBrowser; -Menu *mTagEditor; Menu *mSearcher; Menu *mLibArtists; Menu *mLibAlbums; Menu *mLibSongs; +#ifdef HAVE_TAGLIB_H +Menu *mTagEditor; Menu *mEditorAlbums; Menu *mEditorTagTypes; Menu *mEditorTags; +#endif // HAVE_TAGLIB_H Menu *mPlaylistList; Menu *mPlaylistEditor; @@ -107,40 +104,20 @@ Window *wFooter; MPDConnection *Mpd; -time_t block_delay; time_t timer; -time_t now; int now_playing = -1; int playing_song_scroll_begin = 0; int browsed_dir_scroll_begin = 0; int stats_scroll_begin = 0; -int block_statusbar_update_delay = -1; +int lock_statusbar_delay = -1; string browsed_dir = "/"; -string song_lyrics; -string player_state; -string volume_state; -string switch_state; - -string mpd_repeat; -string mpd_random; -string mpd_crossfade; -string mpd_db_updating; NcmpcppScreen current_screen; NcmpcppScreen prev_screen; -Song edited_song; -Song searched_song; - -bool main_exit = 0; -bool messages_allowed = 0; -bool title_allowed = 0; - -bool header_update_status = 0; - bool dont_change_now_playing = 0; bool block_progressbar_update = 0; bool block_statusbar_update = 0; @@ -148,17 +125,19 @@ bool allow_statusbar_unblock = 1; bool block_playlist_update = 0; bool block_found_item_list_update = 0; -bool search_case_sensitive = 1; -bool search_mode_match = 1; +bool messages_allowed = 0; +bool redraw_screen = 0; -bool redraw_me = 0; +extern bool header_update_status; +extern bool search_case_sensitive; +extern bool search_match_to_pattern; extern string EMPTY_TAG; extern string UNKNOWN_ARTIST; extern string UNKNOWN_TITLE; extern string UNKNOWN_ALBUM; - extern string playlist_stats; +extern string volume_state; const string message_part_of_songs_added = "Only part of requested songs' list added to playlist!"; @@ -218,8 +197,7 @@ int main(int argc, char *argv[]) mBrowser->SetSelectSuffix(Config.selected_item_suffix); mBrowser->SetItemDisplayer(DisplayItem); - mTagEditor = new Menu(0, main_start_y, COLS, main_height, "", Config.main_color, brNone); - mSearcher = static_cast *>(mTagEditor->Clone()); + mSearcher = new Menu(0, main_start_y, COLS, main_height, "", Config.main_color, brNone); mSearcher->SetSelectPrefix(Config.selected_item_prefix); mSearcher->SetSelectSuffix(Config.selected_item_suffix); @@ -237,11 +215,14 @@ int main(int argc, char *argv[]) mLibSongs->SetItemDisplayer(DisplaySong); mLibSongs->SetItemDisplayerUserData(&Config.song_library_format); +# ifdef HAVE_TAGLIB_H + mTagEditor = static_cast *>(mSearcher->Clone()); mEditorAlbums = new Menu(0, main_start_y, lib_artist_width, main_height, "Albums", Config.main_color, brNone); mEditorTagTypes = new Menu(lib_albums_start_x, main_start_y, lib_albums_width, main_height, "Tag types", Config.main_color, brNone); mEditorTags = new Menu(lib_songs_start_x, main_start_y, lib_songs_width, main_height, "Tags", Config.main_color, brNone); mEditorTags->SetItemDisplayer(DisplayTag); mEditorTags->SetItemDisplayerUserData(mEditorTagTypes); +# endif // HAVE_TAGLIB_H mPlaylistList = new Menu(0, main_start_y, lib_artist_width, main_height, "Playlists", Config.main_color, brNone); mPlaylistEditor = new Menu(lib_albums_start_x, main_start_y, lib_albums_width+lib_songs_width+1, main_height, "Playlist's content", Config.main_color, brNone); @@ -299,7 +280,9 @@ int main(int argc, char *argv[]) sHelp->Add(DisplayKeys(Key.NextFoundPosition) + "Go to next found position\n"); sHelp->Add(DisplayKeys(Key.ToggleFindMode) + "Toggle find mode (normal/wrapped)\n"); sHelp->Add(DisplayKeys(Key.GoToContainingDir) + "Go to directory containing current item\n"); - sHelp->Add(DisplayKeys(Key.EditTags) + tag_screen_keydesc); +# ifdef HAVE_TAGLIB_H + sHelp->Add(DisplayKeys(Key.EditTags) + "Edit song's tags/playlist's name\n"); +# endif // HAVE_TAGLIB_H sHelp->Add(DisplayKeys(Key.GoToPosition) + "Go to chosen position in current song\n"); sHelp->Add(DisplayKeys(Key.Lyrics) + "Show/hide song's lyrics\n\n"); @@ -340,16 +323,16 @@ int main(int argc, char *argv[]) sHelp->Add(DisplayKeys(&Key.VolumeUp[0], 1) + "Next column\n"); sHelp->Add(DisplayKeys(Key.Enter) + "Add item to playlist and play\n"); sHelp->Add(DisplayKeys(Key.Space) + "Add to playlist/select item\n"); +# ifndef HAVE_TAGLIB_H + sHelp->Add(DisplayKeys(Key.EditTags) + "Edit playlist's name\n"); +# endif // ! HAVE_TAGLIB_H sHelp->Add(DisplayKeys(Key.MvSongUp) + "Move item/group of items up\n"); - sHelp->Add(DisplayKeys(Key.MvSongDown) + "Move item/group of items down\n\n\n"); + sHelp->Add(DisplayKeys(Key.MvSongDown) + "Move item/group of items down\n"); # ifdef HAVE_TAGLIB_H - sHelp->Add(" [.b]Keys - Tag editor\n -----------------------------------------[/b]\n"); + sHelp->Add("\n\n [.b]Keys - Tag editor\n -----------------------------------------[/b]\n"); sHelp->Add(DisplayKeys(Key.Enter) + "Change option\n"); -# else - sHelp->Add(" [.b]Keys - Tag info\n -----------------------------------------[/b]\n"); - sHelp->Add(DisplayKeys(Key.Enter) + "Return\n"); -# endif +# endif // HAVE_TAGLIB_H if (Config.header_visibility) { @@ -367,20 +350,21 @@ int main(int argc, char *argv[]) wCurrent = mPlaylist; current_screen = csPlaylist; - int input; timer = time(NULL); sHelp->SetTimeout(ncmpcpp_window_timeout); mPlaylist->SetTimeout(ncmpcpp_window_timeout); mBrowser->SetTimeout(ncmpcpp_window_timeout); - mTagEditor->SetTimeout(ncmpcpp_window_timeout); mSearcher->SetTimeout(ncmpcpp_window_timeout); mLibArtists->SetTimeout(ncmpcpp_window_timeout); mLibAlbums->SetTimeout(ncmpcpp_window_timeout); mLibSongs->SetTimeout(ncmpcpp_window_timeout); +# ifdef HAVE_TAGLIB_H + mTagEditor->SetTimeout(ncmpcpp_window_timeout); mEditorAlbums->SetTimeout(ncmpcpp_window_timeout); mEditorTagTypes->SetTimeout(ncmpcpp_window_timeout); mEditorTags->SetTimeout(ncmpcpp_window_timeout); +# endif // HAVE_TAGLIB_H sLyrics->SetTimeout(ncmpcpp_window_timeout); wFooter->SetTimeout(ncmpcpp_window_timeout); mPlaylistList->SetTimeout(ncmpcpp_window_timeout); @@ -388,17 +372,34 @@ int main(int argc, char *argv[]) mPlaylist->HighlightColor(Config.main_highlight_color); mBrowser->HighlightColor(Config.main_highlight_color); - mTagEditor->HighlightColor(Config.main_highlight_color); mSearcher->HighlightColor(Config.main_highlight_color); mLibArtists->HighlightColor(Config.main_highlight_color); mLibAlbums->HighlightColor(Config.main_highlight_color); mLibSongs->HighlightColor(Config.main_highlight_color); +# ifdef HAVE_TAGLIB_H + mTagEditor->HighlightColor(Config.main_highlight_color); + mEditorAlbums->HighlightColor(Config.main_highlight_color); + mEditorTagTypes->HighlightColor(Config.main_highlight_color); + mEditorTags->HighlightColor(Config.main_highlight_color); +# endif // HAVE_TAGLIB_H mPlaylistList->HighlightColor(Config.main_highlight_color); mPlaylistEditor->HighlightColor(Config.main_highlight_color); Mpd->SetStatusUpdater(NcmpcppStatusChanged, NULL); Mpd->SetErrorHandler(NcmpcppErrorCallback, NULL); + // local variables + int input; + + Song edited_song; + Song sought_pattern; + + bool main_exit = 0; + bool title_allowed = 0; + + string lyrics_title; + // local variables end + while (!main_exit) { if (!Mpd->Connected()) @@ -433,7 +434,7 @@ int main(int argc, char *argv[]) title = "Browse: "; break; case csTagEditor: - title = tag_screen; + title = "Tag editor"; break; case csSearcher: title = "Search engine"; @@ -442,7 +443,7 @@ int main(int argc, char *argv[]) title = "Media library"; break; case csLyrics: - title = song_lyrics; + title = lyrics_title; break; case csPlaylistEditor: title = "Playlist editor"; @@ -451,7 +452,7 @@ int main(int argc, char *argv[]) title = "Albums' tag editor"; break; } - + if (title_allowed) { wHeader->Bold(1); @@ -487,7 +488,13 @@ int main(int argc, char *argv[]) } } else - wHeader->WriteXY(0, 0, max_allowed_title_length, "[.b]1:[/b]Help [.b]2:[/b]Playlist [.b]3:[/b]Browse [.b]4:[/b]Search [.b]5:[/b]Library [.b]6:[/b]Playlist editor [.b]7:[/b]Albums' editor", 1); + { + string screens = "[.b]1:[/b]Help [.b]2:[/b]Playlist [.b]3:[/b]Browse [.b]4:[/b]Search [.b]5:[/b]Library [.b]6:[/b]Playlist editor"; +# ifdef HAVE_TAGLIB_H + screens += " [.b]7:[/b]Albums' tag editor"; +# endif // HAVE_TAGLIB_H + wHeader->WriteXY(0, 0, max_allowed_title_length, screens, 1); + } wHeader->SetColor(Config.volume_color); wHeader->WriteXY(max_allowed_title_length, 0, volume_state); @@ -642,7 +649,6 @@ int main(int argc, char *argv[]) if (wCurrent == mPlaylistEditor && mPlaylistEditor->Empty()) { - mPlaylistEditor->HighlightColor(Config.main_highlight_color); mPlaylistList->HighlightColor(Config.active_column_color); wCurrent = mPlaylistList; @@ -655,7 +661,7 @@ int main(int argc, char *argv[]) // playlist editor end // album editor stuff - +# ifdef HAVE_TAGLIB_H if (current_screen == csAlbumEditor) { if (mEditorAlbums->Empty()) @@ -701,14 +707,14 @@ int main(int argc, char *argv[]) mEditorTagTypes->GetChoice() < 10 ? mEditorTags->Refresh(1) : mEditorTags->Window::Clear(); } - +# endif // HAVE_TAGLIB_H // album editor end if (Config.columns_in_playlist && wCurrent == mPlaylist) - wCurrent->Display(redraw_me); + wCurrent->Display(redraw_screen); else - wCurrent->Refresh(redraw_me); - redraw_me = 0; + wCurrent->Refresh(redraw_screen); + redraw_screen = 0; wCurrent->ReadKey(input); if (input == ERR) @@ -744,11 +750,13 @@ int main(int argc, char *argv[]) { mPlaylistEditor->Clear(0); } +# ifdef HAVE_TAGLIB_H else if (wCurrent == mEditorAlbums) { mEditorTags->Clear(0); mEditorTagTypes->Refresh(); } +# endif // HAVE_TAGLIB_H } } default: @@ -783,7 +791,7 @@ int main(int argc, char *argv[]) } else if (input == KEY_RESIZE) { - redraw_me = 1; + redraw_screen = 1; if (COLS < 20 || LINES < 5) { @@ -803,7 +811,6 @@ int main(int argc, char *argv[]) mPlaylist->Resize(COLS, main_height); mPlaylist->SetTitle(Config.columns_in_playlist ? DisplayColumns(Config.song_columns_list_format) : ""); mBrowser->Resize(COLS, main_height); - mTagEditor->Resize(COLS, main_height); mSearcher->Resize(COLS, main_height); sLyrics->Resize(COLS, main_height); @@ -819,6 +826,9 @@ int main(int argc, char *argv[]) mLibAlbums->MoveTo(lib_albums_start_x, main_start_y); mLibSongs->MoveTo(lib_songs_start_x, main_start_y); +# ifdef HAVE_TAGLIB_H + mTagEditor->Resize(COLS, main_height); + mEditorAlbums->Resize(lib_artist_width, main_height); mEditorTagTypes->Resize(lib_albums_width, main_height); mEditorTags->Resize(lib_songs_width, main_height); @@ -828,6 +838,7 @@ int main(int argc, char *argv[]) mPlaylistList->Resize(lib_artist_width, main_height); mPlaylistEditor->Resize(lib_albums_width+lib_songs_width+1, main_height); mPlaylistEditor->MoveTo(lib_albums_start_x, main_start_y); +# endif // HAVE_TAGLIB_H if (Config.header_visibility) wHeader->Resize(COLS, wHeader->GetHeight()); @@ -839,18 +850,21 @@ int main(int argc, char *argv[]) if (wCurrent != sHelp && wCurrent != sLyrics) wCurrent->Window::Clear(); +# ifdef HAVE_TAGLIB_H if (current_screen == csLibrary) { REFRESH_MEDIA_LIBRARY_SCREEN; } - else if (current_screen == csPlaylistEditor) - { - REFRESH_PLAYLIST_EDITOR_SCREEN; - } else if (current_screen == csAlbumEditor) { REFRESH_ALBUM_EDITOR_SCREEN; } + else +# endif // HAVE_TAGLIB_H + if (current_screen == csPlaylistEditor) + { + REFRESH_PLAYLIST_EDITOR_SCREEN; + } header_update_status = 1; PlayerState mpd_state = Mpd->GetState(); MPDStatusChanges changes; @@ -926,9 +940,9 @@ int main(int argc, char *argv[]) } break; } +# ifdef HAVE_TAGLIB_H case csTagEditor: { -# ifdef HAVE_TAGLIB_H int id = mTagEditor->GetRealChoice()+1; int option = mTagEditor->GetChoice(); LOCK_STATUSBAR; @@ -1023,11 +1037,10 @@ int main(int argc, char *argv[]) } case 9: { -# endif // HAVE_TAGLIB_H wCurrent->Clear(); wCurrent = wPrev; current_screen = prev_screen; - redraw_me = 1; + redraw_screen = 1; if (current_screen == csLibrary) { REFRESH_MEDIA_LIBRARY_SCREEN; @@ -1036,21 +1049,20 @@ int main(int argc, char *argv[]) { REFRESH_PLAYLIST_EDITOR_SCREEN; } -# ifdef HAVE_TAGLIB_H break; } } UNLOCK_STATUSBAR; -# endif // HAVE_TAGLIB_H break; } +# endif // HAVE_TAGLIB_H case csSearcher: { ENTER_SEARCH_ENGINE_SCREEN: int option = mSearcher->GetChoice(); LOCK_STATUSBAR; - Song &s = searched_song; + Song &s = sought_pattern; switch (option+1) { @@ -1136,8 +1148,8 @@ int main(int argc, char *argv[]) } case 10: { - search_mode_match = !search_mode_match; - mSearcher->UpdateOption(option, "[.b]Search mode:[/b] " + (search_mode_match ? search_mode_one : search_mode_two)); + search_match_to_pattern = !search_match_to_pattern; + mSearcher->UpdateOption(option, "[.b]Search mode:[/b] " + (search_match_to_pattern ? search_mode_normal : search_mode_strict)); break; } case 11: @@ -1184,7 +1196,7 @@ int main(int argc, char *argv[]) found_pos = 0; vFoundPositions.clear(); FreeSongList(vSearched); - PrepareSearchEngine(searched_song); + PrepareSearchEngine(sought_pattern); ShowMessage("Search state reset"); break; } @@ -1553,6 +1565,7 @@ int main(int argc, char *argv[]) wCurrent = mPlaylistEditor; mPlaylistEditor->HighlightColor(Config.active_column_color); } +# ifdef HAVE_TAGLIB_H else if (current_screen == csAlbumEditor && input == Key.VolumeUp[0]) { found_pos = 0; @@ -1572,6 +1585,7 @@ int main(int argc, char *argv[]) mEditorTags->HighlightColor(Config.active_column_color); } } +# endif // HAVE_TAGLIB_H else Mpd->SetVolume(Mpd->GetVolume()+1); } @@ -1607,6 +1621,7 @@ int main(int argc, char *argv[]) wCurrent = mPlaylistList; mPlaylistList->HighlightColor(Config.active_column_color); } +# ifdef HAVE_TAGLIB_H else if (current_screen == csAlbumEditor && input == Key.VolumeDown[0]) { found_pos = 0; @@ -1626,6 +1641,7 @@ int main(int argc, char *argv[]) mEditorAlbums->HighlightColor(Config.active_column_color); } } +# endif // HAVE_TAGLIB_H else Mpd->SetVolume(Mpd->GetVolume()-1); } @@ -1643,7 +1659,7 @@ int main(int argc, char *argv[]) mPlaylist->DeleteOption(*it); } ShowMessage("Selected items deleted!"); - redraw_me = 1; + redraw_screen = 1; } else { @@ -1705,7 +1721,7 @@ int main(int argc, char *argv[]) mPlaylistEditor->DeleteOption(*it); } ShowMessage("Selected items deleted from playlist '" + mPlaylistList->GetOption() + "'!"); - redraw_me = 1; + redraw_screen = 1; } else { @@ -2057,7 +2073,7 @@ int main(int argc, char *argv[]) mPlaylist->SetItemDisplayer(Config.columns_in_playlist ? DisplaySongInColumns : DisplaySong); mPlaylist->SetItemDisplayerUserData(Config.columns_in_playlist ? &Config.song_columns_list_format : &Config.song_list_format); mPlaylist->SetTitle(Config.columns_in_playlist ? DisplayColumns(Config.song_columns_list_format) : ""); - redraw_me = 1; + redraw_screen = 1; } else if (Keypressed(input, Key.ToggleAutoCenter)) { @@ -2178,37 +2194,35 @@ int main(int argc, char *argv[]) ShowMessage(success ? "Tags written succesfully!" : "Error while writing tags!"); } } - else -# endif - if ((wCurrent == mPlaylist && !mPlaylist->Empty()) + else if ( + (wCurrent == mPlaylist && !mPlaylist->Empty()) || (wCurrent == mBrowser && mBrowser->at(mBrowser->GetChoice()).type == itSong) || (wCurrent == mSearcher && !vSearched.empty() && mSearcher->GetChoice() >= search_engine_static_option) || (wCurrent == mLibSongs && !mLibSongs->Empty()) || (wCurrent == mPlaylistEditor && !mPlaylistEditor->Empty())) { int id = wCurrent->GetChoice(); - Song *s; switch (current_screen) { case csPlaylist: - s = &mPlaylist->at(id); + edited_song = mPlaylist->at(id); break; case csBrowser: - s = mBrowser->at(id).song; + edited_song = *mBrowser->at(id).song; break; case csSearcher: - s = vSearched[id-search_engine_static_option]; + edited_song = *vSearched[id-search_engine_static_option]; break; case csLibrary: - s = &mLibSongs->at(id); + edited_song = mLibSongs->at(id); break; case csPlaylistEditor: - s = &mPlaylistEditor->at(id); + edited_song = mPlaylistEditor->at(id); break; default: break; } - if (GetSongInfo(*s)) + if (GetSongTags(edited_song)) { wPrev = wCurrent; wCurrent = mTagEditor; @@ -2216,9 +2230,11 @@ int main(int argc, char *argv[]) current_screen = csTagEditor; } else - ShowMessage("Cannot read file '" + Config.mpd_music_dir + "/" + s->GetFile() + "'!"); + ShowMessage("Cannot read file '" + Config.mpd_music_dir + "/" + edited_song.GetFile() + "'!"); } - else if (wCurrent == mPlaylistList) + else +# endif // HAVE_TAGLIB_H + if (wCurrent == mPlaylistList) { LOCK_STATUSBAR; wFooter->WriteXY(0, Config.statusbar_visibility, "[.b]Playlist:[/b] ", 1); @@ -2434,7 +2450,7 @@ int main(int argc, char *argv[]) int id = mDialog->GetChoice(); - redraw_me = 1; + redraw_screen = 1; if (current_screen == csLibrary) { REFRESH_MEDIA_LIBRARY_SCREEN; @@ -2632,7 +2648,7 @@ int main(int argc, char *argv[]) wCurrent->Window::Clear(); current_screen = prev_screen; wCurrent = wPrev; - redraw_me = 1; + redraw_screen = 1; if (current_screen == csLibrary) { REFRESH_MEDIA_LIBRARY_SCREEN; @@ -2678,7 +2694,7 @@ int main(int argc, char *argv[]) wCurrent = sLyrics; wCurrent->Clear(); current_screen = csLyrics; - song_lyrics = "Lyrics: " + s->GetArtist() + " - " + s->GetTitle(); + lyrics_title = "Lyrics: " + s->GetArtist() + " - " + s->GetTitle(); sLyrics->WriteXY(0, 0, "Fetching lyrics..."); sLyrics->Refresh(); sLyrics->Add(GetLyrics(s->GetArtist(), s->GetTitle())); @@ -2711,7 +2727,7 @@ int main(int argc, char *argv[]) wCurrent = mPlaylist; wCurrent->Hide(); current_screen = csPlaylist; - redraw_me = 1; + redraw_screen = 1; } } else if (Keypressed(input, Key.Browser)) @@ -2729,7 +2745,7 @@ int main(int argc, char *argv[]) wCurrent = mBrowser; wCurrent->Hide(); current_screen = csBrowser; - redraw_me = 1; + redraw_screen = 1; } } else if (Keypressed(input, Key.SearchEngine)) @@ -2739,11 +2755,11 @@ int main(int argc, char *argv[]) found_pos = 0; vFoundPositions.clear(); if (vSearched.empty()) - PrepareSearchEngine(searched_song); + PrepareSearchEngine(sought_pattern); wCurrent = mSearcher; wCurrent->Hide(); current_screen = csSearcher; - redraw_me = 1; + redraw_screen = 1; if (!vSearched.empty()) { wCurrent->WriteXY(0, 0, "Updating list..."); @@ -2764,7 +2780,7 @@ int main(int argc, char *argv[]) mPlaylist->Hide(); // hack, should be wCurrent, but it doesn't always have 100% width - redraw_me = 1; + redraw_screen = 1; REFRESH_MEDIA_LIBRARY_SCREEN; wCurrent = mLibArtists; @@ -2785,7 +2801,7 @@ int main(int argc, char *argv[]) mPlaylist->Hide(); // hack, should be wCurrent, but it doesn't always have 100% width - redraw_me = 1; + redraw_screen = 1; REFRESH_PLAYLIST_EDITOR_SCREEN; wCurrent = mPlaylistList; @@ -2794,6 +2810,7 @@ int main(int argc, char *argv[]) UpdateSongList(mPlaylistEditor); } } +# ifdef HAVE_TAGLIB_H else if (Keypressed(input, Key.AlbumEditor)) { if (current_screen != csAlbumEditor) @@ -2807,7 +2824,7 @@ int main(int argc, char *argv[]) mPlaylist->Hide(); // hack, should be wCurrent, but it doesn't always have 100% width - redraw_me = 1; + redraw_screen = 1; REFRESH_ALBUM_EDITOR_SCREEN; if (mEditorTagTypes->Empty()) @@ -2831,6 +2848,7 @@ int main(int argc, char *argv[]) current_screen = csAlbumEditor; } } +# endif // HAVE_TAGLIB_H else if (Keypressed(input, Key.Quit)) main_exit = 1; diff --git a/src/ncmpcpp.h b/src/ncmpcpp.h index e585ca1b..9044ef60 100644 --- a/src/ncmpcpp.h +++ b/src/ncmpcpp.h @@ -26,30 +26,33 @@ #endif #ifdef UTF8_ENABLED -const bool UNICODE = 1; +# define UNICODE 1 #else -const bool UNICODE = 0; +# define UNICODE 0 #endif -#ifdef HAVE_TAGLIB_H -# include "fileref.h" -# include "tag.h" -#endif - -#include "libmpdclient.h" - #include #include -#include +#include #include -#include #include "window.h" #include "menu.h" #include "scrollpad.h" #include "misc.h" -enum NcmpcppScreen { csHelp, csPlaylist, csBrowser, csTagEditor, csSearcher, csLibrary, csLyrics, csPlaylistEditor, csAlbumEditor }; +enum NcmpcppScreen +{ + csHelp, + csPlaylist, + csBrowser, + csTagEditor, + csSearcher, + csLibrary, + csLyrics, + csPlaylistEditor, + csAlbumEditor +}; const int ncmpcpp_window_timeout = 500; const int search_engine_static_option = 17; @@ -57,8 +60,8 @@ const int search_engine_static_option = 17; const string home_folder = getenv("HOME"); const string TERMINAL_TYPE = getenv("TERM"); -const string search_mode_one = "Match if tag contains searched phrase"; -const string search_mode_two = "Match only if both values are the same"; +const string search_mode_normal = "Match if tag contains searched phrase"; +const string search_mode_strict = "Match only if both values are the same"; #endif diff --git a/src/search_engine.cpp b/src/search_engine.cpp new file mode 100644 index 00000000..996660cc --- /dev/null +++ b/src/search_engine.cpp @@ -0,0 +1,195 @@ +/*************************************************************************** + * Copyright (C) 2008 by Andrzej Rybczak * + * electricityispower@gmail.com * + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) any later version. * + * * + * This program is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU General Public License for more details. * + * * + * You should have received a copy of the GNU General Public License * + * along with this program; if not, write to the * + * Free Software Foundation, Inc., * + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * + ***************************************************************************/ + +#include +#include "search_engine.h" + +extern MPDConnection *Mpd; +extern Menu *mPlaylist; +extern Menu *mSearcher; + +bool search_match_to_pattern = 0; +bool search_case_sensitive = 1; + +void UpdateFoundList(const SongList &v) +{ + int i = search_engine_static_option; + bool bold = 0; + for (SongList::const_iterator it = v.begin(); it != v.end(); it++, i++) + { + for (int j = 0; j < mPlaylist->Size(); j++) + { + if (mPlaylist->at(j).GetHash() == (*it)->GetHash()) + { + bold = 1; + break; + } + } + mSearcher->BoldOption(i, bold); + bold = 0; + } +} + +void PrepareSearchEngine(Song &s) +{ + s.Clear(); + mSearcher->Clear(); + mSearcher->Reset(); + mSearcher->AddOption("[.b]Filename:[/b] " + s.GetShortFilename()); + mSearcher->AddOption("[.b]Title:[/b] " + s.GetTitle()); + mSearcher->AddOption("[.b]Artist:[/b] " + s.GetArtist()); + mSearcher->AddOption("[.b]Album:[/b] " + s.GetAlbum()); + mSearcher->AddOption("[.b]Year:[/b] " + s.GetYear()); + mSearcher->AddOption("[.b]Track:[/b] " + s.GetTrack()); + mSearcher->AddOption("[.b]Genre:[/b] " + s.GetGenre()); + mSearcher->AddOption("[.b]Comment:[/b] " + s.GetComment()); + mSearcher->AddSeparator(); + mSearcher->AddOption("[.b]Search mode:[/b] " + (search_match_to_pattern ? search_mode_normal : search_mode_strict)); + mSearcher->AddOption("[.b]Case sensitive:[/b] " + (string)(search_case_sensitive ? "Yes" : "No")); + mSearcher->AddSeparator(); + mSearcher->AddOption("Search"); + mSearcher->AddOption("Reset"); +} + +void Search(SongList &result, Song &s) +{ + FreeSongList(result); + + if (s.Empty()) + return; + + SongList list; + Mpd->GetDirectoryRecursive("/", list); + + bool found = 1; + + s.GetEmptyFields(1); + + if (!search_case_sensitive) + { + string t; + t = s.GetShortFilename(); + transform(t.begin(), t.end(), t.begin(), tolower); + s.SetShortFilename(t); + + t = s.GetTitle(); + transform(t.begin(), t.end(), t.begin(), tolower); + s.SetTitle(t); + + t = s.GetArtist(); + transform(t.begin(), t.end(), t.begin(), tolower); + s.SetArtist(t); + + t = s.GetAlbum(); + transform(t.begin(), t.end(), t.begin(), tolower); + s.SetAlbum(t); + + t = s.GetGenre(); + transform(t.begin(), t.end(), t.begin(), tolower); + s.SetGenre(t); + + t = s.GetComment(); + transform(t.begin(), t.end(), t.begin(), tolower); + s.SetComment(t); + } + + for (SongList::const_iterator it = list.begin(); it != list.end(); it++) + { + Song copy = **it; + + if (!search_case_sensitive) + { + string t; + t = copy.GetShortFilename(); + transform(t.begin(), t.end(), t.begin(), tolower); + copy.SetShortFilename(t); + + t = copy.GetTitle(); + transform(t.begin(), t.end(), t.begin(), tolower); + copy.SetTitle(t); + + t = copy.GetArtist(); + transform(t.begin(), t.end(), t.begin(), tolower); + copy.SetArtist(t); + + t = copy.GetAlbum(); + transform(t.begin(), t.end(), t.begin(), tolower); + copy.SetAlbum(t); + + t = copy.GetGenre(); + transform(t.begin(), t.end(), t.begin(), tolower); + copy.SetGenre(t); + + t = copy.GetComment(); + transform(t.begin(), t.end(), t.begin(), tolower); + copy.SetComment(t); + } + + if (search_match_to_pattern) + { + if (found && !s.GetShortFilename().empty()) + found = copy.GetShortFilename().find(s.GetShortFilename()) != string::npos; + if (found && !s.GetTitle().empty()) + found = copy.GetTitle().find(s.GetTitle()) != string::npos; + if (found && !s.GetArtist().empty()) + found = copy.GetArtist().find(s.GetArtist()) != string::npos; + if (found && !s.GetAlbum().empty()) + found = copy.GetAlbum().find(s.GetAlbum()) != string::npos; + if (found && !s.GetYear().empty()) + found = StrToInt(copy.GetYear()) == StrToInt(s.GetYear()) && StrToInt(s.GetYear()); + if (found && !s.GetTrack().empty()) + found = StrToInt(copy.GetTrack()) == StrToInt(s.GetTrack()) && StrToInt(s.GetTrack()); + if (found && !s.GetGenre().empty()) + found = copy.GetGenre().find(s.GetGenre()) != string::npos; + if (found && !s.GetComment().empty()) + found = copy.GetComment().find(s.GetComment()) != string::npos; + } + else + { + if (found && !s.GetShortFilename().empty()) + found = copy.GetShortFilename() == s.GetShortFilename(); + if (found && !s.GetTitle().empty()) + found = copy.GetTitle() == s.GetTitle(); + if (found && !s.GetArtist().empty()) + found = copy.GetArtist() == s.GetArtist(); + if (found && !s.GetAlbum().empty()) + found = copy.GetAlbum() == s.GetAlbum(); + if (found && !s.GetYear().empty()) + found = StrToInt(copy.GetYear()) == StrToInt(s.GetYear()) && StrToInt(s.GetYear()); + if (found && !s.GetTrack().empty()) + found = StrToInt(copy.GetTrack()) == StrToInt(s.GetTrack()) && StrToInt(s.GetTrack()); + if (found && !s.GetGenre().empty()) + found = copy.GetGenre() == s.GetGenre(); + if (found && !s.GetComment().empty()) + found = copy.GetComment() == s.GetComment(); + } + + if (found) + { + Song *ss = new Song(**it); + result.push_back(ss); + } + + found = 1; + } + FreeSongList(list); + s.GetEmptyFields(0); +} + diff --git a/src/search_engine.h b/src/search_engine.h new file mode 100644 index 00000000..b6d23bcd --- /dev/null +++ b/src/search_engine.h @@ -0,0 +1,32 @@ +/*************************************************************************** + * Copyright (C) 2008 by Andrzej Rybczak * + * electricityispower@gmail.com * + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) any later version. * + * * + * This program is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU General Public License for more details. * + * * + * You should have received a copy of the GNU General Public License * + * along with this program; if not, write to the * + * Free Software Foundation, Inc., * + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * + ***************************************************************************/ + +#ifndef HAVE_SEARCH_ENGINE_H +#define HAVE_SEARCH_ENGINE_H + +#include "mpdpp.h" +#include "ncmpcpp.h" + +void UpdateFoundList(const SongList &); +void PrepareSearchEngine(Song &s); +void Search(SongList &, Song &); + +#endif + diff --git a/src/song.cpp b/src/song.cpp index 951f4360..1b881d6f 100644 --- a/src/song.cpp +++ b/src/song.cpp @@ -19,6 +19,7 @@ ***************************************************************************/ #include "song.h" +#include "settings.h" extern ncmpcpp_config Config; @@ -194,32 +195,6 @@ string Song::GetComment() const return itsComment.empty() ? (itsGetEmptyFields ? "" : EMPTY_TAG) : itsComment; } -Song & Song::operator=(const Song &s) -{ - if (this == &s) - return *this; - itsFile = s.itsFile; - itsShortName = s.itsShortName; - itsDirectory = s.itsDirectory; - itsArtist = s.itsArtist; - itsTitle = s.itsTitle; - itsAlbum = s.itsAlbum; - itsTrack = s.itsTrack; - itsYear = s.itsYear; - itsGenre = s.itsGenre; - itsComposer = s.itsComposer; - itsPerformer = s.itsPerformer; - itsDisc = s.itsDisc; - itsComment = s.itsComment; - itsHash = s.itsHash; - itsMinutesLength = s.itsMinutesLength; - itsSecondsLength = s.itsSecondsLength; - itsPosition = s.itsPosition; - itsID = s.itsID; - itsGetEmptyFields = s.itsGetEmptyFields; - return *this; -} - bool Song::operator==(const Song &s) const { return itsFile == s.itsFile && itsArtist == s.itsArtist && itsTitle == s.itsTitle && itsAlbum == s.itsAlbum && itsTrack == s.itsTrack && itsYear == s.itsYear && itsGenre == s.itsGenre && itsComposer == s.itsComposer && itsPerformer == s.itsPerformer && itsDisc == s.itsDisc && itsComment == s.itsComment && itsHash == s.itsHash && itsMinutesLength && s.itsMinutesLength && itsSecondsLength == s.itsSecondsLength && itsPosition == s.itsPosition && itsID == s.itsID; @@ -227,7 +202,7 @@ bool Song::operator==(const Song &s) const bool Song::operator!=(const Song &s) const { - return itsFile != s.itsFile || itsArtist != s.itsArtist || itsTitle != s.itsTitle || itsAlbum != s.itsAlbum || itsTrack != s.itsTrack || itsYear != s.itsYear || itsGenre != s.itsGenre || itsComposer != s.itsComposer || itsPerformer != s.itsPerformer || itsDisc != s.itsDisc || itsComment != s.itsComment || itsHash != s.itsHash || itsMinutesLength != s.itsMinutesLength || itsSecondsLength != s.itsSecondsLength || itsPosition != s.itsPosition || itsID != s.itsID; + return !operator==(s); } bool Song::operator<(const Song &s) const diff --git a/src/song.h b/src/song.h index dd75affa..056153e8 100644 --- a/src/song.h +++ b/src/song.h @@ -27,7 +27,7 @@ #include #include "misc.h" -#include "settings.h" +#include "libmpdclient.h" using std::string; @@ -79,7 +79,6 @@ class Song void Clear(); bool Empty() const; - Song & operator=(const Song &); bool operator==(const Song &) const; bool operator!=(const Song &) const; bool operator<(const Song &rhs) const; diff --git a/src/status_checker.cpp b/src/status_checker.cpp index ed93e0c1..0f734ed5 100644 --- a/src/status_checker.cpp +++ b/src/status_checker.cpp @@ -18,36 +18,35 @@ * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * ***************************************************************************/ -#include "status_checker.h" #include "helpers.h" +#include "search_engine.h" #include "settings.h" +#include "status_checker.h" extern MPDConnection *Mpd; - extern ncmpcpp_config Config; extern Menu *mPlaylist; extern Menu *mBrowser; -extern Menu *mSearcher; extern Menu *mLibArtists; -extern Menu *mLibAlbums; -extern Menu *mEditorAlbums; extern Menu *mLibSongs; extern Menu *mPlaylistEditor; +#ifdef HAVE_TAGLIB_H +extern Menu *mEditorAlbums; +#endif // HAVE_TAGLIB_H + extern Window *wHeader; extern Window *wFooter; extern SongList vSearched; -extern time_t block_delay; extern time_t timer; -extern time_t now; extern int now_playing; extern int playing_song_scroll_begin; -extern int block_statusbar_update_delay; +extern int lock_statusbar_delay; extern string browsed_dir; @@ -62,8 +61,6 @@ extern string mpd_db_updating; extern NcmpcppScreen current_screen; -extern bool header_update_status; - extern bool dont_change_now_playing; extern bool allow_statusbar_unblock; extern bool block_progressbar_update; @@ -71,15 +68,27 @@ extern bool block_statusbar_update; extern bool block_playlist_update; extern bool block_found_item_list_update; -extern bool redraw_me; +extern bool redraw_screen; +bool header_update_status = 0; bool repeat_one_allowed = 0; long long playlist_old_id = -1; int old_playing; +time_t time_of_statusbar_lock; +time_t now; + string playlist_stats; +string volume_state; +string switch_state; +string player_state; + +string mpd_repeat; +string mpd_random; +string mpd_crossfade; +string mpd_db_updating; void TraceMpdStatus() { @@ -89,15 +98,15 @@ void TraceMpdStatus() if (now == timer+Config.playlist_disable_highlight_delay && current_screen == csPlaylist) mPlaylist->Highlighting(!Config.playlist_disable_highlight_delay); - if (block_statusbar_update_delay > 0) + if (lock_statusbar_delay > 0) { - if (now >= block_delay+block_statusbar_update_delay) - block_statusbar_update_delay = 0; + if (now >= time_of_statusbar_lock+lock_statusbar_delay) + lock_statusbar_delay = 0; } - if (!block_statusbar_update_delay) + if (!lock_statusbar_delay) { - block_statusbar_update_delay = -1; + lock_statusbar_delay = -1; if (Config.statusbar_visibility) block_statusbar_update = !allow_statusbar_unblock; @@ -229,9 +238,11 @@ void NcmpcppStatusChanged(MPDConnection *Mpd, MPDStatusChanges changed, void *da if (changed.Database) { GetDirectory(browsed_dir); +# ifdef HAVE_TAGLIB_H + mEditorAlbums->Clear(0); +# endif // HAVE_TAGLIB_H mLibArtists->Clear(0); mPlaylistEditor->Clear(0); - mEditorAlbums->Clear(0); } if (changed.PlayerState) { diff --git a/src/status_checker.h b/src/status_checker.h index 07fef6e1..7fbd2d0d 100644 --- a/src/status_checker.h +++ b/src/status_checker.h @@ -21,8 +21,8 @@ #ifndef HAVE_STATUS_CHECKER_H #define HAVE_STATUS_CHECKER_H -#include "ncmpcpp.h" #include "mpdpp.h" +#include "ncmpcpp.h" void TraceMpdStatus(); void NcmpcppStatusChanged(MPDConnection *, MPDStatusChanges, void *); diff --git a/src/tag_editor.cpp b/src/tag_editor.cpp new file mode 100644 index 00000000..fb6ab623 --- /dev/null +++ b/src/tag_editor.cpp @@ -0,0 +1,138 @@ +/*************************************************************************** + * Copyright (C) 2008 by Andrzej Rybczak * + * electricityispower@gmail.com * + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) any later version. * + * * + * This program is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU General Public License for more details. * + * * + * You should have received a copy of the GNU General Public License * + * along with this program; if not, write to the * + * Free Software Foundation, Inc., * + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * + ***************************************************************************/ + +#include "tag_editor.h" + +#ifdef HAVE_TAGLIB_H + +extern ncmpcpp_config Config; +extern Menu *mTagEditor; + +string FindSharedDir(Menu *menu) +{ + SongList list; + for (int i = 0; i < menu->Size(); i++) + list.push_back(&menu->at(i)); + return FindSharedDir(list); +} + +string FindSharedDir(const SongList &v) +{ + string result; + if (!v.empty()) + { + result = v.front()->GetFile(); + for (SongList::const_iterator it = v.begin()+1; it != v.end(); it++) + { + int i = 1; + while (result.substr(0, i) == (*it)->GetFile().substr(0, i)) + i++; + result = result.substr(0, i); + } + int slash = result.find_last_of("/"); + result = slash != string::npos ? result.substr(0, slash) : "/"; + } + return result; +} + +string DisplayTag(const Song &s, void *data) +{ + switch (static_cast *>(data)->GetChoice()) + { + case 0: + return s.GetTitle(); + case 1: + return s.GetArtist(); + case 2: + return s.GetAlbum(); + case 3: + return s.GetYear(); + case 4: + return s.GetTrack(); + case 5: + return s.GetGenre(); + case 6: + return s.GetComment(); + case 8: + return s.GetShortFilename(); + default: + return ""; + } +} + +bool GetSongTags(Song &s) +{ + string path_to_file = Config.mpd_music_dir + "/" + s.GetFile(); + + TagLib::FileRef f(path_to_file.c_str()); + if (f.isNull()) + return false; + s.SetComment(f.tag()->comment().to8Bit(UNICODE)); + + mTagEditor->Clear(); + mTagEditor->Reset(); + + mTagEditor->AddStaticOption("[.b][.white]Song name: [/white][.green][/b]" + s.GetShortFilename() + "[/green]"); + mTagEditor->AddStaticOption("[.b][.white]Location in DB: [/white][.green][/b]" + s.GetDirectory() + "[/green]"); + mTagEditor->AddStaticOption(""); + mTagEditor->AddStaticOption("[.b][.white]Length: [/white][.green][/b]" + s.GetLength() + "[/green]"); + mTagEditor->AddStaticOption("[.b][.white]Bitrate: [/white][.green][/b]" + IntoStr(f.audioProperties()->bitrate()) + " kbps[/green]"); + mTagEditor->AddStaticOption("[.b][.white]Sample rate: [/white][.green][/b]" + IntoStr(f.audioProperties()->sampleRate()) + " Hz[/green]"); + mTagEditor->AddStaticOption("[.b][.white]Channels: [/white][.green][/b]" + (string)(f.audioProperties()->channels() == 1 ? "Mono" : "Stereo") + "[/green]"); + + mTagEditor->AddSeparator(); + + mTagEditor->AddOption("[.b]Title:[/b] " + s.GetTitle()); + mTagEditor->AddOption("[.b]Artist:[/b] " + s.GetArtist()); + mTagEditor->AddOption("[.b]Album:[/b] " + s.GetAlbum()); + mTagEditor->AddOption("[.b]Year:[/b] " + s.GetYear()); + mTagEditor->AddOption("[.b]Track:[/b] " + s.GetTrack()); + mTagEditor->AddOption("[.b]Genre:[/b] " + s.GetGenre()); + mTagEditor->AddOption("[.b]Comment:[/b] " + s.GetComment()); + mTagEditor->AddSeparator(); + mTagEditor->AddOption("Save"); + mTagEditor->AddOption("Cancel"); + return true; +} + +bool WriteTags(Song &s) +{ + string path_to_file = Config.mpd_music_dir + "/" + s.GetFile(); + TagLib::FileRef f(path_to_file.c_str()); + if (!f.isNull()) + { + s.GetEmptyFields(1); + f.tag()->setTitle(s.GetTitle()); + f.tag()->setArtist(TO_WSTRING(s.GetArtist())); + f.tag()->setAlbum(TO_WSTRING(s.GetAlbum())); + f.tag()->setYear(StrToInt(s.GetYear())); + f.tag()->setTrack(StrToInt(s.GetTrack())); + f.tag()->setGenre(TO_WSTRING(s.GetGenre())); + f.tag()->setComment(TO_WSTRING(s.GetComment())); + s.GetEmptyFields(0); + f.save(); + return true; + } + else + return false; +} + +#endif + diff --git a/src/tag_editor.h b/src/tag_editor.h new file mode 100644 index 00000000..938b326d --- /dev/null +++ b/src/tag_editor.h @@ -0,0 +1,45 @@ +/*************************************************************************** + * Copyright (C) 2008 by Andrzej Rybczak * + * electricityispower@gmail.com * + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) any later version. * + * * + * This program is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU General Public License for more details. * + * * + * You should have received a copy of the GNU General Public License * + * along with this program; if not, write to the * + * Free Software Foundation, Inc., * + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * + ***************************************************************************/ + +#include "ncmpcpp.h" + +#ifdef HAVE_TAGLIB_H + +#ifndef HAVE_TAG_EDITOR_H +#define HAVE_TAG_EDITOR_H + +// taglib headers +#include "fileref.h" +#include "tag.h" + +#include "mpdpp.h" +#include "settings.h" + +string FindSharedDir(Menu *); +string FindSharedDir(const SongList &); +string DisplayTag(const Song &, void *); + +bool GetSongTags(Song &); +bool WriteTags(Song &); + +#endif + +#endif +