Rectangle 27 207

I come from iOS experience and I was frustrated to discover an issue with something so basic as loading and showing an image. After all, everyone that is having this issue is trying to display reasonably sized images. Anyway, here are the two changes that fixed my problem (and made my app very responsive).

BitmapFactory.decodeXYZ()
BitmapFactory.Options
inPurgeable
inInputShareable
true

2) NEVER use Bitmap.createBitmap(width, height, Config.ARGB_8888). I mean NEVER! I've never had that thing not raise memory error after few passes. No amount of recycle(), System.gc(), whatever helped. It always raised exception. The one other way that actually works is to have a dummy image in your drawables (or another Bitmap that you decoded using step 1 above), rescale that to whatever you want, then manipulate the resulting Bitmap (such as passing it on to a Canvas for more fun). So, what you should use instead is: Bitmap.createScaledBitmap(srcBitmap, width, height, false). If for whatever reason you MUST use the brute force create method, then at least pass Config.ARGB_4444.

This is almost guaranteed to save you hours if not days. All that talk about scaling the image, etc. does not really work (unless you consider getting wrong size or degraded image a solution).

BitmapFactory.Options options = new BitmapFactory.Options(); options.inPurgeable = true;
Bitmap.createScaledBitmap(srcBitmap, width, height, false);

In Bitmap.createScaledBitmap() call you should probably use true as the flag parameter. Otherwise the quality of the image will not be smooth when scaling up. Check this thread stackoverflow.com/questions/2895065/

That really is fabulous advice. Wish I could give you an extra +1 for taking Google to task for this amazingly rinky dink bug. I mean... if it's not a bug then the documentation really needs to have some seriously flashing neon signs saying "THIS IS HOW YOU PROCESS PHOTOS", cause I've been struggling with this for 2 years and just now found this post. Great find.

Scaling your images down definitely helps, but this is an important step and what ultimately solved this issue for me. The problem with just scaling your images is if you have a lot of them, or if the source images are very large then you can still run into the same problem. +1 to you Ephraim.

BitmapFactory.Options.inPurgeable
BitmapFactory.Options.inInputShareable

android - Strange out of memory issue while loading an image to a Bitm...

android image bitmap out-of-memory android-bitmap
Rectangle 27 1

Where does "fruitImage" come from in AppDelegate.m? I don't see it declared.

__block NSURLSessionDownloadTask *imgTask

is a bit weird because you're marking imgTask as a reference that can change in the block, but it's also the return value. That might be part of your problem, but in the very least it's unclear. I might argue that all the variables you marked __block aren't required to be as such.

typically a memory leak in these situations is caused by the variable capture aspect of the block, but I'm not seeing an obvious offender. The "Weak Self" pattern might help you here.

Using "leaks" might help you see what objects are leaking, which can help isolate what to focus on, but also try to take a look at your block's life cycles. If a block is being held by an object it can create cycles by implicitly retaining other objects.

ios - Memory leak when making NSURLSession calls and loading images to...

ios objective-c multithreading macos memory-leaks
Rectangle 27 1

Where does "fruitImage" come from in AppDelegate.m? I don't see it declared.

__block NSURLSessionDownloadTask *imgTask

is a bit weird because you're marking imgTask as a reference that can change in the block, but it's also the return value. That might be part of your problem, but in the very least it's unclear. I might argue that all the variables you marked __block aren't required to be as such.

typically a memory leak in these situations is caused by the variable capture aspect of the block, but I'm not seeing an obvious offender. The "Weak Self" pattern might help you here.

Using "leaks" might help you see what objects are leaking, which can help isolate what to focus on, but also try to take a look at your block's life cycles. If a block is being held by an object it can create cycles by implicitly retaining other objects.

ios - Memory leak when making NSURLSession calls and loading images to...

ios objective-c multithreading osx memory-leaks
Rectangle 27 1

Widget only can use 10MB(not documented, just guessed value from my experiments) memory due to prevent unload apps in background.

Memory error when loading an image from a url in iOS today widget - St...

ios image uiimageview ios8-today-widget today-extension
Rectangle 27 1

