25 May 2013, 18:04
Generic-user-small

Andrew Davis (13 posts)

I like how we can overload methods in Lua, like how we overload the move() method in Player so that it calls it instead of Unit:move(), but what I ultimately want to do is make a call to super. This way I can DRY up my code and put the common stuff in Unit:move(), put very little in Player:move() and then call the super method.

Can this be done? Is there a variation of your class.lua file that will allow this?

Thanks, Andy

25 May 2013, 22:01
Silvias_temp_avatar_pragsmall

Silvia Domenech (35 posts)

Hi Andy,

Oops! I thought I had implemented that part of super() in the book’s current beta (2.0), but it looks like the current super() function doesn’t call the function (it only returns it). It was a quick fix, though. I’ll upload the corrected class.lua in the next Beta update, but in the meantime I’ve uploaded it to Dropbox here.

You can use this new class file to call super(). In your example, you can write this in Player:move():

self:super( 'move' )

If the function takes parameters, like setPosition( x, y ), you can pass them normally after the function name:

self:super( 'setPosition', x, y )

You’ll have to pass the function name to the super function. I’m working on another version that doesn’t require the function name from within a function (to avoid typos), but it is not ready yet.

Silvia

25 May 2013, 23:11
Silvias_temp_avatar_pragsmall

Silvia Domenech (35 posts)

Hi again, Andy.

I’ve changed a few things in class.lua, and there is no longer a need need to type function names.

To call a function’s super(), you can call:

self:super( params )

If you want to call a super function (but not necessarily from its namesake), you can use:

self.base:functionName( params )

This new class lets you follow DRY principles without having to write the function names as strings.

Download it here

Enjoy!

Silvia

28 May 2013, 00:09
Generic-user-small

Andrew Davis (13 posts)

Excellent, thank you very much!

01 Jul 2013, 02:51
Generic-user-small

Andrew Davis (13 posts)

Hello again Silvia,

Can you confirm that you can call super with multiple levels of inheritance?

I have:

Unit = Class()
Player = Class(Unit)
Humvee = Class(Player)

I have an instance of a Humvee, and I’m calling move() on it. It’s correctly going to the </code>Player:move()</code> method, but when I call self:super() inside the Player:move() method, the Unit:move() is not being called (according to print statements)

Thanks for your help! Andy

Update I added a print in the findSuperFunction() method of your classes.lua and it does indeed get to the return nil unfortunately. I’m not really sure how to have it find the next class up.

01 Jul 2013, 02:50
Generic-user-small

Andrew Davis (13 posts)

I just wanted to comment on this and say that I seem to have been able to achieve this using “Kikito’s Middleclass Library”:https://github.com/kikito/middleclass.

Unit = class('Unit')
Player = class('Player', Unit)
Humvee = class('Humvee', Player)

That allows me to do this:

function HumveeTom:initialize(physics, group, imageSheet, sequence)
  Player:initialize(self, physics, group, imageSheet, sequence)
  -- Do stuff to the Humvee
end

function Player:initialize(self, physics, group, imageSheet, sequence)
  Unit:initialize(self, physics, group, imageSheet, sequence)
  -- Do stuff to the Player
end

function Unit:initialize(self, physics, group, imageSheet, sequence)
  -- Do stuff to the Unit
end

Now when I create a new instance of a Humvee, it will successfully inherit from the initialize methods of both Player and Unit, this is great for keeping code DRY.

Thanks! Andy

02 Jul 2013, 10:05
Silvias_temp_avatar_pragsmall

Silvia Domenech (35 posts)

Hi Andy,

Nice find! I hadn’t used that class system before, but it looks great from what its website says.

I think that my class system only worked for one super() call when using the super() function, but not when using super() in a function called from super().

In the book’s class system, you can also use the method you mentioned, although using the dot (.) instead of the colon (:) for the function call. Your example would look like this:

require "class"

-- Unit
Unit = Class()

function Unit:new( params )
	print( "new unit" )
end

function Unit:test( )
	print( "Unit test" )
end

-- Player
Player = Class(Unit)

function Player:new( params )
	Unit.new( self, params ) -- This is only necessary if you have set waterfallConstructors to false in class.lua
	print( "new Player" )
end

function Player:test( )
	Unit.test( self )
	print( "Player test" )
end

-- Tank
Humvee = Class(Player)

function Humvee:new( params  )
	Player.new( self, params ) -- This is only necessary if you have set waterfallConstructors to false in class.lua
	print( "new Humvee" )
end

function Humvee:test( )
	Player.test( self )
	print( "Humvee test" )
end

-- Testing
h = Humvee( )
h:test( )

It’s great that you have found an alternate library. I’ll definitely take a look at how they work using the colon instead of the dot; it makes things look nice when calling parent functions.

Silvia

  You must be logged in to comment