Problem loading levels using Director and Ego (or something else I missed)

Hey,

I’m creating my first game with Corona and have come acrross a problem which I haven’t been able to solve. Maybe someone can point me to the right direction. I’m using director for changing scenes and ego by Peach for saving level information.

I have 4 levelsx.lua files (levels1, levels2 etc), each of them has 10 level icons which, if pressed, start the corresponding loadx.lua (load1.lua, load2.lua etc) which will initiate levelx.lua (level1.lua, level2.lua etc)

The code for Levels1.lua:

[lua]module(…, package.seeall)
function new()
local localGroup = display.newGroup()

local function checkForFile ()
currentLevel = loadFile (“currentLevel.txt”)
if currentLevel == “empty” then
currentLevel = 1
saveFile(“currentLevel.txt”, currentLevel)
end
end
checkForFile()

local backgroundImage = display.newImageRect( “images/levels.png”, 480, 320 )
backgroundImage.x = 240
backgroundImage.y = 160
localGroup:insert( backgroundImage )
local level = {}

local function goLevel (event)
director:changeScene(event.target.scene)
end

local function setupLevels()
for i = 1, 10 do
if i <=5 then startY = 80 else startY = 150 end
if i <= 5 then startX = i * 70 else startX = (i - 5) * 70 end
if tonumber(currentLevel) >= i then
level[i] = display.newImage(“images/lev”…i…“btn.png”, startX+0.5, startY+0.5 )
localGroup:insert( level[i] )
level[i].scene = “load”…i…""
level[i]:addEventListener(“tap”, goLevel)
elseif tonumber(currentLevel) < i then
level[i] = display.newImage(“images/lev”…i…“btnH.png”, startX+0.5, startY+0.5 )
localGroup:insert( level[i] )
end
end
end
setupLevels()

local introTwoButton
local onIntroTwoTouch = function( event )
if event.phase == “release” and introTwoBtn.isActive then
audio.play( btnSound )
director:changeScene( “levels2”, “crossfade”)
end
end

introTwoBtn = ui.newButton{
defaultSrc = “images/arrowrbtn.png”,
defaultX = 26,
defaultY = 51,
overSrc = “images/arrowrbtn-over.png”,
overX = 26,
overY = 51,
onEvent = onIntroTwoTouch,
id = “IntroTwoButton”,
text = “”,
font = “Helvetica”,
textColor = { 255, 255, 255, 255 },
size = 16,
emboss = false
}

introTwoBtn.x = 450
introTwoBtn.y = 150

local closeBtn

local onCloseTouch = function( event )
if event.phase == “release” then
audio.play( tapSound )
director:changeScene( “loadmainmenu”, “crossfade” )
end
end

closeBtn = ui.newButton{
defaultSrc = “images/menubtn.png”,
defaultX = 75,
defaultY = 30,
overSrc = “images/menubtn-over.png”,
overX = 75,
overY = 30,
onEvent = onCloseTouch,
id = “CloseButton”,
text = “”,
font = “Helvetica”,
textColor = { 255, 255, 255, 255 },
size = 16,
emboss = false
}

closeBtn.x = 40
closeBtn.y = 300
localGroup:insert( closeBtn )
clean = function()
if btnAnim then transition.cancel( btnAnim ); end
end

return localGroup
end[/lua]

The levels2.lua etc are practically the same, only with a slight different loop in setupLevels()

[lua]local function setupLevels()
for i = 1, 10 do
if i <=5 then startY = 80 else startY = 150 end
if i <= 5 then startX = i * 70 else startX = (i - 5) * 70 end
if tonumber(currentLevel) >= 10+i then
level[10+i] = display.newImage(“images/lev1”…i…“btn.png”, startX+0.5, startY+0.5 )
localGroup:insert( level[10+i] )
– For some reason, works with “level”…10+i… and not with “load1”…i…
level[10+i].scene = “load1”…i…""
level[10+i]:addEventListener(“tap”, goLevel)
elseif tonumber(currentLevel) < 10+i then
level[10+i] = display.newImage(“images/lev1”…i…“btnH.png”, startX+0.5, startY+0.5 )
localGroup:insert( level[10+i] )
end
end
end
setupLevels()[/lua]

