Does finger slide-off produce an "ended" touch.phase event on the device?

Does a finger sliding off a device screen produce an “ended” touch.phase event ? Some forum posts say that this is the case - some say it is not. Anyhow, it is not documented by Ansca and cannot be tested in the simulator. Can anyone provide their experience please? .

not by the looks of things - it’s a shame.

Does not look like it registers when sliding off the screen, yes it is a shame and a been annoying for months…would be great if corona sdk added this feature. You can place it in a certain position so by the time finger slides off it should hit an ended phase because of the location of button, but there are weird circumstances of (especially in my app) button mashing and sliding off finger and spamming stuff that it won’t register leaving the device properly on a dpad that is very close to edge of screen.

There is no concept of sliding “off” the screen on a capacitive touchscreen. “Ended” is passed when the screen detects a break in the active touch event. Lifting your finger from the middle of the screen has no technical difference from sliding off the edge, AFAIK.

Typically, this means that any time you slide “off” the sides of the screen it will immediately register an ended event. It’s possible that some things can confuse your code (or possibly Corona) do trigger another start event instead of an end event, but in theory it should always be captured.

The real tricky part of this is making a touch listener that can properly handle the order of events by using focus. Without careful focus checking it’s all too easy to build a function that tries calling began/moved/ended out of order.

Yes you can “Slide off the screen”

If you create a display object, register a listener - the listener will be called on touch (began) and on the touch moving (moved) and when the person takes finger off (ended). However, if I touch, then slide it off the object, I will never get the ended.

This is because when the user take finger off the screen, it is no longer on that object, but on some other object, or off the screen.

You can say that all touch events should go to that object, by making that object have focus when “began” touch event is fired;;

        buttonPressed.hasFocus = true

        display.getCurrentStage():setFocus( buttonPressed )

Now the ended event will go to the object, even if finger is nowhere near object (providing finger started on object).

Then on the ended event, must give up focus, so no further events go to object;

            display.getCurrentStage():setFocus(nil)

            buttonPressed.hasFocus = false

This would work if there was one button or one finger, but I do not think it would work with multiple buttons, because user could be pressing two buttons at same time.

Really Corona should have a switch in the code when you setup the listener

obj:addListener(“touch”, myFunc, {slideOffEnded=true} )

Then if you slide off the object, it sends an “ended” event to the listener.

I think this is what people expect to happen, and what SHOULD happen.

That’s leaving the bounds of the object, which is definitely a problem for many buttons, but has nothing in particular to do with the edge of the screen. 

While I would agree that having a Corona shortcut for the bounds of an object makes sense, I would say that it’s not a mandatory thing. Focus and checking the bounds (did I lift my finger while still on the object) are very useful tools but not all touch functions need or want them.

It would work with multiple fingers, but you’d need to setup a table and check touch IDs versus the table. (rather than just a boolean check) Not simple but doable.

smith_it2000: You’re right; ideally Corona would have some branch code to handle some of these things. It’s an interesting challenge as in some ways Corona SDK is about doing things easier, but it’s also about doing things simply. A true slideOffEnded check really requires Corona itself (as part of enterFrame) to check every phase == moved and then pass a forced “ended” event if outside of contentBounds. Which is basically solveable user side, and leaving it out keeps the internal code simpler, I imagine. 

Thanks richard9. Exactly what I needed to know.

I’m a bit surprised that this still hasn’t made it into Ansca’s documentation considering it is critical info for any developer using touch, and that it contrarily doesn’t work this way in the simulator.

Some of this is just the nature of screens. I mean, you’re never detecting a touch in motion. There’s no velocity, per se. The moved phase is literally just detecting new hits (as in a touch that doesn’t match the previous position). The real problem is handling what to do when you let your finger go outside of the object, because this is the whole basis of the event model. 

To ensure your actions only count within the button, you should use the classic bounds method, which works roughly like this:

local function isWithinBounds(input, object) return (object.contentBounds.xMin \<= input.x and object.contentBounds.xMax \>= input.x and object.contentBounds.yMin \<= input.y and object.contentBounds.yMax \>= input.y) end

On the simulator, the problem is that the canvas is a desktop canvas. In theory, I guess the SDK Simulator should be globally looking at all touch events and passing “ended” events whenever one goes out of the window contentBounds, but that’s a whole can of worms of which I have no idea how plausible it is to do.

