Nebula
Loading...
Searching...
No Matches
resourceserver.h
Go to the documentation of this file.
1#pragma once
2//------------------------------------------------------------------------------
11//------------------------------------------------------------------------------
12#include <functional>
13#include "core/refcounted.h"
14#include "ids/id.h"
15#include "core/singleton.h"
16#include "resourceid.h"
17#include "resourceloader.h"
19namespace Resources
20{
22{
25public:
29 virtual ~ResourceServer();
30
32 void Open();
34 void Close();
35
37 void Update(IndexT frameIndex);
38
40 Resources::ResourceId CreateResource(const ResourceName& res, std::function<void(const Resources::ResourceId)> success = nullptr, std::function<void(const Resources::ResourceId)> failed = nullptr, bool immediate = false, bool stream = true);
42 Resources::ResourceId CreateResource(const ResourceName& res, const Util::StringAtom& tag, std::function<void(const Resources::ResourceId)> success = nullptr, std::function<void(const Resources::ResourceId)> failed = nullptr, bool immediate = false, bool stream = true);
44 template<class METADATA> Resources::ResourceId CreateResource(const ResourceName& res, const METADATA& metaData, std::function<void(const Resources::ResourceId)> success = nullptr, std::function<void(const Resources::ResourceId)> failed = nullptr, bool immediate = false, bool stream = true);
46 template<class METADATA> Resources::ResourceId CreateResource(const ResourceName& res, const METADATA& metaData, const Util::StringAtom& tag, std::function<void(const Resources::ResourceId)> success = nullptr, std::function<void(const Resources::ResourceId)> failed = nullptr, bool immediate = false, bool stream = true);
48 void DiscardResource(const Resources::ResourceId res);
50 void DiscardResources(const Util::StringAtom& tag);
54 void ReloadResource(const ResourceName& res, std::function<void(const Resources::ResourceId)> success = nullptr, std::function<void(const Resources::ResourceId)> failed = nullptr);
56 void SetMinLod(const ResourceId& id, float lod, bool immediate);
58 void CreateResourceListener(const ResourceId& id, std::function<void(const Resources::ResourceId)> success, std::function<void(const Resources::ResourceId)> failed = nullptr);
59
61 Core::Rtti* GetType(const Resources::ResourceId id);
62
64 const Resources::ResourceName GetName(const Resources::ResourceId id) const;
66 const Util::StringAtom GetTag(const Resources::ResourceId id) const;
68 const Resource::State GetState(const Resources::ResourceId id) const;
70 const SizeT GetUsage(const Resources::ResourceId id) const;
72 bool HasResource(const Resources::ResourceId id) const;
74 const Resources::ResourceId GetId(const Resources::ResourceName& name) const;
75
77 void RegisterStreamLoader(const Util::StringAtom& ext, const Core::Rtti& loaderClass);
79 template <class POOL_TYPE> POOL_TYPE* GetStreamLoader() const;
80
83
86private:
87 friend class ResourceLoader;
88
89 bool open;
93
94 static int32_t UniquePoolCounter;
95};
96
97//------------------------------------------------------------------------------
102inline Resources::ResourceId
104 const ResourceName& id
105 , std::function<void(const Resources::ResourceId)> success
106 , std::function<void(const Resources::ResourceId)> failed
107 , bool immediate
108 , bool stream
109)
110{
111 return this->CreateResource(id, "", success, failed, immediate, stream);
112}
113
114//------------------------------------------------------------------------------
119inline Resources::ResourceId
121 const ResourceName& res
122 , const Util::StringAtom& tag
123 , std::function<void(const Resources::ResourceId)> success
124 , std::function<void(const Resources::ResourceId)> failed
125 , bool immediate
126 , bool stream
127)
128{
129 // get resource loader by extension
130 Util::String ext = res.AsString().GetFileExtension();
131 IndexT i = this->extensionMap.FindIndex(ext);
132 n_assert_fmt(i != InvalidIndex, "No resource loader is associated with file extension '%s'", ext.AsCharPtr());
133 const Ptr<ResourceLoader>& loader = this->loaders[this->extensionMap.ValueAtIndex(i)].downcast<ResourceLoader>();
134
135 // create container and cast to actual resource type
136 Resources::ResourceId id = loader->CreateResource(res, nullptr, 0, tag, success, failed, immediate, stream);
137 return id;
138}
139
140//------------------------------------------------------------------------------
143template<class METADATA>
144inline Resources::ResourceId
146 const ResourceName& res
147 , const METADATA& metaData
148 , std::function<void(const Resources::ResourceId)> success
149 , std::function<void(const Resources::ResourceId)> failed
150 , bool immediate
151 , bool stream
152)
153{
154 return this->CreateResource(res, metaData, "", success, failed, immediate, stream);
155}
156
157//------------------------------------------------------------------------------
160template<class METADATA>
161inline Resources::ResourceId
163 const ResourceName& res
164 , const METADATA& metaData
165 , const Util::StringAtom& tag
166 , std::function<void(const Resources::ResourceId)> success
167 , std::function<void(const Resources::ResourceId)> failed
168 , bool immediate
169 , bool stream
170)
171{
172 // get resource loader by extension
174 IndexT i = this->extensionMap.FindIndex(ext);
175 n_assert_fmt(i != InvalidIndex, "No resource loader is associated with file extension '%s'", ext.AsCharPtr());
177
178 // create container and cast to actual resource type
179 Resources::ResourceId id = loader->CreateResource(res, &metaData, sizeof(METADATA), tag, success, failed, immediate, stream);
180 return id;
181}
182
183//------------------------------------------------------------------------------
186inline void
187ResourceServer::ReloadResource(const ResourceName& res, std::function<void(const Resources::ResourceId)> success, std::function<void(const Resources::ResourceId)> failed)
188{
189 // get resource loader by extension
191 IndexT i = this->extensionMap.FindIndex(ext);
192 n_assert_fmt(i != InvalidIndex, "No resource loader is associated with file extension '%s'", ext.AsCharPtr());
194
195 // create container and cast to actual resource type
196 loader->ReloadResource(res, success, failed);
197}
198
199//------------------------------------------------------------------------------
202inline void
203ResourceServer::SetMinLod(const ResourceId& id, float lod, bool immediate)
204{
205 // get id of loader
206 const Ids::Id8 loaderid = id.loaderIndex;
207
208 // get resource loader by extension
209 n_assert(this->loaders.Size() > loaderid);
210 const Ptr<ResourceLoader>& loader = this->loaders[loaderid].downcast<ResourceLoader>();
211
212 // update LOD
213 loader->SetMinLod(id, lod, immediate);
214}
215
216//------------------------------------------------------------------------------
219inline void
221 const ResourceId& id,
222 std::function<void(const Resources::ResourceId)> success,
223 std::function<void(const Resources::ResourceId)> failed
224)
225{
226 // get id of loader
227 const Ids::Id8 loaderid = id.loaderIndex;
228
229 // get resource loader by extension
230 n_assert(this->loaders.Size() > loaderid);
231 const Ptr<ResourceLoader>& loader = this->loaders[loaderid].downcast<ResourceLoader>();
232
233 loader->CreateListener(id, success, failed);
234}
235
236//------------------------------------------------------------------------------
240inline void
241ResourceServer::DiscardResource(const Resources::ResourceId id)
242{
243 // get id of loader
244 const Ids::Id8 loaderid = id.loaderIndex;
245
246 // get resource loader by extension
247 n_assert(this->loaders.Size() > loaderid);
248 const Ptr<ResourceLoader>& loader = this->loaders[loaderid].downcast<ResourceLoader>();
249
250 // discard container
251 loader->DiscardResource(id);
252}
253
254//------------------------------------------------------------------------------
257inline const Resources::ResourceName
258ResourceServer::GetName(const Resources::ResourceId id) const
259{
260 // get resource loader by extension
261 n_assert(this->loaders.Size() > id.loaderIndex);
262 const Ptr<ResourceLoader>& loader = this->loaders[id.loaderIndex];
263 return loader->GetName(id.resourceId);
264}
265
266//------------------------------------------------------------------------------
269inline const Util::StringAtom
270ResourceServer::GetTag(const Resources::ResourceId id) const
271{
272 // get resource loader by extension
273 n_assert(this->loaders.Size() > id.loaderIndex);
274 const Ptr<ResourceLoader>& loader = this->loaders[id.loaderIndex];
275 return loader->GetTag(id.resourceId);
276}
277
278//------------------------------------------------------------------------------
282ResourceServer::GetState(const Resources::ResourceId id) const
283{
284 // get resource loader by extension
285 n_assert(this->loaders.Size() > id.loaderIndex);
286 const Ptr<ResourceLoader>& loader = this->loaders[id.loaderIndex];
287 return loader->GetState(id.resourceId);
288}
289
290//------------------------------------------------------------------------------
293inline const SizeT
294ResourceServer::GetUsage(const Resources::ResourceId id) const
295{
296 // get resource loader by extension
297 n_assert(this->loaders.Size() > id.loaderIndex);
298 const Ptr<ResourceLoader>& loader = this->loaders[id.loaderIndex];
299 return loader->GetUsage(id.resourceId);
300}
301
302//------------------------------------------------------------------------------
305inline bool
306ResourceServer::HasResource(const Resources::ResourceId id) const
307{
308 if (this->loaders.Size() <= id.loaderIndex) return false;
309 {
310 const Ptr<ResourceLoader>& loader = this->loaders[id.loaderIndex];
311 if (loader->HasResource(id)) return true;
312 return false;
313 }
314}
315
316//------------------------------------------------------------------------------
319inline const Resources::ResourceId
321{
322 IndexT i;
323 for (i = 0; i < this->loaders.Size(); i++)
324 {
325 Resources::ResourceId id = this->loaders[i]->GetId(name);
326 if (id != Resources::ResourceId::Invalid()) return id;
327 }
328 return Resources::ResourceId::Invalid();
329}
330
331//------------------------------------------------------------------------------
334template <class POOL_TYPE>
335inline POOL_TYPE*
337{
338 static_assert(std::is_base_of<ResourceLoader, POOL_TYPE>::value, "Type requested is not a stream pool");
339 IndexT i = this->typeMap.FindIndex(&POOL_TYPE::RTTI);
340 if (i != InvalidIndex)
341 {
342 return static_cast<POOL_TYPE*>(this->loaders[i].get());
343 }
344
345 n_error("No loader registered for this type");
346 return nullptr;
347}
348
349//------------------------------------------------------------------------------
352inline Resources::ResourceId
354 const ResourceName& res
355 , const Util::StringAtom& tag
356 , std::function<void(const Resources::ResourceId)> success = nullptr
357 , std::function<void(const Resources::ResourceId)> failed = nullptr
358 , bool immediate = false
359 , bool stream = true
360)
361{
362 return ResourceServer::Instance()->CreateResource(res, tag, success, failed, immediate, stream);
363}
364
365//------------------------------------------------------------------------------
368template <class METADATA>
369inline Resources::ResourceId
371 const ResourceName& res
372 , const METADATA& metaData
373 , const Util::StringAtom& tag
374 , std::function<void(const Resources::ResourceId)> success = nullptr
375 , std::function<void(const Resources::ResourceId)> failed = nullptr
376 , bool immediate = false
377 , bool stream = true
378)
379{
380 return ResourceServer::Instance()->CreateResource(res, metaData, tag, success, failed, immediate, stream);
381}
382
383//------------------------------------------------------------------------------
386inline void
388 const ResourceId& id
389 , std::function<void(const Resources::ResourceId)> success
390 , std::function<void(const Resources::ResourceId)> failed = nullptr
391)
392{
393 return ResourceServer::Instance()->CreateResourceListener(id, success, failed);
394}
395
396//------------------------------------------------------------------------------
399inline void
400SetMinLod(const ResourceId& id, float lod, bool immediate)
401{
402 return ResourceServer::Instance()->SetMinLod(id, lod, immediate);
403}
404
405//------------------------------------------------------------------------------
408inline void
409DiscardResource(const Resources::ResourceId id)
410{
411 ResourceServer::Instance()->DiscardResource(id);
412}
413
414//------------------------------------------------------------------------------
417inline void
419{
420 return ResourceServer::Instance()->ReloadResource(res);
421}
422
423//------------------------------------------------------------------------------
426inline void
428{
429 ResourceServer::Instance()->WaitForLoaderThread();
430}
431
432//------------------------------------------------------------------------------
435template <class POOL_TYPE>
436inline POOL_TYPE*
438{
439 static_assert(std::is_base_of<ResourceLoader, POOL_TYPE>::value, "Template argument is not a ResourceCache type!");
440 return ResourceServer::Instance()->GetStreamLoader<POOL_TYPE>();
441}
442
443} // namespace Resources
The common base class of Nebula.
Definition refcounted.h:38
Nebula's runtime type information for one class.
Definition rtti.h:27
Nebula's smart pointer class which manages the life time of RefCounted objects.
Definition ptr.h:38
const Ptr< DERIVED > & downcast() const
type-safe downcast operator to other smart pointer
Definition ptr.h:392
State
Definition resource.h:26
Definition resourceloader.h:60
Definition resourceserver.h:22
void SetMinLod(const ResourceId &id, float lod, bool immediate)
stream in a new LOD
Definition resourceserver.h:203
__DeclareClass(ResourceServer)
void Close()
close manager
Definition resourceserver.cc:53
__DeclareInterfaceSingleton(ResourceServer)
void CreateResourceListener(const ResourceId &id, std::function< void(const Resources::ResourceId)> success, std::function< void(const Resources::ResourceId)> failed=nullptr)
Create single-fire listener for resource. When resource is loaded, the callbacks will be invoked and ...
Definition resourceserver.h:220
void Open()
open manager
Definition resourceserver.cc:41
Resources::ResourceId CreateResource(const ResourceName &res, std::function< void(const Resources::ResourceId)> success=nullptr, std::function< void(const Resources::ResourceId)> failed=nullptr, bool immediate=false, bool stream=true)
create a new resource (stream-managed), which will be loaded at some later point, if not already load...
ResourceServer()
constructor
Definition resourceserver.cc:22
Util::Dictionary< Util::StringAtom, IndexT > extensionMap
Definition resourceserver.h:90
Util::Dictionary< const Core::Rtti *, IndexT > typeMap
Definition resourceserver.h:91
Resources::ResourceId CreateResource(const ResourceName &res, const Util::StringAtom &tag, std::function< void(const Resources::ResourceId)> success=nullptr, std::function< void(const Resources::ResourceId)> failed=nullptr, bool immediate=false, bool stream=true)
overload which also takes an identifying tag, which is used to group-discard resources
const Resources::ResourceId GetId(const Resources::ResourceName &name) const
get id from name
Definition resourceserver.h:320
void DiscardResources(const Util::StringAtom &tag)
discard all resources by tag (stream-managed)
Definition resourceserver.cc:139
bool HasResource(const Resources::ResourceId id) const
check if resource id is valid
Definition resourceserver.h:306
void RegisterStreamLoader(const Util::StringAtom &ext, const Core::Rtti &loaderClass)
register a stream pool, which takes an extension and the RTTI of the resource type to create
Definition resourceserver.cc:93
void DiscardResource(const Resources::ResourceId res)
discard resource (stream-managed)
Definition resourceserver.h:241
virtual ~ResourceServer()
destructor
Definition resourceserver.cc:31
Core::Rtti * GetType(const Resources::ResourceId id)
get type of resource pool this resource was allocated with
Definition resourceserver.cc:173
void ReloadResource(const ResourceName &res, std::function< void(const Resources::ResourceId)> success=nullptr, std::function< void(const Resources::ResourceId)> failed=nullptr)
reload resource
Definition resourceserver.h:187
const Resources::ResourceName GetName(const Resources::ResourceId id) const
get resource name
Definition resourceserver.h:258
Util::Array< Ptr< ResourceLoader > > loaders
Definition resourceserver.h:92
const Resource::State GetState(const Resources::ResourceId id) const
get resource state
Definition resourceserver.h:282
static int32_t UniquePoolCounter
Definition resourceserver.h:94
const SizeT GetUsage(const Resources::ResourceId id) const
get usage
Definition resourceserver.h:294
bool HasPendingResources()
returns true if there are pending resources in-flight
Definition resourceserver.cc:153
const Util::StringAtom GetTag(const Resources::ResourceId id) const
get tag resource was first registered with
Definition resourceserver.h:270
void LoadDefaultResources()
goes through all pools and sets up their default resources
Definition resourceserver.cc:110
POOL_TYPE * GetStreamLoader() const
get stream pool for later use
Definition resourceserver.h:336
bool open
Definition resourceserver.h:89
void WaitForLoaderThread()
Wait for all loader threads.
Definition resourceserver.cc:188
Nebula's dynamic array class.
Definition array.h:60
A collection of key/value pairs with quick value retrieval by key at roughly O(log n).
Definition dictionary.h:34
IndexT FindIndex(const KEYTYPE &key) const
find index of key/value pair (InvalidIndex if doesn't exist)
Definition dictionary.h:355
VALUETYPE & ValueAtIndex(IndexT index)
access to value at given index
Definition dictionary.h:408
A StringAtom.
Definition stringatom.h:22
String AsString() const
get containted string as string object (SLOW!!!)
Definition stringatom.h:372
void __cdecl n_error(const char *msg,...)
This function is called when a serious situation is encountered which requires abortion of the applic...
Definition debug.cc:138
#define n_assert_fmt(exp, msg,...)
Definition debug.h:53
#define n_assert(exp)
Definition debug.h:50
uint8_t Id8
Definition id.h:141
A resource is a container for some type of file which is loaded.
Definition resource.cc:9
Resources::ResourceId CreateResource(const ResourceName &res, const Util::StringAtom &tag, std::function< void(const Resources::ResourceId)> success=nullptr, std::function< void(const Resources::ResourceId)> failed=nullptr, bool immediate=false, bool stream=true)
Definition resourceserver.h:353
POOL_TYPE * GetStreamLoader()
Definition resourceserver.h:437
void DiscardResource(const Resources::ResourceId id)
Definition resourceserver.h:409
@ Update
Definition resourceloader.h:53
void WaitForLoaderThread()
Definition resourceserver.h:427
void ReloadResource(const ResourceName &res)
Definition resourceserver.h:418
Util::StringAtom ResourceName
Definition resourceid.h:33
void SetMinLod(const ResourceId &id, float lod, bool immediate)
Definition resourceserver.h:400
void CreateResourceListener(const ResourceId &id, std::function< void(const Resources::ResourceId)> success, std::function< void(const Resources::ResourceId)> failed=nullptr)
Definition resourceserver.h:387
id
Definition resourceid.h:37
Nebula's universal string class.
Definition string.h:50
const char * AsCharPtr() const
return contents as character pointer
Definition string.h:540
String GetFileExtension() const
get filename extension without dot
Definition string.cc:964
static const int InvalidIndex
Definition types.h:54
int SizeT
Definition types.h:49
int IndexT
Definition types.h:48