The loadx.lua:

[lua]local loadgame = {}
loadgame.new = function( params )
local localGroup = display.newGroup()

local myTimer
local loadingImage

local loadGame = function()
loadingImage = display.newImageRect( “images/loading.png”, 480, 320 )
loadingImage.x = 240; loadingImage.y = 160

local goToGame = function()
director:changeScene( “level1”, “crossfade” )
end
myTimer = timer.performWithDelay( 1000, goToGame, 1 )
end

loadGame()
local initVars = function()
localGroup:insert(loadingImage)

end
clean = function()
if myTimer then timer.cancel( myTimer ); end
end

initVars()

return localGroup
end

return loadgame [/lua]

with the level number changing on each next:
[lua]director:changeScene( “level2”, “crossfade” )[/lua]

Everything works fine in the first levels1.lua (which includes the levels from 1-10) - loadx.lua initializes starting levelx.lua, but with others (levels2, levels3 etc), after pressing on level buttons, only the loading (load11.lua) is displayed and that´s it.
If I add one more level icon (for i=1, 11 do) to the levels1.lua, the loading finishes like in previous ones and level11.lua is loaded.
Even funnier that if I skip the load11.lua or any bigger numbers from
[lua] level[10+i].scene = “load1”…i…""[/lua]
and go directly to level11
[lua]level[10+i].scene = “level1”…i…""[/lua]
all works (level11.lua starts).

So I´m not sure if it is related to ego, director, something else or me being new to Corona and Lua, but would be nice if someone could help.

Thanks,
Gert
[import]uid: 105289 topic_id: 30187 reply_id: 330187[/import]

Not quite sure what’s causing the issue, but you could streamline this process quite a bit by having one levels file and one load file. Not sure how director handles reloading the same scene you’re currently in so this might need some tweaking, perhaps a blank dummy scene that you go to in between. Or move to Storyboard which I find a lot easier and less prone to errors.

Within your main.lua file, declare a global variable for the group of levels you want to display (1-4)

[lua]_G.levelGroup = 1 – change this when user clicks back/forward or completes levels 10, 20 & 30.[/lua]

levels.lua:

[lua]module(…, package.seeall)
function new()
local localGroup = display.newGroup()

local function checkForFile ()
currentLevel = loadFile (“currentLevel.txt”)
if currentLevel == “empty” then
currentLevel = 1
saveFile(“currentLevel.txt”, currentLevel)
end
end
checkForFile()

local backgroundImage = display.newImageRect( “images/levels.png”, 480, 320 )
backgroundImage.x = 240
backgroundImage.y = 160
localGroup:insert( backgroundImage )

local level = {}

local function goLevel (event)

local obj = event.target
_G.loadLevel = obj.level – store global variable for next level to load

director:changeScene(“load”)
end

local function setupLevels()

local n = 1 + (_G.levelGroup * 10) – get first level of the group of 10

for i = 1, 10, 1 do
if i <=5 then startY = 80 else startY = 150 end
if i <= 5 then startX = i * 70 else startX = (i - 5) * 70 end
if tonumber(currentLevel) >= n then
level[n] = display.newImage(“images/lev”…n…“btn.png”, startX+0.5, startY+0.5 )
localGroup:insert( level[n] )
level[n].level = n
level[n]:addEventListener(“tap”, goLevel)
elseif tonumber(currentLevel) < n then
level[n] = display.newImage(“images/lev”…n…“btnH.png”, startX+0.5, startY+0.5 )
localGroup:insert( level[n] )
end
n = n + 1
end
end

setupLevels()

local introTwoButton
local onIntroTwoTouch = function( event )
if event.phase == “release” and introTwoBtn.isActive then
audio.play( btnSound )

_G.levelGroup = _G.levelGroup + 1 – move to the next page
director:changeScene( “levels”, “crossfade”)
end
end

introTwoBtn = ui.newButton{
defaultSrc = “images/arrowrbtn.png”,
defaultX = 26,
defaultY = 51,
overSrc = “images/arrowrbtn-over.png”,
overX = 26,
overY = 51,
onEvent = onIntroTwoTouch,
id = “IntroTwoButton”,
text = “”,
font = “Helvetica”,
textColor = { 255, 255, 255, 255 },
size = 16,
emboss = false
}

