Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Corona LUA and OOP Design

So I come from the traditional game development that uses OOP principles and from what I've seen you can mimic this using LUA once you know what you are doing. In some of the code postings I found out how you can use the director class and create files that have a new() function etc.

What I'm looking for is a way to manage my weapons. I have a player and an opponent and I would prefer to have one weapon class, say weaponCanon. What I have done is:

-- private vars here
local power
local canonSprite
local whatever

local someFunction = function()
...
end

-- Private stuff here
local weaponCanon = {}

weaponCanon.fire = function(atX, atY)
...
end

weaponCanon.reset = function()
...
end

return weaponCanon

Then in my level code I simply do:

local weaponCanon = require("weaponCanon")
weaponCanon.fire(100, 100)

This works great and allows me to use a "private" and "public" mentality when coding up my weapons. The problem is that if I want the player and opponent to have a canon:

local playerWeapon = require("weaponCanon")
local opponentWeapon = require("weaponCanon")

This simply returns the same object instead of a new instance to that object. So I only get one weaponCanon at the opponentWeapon location. This is obviously now what I want/need.

Our game has many weapons in it and it would be nice to only have one version of each file with a setting telling us if its the opponents weapon or players weapon. The alternative is to copy each file and create a weaponPlayerCanon and a weaponOpponentCanon but I cringe at the thought of modifications to one file and having to change 2+ files every time.

How can I make it return an instance and what is the structure of the LUA file to do so?

Thanks or any and all help

-d

like image 411
David Nelson Avatar asked Jun 14 '11 14:06

David Nelson


2 Answers

If later on you start needing inheritance (i.e. LaserCannon is a subclass of Weapon) you will probably need to use metatables more profoundly.

There are lots of libraries that will allow you to do "oop on top of Lua". You can see a very good list here:

http://lua-users.org/wiki/ObjectOrientedProgramming

I'm the author of middleclass. With my lib, you would have to do something like this:

local Weapon = class('Weapon')

function Weapon:initialize(a,b,c)
  self.x,self.y,self.z = a,b,c
end

function Weapon:fire(x,y)
 ...
end

LaserCannon would be easy to implement - you just pass a second parameter to class:

local LaserCannon = class('LaserCannon', Weapon)

function LaserCannon:initialize(a,b,c,d)
  self.w = d
  Weapon.initialize(self, a,b,c) -- superclass' constructor
end

function LaserCannon:foo()
 ...
end

You could use it like this:

require 'middleclass' -- so you can use "class"
LaserCannon = require 'laser_cannon'

local playerWeapon = LaserCannon:new() -- a laser
local opponentWeapon = Weapon:new() -- a regular generic weapon

opponentWeapon:fire(100,200) -- typical use
playerWeapon:fire(100, 200) -- LaserCannon inherits fire from Weapon
playerWeapon:foo() -- LaserCannon-exclusive

This is with middleclass, which is the one I prefer, since I made it. Other libraries on the page I mentioned before offer similar features.

like image 64
kikito Avatar answered Oct 18 '22 03:10

kikito


I guess you are trying to model a class with your source file. This means you should also have a function to create a new instance of that class unless you want them to share all their state.

Something along the lines of (untested):

local WeaponCannon = {}
WeaponCannon.__index = WeaponCannon
function WeaponCannon:new()
  return setmetatable({}, self)
end

function WeaponCannon:fire(x, y)
  -- Do something via the self reference and arguments (x, y)
end

return WeaponCannon

And in your calling code (also untested):

require('WeaponCannon')
local playerWeapon = WeaponCannon:new()
local opponentWeapon = WeaponCannon:new()
like image 37
ponzao Avatar answered Oct 18 '22 02:10

ponzao