Advertisement
Kar27

Lua Clases for OC

Apr 8th, 2018
82
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. function class(def)
  2.     local class = {}
  3.     local parents = {}
  4.    
  5.     local upv
  6.     local env = _G
  7.    
  8.     local wraps
  9.     local function super(parent_class)
  10.         if not parent_class then
  11.             parent_class = parents[1]
  12.         end
  13.        
  14.         local this = this
  15.         local that = {}
  16.         for k,v in pairs(parent_class) do
  17.             that[k] = type(v) == 'function' and wraps(this, v) or v
  18.         end
  19.        
  20.         return setmetatable(that, that)
  21.     end
  22.    
  23.     function wraps(this, func)
  24.         return function(...)
  25.                 local t = env.this
  26.                 local s = env.super
  27.                
  28.                 env.this  = this
  29.                 env.super = super
  30.                
  31.                 local ret  = pcall(func, ...)
  32.  
  33.                 env.this  = t
  34.                 env.super = s
  35.                
  36.                 return ret
  37.             end
  38.     end
  39.    
  40.     function class.__init()end
  41.  
  42.     for i=1,math.huge do
  43.         inherit, v = debug.getlocal(def, i)
  44.         if not inherit then break end
  45.        
  46.         local parent_class = _G[inherit]
  47.         for i=1,math.huge do
  48.             local  name, pclass = debug.getlocal(2,i,1)
  49.             if not name then break
  50.             elseif name == inherit then
  51.                 parent_class  = pclass
  52.                 break
  53.             end
  54.         end
  55.  
  56.         if parent_class  and type(parent_class) == 'table' then
  57.             table.insert(parents, parent_class)
  58.             for k,v in pairs(parent_class) do
  59.                 class[k] = v
  60.             end
  61.         else
  62.             error(string.format('Class "%s" not valid.', name))
  63.         end
  64.     end
  65.    
  66.    
  67.     for i=1,math.huge do
  68.         local  name, value = debug.getupvalue(def, i)
  69.         if not name then break
  70.         elseif name == '_ENV' then
  71.             env = value
  72.             upv = i
  73.             break
  74.         end
  75.     end
  76.  
  77.     local _env = setmetatable({}, {
  78.         __index= function(t, name)
  79.             local  value  = class[name]
  80.             return value ~= nil and value or env[name]
  81.         end,
  82.         __newindex = function(t, name, value)
  83.                 class[name] = value
  84.             end
  85.     })
  86.    
  87.     local function senv(env)
  88.         if upv then debug.setupvalue(def, upv, env)
  89.         else _G = env end
  90.     end
  91.    
  92.     senv(_env)
  93.     env.pcall(def, env.table.unpack(parents))
  94.     senv(env)
  95.    
  96.     return setmetatable({}, {
  97.         __ipairs    = function()        return ipairs(class)              end,
  98.         __pairs     = function()        return  pairs(class)              end,
  99.         __index     = function(t, name) return        class[name]         end,
  100.         __index_new = function(t, name, value)        class[name] = value end,
  101.         __call      = function(...)
  102.             local this = {}
  103.             for k,v in pairs(class) do
  104.                 this[k] = type(v) == 'function' and wraps(this, v) or v
  105.             end
  106.             this.__class = class
  107.             this.__init(...)
  108.            
  109.             return setmetatable(this, this)
  110.         end
  111.     })
  112. end
  113.  
  114. return class
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement