Instanceof support for hump class

This commit is contained in:
Mikko Ahlroth 2014-10-17 22:44:08 +03:00
parent 72dd42119d
commit b914b5217c

View file

@ -25,70 +25,98 @@ THE SOFTWARE.
]]--
local function include_helper(to, from, seen)
if from == nil then
return to
elseif type(from) ~= 'table' then
return from
elseif seen[from] then
return seen[from]
end
if from == nil then
return to
elseif type(from) ~= 'table' then
return from
elseif seen[from] then
return seen[from]
end
seen[from] = to
for k,v in pairs(from) do
k = include_helper({}, k, seen) -- keys might also be tables
if not to[k] then
to[k] = include_helper({}, v, seen)
end
end
return to
seen[from] = to
for k,v in pairs(from) do
k = include_helper({}, k, seen) -- keys might also be tables
if not to[k] then
to[k] = include_helper({}, v, seen)
end
end
return to
end
-- deeply copies `other' into `class'. keys in `other' that are already
-- defined in `class' are omitted
local function include(class, other)
return include_helper(class, other, {})
return include_helper(class, other, {})
end
-- returns a deep copy of `other'
local function clone(other)
return setmetatable(include({}, other), getmetatable(other))
return setmetatable(include({}, other), getmetatable(other))
end
local class_id = 1
local function new(class)
-- mixins
local inc = class.__includes or {}
if getmetatable(inc) then inc = {inc} end
-- mixins
local inc = class.__includes or {}
if getmetatable(inc) then inc = {inc} end
for _, other in ipairs(inc) do
include(class, other)
end
for _, other in ipairs(inc) do
include(class, other)
end
-- class implementation
class.__index = class
class.init = class.init or class[1] or function() end
class.include = class.include or include
class.clone = class.clone or clone
-- class implementation
class.__index = class
class.init = class.init or class[1] or function() end
class.include = class.include or include
class.clone = class.clone or clone
-- constructor call
return setmetatable(class, {__call = function(c, ...)
local o = setmetatable({}, c)
o:init(...)
return o
end})
if class.class_tree == nil then
class.class_tree = {}
else
table.insert(class.class_tree, class_id)
end
class.class_id = class_id
class_id = class_id + 1
-- Check if object is instance of given class
-- Note this will not work for child classes
class.isinstance = function(self, class)
if self.class_id == class.class_id then
return true
end
for _, val in pairs(self.class_tree) do
if val == class.class_id then
return true
end
end
return false
end
class_id = class_id + 1
-- constructor call
return setmetatable(class, {__call = function(c, ...)
local o = setmetatable({}, c)
o:init(...)
return o
end})
end
-- interface for cross class-system compatibility (see https://github.com/bartbes/Class-Commons).
if class_commons ~= false and not common then
common = {}
function common.class(name, prototype, parent)
return new{__includes = {prototype, parent}}
end
function common.instance(class, ...)
return class(...)
end
common = {}
function common.class(name, prototype, parent)
return new{__includes = {prototype, parent}}
end
function common.instance(class, ...)
return class(...)
end
end
-- the module
return setmetatable({new = new, include = include, clone = clone},
{__call = function(_,...) return new(...) end})
{__call = function(_,...) return new(...) end})