isModal in composer does not work for me ?

Hi Rob,

i am in Build: 2014.2189 … i tested my app in windows and Mac. both having the same issue. can you please elaborate more in putting all objects in parent sceneGroup…

do you mean the objects in current scene or overlay scene. i tried to trace all objects and it looks they are in sceneGroup… please explain what to check in this case to fi the issue.

thx

Abdul

It’s hard to explain without multiple drawings but let me try.

Each Composer scene is a layer.   At the core it’s a Corona display.newGroup() which can contain other display objects, like images, widgets, lines, circles, etc.  In Composer these scenes stack on top of each other like sheets of paper.   Now for a moment, lets say you create one scene (lay a single sheet of paper down).  Next you want to ad an image to it, so you put a photo on top of the sheet.  But technically that photo isn’t part of the paper, it sits on top of it.  In the real world you can’t insert a photograph into a sheet of paper, but in the computer world you can.  When you do:   sceneGroup:insert(myImage), that’s what you are doing:  adding that image to be physically part of that paper, not sitting on top of it.

Now you come along and create a new scene (be it an overlay or a regular scene).  It’s a new sheet of paper.  Composer moves it on screen (perhaps by sliding it in or fading it in) and you can imagine sliding the new piece of paper over top of your other one.  In real life, the new paper would go on top of the old sheet.  Since the photo is not part of the paper the new sheet of paper would cover it up.  You could then add another photo on top of the stack. 

However this is where it gets out of alignment with the real world.  Instead of Composer sliding that paper on top, it puts it on top of the other sheet of paper but **below** the photograph.  The photograph is not part of the scene since it wasn’t inserted.  This is done on purpose so you can have User Interface elements that are always on top, like a heads-up display or a tabBar controller at the bottom. 

In your situation, if you do not insert an object with a touch handler into it’s scene and you draw another scene on top, in reality it’s only on top of the other scene, but not on top of any objects you think are in the scene.  You end up with paper, paper, photo, photo in this example.  Your objects would still be touchable.

An easy test for this is to give your overlay scene a solid background and see if any of the things you thinks should be underneath are showing up.  If they are, then you have this issue.  If the solid background hides your display objects on the “parent” (bottom) layer, then we have a different issue. 

You can always add your own touch and tap handler to the background to absorb the taps, but it should be working and I’ve tested it to work.

Rob

any news on this? suggested work around? I’m building a login screen, and while I could use an entire composer.gotoScene, that seems excessive and less clean that just an overlay…

The work around is the same for Storyboard.  Put your own touch and tap handler on the background of the overlay if it’s full screen.  If the overlay isn’t full screen, create a full screen transparent image, set it’s .isHitTestable to true, and add a touch and tap handler to it to catch rogue touches.

Rob

Thanks Rob for you detailed explanation. it is clear now to me, i  will try to see if the case is what  you described.  i was trying to see how figure out what object is lying on top of the scene. 

i added the following box in front of scene and it covers all page and no taps went down :

local box= display.newRect( 0, 0, _W, _H )

is this what you meant or there is  a way to change the color of the scene itself.  i checked the docs but there nothing .

thx

Abdul

well local box = display.newRect(0, 0, _W, _H) would create a box centered around 0,0, but that’s the idea, it put a box in your overlay scene and see if it hides your parent scene’s objects.

Rob

Rob,
That what I did. . I insert it in scengroup and it covered everything. So there may be something else.

I will look at it again … I remember I did one sample long back and it was working fine … but not this time.

Thx
Abdul

Hi,

I’ve got exactly the same problem with isModal not working (build 2014.2381). The problem can easily enough be demonstrated with a skeleton project:

main.lua

[lua]local composer = require( “composer” )

display.setDefault( “anchorX”, 0 )
display.setDefault( “anchorY”, 0 )
composer.gotoScene( “parent” )
[/lua]

parent.lua

[lua]local composer = require( “composer” )
local scene = composer.newScene()

local function openOverlay( event )
    local options = {
    effect = “fade”,
    time = 250,
    isModal = true
}
print( “Overlay button tapped” )
composer.showOverlay( “overlay”, options )
end

