// Copyright (c) 2012-2022 Wojciech Figat. All rights reserved.
#pragma once
#include "../AssetInfo.h"
#include "../Config.h"
#include "Engine/Core/Types/Guid.h"
#if ENABLE_ASSETS_DISCOVERY
#include "Engine/Core/Types/DateTime.h"
#endif
#include "Engine/Core/Types/String.h"
#include "Engine/Core/Collections/Dictionary.h"
#include "Engine/Platform/CriticalSection.h"
struct AssetHeader;
struct FlaxStorageReference;
class FlaxStorage;
///
/// Assets cache flags.
///
enum class AssetsCacheFlags
{
///
/// The none.
///
None = 0,
///
/// The serialized paths are relative to the startup folder (should be converted to absolute on load).
///
RelativePaths = 1,
};
DECLARE_ENUM_OPERATORS(AssetsCacheFlags);
///
/// Flax Game Engine assets cache container
///
class FLAXENGINE_API AssetsCache
{
public:
///
/// The registry entry structure.
///
struct Entry
{
///
/// The cached asset information.
///
AssetInfo Info;
#if ENABLE_ASSETS_DISCOVERY
///
/// The file modified date.
///
DateTime FileModified;
#endif
Entry()
{
}
Entry(const Guid& id, const StringView& typeName, const StringView& path)
: Info(id, typeName, path)
#if ENABLE_ASSETS_DISCOVERY
, FileModified(DateTime::NowUTC())
#endif
{
}
};
typedef Dictionary Registry;
typedef Dictionary PathsMapping;
private:
bool _isDirty;
CriticalSection _locker;
Registry _registry;
PathsMapping _pathsMapping;
String _path;
public:
///
/// Initializes a new instance of the class.
///
AssetsCache();
public:
///
/// Gets amount of registered assets
///
/// Registry size
int32 Size() const
{
_locker.Lock();
const int32 result = _registry.Count();
_locker.Unlock();
return result;
}
public:
///
/// Init registry
///
void Init();
///
/// Save registry
///
/// True if cannot save registry
bool Save();
///
/// Saves the registry to the given file.
///
/// The output file path.
/// The registry entries.
/// The assets paths mapping table.
/// The custom flags.
/// True if failed, otherwise false.
static bool Save(const StringView& path, const Registry& entries, const PathsMapping& pathsMapping, const AssetsCacheFlags flags = AssetsCacheFlags::None);
public:
///
/// Finds the asset path by id. In editor it returns the actual asset path, at runtime it returns the mapped asset path.
///
/// The asset id.
/// The asset path, or empty if failed to find.
const String& GetEditorAssetPath(const Guid& id) const;
///
/// Finds the asset info by path.
///
/// The asset path.
/// The output asset info. Filled with valid values if method returns true.
/// True if found any asset, otherwise false.
bool FindAsset(const StringView& path, AssetInfo& info);
///
/// Finds the asset info by id.
///
/// The asset id.
/// The output asset info. Filled with valid values if method returns true.
/// True if found any asset, otherwise false.
bool FindAsset(const Guid& id, AssetInfo& info);
///
/// Checks if asset with given path is in registry.
///
/// The asset path.
/// True if asset is in cache, otherwise false.
bool HasAsset(const StringView& path)
{
AssetInfo info;
return FindAsset(path, info);
}
///
/// Checks if asset with given ID is in registry.
///
/// The asset id.
/// True if asset is in cache, otherwise false.
bool HasAsset(const Guid& id)
{
AssetInfo info;
return FindAsset(id, info);
}
///
/// Gets the asset ids.
///
/// The result array.
void GetAll(Array& result) const;
///
/// Gets the asset ids that match the given typename.
///
/// The asset typename.
/// The result array.
void GetAllByTypeName(const StringView& typeName, Array& result) const;
///
/// Register assets in the cache
///
/// Flax assets container reference
void RegisterAssets(const FlaxStorageReference& storage);
///
/// Register assets in the cache
///
/// Flax assets container
void RegisterAssets(FlaxStorage* storage);
///
/// Register asset in the cache
///
/// Flax asset file header
/// Asset path
void RegisterAsset(const AssetHeader& header, const StringView& path);
///
/// Register asset in the cache
///
/// Asset ID
/// Asset type name
/// Asset path
void RegisterAsset(const Guid& id, const String& typeName, const StringView& path);
///
/// Delete asset
///
/// Asset path
/// Output asset info
/// True if asset has been deleted, otherwise false
bool DeleteAsset(const StringView& path, AssetInfo* info);
///
/// Delete asset
///
/// Asset ID
/// Output asset info
/// True if asset has been deleted, otherwise false
bool DeleteAsset(const Guid& id, AssetInfo* info);
///
/// Rename asset
///
/// Old path
/// New path
/// True if has been deleted, otherwise false
bool RenameAsset(const StringView& oldPath, const StringView& newPath);
///
/// Determines whether cached asset entry is valid.
///
/// The asset entry.
/// True if is valid, otherwise false.
bool IsEntryValid(Entry& e);
};