PS: Ansca doesn’t exist anymore. They’ve been Corona Labs for awhile :slight_smile:

not by the looks of things - it’s a shame.

Does not look like it registers when sliding off the screen, yes it is a shame and a been annoying for months…would be great if corona sdk added this feature. You can place it in a certain position so by the time finger slides off it should hit an ended phase because of the location of button, but there are weird circumstances of (especially in my app) button mashing and sliding off finger and spamming stuff that it won’t register leaving the device properly on a dpad that is very close to edge of screen.

There is no concept of sliding “off” the screen on a capacitive touchscreen. “Ended” is passed when the screen detects a break in the active touch event. Lifting your finger from the middle of the screen has no technical difference from sliding off the edge, AFAIK.

Typically, this means that any time you slide “off” the sides of the screen it will immediately register an ended event. It’s possible that some things can confuse your code (or possibly Corona) do trigger another start event instead of an end event, but in theory it should always be captured.

The real tricky part of this is making a touch listener that can properly handle the order of events by using focus. Without careful focus checking it’s all too easy to build a function that tries calling began/moved/ended out of order.

Yes you can “Slide off the screen”

If you create a display object, register a listener - the listener will be called on touch (began) and on the touch moving (moved) and when the person takes finger off (ended). However, if I touch, then slide it off the object, I will never get the ended.

This is because when the user take finger off the screen, it is no longer on that object, but on some other object, or off the screen.

You can say that all touch events should go to that object, by making that object have focus when “began” touch event is fired;;

        buttonPressed.hasFocus = true

        display.getCurrentStage():setFocus( buttonPressed )

Now the ended event will go to the object, even if finger is nowhere near object (providing finger started on object).

Then on the ended event, must give up focus, so no further events go to object;

            display.getCurrentStage():setFocus(nil)

            buttonPressed.hasFocus = false

This would work if there was one button or one finger, but I do not think it would work with multiple buttons, because user could be pressing two buttons at same time.

Really Corona should have a switch in the code when you setup the listener

obj:addListener(“touch”, myFunc, {slideOffEnded=true} )

Then if you slide off the object, it sends an “ended” event to the listener.

I think this is what people expect to happen, and what SHOULD happen.

That’s leaving the bounds of the object, which is definitely a problem for many buttons, but has nothing in particular to do with the edge of the screen. 

While I would agree that having a Corona shortcut for the bounds of an object makes sense, I would say that it’s not a mandatory thing. Focus and checking the bounds (did I lift my finger while still on the object) are very useful tools but not all touch functions need or want them.

It would work with multiple fingers, but you’d need to setup a table and check touch IDs versus the table. (rather than just a boolean check) Not simple but doable.

smith_it2000: You’re right; ideally Corona would have some branch code to handle some of these things. It’s an interesting challenge as in some ways Corona SDK is about doing things easier, but it’s also about doing things simply. A true slideOffEnded check really requires Corona itself (as part of enterFrame) to check every phase == moved and then pass a forced “ended” event if outside of contentBounds. Which is basically solveable user side, and leaving it out keeps the internal code simpler, I imagine. 

Thanks richard9. Exactly what I needed to know.

I’m a bit surprised that this still hasn’t made it into Ansca’s documentation considering it is critical info for any developer using touch, and that it contrarily doesn’t work this way in the simulator.

Some of this is just the nature of screens. I mean, you’re never detecting a touch in motion. There’s no velocity, per se. The moved phase is literally just detecting new hits (as in a touch that doesn’t match the previous position). The real problem is handling what to do when you let your finger go outside of the object, because this is the whole basis of the event model. 

To ensure your actions only count within the button, you should use the classic bounds method, which works roughly like this:

local function isWithinBounds(input, object) return (object.contentBounds.xMin \<= input.x and object.contentBounds.xMax \>= input.x and object.contentBounds.yMin \<= input.y and object.contentBounds.yMax \>= input.y) end

On the simulator, the problem is that the canvas is a desktop canvas. In theory, I guess the SDK Simulator should be globally looking at all touch events and passing “ended” events whenever one goes out of the window contentBounds, but that’s a whole can of worms of which I have no idea how plausible it is to do.

PS: Ansca doesn’t exist anymore. They’ve been Corona Labs for awhile :slight_smile: