two seconds might be “safer” if you include the fade, but you could in theory recover some of that if you mimicked their logic: grab the time at top of main, grab the time at bottom of main, subtract that elapsed from 2s, then delay for only that difference. (as most non-trivial apps will consume at least some time in main, preloading and etcetera, to take advantage of some of that splash time already)
Rob, I hear what you are saying.
I don’t add listeners until the very end of main.lua and yet this issue still occurs. If there is some weirdness with timers hat I can exploit in a kludgey, indirect way to check for the presence of the splash screen I can experiment.
I think this is a worthy issue for utility or productivity apps that need to launch as soon as possible without superfluous time taken with intro splash and launch screen material. I wouldn’t want to inadvertently add to the already noticeable amount of time taken by the launch screen.
I would think the easiest fix, when and if time allows, is for the corona-provided splash screen to simply include a layer that traps touch events while the splash screen is present.
Corona is now a small company and they will not “fix” this issue. There are far more time critical things they have to work on - like Android 64 bit
You need to use the work around we’ve given you and just pause your UI/UX for at least 2 seconds.
Note: Apart from certain system level events no runtime listeners should ever be instantiated in main anyway.
Quick and dirty:
-
Have your event listeners activate after a timer delay
-
Make a gameStarted = false variable and then after a timer delay -----> gameStarted = true. You can use this as a condition in your event listener functions.
Are you familiar with event propagation? You can set an event listener function to
return true
and it will stop the touch from reaching elements under the target that triggered the listener. So a rectangle covering the whole screen with a listener function set to “return true” will put a stop to those pesky touches.
You can use a rectangle with zero alpha as long as
rectangle.isHitTestable = true
Those solutions should get you going. You can customize them later as your app takes shape
sporkfin, I appreciate your intent!
The problem is not that I don’t know how to trap events so my UI listeners don’t receive them. That I can do; but I would have to guesstimate the amount of time I should wait to enable the listeners to receive taps.
But I do not want to guesstimate.
I want to know the the exact time at which the launch image has finally disappeared.
It would be great if there was an event or function call that triggers when the Corona Labs launch image finally goes away.
Perhaps the Corona folks can pipe in here with some insider advice? Seems a worthy feature request if there isn’t away to test for the existence of the Corona Labs launch image.
I don’t know how to get exactly what you need. I have always used launch scenes.
When an app first launches, it breezes through main.lua and then jumps to launchScreen.lua. This launch scene, as I call it, is just an animated logo, but it could just as well be a still image or a solid colour. Once my animation has run its course, the app proceeds to the next scene, usually menu.lua.
Using this method, you wouldn’t need to know exactly when the image has faded away. The user couldn’t tap anything before the launch scene is gone anyway.
I don’t think launch screens are available in the free version of Corona. I don’t mind having the free versions’ Corona Labs launch screen and promoting the framework. But I dislike not being able to trap when the free version launch screen is done. There are no lua files in the project for launch screens with the free version.
I am not talking about anything paid. Just create the file yourself.
Are you familiar with Corona’s scene manager, Composer (https://docs.coronalabs.com/api/library/composer/index.html)?
At the end of your main.lua file, you go to another scene. This is what my launchScreen.lua is. Once my animation has run its course, the app goes to another scene, which is typically the menu for my games, i.e. menu.lua.
I’ve run afoul of this too!
For what it’s worth, it looks like the splash screen logic happens here. (There are some other bits that turn up in search but that looks most promising.) If so, that doesn’t seem too difficult for an open source fix, especially since it’s all in Lua.
There might also be something that calls for a one-frame delay to make the timer sane again, but maybe it’s not a big deal.
I hadn’t experienced this personally due to my scene setup, so I had to whip up a simple sample project to try this out. This is odd and really feels like an oversight.
The easiest fix to this would probably be to add a touch listener to the splash image (or create an invisible rect to cover the screen and add the touch listener there) which will capture all touches.
I though that the splash screen finished before main.lua is executed. I’ll get Engineering to look at it.
But if you guys are poking in the source code, this might be a great pull request!
Rob
it runs “over the top” of main, in it’s own view, asynchronously, so if main is “fast enough” to “do something interesting” before splash times out on first call to render, then you could see weirdness. fe this ominous note is what got me specifically trying to figure out the timing - once the first frame is rendered and app is effectively “live”, splash is then requested to hide, but it may still be deferred by the remainder up to 1.5s until it actually occurs. or something roughly like that, still puzzling it out
Well… It supposed to be that body of main.lua is executed while splash screen is shown, while frame is not ticking. So, first frame supposedly has to be entered after the splach screen is gone. So, theoretically:
print("this is done during splash screen") timer.performWithDelay(1, function() print("splash screen should be gone by now") end) print("this is also done during splash screen")
I added @vlads’ code to my demo project and it doesn’t work.
My demo project consists of two files:
main.lua
display.setStatusBar( display.HiddenStatusBar ) local composer = require( "composer" ) composer.gotoScene( "menu" )
menu.lua
local composer = require( "composer" ) local scene = composer.newScene() function scene:create( event ) local sceneGroup = self.view local function change( event ) event.target:setFillColor( 1, 0, 0 ) event.target.text.text = "Tapped" end local rect = display.newRect( 160, 240, 320, 480 ) rect.text = display.newText( "Not tapped", 160, 240, system.defaultFont, 40 ) rect.text:setFillColor(0) timer.performWithDelay(1, function() rect:addEventListener( "touch", change ) end) sceneGroup:insert( rect ) sceneGroup:insert( rect.text ) end scene:addEventListener( "create", scene ) return scene
As most probably see straight away, when the app loads, it just jumps to menu.lua and create a white rect and a black text object reading “Not tapped”. Once the white rect is tapped, i.e. the screen is touched, the rect turns red and the text object reads “Tapped”.
The touch event listener is added in menu.lua inside that delay function, but still, if you tap the screen when the splash screen is up, the tap goes through.
How about just buy the splash screen plugin to support development (and remove the obnoxious splash screen)?
It’s not really just about buying or not buying. While I hadn’t encountered this issue before explicitly trying to seek it out yesterday, after seeing how the app can make it to another scene and how the user can interact with touch listeners etc. while the splash screen is still covering the screen, I am guessing surely isn’t intended and could therefore be classified as a bug. If we look at it from this perspective, the argument turns into whether or not to pay 99$/year to bypass a bug. Still worth it, but just a bit odd.
I don’t claim to know what the most elegant fix would be or how it should be done, but something along the lines of what was pointed out before, i.e. having the main.lua run only after the splash screen is gone would be optimal.
For myself, I choose to support development by spending money on actual features. I won’t give them a dime for this junk.
Spending money to remove “annoyances” is NOT something I choose to do. Because 1) it encourages that sort of behavior, 2) it does nothing for me in return (except remove bugs). I am philosophically opposed, and I’m “voting with my pocketbook”. Besides, I can write my own splash screen in about 30 seconds - give me something useful, functional and non-trivial if you want me to spend on it, not this.
We all know the splash screen was added as an annoyance incentive to spend, but that’s not how it’s marketed - it’s marketed as if it’s an actual feature, as something that’d help someone implement a reliable/rigorous splash screen without any effort. But it fails at that, so that leaves it as only an annoyance. Because even if you DO pay for it, the only good use for it is as you say - to disable the “annoyance”, then implement your own splash screen anyway. So it’s a lose-lose dud.
my $0.02
Thanks to everyone who is taking this seriously. Startup splash screens are an annoyance to users and they often attempt tap to dismiss them whether it works or not… kind of like pressing the button to cross the street, even if the button is just a placebo (or just enables an audio signal)-- we all still feel compelled to press the button.
My app has logic in it that measures the distance between the users taps and averages them… Perhaps because of some weirdness with the timer and the splash screen (mentioned in some previous posts in this thread), I was getting an infinite number (inf) as a value if the user was tapping before the splash screen dismissed – this caused the app to freeze (I’ve since added checks for an “inf” value, but still!!)…
Being able to have a routine that waits until a check validates that the splash screen has gone and that its safe to call a function that then adds all the listeners at this time would be great.
@dave I couldn’t agree more. Subscription is the way forward not cheap money grabs!
@gary, why don’t you disable UX until your main form has finished loading?
You could simply delay your module loading by say 2 seconds just to be sure?
I load my own splash and pause whilst doing various network I/O, image caching, etc. When this has completed I allow execution to continue and finally load my first scene.