Skip to content

Lua Object Oriented Programming

Hzj_jie edited this page Aug 24, 2017 · 8 revisions

Lua itself is not an Object-Oriented language. But its metatable system can provide even more powerful functionality. It’s really easy to misuse the metatable system. Follow the example would make life easier.

Rule one and rule last: Both class and instance are tables.

-- Define a "Base" table.
local Base = {}

-- Provide an extend() function to let other class inherit from Base.
function Base:extend(o)
    o = o or {}
    setmetatable(o, self)
    self.__index = self
    return o
end

-- Create a new instance of Base.
function Base:new(o)
    o = self:extend(o)
    Base.init(o)
    return o
end

-- The init() function of Base. Note, it is also executed when an instance of a
-- derived class is created.
-- The tricky is in Derived:new() function.
function Base:init()
    print("Base:init()")
end

-- The render() function of Base.
function Base:render()
    print("Base:render()")
end

-- Define a Derived table.
local Derived = Base:extend()

-- Create a new instance of Derived class. Note: usually this function is not
-- necessary, since Base:new() provides similar functionality. But we would like
-- both Base:init() and Derived:init() to be executed.
function Derived:new(o)
    -- Note: this line is triple important, we should prefer self / Derived instead
    -- of Base to ensure override functions can take effect.
    -- Changing it to Base:new(o) to have a try.
    o = Base.new(self, o)
    Derived.init(o)
    return o
end

-- This function should override Base:init(). But both should be actively called in
-- Derived:new().
function Derived:init()
    print("Derived:init()")
end

-- This function should override Base:render().
function Derived:render()
    print("Derived:render()")
end

Base:new():render()
-- The above statement expects to output
-- Base:init()
-- Base:render()

Derived:new():render()
-- The above statement expects to output
-- Base:init()
-- Derived:init()
-- Derived:render()
Clone this wiki locally