
+ Added pesde support + Added `.search()` to `ref` and made `ref()` (`.set_ref()`) & `.search()` return a clearer which removes the reference + Bumped to 0.1.6
67 lines
1.6 KiB
Text
67 lines
1.6 KiB
Text
--!strict
|
|
--!optimize 2
|
|
local handle = require("./handle")
|
|
local jecs = require("../jecs")
|
|
local WORLD = require("./world").get
|
|
|
|
local refs: { [jecs.World]: { [any]: jecs.Entity<any> } } = {}
|
|
|
|
local function serve_clearer(key: any, world: jecs.World): () -> ()
|
|
return function()
|
|
refs[world][key] = nil
|
|
end
|
|
end
|
|
|
|
--- Gets an entity the given key references to.
|
|
--- If the key is nil, an entirely new entity is created and returned.
|
|
--- If the key doesn't reference an entity, a new entity is made for it to reference and returned.
|
|
--- @param key any
|
|
--- @return handle
|
|
local function ref(key: any): (handle.handle, () -> ()?)
|
|
local world = WORLD()
|
|
if not key then
|
|
return handle(world:entity())
|
|
end
|
|
|
|
if not refs[world] then
|
|
refs[world] = {}
|
|
end
|
|
|
|
local entity = refs[world][key]
|
|
if not entity then
|
|
entity = world:entity()
|
|
refs[world][key] = entity
|
|
end
|
|
|
|
return handle(entity), serve_clearer(key, world)
|
|
end
|
|
|
|
-- For the `__call`` metamethod
|
|
local function __call(_, key: any): (handle.handle, () -> ()?)
|
|
return ref(key)
|
|
end
|
|
|
|
local function search(key: any): (handle.handle?, () -> ()?)
|
|
local world = WORLD()
|
|
if not key then
|
|
return nil
|
|
end
|
|
local entity = refs[world][key]
|
|
|
|
if not entity then
|
|
return nil
|
|
end
|
|
|
|
return handle(entity), serve_clearer(key, world)
|
|
end
|
|
|
|
local metatable = {
|
|
__call = __call,
|
|
__index = {
|
|
search = search,
|
|
set_ref = ref,
|
|
},
|
|
}
|
|
|
|
local REF = setmetatable({}, metatable) :: typeof(ref) & typeof(metatable.__index)
|
|
return REF
|