mirror of
https://github.com/hrydgard/ppsspp.git
synced 2024-11-23 05:19:56 +00:00
Improve the pause screen achievement list, show a game banner at the top
This commit is contained in:
parent
c379f6f486
commit
80ff3f89bf
@ -11,22 +11,35 @@
|
||||
|
||||
void RetroAchievementsListScreen::CreateViews() {
|
||||
auto di = GetI18NCategory(I18NCat::DIALOG);
|
||||
auto ac = GetI18NCategory(I18NCat::ACHIEVEMENTS);
|
||||
|
||||
using namespace UI;
|
||||
|
||||
root_ = new ScrollView(UI::ORIENT_VERTICAL);
|
||||
|
||||
LinearLayout *listLayout = root_->Add(new LinearLayout(UI::ORIENT_VERTICAL));
|
||||
listLayout->SetSpacing(0.0f);
|
||||
listLayout->SetSpacing(5.0f);
|
||||
|
||||
std::vector<Achievements::Achievement> achievements;
|
||||
std::vector<Achievements::Achievement> unlockedAchievements;
|
||||
std::vector<Achievements::Achievement> lockedAchievements;
|
||||
|
||||
listLayout->Add(new GameAchievementSummaryView(Achievements::GetGameID()));
|
||||
|
||||
Achievements::EnumerateAchievements([&](const Achievements::Achievement &achievement) {
|
||||
achievements.push_back(achievement);
|
||||
if (achievement.locked) {
|
||||
lockedAchievements.push_back(achievement);
|
||||
} else {
|
||||
unlockedAchievements.push_back(achievement);
|
||||
}
|
||||
return true;
|
||||
});
|
||||
|
||||
for (auto achievement : achievements) {
|
||||
listLayout->Add(new ItemHeader(ac->T("Unlocked achievements")));
|
||||
for (auto achievement : unlockedAchievements) {
|
||||
listLayout->Add(new AchievementView(achievement));
|
||||
}
|
||||
listLayout->Add(new ItemHeader(ac->T("Locked achievements")));
|
||||
for (auto achievement : lockedAchievements) {
|
||||
listLayout->Add(new AchievementView(achievement));
|
||||
}
|
||||
}
|
||||
@ -106,6 +119,11 @@ void MeasureAchievement(const Achievements::Achievement &achievement, float *w,
|
||||
*h = 60.0f;
|
||||
}
|
||||
|
||||
void MeasureGameAchievementSummary(int gameID, float *w, float *h) {
|
||||
*w = 0.0f;
|
||||
*h = 60.0f;
|
||||
}
|
||||
|
||||
|
||||
// Render style references:
|
||||
|
||||
@ -124,11 +142,11 @@ void RenderAchievement(UIContext &dc, const Achievements::Achievement &achieveme
|
||||
dc.Begin();
|
||||
dc.FillRect(background, bounds);
|
||||
|
||||
dc.SetFontScale(0.7f, 0.7f);
|
||||
dc.SetFontScale(1.0f, 1.0f);
|
||||
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.Inset(iconSpace + 5.0f, 30.0f, 5.0f, 5.0f), dc.theme->itemStyle.fgColor, ALIGN_TOPLEFT);
|
||||
dc.SetFontScale(0.66f, 0.66f);
|
||||
dc.DrawTextRect(achievement.description.c_str(), bounds.Inset(iconSpace + 5.0f, 37.0f, 5.0f, 5.0f), dc.theme->itemStyle.fgColor, ALIGN_TOPLEFT);
|
||||
|
||||
char temp[64];
|
||||
snprintf(temp, sizeof(temp), "%d", achievement.points);
|
||||
@ -150,6 +168,41 @@ void RenderAchievement(UIContext &dc, const Achievements::Achievement &achieveme
|
||||
dc.Flush();
|
||||
}
|
||||
|
||||
void RenderGameAchievementSummary(UIContext &dc, int gameID, const Bounds &bounds, float opacity) {
|
||||
using namespace UI;
|
||||
UI::Drawable background = dc.theme->itemStyle.background;
|
||||
|
||||
background.color = colorAlpha(background.color, opacity);
|
||||
|
||||
float iconSpace = 64.0f;
|
||||
|
||||
dc.Begin();
|
||||
dc.FillRect(background, bounds);
|
||||
|
||||
dc.SetFontScale(1.0f, 1.0f);
|
||||
dc.DrawTextRect(Achievements::GetGameTitle().c_str(), bounds.Inset(iconSpace + 5.0f, 5.0f, 5.0f, 5.0f), dc.theme->itemStyle.fgColor, ALIGN_TOPLEFT);
|
||||
|
||||
std::string description = Achievements::GetGameAchievementSummary();
|
||||
std::string icon = Achievements::GetGameIcon();
|
||||
|
||||
dc.SetFontScale(0.66f, 0.66f);
|
||||
dc.DrawTextRect(description.c_str(), bounds.Inset(iconSpace + 5.0f, 30.0f, 5.0f, 5.0f), dc.theme->itemStyle.fgColor, ALIGN_TOPLEFT);
|
||||
|
||||
dc.SetFontScale(1.0f, 1.0f);
|
||||
dc.Flush();
|
||||
|
||||
std::string name = icon;
|
||||
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();
|
||||
}
|
||||
|
||||
|
||||
void AchievementView::Draw(UIContext &dc) {
|
||||
RenderAchievement(dc, achievement_, AchievementRenderStyle::LISTED, bounds_, 0.0f);
|
||||
}
|
||||
@ -157,3 +210,11 @@ void AchievementView::Draw(UIContext &dc) {
|
||||
void AchievementView::GetContentDimensions(const UIContext &dc, float &w, float &h) const {
|
||||
MeasureAchievement(achievement_, &w, &h);
|
||||
}
|
||||
|
||||
void GameAchievementSummaryView::Draw(UIContext &dc) {
|
||||
RenderGameAchievementSummary(dc, gameID_, bounds_, 0.0f);
|
||||
}
|
||||
|
||||
void GameAchievementSummaryView::GetContentDimensions(const UIContext &dc, float &w, float &h) const {
|
||||
MeasureGameAchievementSummary(gameID_, &w, &h);
|
||||
}
|
||||
|
@ -38,6 +38,8 @@ enum class AchievementRenderStyle {
|
||||
|
||||
void MeasureAchievement(const Achievements::Achievement &achievement, float *w, float *h);
|
||||
void RenderAchievement(UIContext &context, const Achievements::Achievement &achievement, AchievementRenderStyle style, const Bounds &bounds, float time_s);
|
||||
void MeasureGameAchievementSummary(int gameID, float *w, float *h);
|
||||
|
||||
|
||||
class AchievementView : public UI::Item {
|
||||
public:
|
||||
@ -48,3 +50,13 @@ public:
|
||||
private:
|
||||
Achievements::Achievement achievement_;
|
||||
};
|
||||
|
||||
class GameAchievementSummaryView : public UI::Item {
|
||||
public:
|
||||
GameAchievementSummaryView(int gameID, UI::LayoutParams *layoutParams = nullptr) : UI::Item(layoutParams), gameID_(gameID) {}
|
||||
|
||||
void Draw(UIContext &dc) override;
|
||||
void GetContentDimensions(const UIContext &dc, float &w, float &h) const override;
|
||||
private:
|
||||
int gameID_;
|
||||
};
|
||||
|
@ -1064,6 +1064,22 @@ void Achievements::DownloadImage(std::string url, std::string cache_filename)
|
||||
}
|
||||
}
|
||||
|
||||
std::string Achievements::GetGameAchievementSummary() {
|
||||
auto ac = GetI18NCategory(I18NCat::ACHIEVEMENTS);
|
||||
|
||||
std::string summary;
|
||||
if (GetAchievementCount() > 0) {
|
||||
summary = StringFromFormat(ac->T("Earned", "You have unlocked %d of %d achievements, earning %d of %d points"),
|
||||
GetUnlockedAchiementCount(), GetAchievementCount(), GetCurrentPointsForGame(), GetMaximumPointsForGame());
|
||||
} else {
|
||||
summary = ac->T("This game has no achievements");
|
||||
}
|
||||
if (GetLeaderboardCount() > 0) {
|
||||
if (LeaderboardsActive())
|
||||
summary.append("\nLeaderboard submission is enabled.");
|
||||
}
|
||||
return summary;
|
||||
}
|
||||
|
||||
void Achievements::DisplayAchievementSummary()
|
||||
{
|
||||
@ -1075,21 +1091,7 @@ void Achievements::DisplayAchievementSummary()
|
||||
else
|
||||
title = s_game_title;
|
||||
|
||||
std::string summary;
|
||||
if (GetAchievementCount() > 0)
|
||||
{
|
||||
summary = StringFromFormat(ac->T("Earned", "You have earned %d of %d achievements, and %d of %d points"),
|
||||
GetUnlockedAchiementCount(), GetAchievementCount(), GetCurrentPointsForGame(), GetMaximumPointsForGame());
|
||||
} else
|
||||
{
|
||||
summary = ac->T("This game has no achievements");
|
||||
}
|
||||
if (GetLeaderboardCount() > 0)
|
||||
{
|
||||
summary.push_back('\n');
|
||||
if (LeaderboardsActive())
|
||||
summary.append("Leaderboard submission is enabled.");
|
||||
}
|
||||
std::string summary = GetGameAchievementSummary();
|
||||
|
||||
OSDAddNotification(10.0f, title, summary, s_game_icon);
|
||||
|
||||
@ -1814,7 +1816,7 @@ void Achievements::SubmitLeaderboardCallback(s32 status_code, std::string conten
|
||||
rc_runtime_format_lboard_value(best_score, sizeof(best_score), response.best_score, lb->format);
|
||||
|
||||
auto ac = GetI18NCategory(I18NCat::ACHIEVEMENTS);
|
||||
const char *formatString = ac->T("Your Score");
|
||||
const char *formatString = ac->T("Submitted Score");
|
||||
std::string summary = StringFromFormat(formatString,
|
||||
submitted_score, best_score, response.new_rank, response.num_entries);
|
||||
|
||||
|
@ -140,6 +140,8 @@ const std::string &GetGameTitle();
|
||||
const std::string &GetGameIcon();
|
||||
|
||||
bool EnumerateAchievements(std::function<bool(const Achievement &)> callback);
|
||||
|
||||
// TODO: Make these support multiple games, not just the current games, with cached info.
|
||||
u32 GetUnlockedAchiementCount();
|
||||
u32 GetAchievementCount();
|
||||
u32 GetMaximumPointsForGame();
|
||||
@ -154,6 +156,7 @@ u32 GetPrimedAchievementCount();
|
||||
|
||||
const Achievement *GetAchievementByID(u32 id);
|
||||
std::pair<u32, u32> GetAchievementProgress(const Achievement &achievement);
|
||||
std::string GetGameAchievementSummary();
|
||||
std::string GetAchievementProgressText(const Achievement &achievement);
|
||||
std::string GetAchievementBadgePath(const Achievement &achievement, bool download_if_missing = true,
|
||||
bool force_unlocked_icon = false);
|
||||
|
@ -1279,4 +1279,4 @@ VR controllers = VR controllers
|
||||
[Achievements]
|
||||
Earned = You have earned %d of %d achievements, and %d of %d points
|
||||
This game has no achievements = This game has no achievements
|
||||
Your Score = Your Score: %d (Best: %d)\nLeaderboard Position: %d of %d
|
||||
Submitted Score = Submitted score: %d (Best: %d)\nLeaderboard Position: %d of %d
|
Loading…
Reference in New Issue
Block a user