introTwoBtn.x = 450
introTwoBtn.y = 150

if _G.levelGroup == 3 then introTwoBtn.alpha = 0; end – hide button if already on last page

– I assume there is a back button on pages 2-4, which you’ll need to add and hide when levelGroup == 0

local closeBtn

local onCloseTouch = function( event )
if event.phase == “release” then
audio.play( tapSound )
director:changeScene( “loadmainmenu”, “crossfade” )
end
end

closeBtn = ui.newButton{
defaultSrc = “images/menubtn.png”,
defaultX = 75,
defaultY = 30,
overSrc = “images/menubtn-over.png”,
overX = 75,
overY = 30,
onEvent = onCloseTouch,
id = “CloseButton”,
text = “”,
font = “Helvetica”,
textColor = { 255, 255, 255, 255 },
size = 16,
emboss = false
}

closeBtn.x = 40
closeBtn.y = 300
localGroup:insert( closeBtn )
clean = function()
if btnAnim then transition.cancel( btnAnim ); end
end

return localGroup
end

[lua]Load.lua:

[lua] local loadgame = {}
loadgame.new = function( params )
local localGroup = display.newGroup()

local myTimer
local loadingImage

local loadGame = function()
loadingImage = display.newImageRect( “images/loading.png”, 480, 320 )
loadingImage.x = 240; loadingImage.y = 160

local goToGame = function()
director:changeScene( “level”…_G.loadLevel, “crossfade” )
end
myTimer = timer.performWithDelay( 1000, goToGame, 1 )
end

loadGame()
local initVars = function()
localGroup:insert(loadingImage)

end
clean = function()
if myTimer then timer.cancel( myTimer ); end
end

initVars()

return localGroup
end

return loadgame [/lua]

[import]uid: 93133 topic_id: 30187 reply_id: 120865[/import]

@Gert
Ego + Director = Great Tools!

Try replacing the code below into your levels2.lua file

[blockcode]
local function setupLevels()
for i = 1, 10 do
if i <=5 then startY = 80 else startY = 150 end
if i <= 5 then startX = i * 70 else startX = (i - 5) * 70 end
if tonumber(currentLevel) >= i + 10 then
level[i] = display.newImage(“images/lev”…i + 10…“btn.png”, startX+0.5, startY+0.5 )
localGroup:insert( level[i] )
level[i].scene = “load”…i + 10…""
level[i]:addEventListener(“tap”, goLevel)
elseif tonumber(currentLevel) < i + 10 then
level[i] = display.newImage(“images/lev”…i + 10…“btnH.png”, startX+0.5, startY+0.5 )
localGroup:insert( level[i] )
end
end
end
setupLevels()
[import]uid: 41496 topic_id: 30187 reply_id: 120974[/import]

Thank you both!

Tomas, I tried your solution, but still get the same result, level11 and on doesn’t get past loading screens.

Nick, your solution, seems to be working, which is really, really great and makes my wonder, what the actual difference is between them.
By the way, the levels start from 11 now, any suggestions on that?
But at least after changing the level screens from 11-20 to 20-30 levels start and get past loading screen.

Thanks again! [import]uid: 105289 topic_id: 30187 reply_id: 120998[/import]

@gert

No problem. My mistake, set _G.levelGroup equal to zero in main.lua, not 1.

My solution eliminates the need for levels2.lua, levels3.lua, load2.lua, load3.lua etc as the levels.lua and load.lua files handle the four groups of levels dynamically. This should also make it a lot easier to add more levels later on, all you would need to do is update the code which hides the ‘next’ button when you are on the last page. [import]uid: 93133 topic_id: 30187 reply_id: 121001[/import]

Thanks again! Works super.
By the difference I actually meant as process wise, I really would like to get to the point where I went wrong (besides of making a huge pile of files which your solution obsoleted:) ) or what is causing the issue.

If I find something I will post it here, just in case because your current solution is the one I´m going anyways.

