Skip to content

Commit

Permalink
Merge branch 'master' into svc_ach_runtime_export_tests
Browse files Browse the repository at this point in the history
  • Loading branch information
Jamiras committed Feb 10, 2024
2 parents 3427a9e + 791c79e commit ea80421
Show file tree
Hide file tree
Showing 18 changed files with 969 additions and 177 deletions.
4 changes: 2 additions & 2 deletions src/RA_Defs.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -103,10 +103,10 @@ const char* ValueFormatToString(ValueFormat nFormat) noexcept
switch (nFormat)
{
case ValueFormat::Centiseconds: return "MILLISECS";
case ValueFormat::Frames: return "FRAMES";
case ValueFormat::Frames: return "TIME";
case ValueFormat::Minutes: return "MINUTES";
case ValueFormat::Score: return "SCORE";
case ValueFormat::Seconds: return "SECS";
case ValueFormat::Seconds: return "TIMESECS";
case ValueFormat::SecondsAsMinutes: return "SECS_AS_MINS";
case ValueFormat::Value: return "VALUE";
case ValueFormat::Float1: return "FLOAT1";
Expand Down
2 changes: 1 addition & 1 deletion src/RA_Version.rc
Original file line number Diff line number Diff line change
Expand Up @@ -77,7 +77,7 @@ BEGIN
VALUE "FileDescription", "RetroAchievements Integration Toolkit"
VALUE "FileVersion", RA_INTEGRATION_VERSION_MAJOR, RA_INTEGRATION_VERSION_MINOR, RA_INTEGRATION_VERSION_PATCH, RA_INTEGRATION_VERSION_REVISION
VALUE "InternalName", "RA_Integration"
VALUE "LegalCopyright", "Copyright (C) 2023 retroachievements.org"
VALUE "LegalCopyright", "Copyright (C) 2024 retroachievements.org"
VALUE "OriginalFilename", "RA_Integration.dll"
VALUE "ProductName", "RetroAchievements Integration Toolkit"
VALUE "ProductVersion", RA_INTEGRATION_VERSION_PRODUCT_ARCH
Expand Down
173 changes: 90 additions & 83 deletions src/data/context/GameContext.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -218,108 +218,113 @@ void GameContext::FinishLoadGame(int nResult, const char* sErrorMessage, bool bW

void GameContext::EndLoadGame(int nResult, bool bWasPaused, bool bShowSoftcoreWarning)
{
ra::data::models::RichPresenceModel* pRichPresence = nullptr;
std::string sOldRichPresence;

if (nResult == RC_OK && m_nGameId > 0) {
BeginLoad();

auto pCodeNotes = std::make_unique<ra::data::models::CodeNotesModel>();
pCodeNotes->Refresh(m_nGameId,
[this](ra::ByteAddress nAddress, const std::wstring& sNewNote) {
OnCodeNoteChanged(nAddress, sNewNote);
},
[this]() {
EndLoad();
});

m_vAssets.Append(std::move(pCodeNotes));

// the old server value (if different from current server value) will be stored as Local modification.
// capture it now. ReloadAssets will load the XXX-Rich.txt file and replace it
pRichPresence = m_vAssets.FindRichPresence();
if (pRichPresence)
sOldRichPresence = pRichPresence->GetScript();

// merge local assets
std::vector<ra::data::models::AssetModelBase*> vEmptyAssetsList;
m_vAssets.ReloadAssets(vEmptyAssetsList);
}

if (!bWasPaused)
{
ra::services::ServiceLocator::GetMutable<ra::services::AchievementRuntime>().SetPaused(false);
#ifndef RA_UTEST
auto& pAssetList = ra::services::ServiceLocator::GetMutable<ra::ui::viewmodels::WindowManager>().AssetList;
pAssetList.SetProcessingActive(true);
#endif
}
ra::data::models::RichPresenceModel* pRichPresence = nullptr;
std::string sOldRichPresence;

// activate rich presence (or remove if not defined)
if (pRichPresence && nResult == RC_OK)
{
// if the server value differs from the local value, the model will appear as Unpublished
if (pRichPresence->GetChanges() != ra::data::models::AssetChanges::None)
std::lock_guard<std::mutex> lock(m_mLoadMutex);

if (nResult == RC_OK && m_nGameId > 0)
{
// populate another model with the old script so the string gets normalized correctly
ra::data::models::RichPresenceModel pOldRichPresenceModel;
pOldRichPresenceModel.SetScript(sOldRichPresence);

// if the old value matches the current value, then the value on the server changed and
// there are no local modifications. revert to the server state.
if (pRichPresence->GetScript() == pOldRichPresenceModel.GetScript())
pRichPresence->RestoreServerCheckpoint();
BeginLoad();

auto pCodeNotes = std::make_unique<ra::data::models::CodeNotesModel>();
pCodeNotes->Refresh(
m_nGameId,
[this](ra::ByteAddress nAddress, const std::wstring& sNewNote) {
OnCodeNoteChanged(nAddress, sNewNote);
},
[this]() { EndLoad(); });

m_vAssets.Append(std::move(pCodeNotes));

// the old server value (if different from current server value) will be stored as Local modification.
// capture it now. ReloadAssets will load the XXX-Rich.txt file and replace it
pRichPresence = m_vAssets.FindRichPresence();
if (pRichPresence)
sOldRichPresence = pRichPresence->GetScript();

// merge local assets
std::vector<ra::data::models::AssetModelBase*> vEmptyAssetsList;
m_vAssets.ReloadAssets(vEmptyAssetsList);
}

if (pRichPresence->GetScript().empty() && pRichPresence->GetChanges() == ra::data::models::AssetChanges::None)
if (!bWasPaused)
{
const auto nIndex = m_vAssets.FindItemIndex(ra::data::models::AssetModelBase::TypeProperty,
ra::etoi(ra::data::models::AssetType::RichPresence));
m_vAssets.RemoveAt(nIndex);
ra::services::ServiceLocator::GetMutable<ra::services::AchievementRuntime>().SetPaused(false);
#ifndef RA_UTEST
auto& pAssetList = ra::services::ServiceLocator::GetMutable<ra::ui::viewmodels::WindowManager>().AssetList;
pAssetList.SetProcessingActive(true);
#endif
}
else

// activate rich presence (or remove if not defined)
if (pRichPresence && nResult == RC_OK)
{
pRichPresence->Activate();
// if the server value differs from the local value, the model will appear as Unpublished
if (pRichPresence->GetChanges() != ra::data::models::AssetChanges::None)
{
// populate another model with the old script so the string gets normalized correctly
ra::data::models::RichPresenceModel pOldRichPresenceModel;
pOldRichPresenceModel.SetScript(sOldRichPresence);

// if the old value matches the current value, then the value on the server changed and
// there are no local modifications. revert to the server state.
if (pRichPresence->GetScript() == pOldRichPresenceModel.GetScript())
pRichPresence->RestoreServerCheckpoint();
}

if (pRichPresence->GetScript().empty() &&
pRichPresence->GetChanges() == ra::data::models::AssetChanges::None)
{
const auto nIndex = m_vAssets.FindItemIndex(ra::data::models::AssetModelBase::TypeProperty,
ra::etoi(ra::data::models::AssetType::RichPresence));
m_vAssets.RemoveAt(nIndex);
}
else
{
pRichPresence->Activate();
}
}
}

// modified assets should start in the inactive state
size_t nLocalAssets = 0;
for (gsl::index nIndex = 0; nIndex < gsl::narrow_cast<gsl::index>(m_vAssets.Count()); ++nIndex)
{
auto* pAsset = m_vAssets.GetItemAt(nIndex);
if (pAsset != nullptr && pAsset->GetChanges() != ra::data::models::AssetChanges::None)
// modified assets should start in the inactive state
size_t nLocalAssets = 0;
for (gsl::index nIndex = 0; nIndex < gsl::narrow_cast<gsl::index>(m_vAssets.Count()); ++nIndex)
{
if (pAsset->HasUnpublishedChanges())
++nLocalAssets;

if (pAsset->IsActive())
auto* pAsset = m_vAssets.GetItemAt(nIndex);
if (pAsset != nullptr && pAsset->GetChanges() != ra::data::models::AssetChanges::None)
{
if (pAsset->GetType() == ra::data::models::AssetType::RichPresence &&
ra::services::ServiceLocator::Get<ra::ui::viewmodels::WindowManager>()
.RichPresenceMonitor.IsVisible())
if (pAsset->HasUnpublishedChanges())
++nLocalAssets;

if (pAsset->IsActive())
{
// if rich presence monitor is open, allow modified rich presence to remain active. otherwise,
// it will be activated when the monitor is opened. it cannot be activated from the list.
continue;
}
if (pAsset->GetType() == ra::data::models::AssetType::RichPresence &&
ra::services::ServiceLocator::Get<ra::ui::viewmodels::WindowManager>()
.RichPresenceMonitor.IsVisible())
{
// if rich presence monitor is open, allow modified rich presence to remain active. otherwise,
// it will be activated when the monitor is opened. it cannot be activated from the list.
continue;
}

pAsset->SetState(ra::data::models::AssetState::Inactive);
pAsset->SetState(ra::data::models::AssetState::Inactive);
}
}
}
}
if (nLocalAssets > 0)
{
RA_LOG_INFO("%d unpublished assets loaded", nLocalAssets);
}
if (nLocalAssets > 0)
{
RA_LOG_INFO("%d unpublished assets loaded", nLocalAssets);
}

// finish up
m_vAssets.EndUpdate();
// finish up
m_vAssets.EndUpdate();

auto& pRuntime = ra::services::ServiceLocator::GetMutable<ra::services::AchievementRuntime>();
pRuntime.SyncAssets();
auto& pRuntime = ra::services::ServiceLocator::GetMutable<ra::services::AchievementRuntime>();
pRuntime.SyncAssets();

EndLoad();
EndLoad();
}

// non-hardcore warning
auto& pConfiguration = ra::services::ServiceLocator::Get<ra::services::IConfiguration>();
Expand Down Expand Up @@ -504,6 +509,8 @@ void GameContext::EndLoad()

void GameContext::DoFrame()
{
std::lock_guard<std::mutex> lock(m_mLoadMutex);

for (gsl::index nIndex = 0; nIndex < gsl::narrow_cast<gsl::index>(m_vAssets.Count()); ++nIndex)
{
auto* pItem = m_vAssets.GetItemAt(nIndex);
Expand Down
2 changes: 2 additions & 0 deletions src/data/context/GameContext.hh
Original file line number Diff line number Diff line change
Expand Up @@ -148,6 +148,8 @@ private:

std::atomic<int> m_nLoadCount = 0;
int m_nMasteryPopupId = 0;

std::mutex m_mLoadMutex;
};

} // namespace context
Expand Down
Loading

0 comments on commit ea80421

Please sign in to comment.