mirror of
https://github.com/dolphin-emu/dolphin.git
synced 2025-02-09 21:40:10 +00:00
Merge pull request #5706 from JosJuice/more-gamelist-speedup-followup
More follow-up for the gamelist speedup PR
This commit is contained in:
commit
951f6400fb
@ -14,6 +14,8 @@
|
|||||||
namespace fs = std::experimental::filesystem;
|
namespace fs = std::experimental::filesystem;
|
||||||
#define HAS_STD_FILESYSTEM
|
#define HAS_STD_FILESYSTEM
|
||||||
#else
|
#else
|
||||||
|
#include <cstring>
|
||||||
|
#include "Common/CommonFuncs.h"
|
||||||
#include "Common/FileUtil.h"
|
#include "Common/FileUtil.h"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -55,11 +57,10 @@ std::vector<std::string> DoFileSearch(const std::vector<std::string>& directorie
|
|||||||
return true;
|
return true;
|
||||||
if (entry.isDirectory)
|
if (entry.isDirectory)
|
||||||
return false;
|
return false;
|
||||||
std::string name = entry.virtualName;
|
|
||||||
std::transform(name.begin(), name.end(), name.begin(), ::tolower);
|
|
||||||
return std::any_of(exts.begin(), exts.end(), [&](const std::string& ext) {
|
return std::any_of(exts.begin(), exts.end(), [&](const std::string& ext) {
|
||||||
|
const std::string& name = entry.virtualName;
|
||||||
return name.length() >= ext.length() &&
|
return name.length() >= ext.length() &&
|
||||||
name.compare(name.length() - ext.length(), ext.length(), ext) == 0;
|
strcasecmp(name.c_str() + name.length() - ext.length(), ext.c_str()) == 0;
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -25,7 +25,7 @@
|
|||||||
|
|
||||||
namespace DiscIO
|
namespace DiscIO
|
||||||
{
|
{
|
||||||
// Increment CACHE_REVISION (ISOFile.cpp & GameFile.cpp) if the enum below is modified
|
// Increment CACHE_REVISION (GameListCtrl.cpp) if the enum below is modified
|
||||||
enum class BlobType
|
enum class BlobType
|
||||||
{
|
{
|
||||||
PLAIN,
|
PLAIN,
|
||||||
|
@ -16,7 +16,7 @@ bool IsNTSC(Region region)
|
|||||||
return region == Region::NTSC_J || region == Region::NTSC_U || region == Region::NTSC_K;
|
return region == Region::NTSC_J || region == Region::NTSC_U || region == Region::NTSC_K;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Increment CACHE_REVISION (ISOFile.cpp & GameFile.cpp) if the code below is modified
|
// Increment CACHE_REVISION (GameListCtrl.cpp) if the code below is modified
|
||||||
|
|
||||||
Country TypicalCountryForRegion(Region region)
|
Country TypicalCountryForRegion(Region region)
|
||||||
{
|
{
|
||||||
|
@ -10,7 +10,7 @@
|
|||||||
|
|
||||||
namespace DiscIO
|
namespace DiscIO
|
||||||
{
|
{
|
||||||
// Increment CACHE_REVISION (ISOFile.cpp & GameFile.cpp) if these enums are modified
|
// Increment CACHE_REVISION (GameListCtrl.cpp) if these enums are modified
|
||||||
|
|
||||||
enum class Platform
|
enum class Platform
|
||||||
{
|
{
|
||||||
|
@ -80,6 +80,8 @@ public:
|
|||||||
wxProgressDialog* dialog;
|
wxProgressDialog* dialog;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
static constexpr u32 CACHE_REVISION = 2; // Last changed in PR 5687
|
||||||
|
|
||||||
static bool sorted = false;
|
static bool sorted = false;
|
||||||
|
|
||||||
static int CompareGameListItems(const GameListItem* iso1, const GameListItem* iso2,
|
static int CompareGameListItems(const GameListItem* iso1, const GameListItem* iso2,
|
||||||
|
@ -125,7 +125,6 @@ private:
|
|||||||
} m_image_indexes;
|
} m_image_indexes;
|
||||||
|
|
||||||
// Actual backing GameListItems are maintained in a background thread and cached to file
|
// Actual backing GameListItems are maintained in a background thread and cached to file
|
||||||
static constexpr u32 CACHE_REVISION = 2; // Last changed in PR 5687
|
|
||||||
std::list<std::shared_ptr<GameListItem>> m_cached_files;
|
std::list<std::shared_ptr<GameListItem>> m_cached_files;
|
||||||
// Locks the list, not the contents
|
// Locks the list, not the contents
|
||||||
std::mutex m_cache_mutex;
|
std::mutex m_cache_mutex;
|
||||||
|
@ -90,8 +90,9 @@ GameListItem::GameListItem(const std::string& filename)
|
|||||||
m_disc_number = volume->GetDiscNumber().value_or(0);
|
m_disc_number = volume->GetDiscNumber().value_or(0);
|
||||||
m_revision = volume->GetRevision().value_or(0);
|
m_revision = volume->GetRevision().value_or(0);
|
||||||
|
|
||||||
std::vector<u32> buffer = volume->GetBanner(&m_banner.width, &m_banner.height);
|
auto& banner = m_volume_banner;
|
||||||
ReadVolumeBanner(&m_banner.buffer, buffer, m_banner.width, m_banner.height);
|
std::vector<u32> buffer = volume->GetBanner(&banner.width, &banner.height);
|
||||||
|
ReadVolumeBanner(&banner.buffer, buffer, banner.width, banner.height);
|
||||||
|
|
||||||
m_valid = true;
|
m_valid = true;
|
||||||
}
|
}
|
||||||
@ -113,18 +114,17 @@ GameListItem::GameListItem(const std::string& filename)
|
|||||||
// A bit like the Homebrew Channel icon, except there can be multiple files
|
// A bit like the Homebrew Channel icon, except there can be multiple files
|
||||||
// in a folder with their own icons. Useful for those who don't want to have
|
// in a folder with their own icons. Useful for those who don't want to have
|
||||||
// a Homebrew Channel-style folder structure.
|
// a Homebrew Channel-style folder structure.
|
||||||
if (SetWxBannerFromPngFile(path + name + ".png"))
|
if (SetWxBannerFromPNGFile(path + name + ".png"))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
// Homebrew Channel icon. Typical for DOLs and ELFs,
|
// Homebrew Channel icon. The most typical icon format for DOLs and ELFs.
|
||||||
// but can be also used with volumes.
|
if (SetWxBannerFromPNGFile(path + "icon.png"))
|
||||||
if (SetWxBannerFromPngFile(path + "icon.png"))
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// Volume banner. Typical for everything that isn't a DOL or ELF.
|
// Volume banner. Typical for everything that isn't a DOL or ELF.
|
||||||
SetWxBannerFromRaw(m_banner);
|
SetWxBannerFromRaw(m_volume_banner);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -196,12 +196,12 @@ void GameListItem::DoState(PointerWrap& p)
|
|||||||
p.Do(m_blob_type);
|
p.Do(m_blob_type);
|
||||||
p.Do(m_revision);
|
p.Do(m_revision);
|
||||||
p.Do(m_disc_number);
|
p.Do(m_disc_number);
|
||||||
m_banner.DoState(p);
|
m_volume_banner.DoState(p);
|
||||||
m_emu_state.DoState(p);
|
m_emu_state.DoState(p);
|
||||||
p.Do(m_custom_name);
|
p.Do(m_custom_name);
|
||||||
if (p.GetMode() == PointerWrap::MODE_READ)
|
if (p.GetMode() == PointerWrap::MODE_READ)
|
||||||
{
|
{
|
||||||
SetWxBannerFromRaw(m_banner);
|
SetWxBannerFromRaw(m_volume_banner);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -227,7 +227,7 @@ void GameListItem::ReadVolumeBanner(std::vector<u8>* image, const std::vector<u3
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool GameListItem::SetWxBannerFromPngFile(const std::string& path)
|
bool GameListItem::SetWxBannerFromPNGFile(const std::string& path)
|
||||||
{
|
{
|
||||||
if (!File::Exists(path))
|
if (!File::Exists(path))
|
||||||
return false;
|
return false;
|
||||||
@ -242,13 +242,13 @@ bool GameListItem::SetWxBannerFromPngFile(const std::string& path)
|
|||||||
|
|
||||||
void GameListItem::SetWxBannerFromRaw(const Banner& banner)
|
void GameListItem::SetWxBannerFromRaw(const Banner& banner)
|
||||||
{
|
{
|
||||||
|
if (banner.empty())
|
||||||
|
return;
|
||||||
|
|
||||||
// Need to make explicit copy as wxImage uses reference counting for copies combined with only
|
// Need to make explicit copy as wxImage uses reference counting for copies combined with only
|
||||||
// taking a pointer, not the content, when given a buffer to its constructor.
|
// taking a pointer, not the content, when given a buffer to its constructor.
|
||||||
if (!banner.empty())
|
m_banner_wx.Create(banner.width, banner.height, false);
|
||||||
{
|
std::memcpy(m_banner_wx.GetData(), banner.buffer.data(), banner.buffer.size());
|
||||||
m_banner_wx.Create(banner.width, banner.height, false);
|
|
||||||
std::memcpy(m_banner_wx.GetData(), banner.buffer.data(), banner.buffer.size());
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool GameListItem::BannerChanged()
|
bool GameListItem::BannerChanged()
|
||||||
@ -256,27 +256,27 @@ bool GameListItem::BannerChanged()
|
|||||||
// Wii banners can only be read if there is a savefile,
|
// Wii banners can only be read if there is a savefile,
|
||||||
// so sometimes caches don't contain banners. Let's check
|
// so sometimes caches don't contain banners. Let's check
|
||||||
// if a banner has become available after the cache was made.
|
// if a banner has become available after the cache was made.
|
||||||
if ((m_platform == DiscIO::Platform::WII_DISC || m_platform == DiscIO::Platform::WII_WAD) &&
|
|
||||||
m_banner.empty())
|
if (!m_volume_banner.empty())
|
||||||
{
|
return false;
|
||||||
auto& banner = m_pending.banner;
|
if (m_platform != DiscIO::Platform::WII_DISC && m_platform != DiscIO::Platform::WII_WAD)
|
||||||
std::vector<u32> buffer =
|
return false;
|
||||||
DiscIO::Volume::GetWiiBanner(&banner.width, &banner.height, m_title_id);
|
|
||||||
if (buffer.size())
|
auto& banner = m_pending.volume_banner;
|
||||||
{
|
std::vector<u32> buffer = DiscIO::Volume::GetWiiBanner(&banner.width, &banner.height, m_title_id);
|
||||||
ReadVolumeBanner(&banner.buffer, buffer, banner.width, banner.height);
|
if (!buffer.size())
|
||||||
// Only reach here if m_banner was empty, so don't need to explicitly compare to see if
|
return false;
|
||||||
// different
|
|
||||||
return true;
|
ReadVolumeBanner(&banner.buffer, buffer, banner.width, banner.height);
|
||||||
}
|
// We only reach here if m_volume_banner was empty, so we don't need to explicitly
|
||||||
}
|
// compare to see if they are different
|
||||||
return false;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void GameListItem::BannerCommit()
|
void GameListItem::BannerCommit()
|
||||||
{
|
{
|
||||||
m_banner = std::move(m_pending.banner);
|
m_volume_banner = std::move(m_pending.volume_banner);
|
||||||
SetWxBannerFromRaw(m_banner);
|
SetWxBannerFromRaw(m_volume_banner);
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string GameListItem::GetDescription(DiscIO::Language language) const
|
std::string GameListItem::GetDescription(DiscIO::Language language) const
|
||||||
|
@ -94,7 +94,8 @@ private:
|
|||||||
void ReadVolumeBanner(std::vector<u8>* image, const std::vector<u32>& buffer, int width,
|
void ReadVolumeBanner(std::vector<u8>* image, const std::vector<u32>& buffer, int width,
|
||||||
int height);
|
int height);
|
||||||
// Outputs to m_banner_wx
|
// Outputs to m_banner_wx
|
||||||
bool SetWxBannerFromPngFile(const std::string& path);
|
bool SetWxBannerFromPNGFile(const std::string& path);
|
||||||
|
// Outputs to m_banner_wx
|
||||||
void SetWxBannerFromRaw(const Banner& banner);
|
void SetWxBannerFromRaw(const Banner& banner);
|
||||||
|
|
||||||
// IMPORTANT: Nearly all data members must be save/restored in DoState.
|
// IMPORTANT: Nearly all data members must be save/restored in DoState.
|
||||||
@ -120,7 +121,7 @@ private:
|
|||||||
u16 m_revision{};
|
u16 m_revision{};
|
||||||
u8 m_disc_number{};
|
u8 m_disc_number{};
|
||||||
|
|
||||||
Banner m_banner{};
|
Banner m_volume_banner{};
|
||||||
EmuState m_emu_state{};
|
EmuState m_emu_state{};
|
||||||
// Overridden name from TitleDatabase
|
// Overridden name from TitleDatabase
|
||||||
std::string m_custom_name{};
|
std::string m_custom_name{};
|
||||||
@ -133,7 +134,7 @@ private:
|
|||||||
struct
|
struct
|
||||||
{
|
{
|
||||||
EmuState emu_state;
|
EmuState emu_state;
|
||||||
Banner banner;
|
Banner volume_banner;
|
||||||
std::string custom_name;
|
std::string custom_name;
|
||||||
} m_pending{};
|
} m_pending{};
|
||||||
};
|
};
|
||||||
|
Loading…
x
Reference in New Issue
Block a user