How do I clean RAM my app used, in iOS? - ios

I working on a game that has some hitches (freezes for a bit) under certain loading situations.
If I start the phone or remove/reinstall the game, the hitches are there. If I kill the app and re-open, the hitches are gone which makes me believe they happen when the game assets are being loaded into the RAM. When I kill the app, memory becomes inactive but it's still there to be loaded quickly if I re-open the game.
I need a way to clean the RAM so I can reproduce hitches quickly, that is, quicker than restarting the phone or reinstalling the app.
I tried to do a trick involving holding the wake button then home button but that obviously only kill all apps and do not erase the memory.
I also tried to use this project that uses malloc and memset to clean the memory until it crashes (allocate and erase more memory until it crashes), but it doesn't clean the memory my closed game used. I have the impression that iOS deallocates inactive memory from apps that were used before my game, so the memory allocation app never gets the chance to use my game's inactive memory, because it's killed first.
Therefore, I'd like to understand how iOS chooses which inactive memory to use and how can I make my app inactive memory to be cleaned from RAM.
Please notice I'm not trying to find a way to free memory while playing, not trying to make the game use less memory, I'm trying to clear the memory the game used after the game is closed so the hitches happen 100% of the times I open the game.
I'm using an iPhone 6, iOS 10.3.2.

It's impossible to describe this in a couple of words. First of all I'd recommend you to review this article.
If you want to release unnecessary objects manually, take a look at description of didReceiveMemoryWarning() method of UIViewController

Related

How to free up memory when going from one scene to another in unity for ios devices?

This is a game I am working on and it has a lot of textures(many). I am attaching some memory screenshots from Xcode.The scenario is like this first time opening app Home screen(scene 1-298Mb memory usage)>>Select first game (scene 2 -628Mb memory usage). In the same scene I am going to painting section suddenly the memory usage spikes to (scene 2 -1.01Gb memory usage). This is because lot of textures are used.After playing this I come back to Home scene still no change in memory. Now I play another game(Scene 3 -1.52Gb memory usage). It crashes when it reaches 1.81Gb.
No issues for android version as ram is higher for devices I guess.I am using addressables for downloading different scenes.Why the memory is not freeing up when we go from one scene to another.Tried unloading assets but still memory usage is the same.Any method to free up memory usage when we go from one scene to another?

How much does iOS app size impact app launch latency?

I am guessing an iOS App's size has direct impact on its launch latency, since iOS needs to load the App into memory before launching it. If so, I wonder how much is the impact?
Let's say if I reduce my iOS app from 100M to 80M, how much launch latency improvement I can expect?
Does anyone has experience on this?
Consider that programming a faster App Launch experience is not bound to App Size at all. You could assume even the opposite because in some (i would even say in most) cases coding a faster launch process to start up can (and will) involve more code to make it a very short interaction interrupt experience and so your app size would increase without even delivering more valuable content.
In other words just because you deliver more dynamic or static content does not increase launch time unless you load and instanciate everything you need later on in your app life cycle in UIApplicationDelegate instead of allocating objects at the time of its use.
The same ideals apply to tear down processing (dealloc or saving app state user defaults) if needed. But this experience is usually not seen as a visible interruption of interaction with the device and so often forgotten to be part of the apps life cycle.
You can avoid this prolonged start up experience for users with clever use of LaunchScreen storyboards or similar techniques like partly buffered content for the first seconds. Some apps even take screenshots to be presented at the next start up to make the user feel the last app state is loaded already while building up the real interface.
A common mistake, which you may have seen also very often, is to make use of introduction videos or animations to bridge the time in waiting for the window/view to appear after app launch. So just making use of Launch Screens is never the best solution but a wise decision if the content that needs to be loaded first hand will take a noticeably longer time and can not be avoided.
LaunchScreens are just entertaining/informing about processing and keeping the user engaged while it can be beneficial what you and your app want to represent.
So abbreviated launch time is clearly a design pattern issue and is not bound to app size. Ok, apart from downloading band width if that is needed.

Memory management in IOS7 and "Terminated due to Memory Pressure"

The reason why I am doing everything below: I have a GPS tracking application which should run in background all day long. Memory usage doesn't go down when I put application in background. It seems like views are not removed from memory when app goes into the background... That is why the app is closed in few hours of normal usage of iPhone ... From IOS6 experience - memory usage should drop to cca 8KB.
Then I tried to debug/isolate the problem ...
I created simple ViewController with UIMapKitView just to make sure that view is consuming a lot of RAM (e.g.: 12-17MB). When app goes to background app uses same amount of RAM until "Terminated due to Memory Pressure" message. Still - sometimes memory lowers to 4KB and everything is OK. Problem is because it works kind of "random" and the app is plain simple.
Can I manually release RAM which is consumed by views? E.g.: set self.view = nil? Should I do it?
I also noticed that "- (void)didReceiveMemoryWarning" is not always called before app is killed. I would expect that when OS needs more memory it would first release views, than ask me to clear anything I can via this method ... Isn't this a little bit strange?
Apple redesigned the way a VC's (view controller's) views were loaded quite a while back - I want to say starting with iOS 5? iOS 6? It used to be that the system would unload your VC's views when a VC was not front-most and it needed the memory.
With the changes, a VC's views are NEVER unloaded while the VC is active. ViewDidLoad only gets called once in the lifetime of the VC, and viewDidUnload is no longer called at all.
I don't know what would happen if you set your (non-frontmost) VCs' content views to view manually. Would the system load your view hierarchy when that view became frontmost again? You'd have to try it, but it is risky since I don't think the OS is designed that way any more.
If your VCs views are holding significant amounts of memory, you might want to re-architect your app so only the front-most app is kept around, and the other VCs are released (after saving their state.)
Apple does not make this sort of app easy to write. To the contrary, they actively discourage it. The GPS is a huge power drain, so keeping it active constantly is going to drain the user's battery fast.
I remember hearing about a new location chip in the 5s that will record a "crumb trail" of location data for your app even when it's not running, at your request. You might look into that, although it would only work on the newest devices with the A7 chip and location chip.
In my case the problem was specific IOS7 version. Every app was crashing with this version of OS. When we updated OS version, everything started working back as it should.