[import]uid: 105289 topic_id: 30187 reply_id: 121003[/import]

There is a mistake here which would cause it to fall over when i = 10:

[lua]level[10+i].scene = “load1”…i…""[/lua]

When i = 10, the scene variable will equal “load110”.

But Tomas already spotted that one and it would not cause an issue until you tried to click on level 20.

What error did you get when this happened? Perhaps there was an error in your level12.lua files onwards. [import]uid: 93133 topic_id: 30187 reply_id: 121008[/import]

The funny thing is that there is no error, starting form 11-x with my own code or using the Tomas one, clicking on level buttons > load11 etc opens and stays on screen, without loading the level.

I tried print just to see how far it goes and it will go all the way to the end of load11, but that´s it, loading image is displayed and nothing happens. [import]uid: 105289 topic_id: 30187 reply_id: 121010[/import]

Not quite sure what’s causing the issue, but you could streamline this process quite a bit by having one levels file and one load file. Not sure how director handles reloading the same scene you’re currently in so this might need some tweaking, perhaps a blank dummy scene that you go to in between. Or move to Storyboard which I find a lot easier and less prone to errors.

Within your main.lua file, declare a global variable for the group of levels you want to display (1-4)

[lua]_G.levelGroup = 1 – change this when user clicks back/forward or completes levels 10, 20 & 30.[/lua]

levels.lua:

[lua]module(…, package.seeall)
function new()
local localGroup = display.newGroup()

local function checkForFile ()
currentLevel = loadFile (“currentLevel.txt”)
if currentLevel == “empty” then
currentLevel = 1
saveFile(“currentLevel.txt”, currentLevel)
end
end
checkForFile()

local backgroundImage = display.newImageRect( “images/levels.png”, 480, 320 )
backgroundImage.x = 240
backgroundImage.y = 160
localGroup:insert( backgroundImage )

local level = {}

local function goLevel (event)

local obj = event.target
_G.loadLevel = obj.level – store global variable for next level to load

director:changeScene(“load”)
end

local function setupLevels()

local n = 1 + (_G.levelGroup * 10) – get first level of the group of 10

for i = 1, 10, 1 do
if i <=5 then startY = 80 else startY = 150 end
if i <= 5 then startX = i * 70 else startX = (i - 5) * 70 end
if tonumber(currentLevel) >= n then
level[n] = display.newImage(“images/lev”…n…“btn.png”, startX+0.5, startY+0.5 )
localGroup:insert( level[n] )
level[n].level = n
level[n]:addEventListener(“tap”, goLevel)
elseif tonumber(currentLevel) < n then
level[n] = display.newImage(“images/lev”…n…“btnH.png”, startX+0.5, startY+0.5 )
localGroup:insert( level[n] )
end
n = n + 1
end
end

setupLevels()

local introTwoButton
local onIntroTwoTouch = function( event )
if event.phase == “release” and introTwoBtn.isActive then
audio.play( btnSound )

_G.levelGroup = _G.levelGroup + 1 – move to the next page
director:changeScene( “levels”, “crossfade”)
end
end

introTwoBtn = ui.newButton{
defaultSrc = “images/arrowrbtn.png”,
defaultX = 26,
defaultY = 51,
overSrc = “images/arrowrbtn-over.png”,
overX = 26,
overY = 51,
onEvent = onIntroTwoTouch,
id = “IntroTwoButton”,
text = “”,
font = “Helvetica”,
textColor = { 255, 255, 255, 255 },
size = 16,
emboss = false
}

introTwoBtn.x = 450
introTwoBtn.y = 150

if _G.levelGroup == 3 then introTwoBtn.alpha = 0; end – hide button if already on last page

– I assume there is a back button on pages 2-4, which you’ll need to add and hide when levelGroup == 0

local closeBtn

local onCloseTouch = function( event )
if event.phase == “release” then
audio.play( tapSound )
director:changeScene( “loadmainmenu”, “crossfade” )
end
end

