Simplified handles

This commit is contained in:
2026-09-23 23:24:23 -07:00
parent 97267f1a26
commit ae8db07d6f
8 changed files with 27 additions and 43 deletions
+9 -9
View File
@@ -6,7 +6,7 @@
namespace sophia {
template <typename Tag>
template <typename T>
struct Handle {
static constexpr u32 INVALID_INDEX = (1u << 20) - 1;
@@ -24,14 +24,14 @@ struct Handle {
[[nodiscard]] auto operator<=>(const Handle&) const = default;
};
struct MeshTag {};
struct PanelTag {};
struct RenderTargetTag {};
struct SceneTag {};
class Mesh;
class Panel;
class RenderTarget;
class Scene;
using MeshHandle = Handle<MeshTag>;
using PanelHandle = Handle<PanelTag>;
using RenderTargetHandle = Handle<RenderTargetTag>;
using SceneHandle = Handle<SceneTag>;
using MeshHandle = Handle<Mesh>;
using PanelHandle = Handle<Panel>;
using RenderTargetHandle = Handle<RenderTarget>;
using SceneHandle = Handle<Scene>;
} // namespace sophia
@@ -14,30 +14,15 @@
namespace sophia {
class Mesh;
class RenderTarget;
class ResourceRegistry;
template <typename T>
struct ResourceTraits;
template <>
struct ResourceTraits<Mesh> {
using Handle = MeshHandle;
};
template <>
struct ResourceTraits<RenderTarget> {
using Handle = RenderTargetHandle;
};
class ResourceRegistryRef {
public:
template <typename T>
typename ResourceTraits<T>::Handle load(const std::string& path);
Handle<T> load(const std::string& path);
template <typename T, typename... Args>
typename ResourceTraits<T>::Handle create(Args&&... args) {
Handle<T> create(Args&&... args) {
return createResource(std::type_identity<T>{}, std::forward<Args>(args)...);
}
@@ -48,7 +33,7 @@ class ResourceRegistryRef {
bool isAlive(RenderTargetHandle handle) const;
template <typename T>
void release(typename ResourceTraits<T>::Handle handle);
void release(Handle<T> handle);
private:
friend class Application;
+1 -1
View File
@@ -25,7 +25,7 @@ class SceneRegistry {
u32 size() const { return pool.size(); }
private:
Pool<Scene, SceneHandle> pool{"Scene"};
Pool<Scene> pool{"Scene"};
};
} // namespace sophia
+1 -1
View File
@@ -93,7 +93,7 @@ class PanelRegistry {
const DockLayout& getDefaultLayout() const { return defaultLayout; }
private:
Pool<Panel, PanelHandle> pool{"Panel"};
Pool<Panel> pool{"Panel"};
DockLayout defaultLayout;
};
+11 -10
View File
@@ -1,6 +1,7 @@
#pragma once
#include <memory>
#include <sophia/handles.hpp>
#include <sophia/types.hpp>
#include <sophia/util/assert.hpp>
#include <utility>
@@ -8,7 +9,7 @@
namespace sophia {
template <typename T, typename HandleType>
template <typename T>
class Pool {
public:
explicit Pool(const char* name) : name{name} {}
@@ -17,29 +18,29 @@ class Pool {
Pool& operator=(const Pool&) = delete;
template <typename... Args>
HandleType create(Args&&... args) {
Handle<T> create(Args&&... args) {
return add(std::make_unique<T>(std::forward<Args>(args)...));
}
HandleType add(std::unique_ptr<T> item) {
Handle<T> add(std::unique_ptr<T> item) {
if (!freeList.empty()) {
u32 index = freeList.back();
freeList.pop_back();
slots[index].item = std::move(item);
return HandleType{index, slots[index].generation};
return Handle<T>{index, slots[index].generation};
}
slots.push_back(Slot{std::move(item), 0});
return HandleType{static_cast<u32>(slots.size() - 1), 0};
return Handle<T>{static_cast<u32>(slots.size() - 1), 0};
}
T& get(HandleType handle) {
T& get(Handle<T> handle) {
return const_cast<T&>(std::as_const(*this).get(handle));
}
const T& get(HandleType handle) const { return *validate(handle).item; }
const T& get(Handle<T> handle) const { return *validate(handle).item; }
void release(HandleType handle) {
void release(Handle<T> handle) {
validate(handle);
Slot& slot = slots[handle.index];
@@ -48,7 +49,7 @@ class Pool {
freeList.push_back(handle.index);
}
bool isAlive(HandleType handle) const {
bool isAlive(Handle<T> handle) const {
return handle.isValid() && handle.index < slots.size() &&
slots[handle.index].generation == handle.generation &&
slots[handle.index].item != nullptr;
@@ -98,7 +99,7 @@ class Pool {
u32 generation = 0;
};
const Slot& validate(HandleType handle) const {
const Slot& validate(Handle<T> handle) const {
SOPHIA_ASSERT(handle.isValid(), "invalid handle:", name);
SOPHIA_ASSERT(handle.index < slots.size(), name,
"handle index out of range:", handle.index);
-2
View File
@@ -16,8 +16,6 @@ namespace sophia {
class Mesh {
public:
using HandleType = MeshHandle;
struct Vertex {
glm::vec2 position{};
glm::vec3 color{};
@@ -30,7 +30,7 @@ class RenderTargetPool {
Device& device;
vk::Format format;
Pool<RenderTarget, RenderTargetHandle> pool{"RenderTarget"};
Pool<RenderTarget> pool{"RenderTarget"};
};
} // namespace sophia
+1 -1
View File
@@ -18,7 +18,7 @@ class ResourceRegistry {
: device{device}, renderTargetPool{device, renderTargetFormat} {}
Device& device;
Pool<Mesh, MeshHandle> meshPool{"Mesh"};
Pool<Mesh> meshPool{"Mesh"};
RenderTargetPool renderTargetPool;
// TexturePool textures;
// MaterialPool materials;