One issue about loading everything at the very beginning: depending on when you do it, you can take too long to launch, and the watchdog timer will kill your app for being unresponsive. (It didn't sound like this is what's happening to you, but it's a theoretical possibility. Easy to spot the 0x8badf00d in crash logs.)

That's a good point. Do you know how long you get to start processing events before it decides you're not responsive? Does it vary by OS or device type? And indeed it seems like there could be interaction here with the memory manager: I load up some resources and it sends me (and other running apps) memory warnings, but I'm too busy loading more resources to respond to them.

I believe its explicitly not documented so that it can be tuned as needed. The iOS Performance and Power Optimization with Instruments talk at this years WWDC did give some numbers, which depend on what the system is doing (Launch is different from Resume, so if you empty your cache when you go to the background and then reload, you might get burned). The Launch timer is easy to avoid dont load until after youve launched.

iOS, iPhone, iPad: is slow loading a good strategy to avoid memory cra...

ios ipad memory crash timing
Rectangle 27 0

That is possible for some image formats, but not really for jpeg or png files. You'd also have to write it yourself since there is no API for this in iOS, however, if your only concern is the short delay, you can wrap the loading into an async GCD queue and use the thumbnail while the higher res image is loading.

Yeah, I'd done the async queue. I know to decompress a jpeg it usually needs the whole thing, but seems like I've seen a method of breaking it up somehow.

I want to load original image as it is with scaling given width and height. without taking original image in memory.

ios6 - How can I load a section of an image in iOS, without loading th...

ios ios6 alassetslibrary alasset
Rectangle 27 0

Implement the didReceivedMemoryWarning method to clear every memory you don't need (i.e. datasource of your tableview and views that are not part of any hierarchy and therefore not shown). Those methods (one on each view controller) will be called in response to memory warning Level 1 and 2.

Always implement that method in every viewController you have !

Also "Most of the memory leaks ?" is not sufficient : clear them ALL !

uiwebview - Application getting memory warning level 2 when loading we...

iphone uiwebview didreceivememorywarning
Rectangle 27 0

SDWebImage registers for UIApplicationDidReceiveMemoryWarningNotification (which is important because in iOS7, NSCache does not respond to memory pressure like it used to). You can confirm this by placing a breakpoint in clearMemory in SDImageCache, and run the app, simulating/reproducing memory warning and confirm, and confirm that this is getting called. But I think you'll find it is. I can't speak to parse.com's handling of the fact that NSCache is no longer automatically purged like it used to be.

You should do some heapshots/generations in Instruments as illustrated in WWDC 2012 video iOS App Performance: Memory. So run the the app, get it to a point of quiescence, simulate memory warning, mark heapshot/generation, use the app a bit, simulate memory warning again, and mark heapshot/generation again. Then look at the the objects allocated and still live between the two generations and you'll be on your way towards identifying what's not getting released on you. You can probably identify whether there's something that parse.com isn't cleaning up, or whether it's in your code or in SDWebImage.

This is going to sound like curious counsel given that you're trying to reduce memory impact, but cellplaceholder is probably the one situation where you really do want to use imageNamed rather than imageWithContentsOfFile. Assuming this placeholder will be needed a lot, it will (a) be faster; and (b) might actually negligibly reduce your high water mark if the placeholder is temporarily used a lot (rather than having a bunch of short-live instances of the same placeholder).

It's extremely unlikely, but if you're going to be updating the cell asynchronously yourself, you really should be re-retrieving the collection view cell to make sure this cell hasn't scrolled off the screen (call [collectionView cellForItemAtIndexPath:indexPath], not to be confused with the similarly named UICollectionViewDataSource method) and make sure that's not nil).

Frankly I'm not sure why you're dispatching this back to the main queue, anyway. SDWebImage will retrieve the images asynchronously already, so you don't generally have to do any asynchronous processing yourself, and if you really needed some asynchronous processing, you'd send that to some background queue (not back to the main queue).

[[NSOperationQueue mainQueue] addOperationWithBlock:^{
    // ...
}];

Thanks very much for your answer. I will take your advice on the placeholder image for sure. I will run the heap generation and add a profile to this so there's more information to go on. Is there anything you think I should do with autorelease pools and the UIImages loaded by SDWebImage?

I ran the profiler and for the time range when I open the scrollview, 7.18 MB or 59.2% of bytes used are used by "CAKeyframeanimation CA_preparerendervalue. 30% of bytes used are for SDImageCache DiskImageForKey. This time running profiling I got to a higher memory cap than I ever did before (approximately 8 megs live bytes) but it never received a memory warning. I will test further but the only change was resizing images before loading from this thread (stackoverflow.com/questions/12928103/)

