Removing display object from table

Hi!

I have created a table (called myRectangle) that contains 9 rectangles (created with display.newRect). I want to remove a random rectangle until all the rectangles has been removed.

This is what I got so far:

local t = {} function t:timer( event ) local topRand = 10 - event.count local randNumber = (math.random (1, topRand)) table.remove(myRectangle, randNumber) end timer.performWithDelay( 1000, t, 9 )

This works for removing rectangles from the table, but I also want to remove the display object so the rectangle won’t be visible anymore. I have tried to add this both before and after removing from the table:

myRectangle[randNumber]:removeSelf() myRectangle[randNumber] = nil

But this does not remove the same object from the table as the table.remove does.

Does anyone have any ideas for how to remove my rectangles?

I appreciate any help :slight_smile:

Try doing the:

myRectangle[randNumber]:removeSelf()
myRectangle[randNumber] = nil

first, then remove the table entry. 

Yes I have tried to remove the table entry both before and after removing the display object, but I eventually get a runtime error saying “attempt to index field ‘?’ (a nil value)”. 

there is a problem when you call removeSelf() for an object in a table

i only managed to remove all the objects in the table at once counting backwords

function clearObjects()
 local i = 0;
 print (#R2LObjects)
  for i=#R2LObjects,1,-1 do
   local child = table.remove(R2LObjects, i)    – Remove from table
   if child ~= nil then
   print ("object deleted = "… i)
     child:removeSelf()
     child = nil
   end
  end
 R2LObjects = nil
 R2LObjects = {}
 collectgarbage()
 

end

what i got to know that when you call the removeSelf() the complete table index changes and that could let you point to nil object

Thank you for your suggestions!

I found a way to make it work:

function removeRect:timer( event ) local topRand = #recs local randNumber = (math.random (1, topRand)) local removeThis = table.remove(recs, randNumber) if removeThis ~= nil then display.remove(removeThis) removeThis = nil end print("lengde " .. #recs) end timer.performWithDelay( 1000, removeRect, 12 )

When removing elements from a table you HAVE to iterate backwards through the table, otherwise you’ll find yourself in this situation:

local testTable = {1,2,3,4,5}

for i = 1,#testTable do

 table.remove(testTable,i)

end

testTable becomes {2,3,4,5}

So you’ll delete the table element holding the value 3 (because i becomes 2), leaving the slot holding 2 still in the table.

Not explained very succinctly, but just take it that when removing elements from a table you ALWAYS want to work backwards - otherwise you’ll only delete every other value.

Try doing the:

myRectangle[randNumber]:removeSelf()
myRectangle[randNumber] = nil

first, then remove the table entry. 

1 Like

Yes I have tried to remove the table entry both before and after removing the display object, but I eventually get a runtime error saying “attempt to index field ‘?’ (a nil value)”. 

there is a problem when you call removeSelf() for an object in a table

i only managed to remove all the objects in the table at once counting backwords

function clearObjects()
 local i = 0;
 print (#R2LObjects)
  for i=#R2LObjects,1,-1 do
   local child = table.remove(R2LObjects, i)    – Remove from table
   if child ~= nil then
   print ("object deleted = "… i)
     child:removeSelf()
     child = nil
   end
  end
 R2LObjects = nil
 R2LObjects = {}
 collectgarbage()
 

end

what i got to know that when you call the removeSelf() the complete table index changes and that could let you point to nil object

Thank you for your suggestions!

I found a way to make it work:

function removeRect:timer( event ) local topRand = #recs local randNumber = (math.random (1, topRand)) local removeThis = table.remove(recs, randNumber) if removeThis ~= nil then display.remove(removeThis) removeThis = nil end print("lengde " .. #recs) end timer.performWithDelay( 1000, removeRect, 12 )

When removing elements from a table you HAVE to iterate backwards through the table, otherwise you’ll find yourself in this situation:

local testTable = {1,2,3,4,5}

for i = 1,#testTable do

 table.remove(testTable,i)

end

testTable becomes {2,3,4,5}

So you’ll delete the table element holding the value 3 (because i becomes 2), leaving the slot holding 2 still in the table.

Not explained very succinctly, but just take it that when removing elements from a table you ALWAYS want to work backwards - otherwise you’ll only delete every other value.