Removing objects without losing memory

I’m trying to properly remove objects when changing scenes. I can’t get my button to work because the function and button are local. When I press the tutBtn, I get an error to set the tutBtn to global, notice line 30,  well I don’t want to set it to a global. Yet, if I put the button before the function, the function obviously won’t recognize the button and nothing will happen. Also, if I make a createScene() function after setting my variables, it’ll actually skip all the way to my target screen, “tutMenu”, and skip the main menu all together.

module(..., package.seeall) function new() local menuGroup = display.newGroup() local widget = require "widget" local bg local title local tutBtn local bg = display.newRect(0,0, display.contentWidth,display.contentHeight) bg:setReferencePoint(display.CenterReferencePoint) bg:setFillColor(245,245,245) menuGroup:insert(bg) local title = display.newImageRect( "title.png", 480, 164) title:setReferencePoint(display.CenterReferencePoint) title.x = display.contentCenterX title.y = 75 menuGroup:insert(title) local function toTutorials( event ) if event.phase == "ended" then bg:removeSelf();bg = nil title:removeSelf();title = nil tutBtn:removeSelf();tutBtn = nil director:changeScene("tutMenu", "crossfade") end end local tutBtn = widget.newButton { -- left = 10, -- top = 200, width = 321, height = 87, defaultFile = "tutBtn.png", overFile = "tutBtn-over.png", id = "tutBtn", onEvent = toTutorials, } tutBtn.x = display.contentWidth/2 tutBtn.y = 200 menuGroup:insert(tutBtn) return menuGroup end

Remove the word local from your widget.newButton line

That’s exactly what I don’t want, to have my button as a global variable…

no your button is set to local at the top of your code

I forgot to remove those when I tried to put it all in one function. But it’s still the same outcome whether they’re predefined in the beginning or not. 

Solved. Needed a simple if statement within the function. 

local function toTutorials( event ) if event.phase == "ended" then display.remove(bg);bg = nil display.remove(title);title = nil if tutBtn then display.remove(tutBtn) tutBtn = nil end director:changeScene("tutMenu", "crossfade") end end

It turns out you don’t need the “if” statement to make your code work. When you added the “if” statement you also changed 

“tutBtn:removeSelf()” to “display.remove(tutBtn)”

The display.remove API is a wrapper around object:removeSelf and does a check to see if the object is valid before trying to remove it.

Remove the word local from your widget.newButton line

That’s exactly what I don’t want, to have my button as a global variable…

no your button is set to local at the top of your code

I forgot to remove those when I tried to put it all in one function. But it’s still the same outcome whether they’re predefined in the beginning or not. 

Solved. Needed a simple if statement within the function. 

local function toTutorials( event ) if event.phase == "ended" then display.remove(bg);bg = nil display.remove(title);title = nil if tutBtn then display.remove(tutBtn) tutBtn = nil end director:changeScene("tutMenu", "crossfade") end end

It turns out you don’t need the “if” statement to make your code work. When you added the “if” statement you also changed 

“tutBtn:removeSelf()” to “display.remove(tutBtn)”

The display.remove API is a wrapper around object:removeSelf and does a check to see if the object is valid before trying to remove it.