@BrianAllenToronto No, I don't think there's anything that you should be doing with autorelease pool (that is useful when tweaking high-water mark, not for mitigating total memory used when done). But resizing images to the appropriate size for your UI will have huge benefit. That's definitely a good line to pursue. If it's useful, these are the image sizing routines I use.

very nice class you wrote there! I used something similar but a bit less organized than your class. You were right, resizing made a huge difference!

multithreading - iOS Memory Crashes UIScrollview with asynchronous ima...

ios multithreading memory-management uiscrollview sdwebimage
Rectangle 27 0

Keep all the images in memory will not do, there is just not enough memory for this.

You will need to fill the array with the ALAssetRepresentation of the images and load the image only when you are ready to display it. This way you will only have the image in memory that you are really displaying.

iphone - Memory warning while loading above 100 images from specific a...

iphone uiimage alassetslibrary assets
Rectangle 27 0

The problem is with this line

NSString *CellIdentifier =[NSString stringWithFormat:@"%i-%i", indexPath.section,indexPath.row];

Each of the row is created and none of the cells are reused except when scrolling back to already displayed cells.

A better way would be to take advantage of reuse of cells by using a identifier to give a cell back when it goes out of view and then styling it according to the requirement. More like NSString *CellIdentifier =@"MyCellIdentifier";

Now check the section and row for the cell and style it accordingly.

iphone - UITableView cell reuse, low Memory Warning, App Crashing in d...

iphone objective-c xcode uitableview
Rectangle 27 0

I come from iOS experience and I was frustrated to discover such a pathetic issue with something so basic as loading and showing an image. After all, everyone that is having this issue is trying to display reasonably sized images. Anyway, here are the two changes that fixed my problem (and made my app very responsive).

BitmapFactory.decodeXYZ()
BitmapFactory.Options
inPurgeable
inInputShareable
true

2) NEVER use Bitmap.createBitmap(width, height, Config.ARGB_8888). I mean NEVER! I've never had that thing not raise memory error after few passes. No amount of recycle(), System.gc(), whatever helped. It always raised exception. The one other way that actually works is to have a dummy image in your drawables (or another Bitmap that you decoded using step 1 above), rescale that to whatever you want, then manipulate the resulting Bitmap (such as passing it on to a Canvas for more fun). So, what you should use instead is: Bitmap.createScaledBitmap(srcBitmap, width, height, false). If for whatever reason you MUST use the brute force create method, then at least pass Config.ARGB_4444.

This is almost guaranteed to save you hours if not days. All that talk about scaling the image, etc. does not really work (unless you consider getting wrong size or degraded image a solution).

BitmapFactory.Options options = new BitmapFactory.Options(); options.inPurgeable = true;
Bitmap.createScaledBitmap(srcBitmap, width, height, false);

In Bitmap.createScaledBitmap() call you should probably use true as the flag parameter. Otherwise the quality of the image will not be smooth when scaling up. Check this thread stackoverflow.com/questions/2895065/

That really is fabulous advice. Wish I could give you an extra +1 for taking Google to task for this amazingly rinky dink bug. I mean... if it's not a bug then the documentation really needs to have some seriously flashing neon signs saying "THIS IS HOW YOU PROCESS PHOTOS", cause I've been struggling with this for 2 years and just now found this post. Great find.

android - Strange out of memory issue while loading an image to a Bitm...

android image memory bitmap
Rectangle 27 0

