diff --git a/CMakeLists.txt.user b/CMakeLists.txt.user index 86b00b1..ceedb86 100644 --- a/CMakeLists.txt.user +++ b/CMakeLists.txt.user @@ -1,6 +1,6 @@ - + ProjectExplorer.Project.ActiveTarget @@ -236,8 +236,8 @@ UbuntuProjectManager.UploadStep - /home/boghison/Projects/build-MixCloud-Ubuntu_Device_GCC_armhf_ubuntu_sdk_14_10_utopic-Default/com.ubuntu.developer.boghison.mixcloud_0.1_armhf.click /usr/share/qtcreator/ubuntu/scripts/qtc_device_applaunch.py + /home/boghison/Projects/build-MixCloud-Ubuntu_Device_GCC_armhf_ubuntu_sdk_14_10_utopic-Default/com.ubuntu.developer.boghison.mixcloud_0.1_armhf.click 127.0.0.1 @@ -252,8 +252,8 @@ /var/lib/schroot/chroots/click-ubuntu-sdk-14.10-armhf - 2014-11-17T16:46:12 - 2014-11-17T16:46:12 + 2014-11-19T18:08:12 + 2014-11-19T18:08:12 2 @@ -303,21 +303,19 @@ 13 14 - -1 + 1 - - - false - %{buildDir} - Custom Executable - - ProjectExplorer.CustomExecutableRunConfiguration + + mixcloudscope + UbuntuProjectManager.RemoteRunConfiguration.Scopemixcloudscope 3768 false true false false true + false + true 1 diff --git a/include/api/client.h b/include/api/client.h index 3b3eeee..d01296e 100644 --- a/include/api/client.h +++ b/include/api/client.h @@ -41,6 +41,7 @@ class Client { int repost_count; User user; std::string slug; + std::string created; }; /** diff --git a/include/scope/query.h b/include/scope/query.h index 5d40dde..3f17173 100644 --- a/include/scope/query.h +++ b/include/scope/query.h @@ -25,6 +25,7 @@ class Query: public unity::scopes::SearchQueryBase { void cancelled() override; void run(const unity::scopes::SearchReplyProxy &reply) override; + void parseCasts(unity::scopes::CategorisedResult &hotRes, const api::Client::CloudCast &hotCast); private: std::string installdir; diff --git a/src/api/client.cpp b/src/api/client.cpp index 3d9db58..450d649 100644 --- a/src/api/client.cpp +++ b/src/api/client.cpp @@ -7,6 +7,8 @@ #include #include #include +#include +#include namespace http = core::net::http; @@ -52,7 +54,9 @@ void Client::get(const net::Uri::Path &path, // Build the URI from its components net::Uri uri = net::make_uri(config_->apiroot, path, parameters); - configuration.uri = client->uri_to_string(uri); + std::string temporaryUri = client->uri_to_string(uri); + configuration.uri = boost::replace_all_copy(temporaryUri, "%20", "+"); + qDebug(configuration.uri.c_str()); // Give out a user agent string configuration.header.add("User-Agent", config_->user_agent); @@ -118,7 +122,8 @@ Client::CloudCasts Client::parseJson(QJsonDocument root){ listener_count, repost_count, myUser, - item["slug"].toString().toStdString() + item["slug"].toString().toStdString(), + item["created_time"].toString().toStdString() }); } return result; diff --git a/src/scope/preview.cpp b/src/scope/preview.cpp index ace953e..2144daa 100644 --- a/src/scope/preview.cpp +++ b/src/scope/preview.cpp @@ -28,54 +28,53 @@ void Preview::run(sc::PreviewReplyProxy const& reply) { if (result["getExtra"].get_bool()){ layoutcol1.add_column({"image", "header", "description", "expandable", "button"}); layoutcol2.add_column({"image", "header", "button"}); - layoutcol2.add_column({"description", "audio_length", "favoritecount", "listencount", "repostcount"}); + layoutcol2.add_column({"description", "audio_length", "favoritecount", "listencount", "repostcount", "created"}); } else{ layoutcol1.add_column({"image", "header", "expandable", "button"}); layoutcol2.add_column({"image", "header", "button"}); - layoutcol2.add_column({"audio_length", "favoritecount", "listencount", "repostcount"}); + layoutcol2.add_column({"audio_length", "favoritecount", "listencount", "repostcount", "created"}); } reply->register_layout({layoutcol1, layoutcol2}); - sc::PreviewWidget header("header", "header"); + sc::PreviewWidget created("created", "text"), header("header", "header"), button("button", "actions"), image("image", "image"), expandable("expandable", "expandable"), listencount("listencount", "text"), favoritecount("favoritecount", "text"), repostcount("repostcount", "text"), audio_length("audio_length", "text"); + QString dateString = QString::fromUtf8(result["created"].get_string().data(), result["created"].get_string().size()); + QDate date = QDate::fromString(dateString, Qt::ISODate); + QString fullDate = date.toString(Qt::SystemLocaleShortDate); + created.add_attribute_value("text", sc::Variant("Uploaded on " + fullDate.toStdString())); header.add_attribute_mapping("title", "title"); header.add_attribute_mapping("subtitle", "subtitle"); - sc::PreviewWidget button("button", "actions"); sc::VariantBuilder builder; builder.add_tuple({ {"id", sc::Variant("open")}, {"label",sc::Variant("Open")}, {"uri", result["uri"]} }); - sc::PreviewWidget image("image", "image"); image.add_attribute_mapping("source", "art"); button.add_attribute_value("actions", builder.end()); - sc::PreviewWidget expandable("expandable", "expandable"); expandable.add_attribute_value("title", sc::Variant("Additional info")); - sc::PreviewWidget audio_length("audio_length", "text"); - audio_length.add_attribute_value("title", sc::Variant("Length")); - audio_length.add_attribute_value("text", result["audio_length"]); - sc::PreviewWidget listencount("listencount", "text"); - sc::PreviewWidget favoritecount("favoritecount", "text"); - sc::PreviewWidget repostcount("repostcount", "text"); - listencount.add_attribute_value("title", sc::Variant("Play Count")); - favoritecount.add_attribute_value("title", sc::Variant("Favorite Count")); - repostcount.add_attribute_value("title", sc::Variant("Repost Count")); - listencount.add_attribute_value("text", (result["listen"].get_int() == 0) ? sc::Variant("None") : result["listen"]); - favoritecount.add_attribute_value("text", (result["favorite"].get_int() == 0) ? sc::Variant("None") : result["favorite"]); - repostcount.add_attribute_value("text", (result["repost"].get_int() == 0) ? sc::Variant("None") : result["repost"]); + audio_length.add_attribute_value("text", sc::Variant("⌚ " + result["audio_length"].get_string())); + listencount.add_attribute_value("text", sc::Variant(std::to_string(result["listen"].get_int()) + " ♪♫")); + favoritecount.add_attribute_value("text", sc::Variant(std::to_string(result["favorite"].get_int()) + " ♥")); + repostcount.add_attribute_value("text", sc::Variant(std::to_string(result["repost"].get_int()) + " ♺")); expandable.add_widget(audio_length); - expandable.add_widget(listencount); expandable.add_widget(favoritecount); + expandable.add_widget(listencount); expandable.add_widget(repostcount); + expandable.add_widget(created); if (result["getExtra"].get_bool()){ sc::PreviewWidget description("description", "text"); description.add_attribute_value("title", sc::Variant("Description")); std::vector full = client_.getExtra(1, result["username"].get_string() + "/" + result["slug"].get_string()); - description.add_attribute_value("text", sc::Variant(full[0])); - reply->push({image, header, description, button, expandable, audio_length, listencount, favoritecount, repostcount}); + if (full[0] != ""){ + description.add_attribute_value("text", sc::Variant(full[0])); + reply->push({image, header, description, button, expandable, audio_length, favoritecount, listencount, repostcount, created}); + } + else { + reply->push({image, header, button, expandable, audio_length, favoritecount, listencount, repostcount, created}); + } } else{ - reply->push({image, header, button, expandable, audio_length, listencount, favoritecount, repostcount}); + reply->push({image, header, button, expandable, audio_length, favoritecount, listencount, repostcount, created}); } } else { @@ -83,7 +82,7 @@ void Preview::run(sc::PreviewReplyProxy const& reply) { sc::ColumnLayout layoutcol1(1), layoutcol2(2); layoutcol1.add_column({"image", "header", "bio", "expandable", "button"}); layoutcol2.add_column({"image", "header", "button"}); - layoutcol2.add_column({"bio", "location", "created_time", "cloudcast_count", "favorite_count", "follower_count", "following_count"}); + layoutcol2.add_column({"bio", "location", "favorite_count", "cloudcast_count", "follower_count", "following_count", "created_time"}); reply->register_layout({layoutcol1, layoutcol2}); } else { @@ -91,17 +90,15 @@ void Preview::run(sc::PreviewReplyProxy const& reply) { layout.add_column({"image", "header", "button"}); reply->register_layout({layout}); } - sc::PreviewWidget header("header", "header"); + sc::PreviewWidget header("header", "header"), button("button", "actions"), image("image", "image"); header.add_attribute_mapping("title", "title"); header.add_attribute_mapping("subtitle", "subtitle"); - sc::PreviewWidget button("button", "actions"); sc::VariantBuilder builder; builder.add_tuple({ {"id", sc::Variant("open")}, {"label",sc::Variant("Open")}, {"uri", result["uri"]} }); - sc::PreviewWidget image("image", "image"); image.add_attribute_mapping("source", "art"); button.add_attribute_value("actions", builder.end()); if (result["getExtra"].get_bool()) { @@ -109,30 +106,36 @@ void Preview::run(sc::PreviewReplyProxy const& reply) { sc::PreviewWidget bio("bio", "text"), expandable("expandable", "expandable"), location("location", "text"), created_time("created_time", "text"), cloudcast_count("cloudcast_count", "text"), favorite_count("favorite_count", "text"), follower_count("follower_count", "text"), following_count("following_count", "text"); bio.add_attribute_value("title", sc::Variant("Bio")); bio.add_attribute_value("text", sc::Variant(full[7])); - std::string fullLocation = full[0] + ", " + full[2]; - //location.add_attribute_value("title", sc::Variant("Location")); + string fullLocation; + if (full[0] == "" && full[2] == ""){ + fullLocation = "N/A"; + } + else if (full[0] == "" && full[2] != ""){ + fullLocation = full[2]; + } + else if (full[0] != "" && full [2] != ""){ + fullLocation = full[0] + ", " + full[2]; + } + else { + fullLocation = full[0]; + } location.add_attribute_value("text", sc::Variant("Lives in " + fullLocation)); QString dateString = QString::fromUtf8(full[3].data(), full[3].size()); QDate date = QDate::fromString(dateString, Qt::ISODate); - QString fullDate = date.toString("d MMMM yyyy"); - //created_time.add_attribute_value("title", sc::Variant("Created on")); - created_time.add_attribute_value("text", sc::Variant("Created on " + fullDate.toStdString())); - //cloudcast_count.add_attribute_value("title", sc::Variant("Cloucast Count")); - cloudcast_count.add_attribute_value("text", sc::Variant(full[4] + " Cloudcasts")); - //favorite_count.add_attribute_value("title", sc::Variant("Favorite Count")); - favorite_count.add_attribute_value("text", sc::Variant(full[5] + " Favorites")); - //follower_count.add_attribute_value("title", sc::Variant("Follower Count")); + QString fullDate = date.toString(Qt::SystemLocaleShortDate); + created_time.add_attribute_value("text", sc::Variant("Account created on " + fullDate.toStdString())); + cloudcast_count.add_attribute_value("text", sc::Variant(full[4] + " ☁")); + favorite_count.add_attribute_value("text", sc::Variant(full[5] + " ♥")); follower_count.add_attribute_value("text", sc::Variant(full[6] + " Followers")); - //following_count.add_attribute_value("title", sc::Variant("Following Count")); following_count.add_attribute_value("text", sc::Variant("Following " + full[1])); expandable.add_attribute_value("title", sc::Variant("Additional Info")); - expandable.add_widget(created_time); expandable.add_widget(location); - expandable.add_widget(cloudcast_count); expandable.add_widget(favorite_count); + expandable.add_widget(cloudcast_count); expandable.add_widget(follower_count); expandable.add_widget(following_count); - reply->push({image, header, button, expandable, bio, location, created_time, cloudcast_count, favorite_count, follower_count, following_count}); + expandable.add_widget(created_time); + reply->push({image, header, expandable, button, bio, location, favorite_count, cloudcast_count, follower_count, following_count, created_time}); } else{ reply->push({image, header, button}); diff --git a/src/scope/query.cpp b/src/scope/query.cpp index 449d9d3..ece4697 100644 --- a/src/scope/query.cpp +++ b/src/scope/query.cpp @@ -1,5 +1,3 @@ -#include -#include #include #include @@ -10,9 +8,10 @@ #include #include #include +#include +#include namespace sc = unity::scopes; -namespace alg = boost::algorithm; using namespace std; using namespace api; @@ -56,8 +55,7 @@ void Query::run(sc::SearchReplyProxy const& reply) { const sc::CannedQuery &query(sc::SearchQueryBase::query()); sc::SearchMetadata myData = sc::SearchQueryBase::search_metadata(); client_.cardinality = myData.cardinality(); - string query_string = alg::trim_copy(query.query_string()); - string emblemPath = Query::installdir + "/mixcloud.svg"; + string query_string = query.query_string(); if (query_string.empty()){ Client::CloudCasts hotCasts; Client::CloudCasts newCasts; @@ -67,24 +65,7 @@ void Query::run(sc::SearchReplyProxy const& reply) { auto new_category = reply->register_category("newCasts", "New", "", sc::CategoryRenderer(TRACKS_TEMPLATE)); for (const auto &hotCast : hotCasts.cloudcast){ sc::CategorisedResult hotRes(hot_category); - hotRes.set_uri(hotCast.url); - hotRes.set_title(hotCast.name); - hotRes.set_art(hotCast.thumbnail); - hotRes["subtitle"] = hotCast.user.name; - hotRes["username"] = hotCast.user.username; - hotRes["type"] = "cloudcast"; - hotRes["getExtra"] = getExtra; - hotRes["repost"] = hotCast.repost_count; - hotRes["slug"] = hotCast.slug; - hotRes["listen"] = hotCast.listener_count; - hotRes["favorite"] = hotCast.favorite_count; - hotRes["audio_length"] = hotCast.audio_length; - string myValue = "♥ " + std::to_string(hotCast.favorite_count); - sc::VariantBuilder builder; - builder.add_tuple({{"value", sc::Variant(hotCast.audio_length)}}); - builder.add_tuple({{"value", sc::Variant(myValue)}}); - hotRes["attributes"] = builder.end(); - hotRes["emblem"] = emblemPath; + parseCasts(hotRes, hotCast); if (!reply->push(hotRes)){ return; } @@ -92,24 +73,7 @@ void Query::run(sc::SearchReplyProxy const& reply) { if (showNew){ for (const auto &newCast : newCasts.cloudcast){ sc::CategorisedResult newRes(new_category); - newRes.set_uri(newCast.url); - newRes.set_title(newCast.name); - newRes.set_art(newCast.thumbnail); - newRes["subtitle"] = newCast.user.name; - newRes["type"] = "cloudcast"; - newRes["slug"] = newCast.slug; - newRes["repost"] = newCast.repost_count; - newRes["username"] = newCast.user.username; - newRes["listen"] = newCast.listener_count; - newRes["favorite"] = newCast.favorite_count; - newRes["audio_length"] = newCast.audio_length; - newRes["getExtra"] = getExtra; - string myValue = "♪♫" + std::to_string(newCast.listener_count); - sc::VariantBuilder builder; - builder.add_tuple({{"value", sc::Variant(newCast.audio_length)}}); - builder.add_tuple({{"value", sc::Variant(myValue)}}); - newRes["attributes"] = builder.end(); - newRes["emblem"] = emblemPath; + parseCasts(newRes, newCast); if (!reply->push(newRes)){ return; } @@ -124,24 +88,7 @@ void Query::run(sc::SearchReplyProxy const& reply) { auto user_category = reply->register_category("users", "Users", "", sc::CategoryRenderer(USERS_TEMPLATE)); for (const auto &cast : castResults.cloudcast){ sc::CategorisedResult castRes(cast_category); - castRes.set_title(cast.name); - castRes.set_uri(cast.url); - castRes.set_art(cast.thumbnail); - castRes["subtitle"] = cast.user.name; - castRes["repost"] = cast.repost_count; - castRes["listen"] = cast.listener_count; - castRes["favorite"] = cast.favorite_count; - castRes["type"] = "cloudcast"; - castRes["username"] = cast.user.username; - castRes["slug"] = cast.slug; - castRes["getExtra"] = getExtra; - castRes["audio_length"] = cast.audio_length; - string myValue = "♥ " + std::to_string(cast.favorite_count); - sc::VariantBuilder builder; - builder.add_tuple({{"value", sc::Variant(cast.audio_length)}}); - builder.add_tuple({{"value", sc::Variant(myValue)}}); - castRes["attributes"] = builder.end(); - castRes["emblem"] = emblemPath; + parseCasts(castRes, cast); if (!reply->push(castRes)){ return; } @@ -167,3 +114,33 @@ void Query::run(sc::SearchReplyProxy const& reply) { } } +void Query::parseCasts(sc::CategorisedResult &hotRes, const api::Client::CloudCast &hotCast){ + string emblemPath = Query::installdir + "/mixcloud.svg"; + hotRes.set_uri(hotCast.url); + hotRes.set_title(hotCast.name); + hotRes.set_art(hotCast.thumbnail); + hotRes["subtitle"] = hotCast.user.name; + hotRes["username"] = hotCast.user.username; + hotRes["type"] = "cloudcast"; + hotRes["getExtra"] = getExtra; + hotRes["repost"] = hotCast.repost_count; + hotRes["slug"] = hotCast.slug; + hotRes["listen"] = hotCast.listener_count; + hotRes["favorite"] = hotCast.favorite_count; + hotRes["audio_length"] = hotCast.audio_length; + hotRes["created"] = hotCast.created; + string myValue; + if (hotCast.favorite_count != 0) { + myValue = std::to_string(hotCast.favorite_count) + " ♥"; + } + else { + myValue = std::to_string(hotCast.listener_count) + " ♪♫"; + } + sc::VariantBuilder builder; + builder.add_tuple({{"value", sc::Variant("⌚ " + hotCast.audio_length)}}); + builder.add_tuple({{"value", sc::Variant(myValue)}}); + hotRes["attributes"] = builder.end(); + hotRes["emblem"] = emblemPath; +} + +