Page 1 of 2

I suck at tables! Help!!

Posted: Mon Sep 02, 2013 10:57 pm
by Mangl
Hi guys, I'm new around these parts! I've been using Love for a few weeks and run into my first problem.. Which is my poor table comprehension.

To cut to the chase: I'm working on code for pickups.. and whilst I can successfully create pickups and have the player pick them up there's a problem! If I create 4 pickups, and have the player pick up #2, then #3 and #4 will also be picked up simultaneously.

Any pointers on tables, how to number them and remove them properly would be much appreciated!

Code: Select all

pickup = {}

	function pickup:create(id, x, y, number)
		table.insert(pickup, {id = id, x = x, y = y})
	end

function pickup:update()
	for i,v in ipairs(pickup) do
		if player.x > v.x - 16 and player.x < v.x + 16 and player.y > v.y - 16 and player.y < v.y + 16 then
			print("Picked up")
			--dostuff
			pickup:destroy()
		end
	end
end

function pickup:draw()
	for i,v in ipairs(pickup) do
		if v.id == 0 then
			love.graphics.draw(pickup0, v.x, v.y)
		elseif v.id == 1 then
			love.graphics.draw(pickup1, v.x, v.y)
		end
	end
end

function pickup:destroy()
	table.remove(pickup)
end

Re: I suck at tables! Help!!

Posted: Tue Sep 03, 2013 5:57 am
by micha
To remove an entry from a talbe you need to call the table.remove with the tables name and the index of the entry to remove. You only handle the table name.

Code: Select all

function pickup:update()
  for i,v in ipairs(pickup) do
    if player.x > v.x - 16 and player.x < v.x + 16 and player.y > v.y - 16 and player.y < v.y + 16 then
      print("Picked up")
      --dostuff
      table.remove(pickup,i)
    end
  end
end
This will then cause another problem: If you have pickup 1,2 and 3 and remove the first one, then you are left with 2 and 3 which get rearrange to 1 and 2. That confuses the for-loop. To avoid this problem, traverse the table backwards:

Code: Select all

for i = #pickup,1,-1 do
  v = pickup[i]
  -- your suff
end

Re: I suck at tables! Help!!

Posted: Tue Sep 03, 2013 2:54 pm
by Robin
Or better:

Code: Select all

for i = #pickup,1,-1 do
  local v = pickup[i]
  -- your suff
end
This way you don't leak v outside of the relevant scope.

Re: I suck at tables! Help!!

Posted: Tue Sep 03, 2013 5:55 pm
by Mangl
Ahh! I knew I was missing something, this helps a lot thanks guys! Works perfectly now! :awesome:

Re: I suck at tables! Help!! :O

Posted: Wed Sep 04, 2013 11:13 pm
by Mangl
Is there any way I can create a for statement that looks in more than one ipairs table simultaneously? I've thoroughly searched .lua documentation and intensively googled and haven't come up with anything.

Just for an example: If I use ipairs tables for both bullets and enemies, and I want to check for collisions, how would I go about that? I've tried using one for statement within another.

Re: I suck at tables! Help!!

Posted: Wed Sep 04, 2013 11:17 pm
by Nixola
That's what you should do if you want to check each element of one table agains each of the other

Re: I suck at tables! Help!!

Posted: Thu Sep 05, 2013 2:12 am
by Mangl
Thanks for clarification!

Re: I suck at tables! Help!!

Posted: Thu Sep 05, 2013 2:42 am
by substitute541
Mangl wrote:Is there any way I can create a for statement that looks in more than one ipairs table simultaneously? I've thoroughly searched .lua documentation and intensively googled and haven't come up with anything.

Just for an example: If I use ipairs tables for both bullets and enemies, and I want to check for collisions, how would I go about that? I've tried using one for statement within another.
You would use a double for-loop (of course.)

Code: Select all

for i, enemy in ipairs(enemies) do
    for j, bullet in ipairs(bullets) do
        if collides(enemy, bullet) then
            enemy.explode()
        end
    end
end
Edit: Didn't read the bottom paragraph, nevermind.

Re: I suck at tables! Help!!

Posted: Thu Sep 05, 2013 2:59 am
by davisdude
You just have to have different iterator names. Iterators are the things before the comma (usually i).
Then it's just a matter of the tables.

Code: Select all

for i, b in ipairs( bullet ) do
    for ii, e in ipairs( enemy ) do
        -collisions
    end
end
Two things:
A lot of people have trouble with remembering which letter goes with which table. If that's the case, make names that make sense to you! :awesome:
I personally, find it easiest to go by vowels for my iterators, and first letter of table. For example:

Code: Select all

for a, b in ipairs( bullet ) do
    for e, enemy in ipairs( enemy ) do
        --collision detection
    end
end
Ultimately, it's up to you, though.

The other thing:
If you're super detail oriented like I am, check out my circle-rectangle collision for your bullet collision.
That was my first post, so the coding is a bit messy (sorry about that :P )
Post: http://www.love2d.org/forums/viewtopic.php?f=4&t=33493

Edit: beat by substitute. :P

Re: I suck at tables! Help!!

Posted: Thu Sep 05, 2013 11:48 pm
by Robin
davisdude wrote:iterators
Nope, what you're talking about is not an iterator. They are indices (plural of index). An iterator is the thing returned by ipairs.