From e269ce5bd885f27b8feac922652b58e413393b7d Mon Sep 17 00:00:00 2001 From: Klaus Basan Date: Tue, 19 Sep 2017 00:44:19 +0200 Subject: [PATCH] Ref T152, do not start loading if the model dir does not exists/is empty --- src/blackmisc/directoryutils.cpp | 8 +++ src/blackmisc/directoryutils.h | 3 + .../simulation/aircraftmodelloader.cpp | 56 ++++++++++++++++++- .../simulation/aircraftmodelloader.h | 33 ++++++++--- 4 files changed, 90 insertions(+), 10 deletions(-) diff --git a/src/blackmisc/directoryutils.cpp b/src/blackmisc/directoryutils.cpp index 0d980a6fb..eea7e4e61 100644 --- a/src/blackmisc/directoryutils.cpp +++ b/src/blackmisc/directoryutils.cpp @@ -360,6 +360,14 @@ namespace BlackMisc return failed; } + bool CDirectoryUtils::existsUnemptyDirectory(const QString &testDir) + { + if (testDir.isEmpty()) { return false; } + const QDir dir(testDir); + if (!dir.exists()) { return false; } + return !dir.isEmpty(); + } + QSet CDirectoryUtils::fileNamesToQSet(const QFileInfoList &fileInfoList) { QSet sl; diff --git a/src/blackmisc/directoryutils.h b/src/blackmisc/directoryutils.h index 1526a6e85..2f875b07a 100644 --- a/src/blackmisc/directoryutils.h +++ b/src/blackmisc/directoryutils.h @@ -112,6 +112,9 @@ namespace BlackMisc //! Check if the (most important) runtime directories are available static QStringList verifyRuntimeDirectoriesAndFiles(); + //! Exists directory and does it contains files + static bool existsUnemptyDirectory(const QString &testDir); + //! Result of directory comparison struct DirComparison { diff --git a/src/blackmisc/simulation/aircraftmodelloader.cpp b/src/blackmisc/simulation/aircraftmodelloader.cpp index da38e51d2..1f8823bff 100644 --- a/src/blackmisc/simulation/aircraftmodelloader.cpp +++ b/src/blackmisc/simulation/aircraftmodelloader.cpp @@ -11,6 +11,7 @@ #include "blackmisc/simulation/fscommon/aircraftcfgparser.h" #include "blackmisc/simulation/xplane/aircraftmodelloaderxplane.h" #include "blackmisc/simulation/xplane/xplaneutil.h" +#include "blackmisc/directoryutils.h" #include "blackmisc/compare.h" #include "blackmisc/logmessage.h" @@ -18,6 +19,7 @@ #include #include +using namespace BlackMisc; using namespace BlackMisc::Simulation::Data; using namespace BlackMisc::Simulation::FsCommon; using namespace BlackMisc::Simulation::XPlane; @@ -36,6 +38,44 @@ namespace BlackMisc connect(&m_caches, &IMultiSimulatorModelCaches::cacheChanged, this, &IAircraftModelLoader::ps_cacheChanged); } + QString IAircraftModelLoader::enumToString(IAircraftModelLoader::LoadFinishedInfo info) + { + switch (info) + { + case CacheLoaded: return "cache loaded"; + case LoadingSkipped: return "loading skipped"; + case ParsedData: return "parsed data"; + default: break; + } + return "??"; + } + + QString IAircraftModelLoader::enumToString(IAircraftModelLoader::LoadModeFlag modeFlag) + { + switch (modeFlag) + { + case NotSet: return "not set"; + case LoadDirectly: return "load directly"; + case LoadInBackground: return "load in background"; + case CacheFirst: return "cache first"; + case CacheSkipped: return "cache skipped"; + case CacheOnly: return "cache only"; + default: break; + } + return "??"; + } + + QString IAircraftModelLoader::enumToString(LoadMode mode) + { + QStringList modes; + if (mode.testFlag(NotSet)) modes << enumToString(NotSet); + if (mode.testFlag(LoadDirectly)) modes << enumToString(LoadDirectly); + if (mode.testFlag(LoadInBackground)) modes << enumToString(LoadInBackground); + if (mode.testFlag(CacheFirst)) modes << enumToString(CacheFirst); + if (mode.testFlag(CacheSkipped)) modes << enumToString(CacheSkipped); + return modes.join(", "); + } + IAircraftModelLoader::~IAircraftModelLoader() { this->gracefulShutdown(); @@ -139,6 +179,8 @@ namespace BlackMisc { if (m_loadingInProgress) { return; } m_loadingInProgress = true; + m_loadingMessages.clear(); + const bool useCachedData = !mode.testFlag(CacheSkipped) && this->hasCachedData(); if (useCachedData && (mode.testFlag(CacheFirst) || mode.testFlag(CacheOnly))) { @@ -156,7 +198,16 @@ namespace BlackMisc return; } - // really load from disk + // really load from disk? + if (m_skipLoadingEmptyModelDir && !CDirectoryUtils::existsUnemptyDirectory(directory)) + { + const CStatusMessage status = CStatusMessage(this, CStatusMessage::SeverityWarning, "Empty or not existing %1 directory '%2', skipping read") + << this->getSimulator().toQString() << directory; + m_loadingMessages.push_back(status); + emit loadingFinished(status, this->getSimulator(), LoadingSkipped); + return; + } + this->startLoadingFromDisk(mode, modelConsolidation, directory); } @@ -177,13 +228,14 @@ namespace BlackMisc void IAircraftModelLoader::cancelLoading() { + if (!m_loadingInProgress) { return; } m_cancelLoading = true; - m_loadingInProgress = true; } void IAircraftModelLoader::gracefulShutdown() { this->cancelLoading(); + m_loadingInProgress = true; // avoids further startups } QString IAircraftModelLoader::getInfoString() const diff --git a/src/blackmisc/simulation/aircraftmodelloader.h b/src/blackmisc/simulation/aircraftmodelloader.h index f11d7ca26..b23dede58 100644 --- a/src/blackmisc/simulation/aircraftmodelloader.h +++ b/src/blackmisc/simulation/aircraftmodelloader.h @@ -68,10 +68,20 @@ namespace BlackMisc //! Load mode enum LoadFinishedInfo { - CacheLoaded, //!< cache was loaded - ParsedData //!< parsed data + CacheLoaded, //!< cache was loaded + ParsedData, //!< parsed data + LoadingSkipped //!< Loading skipped (empty directory) }; + //! Enum as string + static QString enumToString(LoadFinishedInfo info); + + //! Enum as string + static QString enumToString(LoadModeFlag modeFlag); + + //! Enum as string + static QString enumToString(LoadMode mode); + //! Destructor virtual ~IAircraftModelLoader(); @@ -102,8 +112,14 @@ namespace BlackMisc BlackMisc::Simulation::CAircraftModelList getCachedAircraftModels(const CSimulatorInfo &simulator) const; //! Count of loaded models + //! \threadsafe int getAircraftModelsCount() const { return getAircraftModels().size(); } + //! Skip the loading of empty (model) directories + //! \remark loading of empty directories might erase the cache and is normally disable + //! \threadsafe + void setSkipLoadingOfEmptyDirectories(bool skip); + //! Which simulator is supported by that very loader const CSimulatorInfo getSimulator() const; @@ -122,7 +138,7 @@ namespace BlackMisc //! Exclude directories QStringList getModelExcludeDirectoryPatterns() const; - //! Cancel read + //! Cancel loading void cancelLoading(); //! Shutdown @@ -176,11 +192,12 @@ namespace BlackMisc //! Start the loading process from disk virtual void startLoadingFromDisk(LoadMode mode, const ModelConsolidation &modelConsolidation, const QString &directory) = 0; - std::atomic m_cancelLoading { false }; //!< flag, requesting to cancel loading - std::atomic m_loadingInProgress { false }; //!< Loading in progress - BlackMisc::Simulation::Data::CModelCaches m_caches { false, this }; //!< caches - BlackMisc::Simulation::Settings::CMultiSimulatorSettings m_settings { this }; //!< settings - BlackMisc::CStatusMessageList m_loadingMessages; //!< loading messages + std::atomic m_cancelLoading { false }; //!< flag, requesting to cancel loading + std::atomic m_loadingInProgress { false }; //!< Loading in progress + std::atomic m_skipLoadingEmptyModelDir { true }; //!< Loading empty model dirs might erase the cache, so normally we skip it + Data::CModelCaches m_caches { false, this }; //!< caches used with this loader + Settings::CMultiSimulatorSettings m_settings { this }; //!< settings + CStatusMessageList m_loadingMessages; //!< loading messages protected slots: //! Loading finished, also logs messages