diff --git a/class.lua b/class.lua index b0fec0c..de242a9 100644 --- a/class.lua +++ b/class.lua @@ -1,14 +1,24 @@ --[[ barebones oop basics - call the class object to construct a new instance + construction + + call the class object to construct a new instance + + this will construct a new table, assign it as a class + instance, and call `new` + + if you are defining a subclass, you will need to call + `self:super(...)` as part of `new` to complete superclass + construction - if done correctly this will propagate + up the chain and you wont have to think about it classes are used as metatables directly so that metamethods "just work" - except for index, which is used to hook up instance methods - classes do use a prototype chain for inheritance, but - also copy their interfaces (including superclass) + classes do use a prototype chain for inheritance, but + also copy their interfaces (including superclass) we copy interfaces in classes rather than relying on a prototype chain, so that pairs on the class gets @@ -100,14 +110,24 @@ local function class(config) --get the inherited class for super calls if/as needed --allows overrides that still refer to superclass behaviour c.__super = extends - --nop by default - function c:super() end + + --perform a (partial) super construction for an instance + --for any nested super calls, it'll call the relevant one in the + --heirarchy, assuming no super calls have been missed + function c:super(...) + if not c.__super then return end + --hold reference so we can restore + local current_super = c.__super + --push next super + c.__super = c.__super.__super + --call + current_super.new(self, ...) + --restore + c.__super = current_super + end + if c.__super then - --perform a super construction for an instance - function c:super(...) - c.__super.new(self, ...) - end --implement superclass interface implement(c, c.__super) end diff --git a/pubsub.lua b/pubsub.lua index e0220ec..e52f975 100644 --- a/pubsub.lua +++ b/pubsub.lua @@ -31,7 +31,7 @@ end --subscribe to an event --can be a specifically named event, or "everything" to get notified for any event ---for "everything", the callback will recieve the event name as the first argument +--for "everything", the callback will receive the event name as the first argument function pubsub:subscribe(event, callback) local callbacks = self.subscriptions[event] if not callbacks then diff --git a/timer.lua b/timer.lua index 961ac6c..07712cc 100644 --- a/timer.lua +++ b/timer.lua @@ -14,7 +14,7 @@ local timer = class({ }) --create a timer, with optional callbacks ---callbacks recieve as arguments: +--callbacks receive as arguments: -- the current progress as a number from 0 to 1, so can be used for lerps -- the timer object, so can be reset if needed function timer:new(time, on_progress, on_finish) diff --git a/vec2.lua b/vec2.lua index 9cd1aa6..e712228 100644 --- a/vec2.lua +++ b/vec2.lua @@ -21,7 +21,7 @@ function vec2:new(x, y) if type(x) == "number" or type(x) == "nil" then self:sset(x or 0, y) elseif type(x) == "table" then - if x.type and x:type() == "vec2" then + if type(x.type) == "function" and x:type() == "vec2" then self:vset(x) elseif x[1] then self:sset(x[1], x[2]) diff --git a/vec3.lua b/vec3.lua index b1a7b72..695b2ee 100644 --- a/vec3.lua +++ b/vec3.lua @@ -23,7 +23,7 @@ function vec3:new(x, y, z) if type(x) == "number" or type(x) == "nil" then self:sset(x or 0, y, z) elseif type(x) == "table" then - if x.type and x:type() == "vec3" then + if type(x.type) == "function" and x:type() == "vec3" then self:vset(x) elseif x[1] then self:sset(x[1], x[2], x[3])