For clarity's sake, on iOS all of the App Inventor screens are subclasses of UIViewController. The app itself at the top level is a UINavigationController with the root view being Screen1. Opening a screen is equivalent to pushing a new instance of the screen onto the UINavigationController's viewController stack. Closing a screen is equivalent to popping the calling screen off of that stack. This is slightly different to Android where the activity stack is managed more by the Android framework and activities can be somewhat independently closed/opened. In theory we could support something like the tribblehunter method where a screen is both open and closed within the same event handler, but I think it might be better to keep to the underlying semantics of how the stack-based view system is supposed to work since both platforms provide some form of "back" button.
Hmm, difficult to understand.
I have had strange experiences after renaming the components in the designer. As I said, I'll report on it later.
But I found a way to make it work (also the way it currently is).
I would like to return to this fundamental topic.
Here is a very simple app that only switches 3 screens.
switch3Screens_1.aia (5.6 KB)
The compiled app (IPA) does not work on any of my 4 iOS test devices (3 iPhones (iPhone 6s, 13, 15 Pro Max, iPad Pro 12.9).
Please test this app (as IPA) on your iOS devices. As soon as the screens have been switched 5-10 times, error messages appear, the app crashes or screens can no longer be switched.
Before we continue to discuss individual problems with components and other details, the basic problem of switching screens should first be resolved.
If this cannot be solved (satisfactorily), the only option left is to do it via “virtual screens”. This would mean a complete overhaul of existing apps and would also raise the question of whether there would be a limit to the number of blocks allowed on a single screen.
PS:
-
I found a way though to get this app to run (so that there are no errors and crashes), but unfortunately that doesn't solve the problem(s) of switching screens in other more complex apps. Finding the solution for this simple test app was already a long process of trial and error.
-
Another question is whether there is a way to switch between 2 non-Screen1 screens WITHOUT this switch first going through Screen1.
To clarify, you mean going from something like Screen2 to Screen3 without leaving Screen2 on the activity stack, correct? Otherwise, you can certainly open Screen3 from Screen2. I usually test with our BostonTourGuide app which has 3 screens but the first opens the second opens the third.
I think the stability issues may be related to garbage collection. Eventually, after opening enough screens the garbage collector gets triggered and erroneously cleans up older screens that are technically still alive. I will look further to see if that hypothesis holds up.
Yes, but it goes over Screen1 first. In other words, Screen1 pops up briefly before switching to Screen3.
I have detected and reported the same switch-navigation garbage screen. See Problems with Screen Navigation testing IPAs
After a few screens navigation the app stops.
As I said, there is a solution for my simple test app. But this solution doesn't seem to solve all switching problems with more complex apps.
As my test app shows, every switch between Screen2 and 3 is also counted on Screen1. Of course, this doesn't happen on Android.
In my tests with real AIA when I'm in Screen2 without doing nothing after 20 or 40 seconds the app close itself. It seems your suspect over the iOS garbage collector can be right because my app close itself without any hand operation on Screen2 visible.
Yes, I noticed that in various of my apps too. That's why I first tried a simple app that doesn't have this problem. To find the cause, you must gradually remove all components until the problem no longer occurs. This is very long and tedious, but without knowing the cause, I don't see any other way.
And that's why I said that the first thing that needs to be clarified is how exactly switching works under AppInventor for iOS.
A very simple test with real AIAs. We open Screen1 with Timer and Location sensors. Then we open a Screen2 previously disabling the Timer and the GPS of Screen1. No operation is performed on Screen2. After a few seconds the App closes by itself. It is as if an iOS process deleted or stoped the App since without performing any operation, it closes by itself. The iOS operative system close the app in this case when we have the Screen1 on the second position or undergrund.
May be iOS has a special process to close the Apps in undergrund position that we don't know the selection algorithm.
Post this aia.
I'm sorry @Anke. The real AIA has sensible data about web access and others.
But with examples happens the same (we only need wait more seconds to stop the app)
What about posting this simple example aia...
Thanks. I will run some tests on this and see what I can learn.
Unfortunately, I couldn't learn anything except what I already knew, namely that you shouldn't open any screen (especially not Screen1) twice. I have modified the app (blocks) so that switching the screens should now work properly.
But as I said, switching between Screen2 and 3 always goes through Screen1 first.
testNavigation_iOS2a.aia (17.1 KB)
So my question again:
How does switching screens work correctly in AppInventor for iOS? In other words, does navigation basically have to be done via Screen1?
@ewpatton
Again, it depends on what you are trying to accomplish, and I think the answer is that what you want to do you just cannot do with how screen switching is implemented in iOS. In iOS we have a UINavigationController at the root of the view hierarchy and its first item in its stack is Screen1. If you open Screen2, it is pushed onto the nav stack. If you want to do what your test app does which is both close and open a screen simultaneously, this results in a pop operation on the UINavigationController which goes back to Screen1 and then a push to open Screen3. On Android, the framework doesn't seem to bother drawing Screen1 when an activity is finished but an intent is pending to open a new screen but that's not the case with the iOS code.
In order for this to work, I will have to add some code to the navigation logic to detect when this sequence of events is triggered and then swap the behavior out for something more like what Android does (although what iOS does is technically correct based on the code you've written--it closes the screen then opens the new one).
I think I have coded something that mimics this behavior. I will need to figure out how best to deploy a parallel build infrastructure for you to test it.