- (UIMenuItemCell *) getCellContentView:(NSString *)cellIdentifier
UIMenuItemCell *cell = [[[UIMenuItemCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:cellIdentifier] autorelease];

The proper way to release the iVars is in the dealloc method. If it's not getting called, that means your UIMenuItemCells aren't being released. Possibly this is because of the way that your implementation works; you're creating a reusable cell for every row in your table view. I think that if you mark a cell for reuse it doesn't get released until the table view is released.

You could test this by seeing if all the memory is released when your table view is released (if this happens in your app). That would mean that you don't actually have a leak, just that your app uses a lot of memory (most likely unnecessarily). You could also test to see if the memory increases when you scroll rows that you've already created back onto the screen, because in that case I think you will be reusing your cells, so the memory shouldn't increase. You could also try initializing your table view cells with nil for the cell identifier so that they get released when they scroll off screen.

I tried, but still having the leak.

@john If you're autoreleasing the cell, there is no longer a leak. If you still see one, then it means you didn't post your actual, cut-and-paste code. If you don't post your actual code, we can't help you.

thanks for your reply, I have updated the code, in addition to that, I need to keep the progress bar progress even after some navigations. Thats why I afraid to release the entire cell. I tried the autorelease as you said, but no effect. Please check the code.

@John Are you releasing your synthesized iVars in your UIMenuItemCell dealloc method?

No, but I had added -(void)dealloc method in UIMenuItemCell.m and tried to release the iVars, but that method wasn't called. Is there any proper way to release the objects in a subclass?

Sign up for our newsletter and get our top new questions delivered to your inbox (see an example).

ios - Memory leak when loading image to custom cell in UITableView - S...

ios uitableview memory-leaks uiimageview custom-cell
Rectangle 27 0

it is still not entirely there but i found 2 ways that perform much much better and i get warning just rarely .If you have any advice to approve this more, i am glad to hear. (for example why shouldn't i load here the url asynchrony like before )

dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0ul);
 dispatch_async(queue, ^
    {
        NSDictionary *dic=[mainData objectAtIndex:index];
        NSString *userImageUrl=[dic objectForKey:@"url"];
        NSURL *userUrl=[NSURL URLWithString:userImageUrl];

        UIImage *image = [UIImage imageWithData:[NSData dataWithContentsOfURL:userUrl]];
        if (image)
        {
            UIGraphicsBeginImageContextWithOptions(image.size, NO, 0.8);
            [image drawAtPoint:CGPointZero];

            image = UIGraphicsGetImageFromCurrentImageContext();
            UIGraphicsEndImageContext();
        }


 dispatch_sync(dispatch_get_main_queue(), ^
        {

            view.image=image;
            [imagesAreLoading removeObject:[NSNumber numberWithLong:index]];


       });
    });

}

And the second which is using NSOperation , do pretty much the same performance :

[self.imageOperationQueue addOperationWithBlock:^
    {
        NSDictionary *dic=[mainData objectAtIndex:index];
        NSString *userImageUrl=[dic objectForKey:@"url"];
        NSURL *userUrl=[NSURL URLWithString:userImageUrl];

        UIImage *image = [UIImage imageWithData:[NSData dataWithContentsOfURL:userUrl]];
        if (image)
        {
            UIGraphicsBeginImageContextWithOptions(image.size, NO, 0.8);
            [image drawAtPoint:CGPointZero];

            image = UIGraphicsGetImageFromCurrentImageContext();
            UIGraphicsEndImageContext();
        }



        if (image != nil)
        {


            // now update UI in main queue
            [[NSOperationQueue mainQueue] addOperationWithBlock:^
            {


                view.image=image;


           }];
        }
    }];

ios - Lost with memory warning when loading images to scroller - Stack...

ios objective-c memory-management uiimageview
Rectangle 27 0

It looks like you want to use a UICollectionView - whats happening is you are loading lots of these webviews into memory and its just too much. You need to take advantage of cell reuse.

Take a read of a few tutorials and get yourself upto speed -

ios - Received memory warning when loading uibweview - Stack Overflow

ios iphone ios5 uiwebview didreceivememorywarning
Rectangle 27 0

Wht you are asking for is exactly what -viewDidLoad and -viewDidUnload provide. A UIViewController may load and unload it's view many times during the view controller's life (view controllers unload their views in response to memory warnings if the view is not visible). You should be able to register for notifications every time the view is loaded as long as you unregister when the view is unloaded.

iphone - Loading of view in memory -- viewWillAppear method calls - St...

iphone cocoa-touch ios viewwillappear
Rectangle 27 0

You could try saving you data to a file first, then pointing the UIWebView at it for loading. ASIHTTPRequest can also save a response directly to a file as it streams in.

Thank you for the suggestion. I realised the problem is that since I have a lot of text to show, the height of the UIWebView is too high - over 26000. I'll have to tile the UIWebView somehow...

iphone - Memory warnings when loading UIWebView - Stack Overflow

iphone uiwebview didreceivememorywarning
Rectangle 27 0

I come from iOS experience and I was frustrated to discover such a pathetic issue with something so basic as loading and showing an image. After all, everyone that is having this issue is trying to display reasonably sized images. Anyway, here are the two changes that fixed my problem (and made my app very responsive).

BitmapFactory.decodeXYZ()
BitmapFactory.Options
inPurgeable
inInputShareable
true

