aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authordec05eba <dec05eba@protonmail.com>2021-09-22 20:10:48 +0200
committerdec05eba <dec05eba@protonmail.com>2021-09-22 20:10:48 +0200
commitfdeb82815db468ac7e99e9646f57bed2bf1832de (patch)
treeffc1ca95e05f47e26c21cce29f5510275e01787e
parent7934864d58ec39b237e2b45d0180aa567b29b944 (diff)
Sort anilist recommendations by best match, show episode duration, show titles differently
-rw-r--r--include/Body.hpp3
-rw-r--r--include/BodyItem.hpp8
-rw-r--r--src/Body.cpp41
-rw-r--r--src/BodyItem.cpp13
-rw-r--r--src/QuickMedia.cpp2
-rw-r--r--src/plugins/AniList.cpp25
-rw-r--r--src/plugins/Manga.cpp2
-rw-r--r--src/plugins/MangaCombined.cpp12
-rw-r--r--src/plugins/MyAnimeList.cpp8
9 files changed, 68 insertions, 46 deletions
diff --git a/include/Body.hpp b/include/Body.hpp
index 91913b5..4126697 100644
--- a/include/Body.hpp
+++ b/include/Body.hpp
@@ -117,8 +117,6 @@ namespace QuickMedia {
// TODO: Highlight the part of the text that matches the search.
void filter_search_fuzzy(const std::string &text);
- bool no_items_visible() const;
-
int get_selected_item() const { return selected_item; }
bool is_selected_item_last_visible_item() const;
@@ -162,6 +160,7 @@ namespace QuickMedia {
void update_dirty_state(BodyItem *body_item, float width);
void clear_body_item_cache(BodyItem *body_item);
sf::Vector2i get_item_thumbnail_size(BodyItem *item) const;
+
// Returns -1 if not found
int get_previous_visible_item(int start_index);
// Returns -1 if not found
diff --git a/include/BodyItem.hpp b/include/BodyItem.hpp
index e2f4918..5889d58 100644
--- a/include/BodyItem.hpp
+++ b/include/BodyItem.hpp
@@ -43,11 +43,10 @@ namespace QuickMedia {
class BodyItem {
public:
- BodyItem(std::string _title);
BodyItem(const BodyItem&) = delete;
BodyItem& operator=(const BodyItem &other);
- static std::shared_ptr<BodyItem> create(std::string title) { return std::make_shared<BodyItem>(std::move(title)); }
+ static std::shared_ptr<BodyItem> create(std::string title, bool selectable = true);
void set_title(std::string new_title) {
if(title == new_title)
@@ -122,6 +121,8 @@ namespace QuickMedia {
sf::Color get_description_color() const { return description_color; }
sf::Color get_author_color() const { return author_color; }
+ bool is_selectable() const { return selectable; }
+
void draw_list(Body *body, sf::RenderTarget &render_target);
// TODO: Use a list of strings instead, not all plugins need all of these fields
@@ -162,6 +163,8 @@ namespace QuickMedia {
// Internal use only
int keep_alive_frames = 0;
private:
+ BodyItem(std::string _title, bool selectable);
+ private:
// TODO: Clean up these strings when set in text, and get_title for example should return |title_text.getString()|
// TODO: Use sf::String instead, removes the need to convert to utf32 every time the text is dirty (for example when resizing window)
std::string title;
@@ -171,6 +174,7 @@ namespace QuickMedia {
sf::Color title_color;
sf::Color author_color;
sf::Color description_color;
+ bool selectable;
};
using BodyItems = std::vector<std::shared_ptr<BodyItem>>;
diff --git a/src/Body.cpp b/src/Body.cpp
index 5509938..d5395fd 100644
--- a/src/Body.cpp
+++ b/src/Body.cpp
@@ -441,13 +441,13 @@ namespace QuickMedia {
}
BodyItem* Body::get_selected() const {
- if(selected_item < 0 || selected_item >= (int)items.size() || !items[selected_item]->visible)
+ if(selected_item < 0 || selected_item >= (int)items.size() || !items[selected_item]->visible || !items[selected_item]->is_selectable())
return nullptr;
return items[selected_item].get();
}
std::shared_ptr<BodyItem> Body::get_selected_shared() {
- if(selected_item < 0 || selected_item >= (int)items.size() || !items[selected_item]->visible)
+ if(selected_item < 0 || selected_item >= (int)items.size() || !items[selected_item]->visible || !items[selected_item]->is_selectable())
return nullptr;
return items[selected_item];
}
@@ -694,11 +694,13 @@ namespace QuickMedia {
if(mouse_scroll_accel.y > 0.1f && prev_first_visible_item != -1) {
selected_item = prev_first_visible_item;
// TODO: Cache this
+ // TODO: Selectable item
if(on_top_reached && get_previous_visible_item(selected_item) == -1)
on_top_reached();
} else if(mouse_scroll_accel.y < -0.1f && prev_last_visible_item != -1) {
selected_item = prev_last_visible_item;
// TODO: Cache this
+ // TODO: Selectable item
if(on_bottom_reached && get_next_visible_item(selected_item) == -1)
on_bottom_reached();
}
@@ -1094,7 +1096,7 @@ namespace QuickMedia {
item_pos.x = std::floor(pos.x);
item_pos.y = std::floor(pos.y);
- if(body_theme == BODY_THEME_MODERN_SPACIOUS) {
+ if(body_theme == BODY_THEME_MODERN_SPACIOUS && item->is_selectable()) {
item_background.set_position(item_pos);
item_background.set_size(sf::Vector2f(size.x, item->loaded_height));
item_background.set_color(get_theme().shade_color);
@@ -1273,10 +1275,12 @@ namespace QuickMedia {
new_view.setViewport(sf::FloatRect(0.0f, scissor_y / (float)window_size.y, 1.0f, size.y / (float)window_size.y));
window.setView(new_view);
- item_background.set_position(round(pos + pos_offset));
- item_background.set_size(round(sf::Vector2f(card_width, item_height)));
- item_background.set_color(get_theme().card_item_background_color);
- item_background.draw(window);
+ if(item->is_selectable()) {
+ item_background.set_position(round(pos + pos_offset));
+ item_background.set_size(round(sf::Vector2f(card_width, item_height)));
+ item_background.set_color(get_theme().card_item_background_color);
+ item_background.draw(window);
+ }
handle_item_render(pos + pos_offset, card_width, item_height, item_index);
@@ -1759,11 +1763,15 @@ namespace QuickMedia {
void Body::filter_search_fuzzy_item(const std::string &text, BodyItem *body_item) {
const bool prev_visible = body_item->visible;
- body_item->visible = string_find_fuzzy_case_insensitive(body_item->get_title(), text);
- if(!body_item->visible && !body_item->get_description().empty())
- body_item->visible = string_find_fuzzy_case_insensitive(body_item->get_description(), text);
- if(!body_item->visible && !body_item->get_author().empty())
- body_item->visible = string_find_fuzzy_case_insensitive(body_item->get_author(), text);
+ if(!body_item->is_selectable()) {
+ body_item->visible = true;
+ } else {
+ body_item->visible = string_find_fuzzy_case_insensitive(body_item->get_title(), text);
+ if(!body_item->visible && !body_item->get_description().empty())
+ body_item->visible = string_find_fuzzy_case_insensitive(body_item->get_description(), text);
+ if(!body_item->visible && !body_item->get_author().empty())
+ body_item->visible = string_find_fuzzy_case_insensitive(body_item->get_author(), text);
+ }
if(prev_visible && !body_item->visible) {
clear_body_item_cache(body_item);
@@ -1773,14 +1781,7 @@ namespace QuickMedia {
}
}
- bool Body::no_items_visible() const {
- for(auto &item : items) {
- if(item->visible)
- return false;
- }
- return true;
- }
-
+ // TODO: Selectable
bool Body::is_selected_item_last_visible_item() const {
if(selected_item < 0 || selected_item >= (int)items.size() || !items[selected_item]->visible)
return false;
diff --git a/src/BodyItem.cpp b/src/BodyItem.cpp
index 0b41893..6523738 100644
--- a/src/BodyItem.cpp
+++ b/src/BodyItem.cpp
@@ -4,7 +4,12 @@
#include <cmath>
namespace QuickMedia {
- BodyItem::BodyItem(std::string _title) :
+ // static
+ std::shared_ptr<BodyItem> BodyItem::create(std::string title, bool selectable) {
+ return std::shared_ptr<BodyItem>(new BodyItem(std::move(title), selectable));
+ }
+
+ BodyItem::BodyItem(std::string _title, bool selectable) :
visible(true),
dirty(false),
dirty_description(false),
@@ -15,7 +20,8 @@ namespace QuickMedia {
timestamp(0),
title_color(get_theme().text_color),
author_color(get_theme().text_color),
- description_color(get_theme().text_color)
+ description_color(get_theme().text_color),
+ selectable(selectable)
{
if(!_title.empty())
set_title(std::move(_title));
@@ -43,7 +49,7 @@ namespace QuickMedia {
loaded_content_height = 0.0f;
embedded_item_status = other.embedded_item_status;
if(other.embedded_item) {
- embedded_item.reset(new BodyItem(""));
+ embedded_item.reset(new BodyItem("", true));
*embedded_item = *other.embedded_item;
} else {
embedded_item.reset();
@@ -66,6 +72,7 @@ namespace QuickMedia {
description_color = other.description_color;
extra = other.extra;
keep_alive_frames = other.keep_alive_frames;
+ selectable = other.selectable;
return *this;
}
diff --git a/src/QuickMedia.cpp b/src/QuickMedia.cpp
index 9b31580..bb71c73 100644
--- a/src/QuickMedia.cpp
+++ b/src/QuickMedia.cpp
@@ -4704,7 +4704,7 @@ namespace QuickMedia {
if(!related_body_item)
return false;
- body_item->embedded_item = std::make_shared<BodyItem>("");
+ body_item->embedded_item = BodyItem::create("");
*body_item->embedded_item = *related_body_item;
body_item->embedded_item->embedded_item = nullptr;
body_item->embedded_item->reactions.clear();
diff --git a/src/plugins/AniList.cpp b/src/plugins/AniList.cpp
index 0c7229f..5043eb7 100644
--- a/src/plugins/AniList.cpp
+++ b/src/plugins/AniList.cpp
@@ -28,6 +28,7 @@ query ($page: Int, $perPage: Int, $search: String) {
averageScore
episodes
chapters
+ duration
genres
coverImage {
medium
@@ -62,6 +63,7 @@ query ($id: Int) {
averageScore
episodes
chapters
+ duration
genres
description (asHtml: false)
coverImage {
@@ -99,6 +101,7 @@ query ($id: Int) {
averageScore
episodes
chapters
+ duration
genres
coverImage {
medium
@@ -117,7 +120,7 @@ query ($id: Int) {
static const std::string recommendations_query_graphql = R"END(
query ($id: Int, $page: Int, $perPage: Int) {
Media (id: $id) {
- recommendations (page: $page, perPage: $perPage) {
+ recommendations (page: $page, perPage: $perPage, sort: RATING_DESC) {
nodes {
mediaRecommendation {
id
@@ -137,6 +140,7 @@ query ($id: Int, $page: Int, $perPage: Int) {
averageScore
episodes
chapters
+ duration
genres
coverImage {
medium
@@ -288,6 +292,7 @@ query ($id: Int, $page: Int, $perPage: Int) {
const Json::Value &status_json = media_json["status"];
const Json::Value &episodes_json = media_json["episodes"];
const Json::Value &chapters_json = media_json["chapters"];
+ const Json::Value &duration_json = media_json["duration"];
const Json::Value &genres_json = media_json["genres"];
const Json::Value &description_json = media_json["description"];
@@ -356,6 +361,12 @@ query ($id: Int, $page: Int, $perPage: Int) {
description += "Chapters: " + std::to_string(chapters_json.asInt());
}
+ if(duration_json.isInt()) {
+ if(!description.empty())
+ description += '\n';
+ description += "Episode duration: " + std::to_string(duration_json.asInt()) + " minute" + (duration_json.asInt() == 1 ? "" : "s");
+ }
+
if(status_json.isString()) {
if(!description.empty())
description += '\n';
@@ -598,8 +609,8 @@ query ($id: Int, $page: Int, $perPage: Int) {
if(it.second.empty())
continue;
- auto anime_title_item = BodyItem::create("");
- anime_title_item->set_author("------------------------ " + it.first + " ------------------------");
+ auto anime_title_item = BodyItem::create("", false);
+ anime_title_item->set_author(it.first);
result_items.push_back(std::move(anime_title_item));
result_items.insert(result_items.end(), std::move_iterator(it.second.begin()), std::move_iterator(it.second.end()));
}
@@ -754,15 +765,15 @@ query ($id: Int, $page: Int, $perPage: Int) {
}
if(!anime_items.empty()) {
- auto anime_title_item = BodyItem::create("");
- anime_title_item->set_author("------------------------ Anime ------------------------");
+ auto anime_title_item = BodyItem::create("", false);
+ anime_title_item->set_author("Anime");
result_items.push_back(std::move(anime_title_item));
result_items.insert(result_items.end(), std::move_iterator(anime_items.begin()), std::move_iterator(anime_items.end()));
}
if(!manga_items.empty()) {
- auto manga_title_item = BodyItem::create("");
- manga_title_item->set_author("------------------------ Manga ------------------------");
+ auto manga_title_item = BodyItem::create("", false);
+ manga_title_item->set_author("Manga");
result_items.push_back(std::move(manga_title_item));
result_items.insert(result_items.end(), std::move_iterator(manga_items.begin()), std::move_iterator(manga_items.end()));
}
diff --git a/src/plugins/Manga.cpp b/src/plugins/Manga.cpp
index 1d44bee..5f0aae7 100644
--- a/src/plugins/Manga.cpp
+++ b/src/plugins/Manga.cpp
@@ -22,7 +22,7 @@ namespace QuickMedia {
}
std::shared_ptr<BodyItem> MangaChaptersPage::get_bookmark_body_item() {
- auto body_item = std::make_shared<BodyItem>(content_title);
+ auto body_item = BodyItem::create(content_title);
body_item->url = content_url;
return body_item;
}
diff --git a/src/plugins/MangaCombined.cpp b/src/plugins/MangaCombined.cpp
index 5440871..c7fdd13 100644
--- a/src/plugins/MangaCombined.cpp
+++ b/src/plugins/MangaCombined.cpp
@@ -56,8 +56,8 @@ namespace QuickMedia {
if(num_finished_plugins == search_threads.size()) {
for(auto &f : plugin_finished_state) {
if(f.second && !f.second->empty()) {
- auto title_item = BodyItem::create("");
- title_item->set_author("------------------------ " + f.first->title + " ------------------------");
+ auto title_item = BodyItem::create("", false);
+ title_item->set_author(f.first->title);
result_items.push_back(std::move(title_item));
result_items.insert(result_items.end(), std::move_iterator(f.second->begin()), std::move_iterator(f.second->end()));
}
@@ -72,14 +72,14 @@ namespace QuickMedia {
for(auto &f : plugin_finished_state) {
if(f.second) {
if(!f.second->empty()) {
- auto title_item = BodyItem::create("");
- title_item->set_author("------------------------ " + f.first->title + " ------------------------");
+ auto title_item = BodyItem::create("", false);
+ title_item->set_author(f.first->title);
result_items.push_back(std::move(title_item));
result_items.insert(result_items.end(), std::move_iterator(f.second->begin()), std::move_iterator(f.second->end()));
}
} else {
- auto title_item = BodyItem::create("");
- title_item->set_author("------------------------ " + f.first->title + " timed out ------------------------");
+ auto title_item = BodyItem::create("", false);
+ title_item->set_author(f.first->title + " timed out ");
result_items.push_back(std::move(title_item));
}
}
diff --git a/src/plugins/MyAnimeList.cpp b/src/plugins/MyAnimeList.cpp
index ceba73a..a4d1d30 100644
--- a/src/plugins/MyAnimeList.cpp
+++ b/src/plugins/MyAnimeList.cpp
@@ -134,15 +134,15 @@ namespace QuickMedia {
}
if(!anime_items.empty()) {
- auto anime_title_item = BodyItem::create("");
- anime_title_item->set_author("------------------------ Anime ------------------------");
+ auto anime_title_item = BodyItem::create("", false);
+ anime_title_item->set_author("Anime");
result_items.push_back(std::move(anime_title_item));
result_items.insert(result_items.end(), std::move_iterator(anime_items.begin()), std::move_iterator(anime_items.end()));
}
if(!manga_items.empty()) {
- auto manga_title_item = BodyItem::create("");
- manga_title_item->set_author("------------------------ Manga ------------------------");
+ auto manga_title_item = BodyItem::create("", false);
+ manga_title_item->set_author("Manga");
result_items.push_back(std::move(manga_title_item));
result_items.insert(result_items.end(), std::move_iterator(manga_items.begin()), std::move_iterator(manga_items.end()));
}