function scene:create( event )
    local sceneGroup = self.view
    local rect = display.newRect( sceneGroup, 0, 100, 400, 100 );
    rect.strokeWidth = 0;
    rect:setFillColor( 1, 1, 1 );
    rect:addEventListener( “tap”, openOverlay );
    local text = display.newText( sceneGroup, ‘Overlay’, 0, 100, 400, 100, native.systemFont, 48, “center”);
    text:setFillColor( 0, 0, 0 );
end

scene:addEventListener( “create”, scene )

return scene[/lua]

overlay.lua

[lua]local composer = require( “composer” )
local scene = composer.newScene()

local function tapOverlay ( event )
    print ( “Overlay Background Tapped” )
end

function scene:create( event )
    local sceneGroup = self.view
    local rect = display.newRect( sceneGroup, 0, 0, display.pixelWidth, display.pixelHeight )
    rect.strokeWidth = 0;
    rect:setFillColor( 0, 0, 0, 0.25 );
    rect:addEventListener( “tap”, tapOverlay );
end

scene:addEventListener( “create”, scene )

return scene[/lua]

When you tap the white rectangle with the caption Overlay, the console prints “Overlay button tapped” and it invokes the overlay (which draws a semi transparent rectangle on top of the parent, obscuring it correctly and demonstrating it effectively sits on top)

If you tap the overlay background rectangle, the console first prints “Overlay Background tapped”, followed again by “Overlay button tapped” (and you can see the screen flashing as the overlay scene is loaded again).

isModal is not working.

Please package this up in a .zip file along with a config.lua and build.settings.  Then use the Report a bug link at the top of the page.  Engineering will need this to solve the problem.

Thanks

Rob

In the function openOverlay, include a “return true” statement right at the end of the function. Let us know if this solves your problem.

Hi,

Thanks - adding a “return true” to the end of the openOverlay function makes no difference (and it’s hard to see why it would, that’s outside the context of the showOverlay call).

I’ll zip the test skeleton up (all few hundred bytes of it…), although you would have thought the engineering team could have copy and pasted it with minimal effort from the post above.

G.

Hey guys,

It looks like a bug. It’s being investigated.

Thanks,

alex

Err… my bad.

The “return true” is required in function ‘tapOverlay’ in overlay.lua and not function ‘openOverlay’ in parent.lua. I tried this and it works.

Reasoning: Whenever a listener function is invoked by an object’s tap/touch event, the tap/touch propogates further down the display hierarchy unless the “return true” statement is specified at the end of the listener function.

You could argue that ‘isModal = true’ should disallow this behaviour in the first place, and you wouldn’t be wrong. Corona engineers will probably have a look at that. In the meantime, my fix should keep you going. :slight_smile:

I understand your point and if you stop touch events from propagating altogether by returning true in the example’s overlay listener, then in the example the dialogue indeed becomes modal, but that is not my point.

The propagation we’re discussing is not with respect to the listener in the scene itself (where returning true would stop propagation to other layers in the same scene) - indeed there may be perfectly good reasons for designing a scene where certain events do propagate down from one layer (in the scene) to another (in the same scene).

Or, one could have a scene that is used in both modal and non-modal versions and where therefore, at the scene level, propagation of touch events need to be handled differently for modal/non-modal scenarios.

isModal applies to the scene as a whole and should really do what it says on the tin, which is to prevent touch events from propagating outside the overlay scene. If it does not do that, it serves little purpose in my humble opinion.

Agreed.

This bug has been around since the Storyboard days. I thought this was fixed in Composer, maybe not.

any news on this? suggested work around? I’m building a login screen, and while I could use an entire composer.gotoScene, that seems excessive and less clean that just an overlay…

The work around is the same for Storyboard.  Put your own touch and tap handler on the background of the overlay if it’s full screen.  If the overlay isn’t full screen, create a full screen transparent image, set it’s .isHitTestable to true, and add a touch and tap handler to it to catch rogue touches.

Rob

Migrating to composer and running into this issue. Does not seem to be addressed yet? 

Hey guys,

It’s being tested atm. Should be in a daily build very soon.

Thanks,

alex

Thanks. Doing a nasty workaround for this too, can you take a look: http://forums.coronalabs.com/topic/52620-bug-composergetscenenameoverlay-in-did-show-event-of-overlay-returns-nil/