Should my iOS game free memory at all when it enters background mode?

There are a couple of games that I want to mention, to show how they handle entering the background mode:
Clash of Clans. It seems it doesn't free any memory at all when it enters background mode, in fact I can open lightweight applications like Notes and get back to the game to continue playing without any noticeable delay, which seems pretty cool to me from the user's perspective.
Game of War. The game immediately falls back to the loading screen and the initialization process starts all over again when it runs inmediately after it enters background mode, it's just like restarting the game, which is very annoying sometimes.
So, in the case of my game, it has an average memory footprint of 25 mb (and it's going to be less with some optimisations), I know the "Free up as much memory as possible" stuff recommended in order to be a good neighbour on the iOS platform, but considering that freeing memory when the game enters background mode could cause my game to have an "annoying" pause when it enters foreground mode...
...should I save the progress and pause the game when entering background mode without freeing up any memory at all, or should I free as much memory as possible and load those resources again when entering foreground mode, with the respective loading pause?
As you yourself point out (by giving two games as examples that use opposite strategies), there is no unique answer to your question.
I think a proper answer can be worked out in a given case by clearly defining the use cases you want your app to support.
E.g., one use case, as you mention, could be "the user can switch to a lightweight app and go back to the game without unnecessary waits". (UC1) Then, you should also have a list of lightweight apps and reference devices where you want to make sure that the use case is actually satisfied.
On the other hand, you may want to support a slightly different use case: "the user will always come back to the point where she left the game, unless the app was terminated, in which case the app should present the main menu". (UC2)
In the first case, not freeing up could be the best approach; in the second case, you may want to minimise the chance that the app is terminated while the user does another task (lightweight or not), so that she can go back to the place where she left, even though she has to wait for all resources to load.
There might even be cases where an intermediate approach is best, where you free up only a part of memory, so to strike a balance.
And, of course, it would make no sense going for the first use case (UC1) if your app memory footprint is so large that it will be terminated almost immediately after switching to another app on most of the devices. In such case, it might make more sense freeing up memory, so you at least can spare the app load time (vs. resources load time) when you go back to it.
So, in the end, it depends...
I would save the progress and pause the game when entering the background without freeing up memory, as many people if they need the memory just delete it from the history thing, or the "carousel of cards". Multi tasking is emphasized in ios 7 so you don't want them to restart the game.
for example, somebody wants to text someone in the middle of playing your game. They exit the game and text someone. But then they have to load the game again. Nobody likes this.
While your game doesn't take up much memory, most users don't bother to close out of applications. I would recommend freeing up as much memory as possible without sending them back to the start menu, much like #sergio recommended with his 'intermediate' option.
I strongly suggest to free up memory. I have an iPhone 4, and some apps are now taking too much persistent memory, so that switching between them becomes a nightmare. E.g. recently, I could not switch between Safari and Twitter anymore, without them reloading all their state (taking more than 20 seconds in both directions).
Bottom line: Try to keep important state, but with as little memory as possible (i.e. not retaining images / textures), otherwise the app will get closed on older devices and you will effectively lose more state.
Save the progress and free the memory with the loading pause, especially if your game is for older devices. I have an iPhone 4, and when a game is running in the background without freeing memory, my foreground apps crash every 15 minutes. But if you have things such as "Vehicle/weapon upgrade is done in x minutes", you will need to save game progress and free the memory, so only the upgrade timer is running. If you do enough optimisations you may decrease the memory footprint, so I would recommend you to keep the optimisations in mind while coding and then the background performance will be your least problem.

Array object gets released in iPad app due to memory warnings in iPad app

I am developing an iPad app. In my iPad if i run that app only then nothing happens, if i start some other apps nearly 4 to 5 then my app shows application received memory warning level 1 & application received memory warning level 2 and also in my app user has the ability to draw their work.i have stored that draw views (Max upto 50 views) in a NSMutableArray whenever the memory warning happened all the user drawings gets erased view gets loaded as in initial stage. I have also used core plot frame work in that app.I have also checked with Analyzer and Instruments tool there is leak in my app.
What may the problem in that app ?
2 . How to avoid drawing views gets erased ?
How to stop the memory warnings?
You can't prevent memory warnings -- they're part of the way the system works. When it needs more memory, it sends warnings to the various running apps to get them to release memory that they don't need.
To prevent your drawings from being erased, you need to write them into one or more files so that you can restore them at a later point. You can then safely release the drawings when you get a warning, and read them back as you need them.

Resources