diff --git a/clementine-1.0.0rc1-fix-clementine-desktop.patch b/clementine-1.0.0rc1-fix-clementine-desktop.patch new file mode 100644 index 0000000..7ecca7c --- /dev/null +++ b/clementine-1.0.0rc1-fix-clementine-desktop.patch @@ -0,0 +1,34 @@ +Index: dist/clementine.desktop +=================================================================== +--- a/dist/clementine.desktop ++++ b/dist/clementine.desktop 2011-12-20 11:25:50.096248655 -0300 +@@ -13,29 +13,3 @@ + Categories=AudioVideo;Player;Qt; + StartupNotify=false + MimeType=application/ogg;application/x-ogg;application/x-ogm-audio;audio/aac;audio/mp4;audio/mpeg;audio/mpegurl;audio/ogg;audio/vnd.rn-realaudio;audio/vorbis;audio/x-flac;audio/x-mp3;audio/x-mpeg;audio/x-mpegurl;audio/x-ms-wma;audio/x-musepack;audio/x-oggflac;audio/x-pn-realaudio;audio/x-scpls;audio/x-speex;audio/x-vorbis;audio/x-vorbis+ogg;audio/x-wav;video/x-ms-asf;x-content/audio-player; +-X-Ayatana-Desktop-Shortcuts=Play;Pause;Stop;Previous;Next; +- +-[Play Shortcut Group] +-Name=Play +-Exec=clementine --play +-TargetEnvironment=Unity +- +-[Pause Shortcut Group] +-Name=Pause +-Exec=clementine --pause +-TargetEnvironment=Unity +- +-[Stop Shortcut Group] +-Name=Stop +-Exec=clementine --stop +-TargetEnvironment=Unity +- +-[Previous Shortcut Group] +-Name=Previous +-Exec=clementine --previous +-TargetEnvironment=Unity +- +-[Next Shortcut Group] +-Name=Next +-Exec=clementine --next +-TargetEnvironment=Unity diff --git a/clementine-1.0.1-liblastfm-1.0.patch b/clementine-1.0.1-liblastfm-1.0.patch new file mode 100644 index 0000000..691dba4 --- /dev/null +++ b/clementine-1.0.1-liblastfm-1.0.patch @@ -0,0 +1,475 @@ +--- a/src/core/song.cpp ++++ b/src/core/song.cpp +@@ -49,7 +49,7 @@ + + #ifdef HAVE_LIBLASTFM + #include "internet/fixlastfm.h" +- #include ++ #include + #endif + + #include +--- a/src/covers/lastfmcoverprovider.cpp ++++ b/src/covers/lastfmcoverprovider.cpp +@@ -19,8 +19,8 @@ + #include "coverprovider.h" + #include "lastfmcoverprovider.h" + +-#include +-#include ++#include ++#include + #include + + #include +@@ -52,14 +52,8 @@ void LastFmCoverProvider::QueryFinished( + + CoverSearchResults results; + +- try { +- lastfm::XmlQuery query(lastfm::ws::parse(reply)); +-#ifdef Q_OS_WIN32 +- if (lastfm::ws::last_parse_error != lastfm::ws::NoError) { +- throw std::runtime_error(""); +- } +-#endif +- ++ lastfm::XmlQuery query; ++ if (query.parse(reply->readAll())) { + // parse the list of search results + QList elements = query["results"]["albummatches"].children("album"); + +@@ -69,7 +63,7 @@ void LastFmCoverProvider::QueryFinished( + result.image_url = element["image size=extralarge"].text(); + results << result; + } +- } catch(std::runtime_error&) { ++ } else { + // Drop through and emit an empty list of results. + } + +--- a/src/internet/lastfmservice.cpp ++++ b/src/internet/lastfmservice.cpp +@@ -33,20 +33,18 @@ + + #include + +-#include ++#include + #include +-#include +-#include +-#include +-#include ++#include ++#include ++#include + #include +-#include ++#include + + #include + #include + + using boost::scoped_ptr; +-using lastfm::Scrobble; + using lastfm::XmlQuery; + + uint qHash(const lastfm::Track& track) { +@@ -300,13 +298,8 @@ void LastFMService::AuthenticateReplyFin + reply->deleteLater(); + + // Parse the reply +- try { +- lastfm::XmlQuery const lfm = lastfm::ws::parse(reply); +-#ifdef Q_OS_WIN32 +- if (lastfm::ws::last_parse_error != lastfm::ws::NoError) +- throw std::runtime_error(""); +-#endif +- ++ lastfm::XmlQuery lfm; ++ if (lfm.parse(reply->readAll())) { + lastfm::ws::Username = lfm["session"]["name"].text(); + lastfm::ws::SessionKey = lfm["session"]["key"].text(); + QString subscribed = lfm["session"]["subscriber"].text(); +@@ -318,8 +311,8 @@ void LastFMService::AuthenticateReplyFin + settings.setValue("Username", lastfm::ws::Username); + settings.setValue("Session", lastfm::ws::SessionKey); + settings.setValue("Subscriber", is_subscriber); +- } catch (std::runtime_error& e) { +- qLog(Error) << e.what(); ++ } else { ++ qLog(Error) << lfm.parseError().message(); + emit AuthenticationComplete(false); + return; + } +@@ -347,13 +340,8 @@ void LastFMService::UpdateSubscriberStat + + bool is_subscriber = false; + +- try { +- const lastfm::XmlQuery lfm = lastfm::ws::parse(reply); +-#ifdef Q_OS_WIN32 +- if (lastfm::ws::last_parse_error != lastfm::ws::NoError) +- throw std::runtime_error(""); +-#endif +- ++ lastfm::XmlQuery lfm; ++ if (lfm.parse(reply->readAll())) { + connection_problems_ = false; + QString subscriber = lfm["user"]["subscriber"].text(); + is_subscriber = (subscriber.toInt() == 1); +@@ -362,11 +350,9 @@ void LastFMService::UpdateSubscriberStat + settings.beginGroup(kSettingsGroup); + settings.setValue("Subscriber", is_subscriber); + qLog(Info) << lastfm::ws::Username << "Subscriber status:" << is_subscriber; +- } catch (lastfm::ws::ParseError e) { +- qLog(Error) << "Last.fm parse error: " << e.enumValue(); +- connection_problems_ = e.enumValue() == lastfm::ws::MalformedResponse; +- } catch (std::runtime_error& e) { +- qLog(Error) << e.what(); ++ } else { ++ qLog(Error) << "Last.fm parse error: " << lfm.parseError().message(); ++ connection_problems_ = lfm.parseError().enumValue() == lastfm::ws::MalformedResponse; + } + + emit UpdatedSubscriberStatus(is_subscriber); +@@ -469,7 +455,8 @@ bool LastFMService::InitScrobbler() { + scrobbler_ = new lastfm::Audioscrobbler(kAudioscrobblerClientId); + + //reemit the signal since the sender is private +- connect(scrobbler_, SIGNAL(status(int)), SIGNAL(ScrobblerStatus(int))); ++ connect(scrobbler_, SIGNAL(scrobblesSubmitted(QList)), SIGNAL(ScrobbleSubmitted())); ++ connect(scrobbler_, SIGNAL(nowPlayingError(int,QString)), SIGNAL(ScrobbleError(int))); + return true; + } + +@@ -497,7 +484,7 @@ void LastFMService::NowPlaying(const Son + if (!last_track_.isNull() && + last_track_.source() == lastfm::Track::NonPersonalisedBroadcast) { + const int duration_secs = last_track_.timestamp().secsTo(QDateTime::currentDateTime()); +- if (duration_secs >= ScrobblePoint::kScrobbleMinLength) { ++ if (duration_secs >= lastfm::ScrobblePoint::scrobbleTimeMin()) { + lastfm::MutableTrack mtrack(last_track_); + mtrack.setDuration(duration_secs); + +@@ -514,14 +501,16 @@ void LastFMService::NowPlaying(const Son + already_scrobbled_ = false; + last_track_ = mtrack; + +- //check immediately if the song is valid +- Scrobble::Invalidity invalidity; +- +- if (!lastfm::Scrobble(last_track_).isValid( &invalidity )) { +- //for now just notify this, we can also see the cause +- emit ScrobblerStatus(-1); +- return; +- } ++// TODO: validity was removed from liblastfm1 but might reappear, it should have ++// no impact as we get a different error when actually trying to scrobble. ++// //check immediately if the song is valid ++// Scrobble::Invalidity invalidity; ++// ++// if (!lastfm::Scrobble(last_track_).isValid( &invalidity )) { ++// //for now just notify this, we can also see the cause ++// emit ScrobbleError(-1); ++// return; ++// } + + scrobbler_->nowPlaying(mtrack); + } +@@ -530,12 +519,12 @@ void LastFMService::Scrobble() { + if (!InitScrobbler()) + return; + +- ScrobbleCache cache(lastfm::ws::Username); ++ lastfm::ScrobbleCache cache(lastfm::ws::Username); + qLog(Debug) << "There are" << cache.tracks().count() << "tracks in the last.fm cache."; + scrobbler_->cache(last_track_); + + // Let's mark a track as cached, useful when the connection is down +- emit ScrobblerStatus(30); ++ emit ScrobbleError(30); + scrobbler_->submit(); + + already_scrobbled_ = true; +@@ -640,7 +629,7 @@ void LastFMService::RefreshFriends(bool + return; + } + +- lastfm::AuthenticatedUser user; ++ lastfm::User user; + QNetworkReply* reply = user.getFriends(); + connect(reply, SIGNAL(finished()), SLOT(RefreshFriendsFinished())); + } +@@ -649,7 +638,7 @@ void LastFMService::RefreshNeighbours() + if (!neighbours_list_ || !IsAuthenticated()) + return; + +- lastfm::AuthenticatedUser user; ++ lastfm::User user; + QNetworkReply* reply = user.getNeighbours(); + connect(reply, SIGNAL(finished()), SLOT(RefreshNeighboursFinished())); + } +@@ -661,14 +650,11 @@ void LastFMService::RefreshFriendsFinish + + QList friends; + +- try { +- friends = lastfm::User::list(reply); +-#ifdef Q_OS_WIN32 +- if (lastfm::ws::last_parse_error != lastfm::ws::NoError) +- throw std::runtime_error(""); +-#endif +- } catch (std::runtime_error& e) { +- qLog(Error) << e.what(); ++ lastfm::XmlQuery lfm; ++ if (lfm.parse(reply->readAll())) { ++ friends = lastfm::UserList(lfm).users(); ++ } else { ++ qLog(Error) << lfm.parseError().message(); + return; + } + +@@ -708,14 +694,11 @@ void LastFMService::RefreshNeighboursFin + + QList neighbours; + +- try { +- neighbours = lastfm::User::list(reply); +-#ifdef Q_OS_WIN32 +- if (lastfm::ws::last_parse_error != lastfm::ws::NoError) +- throw std::runtime_error(""); +-#endif +- } catch (std::runtime_error& e) { +- qLog(Error) << e.what(); ++ lastfm::XmlQuery lfm; ++ if (lfm.parse(reply->readAll())) { ++ neighbours = lastfm::UserList(lfm).users(); ++ } else { ++ qLog(Error) << lfm.parseError().message(); + return; + } + +@@ -869,13 +852,8 @@ void LastFMService::FetchMoreTracksFinis + model()->task_manager()->SetTaskFinished(tune_task_id_); + tune_task_id_ = 0; + +- try { +- const XmlQuery& query = lastfm::ws::parse(reply); +-#ifdef Q_OS_WIN32 +- if (lastfm::ws::last_parse_error != lastfm::ws::NoError) +- throw std::runtime_error(""); +-#endif +- ++ XmlQuery query; ++ if (query.parse(reply->readAll())) { + const XmlQuery& playlist = query["playlist"]; + foreach (const XmlQuery& q, playlist["trackList"].children("track")) { + lastfm::MutableTrack t; +@@ -890,17 +868,9 @@ void LastFMService::FetchMoreTracksFinis + art_urls_[t] = q["image"].text(); + playlist_ << t; + } +- } catch (std::runtime_error& e) { +- // For some reason a catch block that takes a lastfm::ws::ParseError& +- // doesn't get called, even when a lastfm::ws::ParseError is thrown... +- // Hacks like this remind me of Java... +- if (QString(typeid(e).name()).contains("ParseError")) { +- // dynamic_cast throws a std::bad_cast ... *boggle* ++ } else { + emit StreamError(tr("Couldn't load the last.fm radio station") +- .arg(e.what())); +- } else { +- emit StreamError(tr("An unknown last.fm error occurred: %1").arg(e.what())); +- } ++ .arg(query.parseError().message())); + return; + } + +@@ -913,7 +883,7 @@ void LastFMService::Tune(const QUrl& url + + last_url_ = url; + initial_tune_ = true; +- const lastfm::RadioStation station(FixupUrl(url)); ++ const lastfm::RadioStation station(FixupUrl(url).toString()); + + playlist_.clear(); + +--- a/src/internet/lastfmservice.h ++++ b/src/internet/lastfmservice.h +@@ -27,7 +27,8 @@ class Track; + uint qHash(const lastfm::Track& track); + + #include "fixlastfm.h" +-#include ++#include ++#include + #include + + #include "internetmodel.h" +@@ -132,7 +133,8 @@ class LastFMService : public InternetSer + void ScrobblingEnabledChanged(bool value); + void ButtonVisibilityChanged(bool value); + void ScrobbleButtonVisibilityChanged(bool value); +- void ScrobblerStatus(int value); ++ void ScrobbleSubmitted(); ++ void ScrobbleError(int value); + void UpdatedSubscriberStatus(bool is_subscriber); + void ScrobbledRadioStream(); + +--- a/src/songinfo/lastfmtrackinfoprovider.cpp ++++ b/src/songinfo/lastfmtrackinfoprovider.cpp +@@ -22,7 +22,7 @@ + #include "ui/iconloader.h" + + #include +-#include ++#include + + void LastfmTrackInfoProvider::FetchInfo(int id, const Song& metadata) { + QMap params; +@@ -50,18 +50,12 @@ void LastfmTrackInfoProvider::RequestFin + return; + } + +- try { +- lastfm::XmlQuery query = lastfm::ws::parse(reply); +-#ifdef Q_OS_WIN32 +- if (lastfm::ws::last_parse_error != lastfm::ws::NoError) +- throw std::runtime_error(""); +-#endif +- ++ lastfm::XmlQuery query; ++ if (query.parse(reply->readAll())) { + GetPlayCounts(id, query); + GetWiki(id, query); + GetTags(id, query); + +- } catch (std::runtime_error&) { + } + emit Finished(id); + } +--- a/src/suggesters/lastfmsuggester.cpp ++++ b/src/suggesters/lastfmsuggester.cpp +@@ -1,6 +1,6 @@ + #include "lastfmsuggester.h" + +-#include ++#include + + #include "core/logging.h" + #include "core/timeconstants.h" +@@ -39,13 +39,8 @@ void LastFMSuggester::RequestFinished() + int id = it.value(); + replies_.erase(it); + +- try { +- lastfm::XmlQuery const lfm = lastfm::ws::parse(reply); +-#ifdef Q_OS_WIN32 +- if (lastfm::ws::last_parse_error != lastfm::ws::NoError) +- throw std::runtime_error(""); +-#endif +- ++ lastfm::XmlQuery lfm; ++ if (lfm.parse(reply->readAll())) { + const QList tracks = lfm["similartracks"].children("track"); + SongList songs; + foreach (const XmlQuery& q, tracks) { +@@ -59,8 +54,8 @@ void LastFMSuggester::RequestFinished() + } + qLog(Debug) << songs.length() << "suggested songs from Last.fm"; + emit SuggestSongsFinished(id, songs); +- } catch (std::runtime_error& e) { +- qLog(Error) << e.what(); ++ } else { ++ qLog(Error) << lfm.parseError().message(); + emit SuggestSongsFinished(id, SongList()); + } + } +--- a/src/ui/mainwindow.cpp ++++ b/src/ui/mainwindow.cpp +@@ -700,7 +700,8 @@ MainWindow::MainWindow( + connect(player_->playlists()->sequence(), SIGNAL(ShuffleModeChanged(PlaylistSequence::ShuffleMode)), osd_, SLOT(ShuffleModeChanged(PlaylistSequence::ShuffleMode))); + + #ifdef HAVE_LIBLASTFM +- connect(InternetModel::Service(), SIGNAL(ScrobblerStatus(int)), SLOT(ScrobblerStatus(int))); ++ connect(InternetModel::Service(), SIGNAL(ScrobbleSubmitted()), SLOT(ScrobbleSubmitted())); ++ connect(InternetModel::Service(), SIGNAL(ScrobbleError(int)), SLOT(ScrobbleError(int))); + + LastFMButtonVisibilityChanged(internet_model_->InternetModel::Service()->AreButtonsVisible()); + ScrobbleButtonVisibilityChanged(internet_model_->InternetModel::Service()->IsScrobbleButtonVisible()); +@@ -2201,30 +2202,26 @@ void MainWindow::SetToggleScrobblingIcon + } + + #ifdef HAVE_LIBLASTFM +-void MainWindow::ScrobblerStatus(int value) { ++void MainWindow::ScrobbleSubmitted() { + const LastFMService* lastfm_service = InternetModel::Service(); + const bool last_fm_enabled = ui_->action_toggle_scrobbling->isVisible() && + lastfm_service->IsScrobblingEnabled() && + lastfm_service->IsAuthenticated(); + ++ playlists_->active()->set_lastfm_status(Playlist::LastFM_Scrobbled); ++ // update the button icon ++ if (last_fm_enabled) ++ ui_->action_toggle_scrobbling->setIcon(QIcon(":/last.fm/as.png")); ++} ++ ++void MainWindow::ScrobbleError(int value) { ++ + switch (value) { + case -1: + // custom error value got from initial validity check + playlists_->active()->set_lastfm_status(Playlist::LastFM_Invalid); + break; + +- case 2: +- case 3: +- // we should get 3 for a correct scrobbling, but I just get 2 for +- // mysterious reasons +- // seems to scrobble fine though, so for now we accept it as correct +- playlists_->active()->set_lastfm_status(Playlist::LastFM_Scrobbled); +- +- // update the button icon +- if (last_fm_enabled) +- ui_->action_toggle_scrobbling->setIcon(QIcon(":/last.fm/as.png")); +- break; +- + case 30: + // Hack: when offline, liblastfm doesn't inform us, so set the status + // as queued; in this way we won't try to scrobble again, it will be done automatically +--- a/src/ui/mainwindow.h ++++ b/src/ui/mainwindow.h +@@ -224,7 +224,8 @@ class MainWindow : public QMainWindow, p + + void ShowCoverManager(); + #ifdef HAVE_LIBLASTFM +- void ScrobblerStatus(int value); ++ void ScrobbleSubmitted(); ++ void ScrobbleError(int value); + #endif + void ShowAboutDialog(); + void ShowTranscodeDialog(); +--- a/tests/mpris1_test.cpp ++++ b/tests/mpris1_test.cpp +@@ -22,7 +22,7 @@ + #include "playlist/playlistsequence.h" + #ifdef HAVE_LIBLASTFM + #include "internet/fixlastfm.h" +-#include ++#include + #endif + + #include "gmock/gmock.h" +--- a/tests/song_test.cpp ++++ b/tests/song_test.cpp +@@ -20,7 +20,7 @@ + #include "core/song.h" + #ifdef HAVE_LIBLASTFM + #include "internet/fixlastfm.h" +-#include ++#include + #endif + + #include "gmock/gmock.h" diff --git a/clementine.spec b/clementine.spec index 4c357ed..6ef9a95 100644 --- a/clementine.spec +++ b/clementine.spec @@ -2,7 +2,7 @@ Name: clementine Summary: A cross-platform music player based on Amarok 1.4 Group: Sound Version: 1.0.1 -Release: 2 +Release: 3 License: GPLv3 URL: http://www.clementine-player.org/ Source0: http://clementine-player.googlecode.com/files/%{name}-%{version}.tar.gz @@ -21,6 +21,10 @@ Patch4: clementine-1.0.1-fix-albumcoverfetch-crash.patch Patch5: clementine-1.0.1-fresh-start.patch # Fix build with new imobiledevice lib (from upstream) Patch6: clementine-1.0.1-new-imobiledevice.patch +# Fix desktop file +Patch7: clementine-1.0.0rc1-fix-clementine-desktop.patch +# Fix build with new liblastfm +Patch8: clementine-1.0.1-liblastfm-1.0.patch BuildRequires: qt4-devel >= 4.5.0 BuildRequires: pkgconfig(taglib) >= 1.6 @@ -84,6 +88,8 @@ Features: %patch4 -p1 %patch5 -p1 %patch6 -p1 +%patch7 -p1 +%patch8 -p1 %build %cmake_qt4 -DBUNDLE_PROJECTM_PRESETS=OFF -DBUILD_WERROR=OFF