Going from overlay scene to regular scene in composer

I’m not a big fan of questions like this, because you’re basically saying.  It doesn’t work the way I want it to, so it must be Corona’s fault.

The problem here is your code isn’t written to handle cleaning up the scene and re-building it without destroying the scene group. 

(Recall suggestion one above)

 you’ll have to write your own functions destroy and re-create the content and call them directly

This is why I always encourage people NOT to start with composer till they can write a module that creates the ‘scene’, destroys the scene, and re-builds the scene. Then I tell them, “Call the module from your composer scene, but let your module do all the work.”

I’ll respond later with a simple example demonstrating this concept.  Right now I’m catching up on e-mails and don’t want to stop for this.

PS - If I sound snippy, don’t be offended.  I realize what you’re trying to do, and I understand where the confusion is coming from.

Composer.* is a fine piece of code, you simply have to use it correctly to get the results you desire.

I’ll help a bit more later.

It seems I basically have two choices:

  1. Refactor the playGame scene so that I don’t need to destroy it to replay a level or go to the next level. I tried this and it worked fine except that display objects used in one level still existed in the sceneGroup (from self.view) in the next level, causing different problems. I couldn’t find a way to get rid of them without manually fiddling with sceneGroup, which I am not sure is a good idea. I also tried to put these objects in a separate display group and delete them in the hide() function but since they were not in the sceneGroup, they were displayed on top of everything else, inlcluding the overlay scene.
  2. Write my own methods for creating and destroying scenes, as you suggest.

Again, I would assume that what I want to achieve is pretty common since a lot of level based games have this “scene sequence”. Generally speaking, what would be the best practice to do this?

My preferred solution would be not having to destroy the playGame scene at all and simply making it work by reseting all game elements to an initial state when the level starts. The only problem here is that the (level specific) display objects from the previous scene remain in self.view since the scene has not been destroyed before restarting the level, and thus causing problems in the next level. However, if I put them in another display group instead to get around that, they are always displayed on top (like all display objects not in self.view), which is not good either.

This is basically the problem I need to solve…

  1. Download this file:

https://github.com/roaminggamer/CoronaGeek/raw/master/Hangouts/composer_scene_manager.zip

  1. Run example 12_rebuild_playgui

  2. Review the sample and pay particular attention to these files:

  • ifc/playGUI.lua
  • ifc/gameOverOverlay.lua
  • scripts/game.lua

Note: If you have objects from sceneA lingering in sceneB, you didn’t put them in the scenegroup (or or child of that group) owned by sceneA.  This is a common mistake.

I have downloaded it and I will analyze it now, let me get back…

About your second posting: what I meant was that when I go back to the playGame scene the second time (after completing a level and continuing with the next via the overlay scene), the display objects are still in the sceneGroup causing problems. In other words the first time I call playGame some scene specific objects are inserted into sceneGroup. When I have finished the level and want to play the next level, I call playGame a second time. At this point, all display objects from the first time are still in the sceneGroup (together with the new objects from the second time). As I said, one solution would be not to put them in the sceneGroup at all but in another displayGroup which I delete manually after each level. However, then all these object are displayed on top of everything else…

You should always manage your own group hierarchy and simply add that hierarchy as a child of sceneGroup
 
In my client and personal games I never place anything directly in scenegroup.  Instead I do something like this:

local layers function scene:create( event ) sceneGroup = self.view -- Create some rendering layers layers = ssk.display.quickLayers( sceneGroup, "underlay", "world", { "background", "content", }, "buttons", "overlay" ) newImageRect( layers.underlay, centerX, centerY, "images/interface/protoBack.png", { w = 380, h = 570, rotation = (isLandscape) and 90 or 0 } ) easyIFC:quickLabel( layers.buttons, "Credits", centerX, 30, gameFont, 30 ) easyIFC:presetPush( layers.buttons, "default", 55, h - 25, 100, 40, "Back", onBack ) end

The above code creates a display group hierarchy and places it in the sceneGroup

_ Personal Request :_ I have real difficulty reading wall-of-text posts.  Can you please use paragraphs in your posts.  
 
I want to help, but I have to guard my time jealously.  So, anything that takes multiple readings to understand gets cut.

Followup:  In examples on the other hand I do place things in ‘sceneGroup’ because it keeps the example short and easy to read.  
 
It just isn’t what I consider a good practice for for anything but the most trivial real apps and games.

Note:trivial’ is not a derogatory term here.  It is an assessment of complexity.

You can’t remove the scene you’re in. An overlay scene is still dependent on it’s parent scene so you can’t remove it. Simply turn your overlay into a regular scene, go to the game over scene, remove the game and go back.

Rob

@Rob: thanks!

@roaminggamer: I looked at your files and I now understand what you mean. I have refactored my code so that I put all the “level specific” objects in a separate group, which I then add to the sceneGroup. I also made custom functions to create and destroy the game scene (like in your code). It works like a charm! :o) Thank you very much for all your help, I really appreciate it! You should be on the Corona payroll for the service you do to the community in these forums…

The simple solution is to create a blank composer scene called loading that immediately purges and reloads the scene it just came from.

@nick_sherman: i tried that but that gave me weird effects with listeners that got registered twice etc. It worked when I added a delay of 100 ms but it did not seem like a very safe solution. Doing what roaminggamer suggested did the trick…