From 58e9afd7adc54eecfcb25dea75ed9147bb26a748 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Henrik=20Rydg=C3=A5rd?= Date: Sun, 18 Jun 2023 15:13:16 +0200 Subject: [PATCH] Achievements: Show achievement icons in list --- Common/Math/geom2d.h | 7 +++++++ UI/RetroAchievementScreens.cpp | 16 ++++++++++++++-- UI/RetroAchievements.cpp | 17 ++++++++--------- UI/RetroAchievements.h | 6 +----- 4 files changed, 30 insertions(+), 16 deletions(-) diff --git a/Common/Math/geom2d.h b/Common/Math/geom2d.h index c063ca0d604b..7b470b1371cb 100644 --- a/Common/Math/geom2d.h +++ b/Common/Math/geom2d.h @@ -73,6 +73,13 @@ struct Bounds { return Bounds(x + xAmount, y + yAmount, w, h); } + Bounds Inset(float xAmount, float yAmount) const { + return Bounds(x + xAmount, y + yAmount, w - xAmount * 2, h - yAmount * 2); + } + Bounds Inset(float left, float top, float right, float bottom) const { + return Bounds(x + left, y + top, w - left - right, h - top - bottom); + } + float x; float y; float w; diff --git a/UI/RetroAchievementScreens.cpp b/UI/RetroAchievementScreens.cpp index 96444d3a8052..a9781c861162 100644 --- a/UI/RetroAchievementScreens.cpp +++ b/UI/RetroAchievementScreens.cpp @@ -4,6 +4,7 @@ #include "Common/UI/ViewGroup.h" #include "Common/UI/Context.h" #include "Common/Data/Text/I18n.h" +#include "Common/UI/IconCache.h" void RetroAchievementsListScreen::CreateViews() { auto di = GetI18NCategory(I18NCat::DIALOG); @@ -82,14 +83,16 @@ void RenderAchievement(UIContext &dc, const Achievements::Achievement &achieveme background.color = colorAlpha(background.color, opacity); + float iconSpace = 64.0f; + dc.Begin(); dc.FillRect(background, bounds); dc.SetFontScale(0.7f, 0.7f); - dc.DrawTextRect(achievement.title.c_str(), bounds.Expand(-5.0f, -5.0f), dc.theme->itemStyle.fgColor, ALIGN_TOPLEFT); + dc.DrawTextRect(achievement.title.c_str(), bounds.Inset(iconSpace + 5.0f, 5.0f, 5.0f, 5.0f), dc.theme->itemStyle.fgColor, ALIGN_TOPLEFT); dc.SetFontScale(0.5f, 0.5f); - dc.DrawTextRect(achievement.description.c_str(), bounds.Expand(-5.0f, -5.0f).Offset(0.0f, 30.0f), dc.theme->itemStyle.fgColor, ALIGN_TOPLEFT); + dc.DrawTextRect(achievement.description.c_str(), bounds.Inset(iconSpace + 5.0f, 30.0f, 5.0f, 5.0f), dc.theme->itemStyle.fgColor, ALIGN_TOPLEFT); char temp[64]; snprintf(temp, sizeof(temp), "%d", achievement.points); @@ -98,6 +101,15 @@ void RenderAchievement(UIContext &dc, const Achievements::Achievement &achieveme dc.DrawTextRect(temp, bounds.Expand(-5.0f, -5.0f), dc.theme->itemStyle.fgColor, ALIGN_RIGHT | ALIGN_VCENTER); dc.SetFontScale(1.0f, 1.0f); + dc.Flush(); + + std::string name = Achievements::GetAchievementBadgePath(achievement); + if (g_iconCache.BindIconTexture(&dc, name)) { + dc.Draw()->DrawTexRect(Bounds(bounds.x, bounds.y, iconSpace, iconSpace), 0.0f, 0.0f, 1.0f, 1.0f, 0xFFFFFFFF); + } + + dc.Flush(); + dc.RebindTexture(); dc.Flush(); } diff --git a/UI/RetroAchievements.cpp b/UI/RetroAchievements.cpp index f2d5b401719f..5ef8089bac6e 100644 --- a/UI/RetroAchievements.cpp +++ b/UI/RetroAchievements.cpp @@ -319,7 +319,6 @@ struct RAPIRequest : public T _dbg_assert_msg_(!api_request.post_data, "Download request does not have POST data"); - INFO_LOG(ACHIEVEMENTS, "Downloading image: %s (%s)", api_request.url, cache_filename.c_str()); Achievements::DownloadImage(api_request.url, std::move(cache_filename)); return true; } @@ -1086,9 +1085,13 @@ void Achievements::DownloadImage(std::string url, std::string cache_filename) g_iconCache.InsertIcon(cache_filename, IconFormat::PNG, std::move(data)); }; - s_http_downloader->CreateRequest(std::move(url), std::move(callback)); + if (g_iconCache.MarkPending(cache_filename)) { + INFO_LOG(ACHIEVEMENTS, "Downloading image: %s (%s)", url.c_str(), cache_filename.c_str()); + s_http_downloader->CreateRequest(std::move(url), std::move(callback)); + } } + void Achievements::DisplayAchievementSummary() { auto ac = GetI18NCategory(I18NCat::ACHIEVEMENTS); @@ -1209,7 +1212,7 @@ void Achievements::GetPatchesCallback(s32 status_code, std::string content_type, // try for a icon. not that we really need one, PSP games have their own icons... if (response.image_name && std::strlen(response.image_name) > 0) { - s_game_icon = g_gameIconCachePrefix + StringFromFormat("%d", s_game_id)); + s_game_icon = g_gameIconCachePrefix + StringFromFormat("%d", s_game_id); if (!g_iconCache.Contains(s_game_icon)) { RAPIRequest request; @@ -1988,15 +1991,11 @@ std::string Achievements::GetAchievementProgressText(const Achievement &achievem } // Note that this returns an g_iconCache key, rather than an actual filename. So look up your image there. -const std::string &Achievements::GetAchievementBadgePath(const Achievement &achievement, bool download_if_missing, bool force_unlocked_icon) +std::string Achievements::GetAchievementBadgePath(const Achievement &achievement, bool download_if_missing, bool force_unlocked_icon) { const bool use_locked = (achievement.locked && !force_unlocked_icon); - std::string &badge_path = use_locked ? achievement.locked_badge_path : achievement.unlocked_badge_path; - if (!badge_path.empty() || achievement.badge_name.empty()) - return badge_path; - - std::string badge_path = g_iconCachePrefix + achievement.badge_name + (use_locked ? "_lock" : ""); + std::string badge_path = g_iconCachePrefix + achievement.badge_name + std::string(use_locked ? "_lock" : ""); if (g_iconCache.Contains(badge_path)) { return badge_path; } diff --git a/UI/RetroAchievements.h b/UI/RetroAchievements.h index c726db6d3f42..3cbea6077d69 100644 --- a/UI/RetroAchievements.h +++ b/UI/RetroAchievements.h @@ -38,10 +38,6 @@ struct Achievement std::string memaddr; std::string badge_name; - // badge paths are mutable because they're resolved when they're needed. - mutable std::string locked_badge_path; - mutable std::string unlocked_badge_path; - u32 points; AchievementCategory category; bool locked; @@ -160,7 +156,7 @@ u32 GetPrimedAchievementCount(); const Achievement *GetAchievementByID(u32 id); std::pair GetAchievementProgress(const Achievement &achievement); std::string GetAchievementProgressText(const Achievement &achievement); -const std::string &GetAchievementBadgePath(const Achievement &achievement, bool download_if_missing = true, +std::string GetAchievementBadgePath(const Achievement &achievement, bool download_if_missing = true, bool force_unlocked_icon = false); std::string GetAchievementBadgeURL(const Achievement &achievement);