void ArtistBiography::FetchInfo(int id, const Song& metadata) { if (metadata.artist().isEmpty()) { emit Finished(id); return; } QUrl url(kArtistBioUrl); url.addQueryItem("artist", metadata.artist()); url.addQueryItem("lang", GetLocale()); qLog(Debug) << "Biography url: " << url; QNetworkRequest request(url); QNetworkReply* reply = network_->get(request); NewClosure(reply, SIGNAL(finished()), [this, reply, id]() { reply->deleteLater(); QJson::Parser parser; QVariantMap response = parser.parse(reply).toMap(); QString body = response["articleBody"].toString(); QString url = response["url"].toString(); CountdownLatch* latch = new CountdownLatch; if (url.contains("wikipedia.org")) { FetchWikipediaImages(id, url, latch); FetchWikipediaArticle(id, url, latch); } else { latch->Wait(); // Use the simple article body from KG. if (!body.isEmpty()) { CollapsibleInfoPane::Data data; data.id_ = url; data.title_ = tr("Biography"); data.type_ = CollapsibleInfoPane::Data::Type_Biography; QString text; text += "<p><a href=\"" + url + "\">" + tr("Open in your browser") + "</a></p>"; text += body; SongInfoTextView* editor = new SongInfoTextView; editor->SetHtml(text); data.contents_ = editor; emit InfoReady(id, data); } latch->CountDown(); } NewClosure(latch, SIGNAL(Done()), [this, id, latch]() { latch->deleteLater(); emit Finished(id); }); }); }
void ArtistBiography::FetchWikipediaArticle(int id, const QString& wikipedia_url, CountdownLatch* latch) { latch->Wait(); QRegExp regex("([a-z]+)\\.wikipedia\\.org/wiki/(.*)"); if (regex.indexIn(wikipedia_url) == -1) { emit Finished(id); return; } QString wiki_title = QUrl::fromPercentEncoding(regex.cap(2).toUtf8()); QString language = regex.cap(1); QUrl url(QString(kWikipediaExtractUrl).arg(language)); url.addQueryItem("titles", wiki_title); QNetworkRequest request(url); QNetworkReply* reply = network_->get(request); qLog(Debug) << "Article url:" << url; NewClosure(reply, SIGNAL(finished()), [this, id, reply, wikipedia_url, latch]() { reply->deleteLater(); QJson::Parser parser; QVariantMap json = parser.parse(reply).toMap(); QString html = ExtractExtract(json); CollapsibleInfoPane::Data data; data.id_ = wikipedia_url; data.title_ = tr("Biography"); data.type_ = CollapsibleInfoPane::Data::Type_Biography; data.icon_ = IconLoader::Load("wikipedia", IconLoader::Provider); QString text; text += "<p><a href=\"" + wikipedia_url + "\">" + tr("Open in your browser") + "</a></p>"; text += html; SongInfoTextView* editor = new SongInfoTextView; editor->SetHtml(text); data.contents_ = editor; emit InfoReady(id, data); latch->CountDown(); }); }
void LastfmTrackInfoProvider::GetWiki(int id, const lastfm::XmlQuery& q) { // Parse the response if (q["track"].children("wiki").isEmpty()) return; // No wiki element const QString content = q["track"]["wiki"]["content"].text(); if (content.isEmpty()) return; // No useful data CollapsibleInfoPane::Data data; data.id_ = "lastfm/songwiki"; data.title_ = tr("Last.fm wiki"); data.type_ = CollapsibleInfoPane::Data::Type_Biography; data.icon_ = QIcon(":/last.fm/as.png"); SongInfoTextView* widget = new SongInfoTextView; data.contents_ = widget; widget->SetHtml(content); emit InfoReady(id, data); }
void LastfmTrackInfoProvider::GetPlayCounts(int id, const lastfm::XmlQuery& q) { // Parse the response const int listeners = q["track"]["listeners"].text().toInt(); const int playcount = q["track"]["playcount"].text().toInt(); int myplaycount = -1; bool love = false; if (!q["track"].children("userplaycount").isEmpty()) { myplaycount = q["track"]["userplaycount"].text().toInt(); love = q["track"]["userloved"].text() == "1"; } if (!listeners && !playcount && myplaycount == -1) return; // No useful data CollapsibleInfoPane::Data data; data.id_ = "lastfm/playcounts"; data.title_ = tr("Last.fm play counts"); data.type_ = CollapsibleInfoPane::Data::Type_PlayCounts; data.icon_ = QIcon(":/last.fm/as.png"); SongPlayStats* widget = new SongPlayStats; data.contents_ = widget; if (myplaycount != -1) { if (love) widget->AddItem(QIcon(":/last.fm/love.png"), tr("You love this track")); widget->AddItem(QIcon(":/last.fm/icon_user.png"), tr("Your scrobbles: %1").arg(myplaycount)); } if (playcount) widget->AddItem(IconLoader::Load("media-playback-start"), tr("%L1 total plays").arg(playcount)); if (listeners) widget->AddItem(QIcon(":/last.fm/my_neighbours.png"), tr("%L1 other listeners").arg(listeners)); emit InfoReady(id, data); }
void LastfmTrackInfoProvider::GetTags(int id, const lastfm::XmlQuery& q) { // Parse the response if (q["track"].children("toptags").isEmpty() || q["track"]["toptags"].children("tag").isEmpty()) return; // No tag elements CollapsibleInfoPane::Data data; data.id_ = "lastfm/songtags"; data.title_ = tr("Last.fm tags"); data.type_ = CollapsibleInfoPane::Data::Type_Biography; data.icon_ = QIcon(":/last.fm/icon_tag.png"); TagWidget* widget = new TagWidget(TagWidget::Type_Tags); data.contents_ = widget; widget->SetIcon(data.icon_); for (const lastfm::XmlQuery& e : q["track"]["toptags"].children("tag")) { widget->AddTag(e["name"].text()); } emit InfoReady(id, data); }