// Copyright (c) 2012-2022 Wojciech Figat. All rights reserved. #pragma once #include "Engine/Core/Delegate.h" #include "Engine/Core/Collections/SamplesBuffer.h" class StreamingGroup; class Task; /// /// Base class for all resource types that can be dynamically streamed. /// class FLAXENGINE_API StreamableResource { protected: StreamingGroup* _group; bool _isDynamic, _isStreaming; float _streamingQuality; StreamableResource(StreamingGroup* group); ~StreamableResource(); public: /// /// Gets resource group. /// FORCE_INLINE StreamingGroup* GetGroup() const { return _group; } /// /// Gets value indicating whenever resource can be used in dynamic streaming (otherwise use always the best quality). /// FORCE_INLINE bool IsDynamic() const { return _isDynamic; } /// /// Gets resource streaming quality level /// FORCE_INLINE float GetStreamingQuality() const { return _streamingQuality; } /// /// Gets resource target residency level. /// FORCE_INLINE int32 GetTargetResidency() const { return Streaming.TargetResidency; } /// /// Gets a value indicating whether this resource has been allocated. /// FORCE_INLINE bool IsAllocated() const { return GetAllocatedResidency() != 0; } /// /// Gets resource maximum residency level. /// virtual int32 GetMaxResidency() const = 0; /// /// Gets resource current residency level. /// virtual int32 GetCurrentResidency() const = 0; /// /// Gets resource allocated residency level. /// virtual int32 GetAllocatedResidency() const = 0; public: /// /// Determines whether this instance can be updated. Which means: no async streaming, no pending action in background. /// /// true if this instance can be updated; otherwise, false. virtual bool CanBeUpdated() const = 0; /// /// Updates the resource allocation to the given residency level. May not be updated now but in an async operation. /// /// The target allocation residency. /// Async task that updates resource allocation or null if already done it. Warning: need to call task start to perform allocation. virtual Task* UpdateAllocation(int32 residency) = 0; /// /// Creates streaming task (or tasks sequence) to perform resource streaming for the desire residency level. /// /// The target residency. /// Async task or tasks that update resource residency level. Must be preceded with UpdateAllocation call. virtual Task* CreateStreamingTask(int32 residency) = 0; public: struct StreamingCache { int64 LastUpdate = 0; int32 TargetResidency = 0; int64 TargetResidencyChange = 0; SamplesBuffer QualitySamples; }; StreamingCache Streaming; /// /// Event called when current resource residency gets changed (eg. model LOD or texture MIP gets loaded). Usually called from async thread. /// Action ResidencyChanged; /// /// Requests the streaming update for this resource during next streaming manager update. /// void RequestStreamingUpdate(); /// /// Stops the streaming (eg. on streaming fail). /// void CancelStreaming(); protected: void StartStreaming(bool isDynamic); void StopStreaming(); };