2) NEVER use Bitmap.createBitmap(width, height, Config.ARGB_8888). I mean NEVER! I've never had that thing not raise memory error after few passes. No amount of recycle(), System.gc(), whatever helped. It always raised exception. The one other way that actually works is to have a dummy image in your drawables (or another Bitmap that you decoded using step 1 above), rescale that to whatever you want, then manipulate the resulting Bitmap (such as passing it on to a Canvas for more fun). So, what you should use instead is: Bitmap.createScaledBitmap(srcBitmap, width, height, false). If for whatever reason you MUST use the brute force create method, then at least pass Config.ARGB_4444.

This is almost guaranteed to save you hours if not days. All that talk about scaling the image, etc. does not really work (unless you consider getting wrong size or degraded image a solution).

BitmapFactory.Options options = new BitmapFactory.Options(); options.inPurgeable = true;
Bitmap.createScaledBitmap(srcBitmap, width, height, false);

In Bitmap.createScaledBitmap() call you should probably use true as the flag parameter. Otherwise the quality of the image will not be smooth when scaling up. Check this thread stackoverflow.com/questions/2895065/

That really is fabulous advice. Wish I could give you an extra +1 for taking Google to task for this amazingly rinky dink bug. I mean... if it's not a bug then the documentation really needs to have some seriously flashing neon signs saying "THIS IS HOW YOU PROCESS PHOTOS", cause I've been struggling with this for 2 years and just now found this post. Great find.

android - Strange out of memory issue while loading an image to a Bitm...

android image memory bitmap
Rectangle 27 0

I come from iOS experience and I was frustrated to discover such a pathetic issue with something so basic as loading and showing an image. After all, everyone that is having this issue is trying to display reasonably sized images. Anyway, here are the two changes that fixed my problem (and made my app very responsive).

BitmapFactory.decodeXYZ()
BitmapFactory.Options
inPurgeable
inInputShareable
true

2) NEVER use Bitmap.createBitmap(width, height, Config.ARGB_8888). I mean NEVER! I've never had that thing not raise memory error after few passes. No amount of recycle(), System.gc(), whatever helped. It always raised exception. The one other way that actually works is to have a dummy image in your drawables (or another Bitmap that you decoded using step 1 above), rescale that to whatever you want, then manipulate the resulting Bitmap (such as passing it on to a Canvas for more fun). So, what you should use instead is: Bitmap.createScaledBitmap(srcBitmap, width, height, false). If for whatever reason you MUST use the brute force create method, then at least pass Config.ARGB_4444.

This is almost guaranteed to save you hours if not days. All that talk about scaling the image, etc. does not really work (unless you consider getting wrong size or degraded image a solution).

BitmapFactory.Options options = new BitmapFactory.Options(); options.inPurgeable = true;
Bitmap.createScaledBitmap(srcBitmap, width, height, false);

In Bitmap.createScaledBitmap() call you should probably use true as the flag parameter. Otherwise the quality of the image will not be smooth when scaling up. Check this thread stackoverflow.com/questions/2895065/

That really is fabulous advice. Wish I could give you an extra +1 for taking Google to task for this amazingly rinky dink bug. I mean... if it's not a bug then the documentation really needs to have some seriously flashing neon signs saying "THIS IS HOW YOU PROCESS PHOTOS", cause I've been struggling with this for 2 years and just now found this post. Great find.

android - Strange out of memory issue while loading an image to a Bitm...

android image memory bitmap
Rectangle 27 0

because your table cell would be reused later,

ios - Memory leak when loading image to custom cell in UITableView - S...

ios uitableview memory-leaks uiimageview custom-cell
Rectangle 27 0

The problem is probably that the method imageNamed: caches the images loaded, and there is apparently no way to clear the cache after a memory warning programmatically. Instead of imageNamed:, you could use other methods like initWithData: that do not cache the images. You will find a detailed discussion here.

Thanks for the input. But its still the same result. Also from documentation it states that "This method looks in the system caches for an image object with the specified name and returns that object if it exists. If a matching image object is not already in the cache, this method loads the image data from the specified file, caches it, and then returns the resulting object."

I thought the problem is that imageNamed: caches MULTIPLE images, and does not free memory automatically when an image is no longer needed. But if you get the same result with non-caching methods, let's look for another reason...

objective c - iOS Application Crash while UIImage loading (virtual mem...

objective-c crash uiimage virtual-memory