Reputation: 4287
I've got a couple of activities where I display images with help of this lib. The thing is the app is running out of memory. I tried to gc.clean(), null references, call clear on imageloader object but in vain.
In MAT i've found out that I have multiple objects of the same activity and it a default behaviour, if I'm not mistaken. I used singleInstance to suppress multiple instances and it has helped with memory leaks.
Right now, due to singleInstance, I'm having troubles with navigation. Do you think I should continue with singleInstance or try to fix memory leak with multiple instances ?
Here's ImageView gc roots inspection:
UPD:
Bitmap bitmap=null;
URL imageUrl = new URL(url);
HttpURLConnection conn = (HttpURLConnection)imageUrl.openConnection();
conn.setConnectTimeout(30000);
conn.setReadTimeout(30000);
conn.setInstanceFollowRedirects(true);
InputStream is=conn.getInputStream();
OutputStream os = new FileOutputStream(f);
Utils.CopyStream(is, os);
os.close();
bitmap = decodeFile(f);
return bitmap;
ImageView imageView = (ImageView) convertView;
if(convertView == null){
imageView = new ImageView(_currentActivity);
}
UPD2(navigation strategies):
I've got a constant header with buttons which start home activity(with gallery) and profile activity; secondly there's a subheader wich also holds 3 buttons which point to another 3 activities with listviews(consisting of imageviews + labels).
These header, subheader elements are available on every activity in application; The link-buttons do nothing but:
startActivity(new Intent(getActivity(), MainActivity.class));
or
Intent activityIntent = new Intent(getActivity(), SomeActivityWithListViewInside.class);
// passing some data like list id
activityIntent.putExtra("list_id", listId);
startActivity(activityIntent);
So, those activity instances are caused by those startActivity calls - do you think I should play with singleTop or any other intent parameter to avoid this issue ?
Upvotes: 1
Views: 1324
Reputation: 95578
You shouldn't use singleInstance launchMode. You need to get your navigation to work correctly using standard and/or singleTop launchMode. If you find that you have multiple instances of your activites, but you weren't expecting that, then you have something wrong in your navigation. Having multiple instances of your activities is keeping all your views and images around and that's probably what is causing the out-of-memory problems.
Update your post with your expected navigation and how you are managing it and maybe we can help you fix that.
EDIT: Respond to poster's UPD:
I don't know where you are setting _currentActivity
, but that may be your problem. When you create a view inside an adapter you should always use the adapter's context (which is set up when it was created). So try this:
ImageView imageView = (ImageView) convertView;
if(convertView == null){
imageView = new ImageView(getContext());
}
EDIT: Respond to poster's UPD2:
You need to check your navigation to make sure that when the user chooses one of the buttons in your header or subheader that you don't have multiple instances of your activities in the activity stack (if that isn't what you want). If your activities use lots of image space (bitmaps, etc.) then you want to ensure that you don't have multiple instances. You can rethink your navigation or you can use combinations of singleTop, clearTop, reorderToFront, etc. so that you don't keep creating instances of your activities but just rearrange them in the activity stack to get the desired navigation behaviour.
Upvotes: 1
Reputation: 13506
Passing activity as a context when creating a view is not good: this prevents the activity from being "released". Also you may want to scale down bitmaps to the size you really need.
Upvotes: 0
Reputation: 116382
i would strongly recommend not to use the weird flags of the activities . i also always had problems with navigation (and still have , even with fragments) using the android API.
instead, i suggest that you solve the memory problems .
you should watch this video about memory leaks , and read this about bitmaps.
in short , here are some tips:
try to avoid static references , especially if they reference to context.
try to avoid referencing to context .
if you must reference to context , consider using the ApplicationContext.
remember to close threads and dialogs when closing the activity (if needed). try to close services when they are no longer needed.
prefer static inner classes over non static inner classes (since those have reference to the containing class) .
remember that anonymous classes also have reference to the containing class .
be careful with what you caches . try to avoid caching classes that contain a reference to context , such as views and drawables .
if possible try to use softReference and/or weakReference for referencing to "dangerous" objects that reference to context .
on android API 10 and below , remember to recycle your bitmaps . they usualy take a lot of memory.
if an activity takes too much memory and you go from it to another activity , consider finishing it and re-creating it when needed instead of going back to its old instance.
if you use any third party libraries or you are using native code (using NDK for example) , don't forget to release its memory when not needed . dalvik won't help you much about it .
Upvotes: 3