closeBtn = ui.newButton{
defaultSrc = “images/menubtn.png”,
defaultX = 75,
defaultY = 30,
overSrc = “images/menubtn-over.png”,
overX = 75,
overY = 30,
onEvent = onCloseTouch,
id = “CloseButton”,
text = “”,
font = “Helvetica”,
textColor = { 255, 255, 255, 255 },
size = 16,
emboss = false
}

closeBtn.x = 40
closeBtn.y = 300
localGroup:insert( closeBtn )
clean = function()
if btnAnim then transition.cancel( btnAnim ); end
end

return localGroup
end

[lua]Load.lua:

[lua] local loadgame = {}
loadgame.new = function( params )
local localGroup = display.newGroup()

local myTimer
local loadingImage

local loadGame = function()
loadingImage = display.newImageRect( “images/loading.png”, 480, 320 )
loadingImage.x = 240; loadingImage.y = 160

local goToGame = function()
director:changeScene( “level”…_G.loadLevel, “crossfade” )
end
myTimer = timer.performWithDelay( 1000, goToGame, 1 )
end

loadGame()
local initVars = function()
localGroup:insert(loadingImage)

end
clean = function()
if myTimer then timer.cancel( myTimer ); end
end

initVars()

return localGroup
end

return loadgame [/lua]

[import]uid: 93133 topic_id: 30187 reply_id: 120865[/import]

@Gert
Ego + Director = Great Tools!

Try replacing the code below into your levels2.lua file

[blockcode]
local function setupLevels()
for i = 1, 10 do
if i <=5 then startY = 80 else startY = 150 end
if i <= 5 then startX = i * 70 else startX = (i - 5) * 70 end
if tonumber(currentLevel) >= i + 10 then
level[i] = display.newImage(“images/lev”…i + 10…“btn.png”, startX+0.5, startY+0.5 )
localGroup:insert( level[i] )
level[i].scene = “load”…i + 10…""
level[i]:addEventListener(“tap”, goLevel)
elseif tonumber(currentLevel) < i + 10 then
level[i] = display.newImage(“images/lev”…i + 10…“btnH.png”, startX+0.5, startY+0.5 )
localGroup:insert( level[i] )
end
end
end
setupLevels()
[import]uid: 41496 topic_id: 30187 reply_id: 120974[/import]

Thank you both!

Tomas, I tried your solution, but still get the same result, level11 and on doesn’t get past loading screens.

Nick, your solution, seems to be working, which is really, really great and makes my wonder, what the actual difference is between them.
By the way, the levels start from 11 now, any suggestions on that?
But at least after changing the level screens from 11-20 to 20-30 levels start and get past loading screen.

Thanks again! [import]uid: 105289 topic_id: 30187 reply_id: 120998[/import]

@gert

No problem. My mistake, set _G.levelGroup equal to zero in main.lua, not 1.

My solution eliminates the need for levels2.lua, levels3.lua, load2.lua, load3.lua etc as the levels.lua and load.lua files handle the four groups of levels dynamically. This should also make it a lot easier to add more levels later on, all you would need to do is update the code which hides the ‘next’ button when you are on the last page. [import]uid: 93133 topic_id: 30187 reply_id: 121001[/import]

Thanks again! Works super.
By the difference I actually meant as process wise, I really would like to get to the point where I went wrong (besides of making a huge pile of files which your solution obsoleted:) ) or what is causing the issue.

If I find something I will post it here, just in case because your current solution is the one I´m going anyways.

[import]uid: 105289 topic_id: 30187 reply_id: 121003[/import]

There is a mistake here which would cause it to fall over when i = 10:

[lua]level[10+i].scene = “load1”…i…""[/lua]

When i = 10, the scene variable will equal “load110”.

But Tomas already spotted that one and it would not cause an issue until you tried to click on level 20.

What error did you get when this happened? Perhaps there was an error in your level12.lua files onwards. [import]uid: 93133 topic_id: 30187 reply_id: 121008[/import]

The funny thing is that there is no error, starting form 11-x with my own code or using the Tomas one, clicking on level buttons > load11 etc opens and stays on screen, without loading the level.

I tried print just to see how far it goes and it will go all the way to the end of load11, but that´s it, loading image is displayed and nothing happens. [import]uid: 105289 topic_id: 30187 reply_id: 121010[/import]