This unusual topic came around quite a few times in the last couple of days, first with our own rss parser, and today with android-xmlrpc.
In our rss parser, we wanted to have as much flexibility as possible, so we could use many types of localized rss pages, that have different date formats.
ERROR/dalvikvm-heap(4204): 691456-byte external allocation too large for this process.
01-25 22:13:18.694: ERROR/(4204): VM won't let us allocate 691456 bytes 01-25 22:13:18.694
If you have ever got the message above, you are at the right place.
First of all the reason:
Heap size != External Memory size
Dalvik's external memory is limited to ~ 4MBs for each process (That is the Ugly Truth). If it overflows, you get the BitmapFactory.DecodeFile Error.
That's why even if you have like 2MB-s heap memory free, VM won't let you allocate ~700KB.
Since you can't modify external memory's size, you have to reduce your memory usage. This is the only solution I have, but it really works at least.
The solution:
Let say you have a nice big Gallery with lots of large images. An ImageAdapter class will provide all of the images that you are going to use. Therefore you'll need a List of ImageViews.
Step 1.
First thing I want you to think about is that do You really need to use Bitmaps?
If the answer is No, go to step 2. :) Otherwise, think again.
Ok, Let me explain it. I needed Bitmaps to get the width of the images, to create an ImageAdapter for my Gallery. As far as I know, there's no other way to do that. So I used Bitmaps, and even if I recycled them, once in a while it stopped with the message: DDMS: OutOfMemory .. Phone: Force Close..
Not to speak about how laggy your app will be if you are using Bitmaps..
I've spent 2 weeks to find a solution for this problem, but I couldn't find any usable of them. Then I thought, I try not using Bitmaps anymore. So I have to find another way to get the width of images. Unfortunately, it's just a workaround, but it works so who cares, right?
I can determine widths with a PHP script, store it in my existing database. After I did that, everything was working properly.
In this last part of the tutorial we will implement buttons to the appWidget, which will directly interact with the appWidget functionality.
We will have 2 buttons, a plus button to add one more day to the target date, and a minus button to decrease time left by one day.
First add the buttons to the countdownwidget.xml layout:
We have updated our Hello Baby widget, with a notification feature. So I'm using this opportunity, to show you how to use notifications with widgets.
Hello readers, my name is Tamas, and I'm the newest member of the HelloAndroid.com team :)
Today we decided to update our Hello Baby widget, with a notification feature. So I'm using this opportunity, to show you how to use notifications with widgets.
The plan was to alert the user with a status bar notification 1,2,3 and 7 days before the days-left counter reaches 0.
As described in the previous part, we will use a Service to update the appWidget.
So we will have the Service below, which gets the command (right now we have only the update command), ant the appwidgetId, reads the date from sharedPreferences and updates the widget.
So here's how you can optimize, analyze your current application using TraceView.
Open your Project, and after onCreate(), or anywhere you want to start Log tracing, paste the following lines:
/* start tracing to "/sdcard/filename.trace" */
Debug.startMethodTracing("filename");
It is very important to stop tracing after you have done debugging. To do that, place these lines before onCreate().
publicvoid onDestroy(){
// stop tracing
Debug.stopMethodTracing();
}
Now run your Project, do anything you'd like to optimize, and quit. Open up DDMS File Explorer, and download /sdcard/filename.trace to your hard disk drive.
Go to your Android SDK folder, open Tools directory, and run ./traceview filename.trace
I just come to a new discovery regarding widgets. I was developing an appwidget, which - just like the widgets we are trying to make in this series of tutorials - and tried it out multiple phones. Unfortunatelly on one of our test phones it didn't function properly. For random intervals it stopped to refresh, and it din't responded to button presses on the widget, only after 1-2 minutes. After hard work I discivered the following:
Buttons on appwiget can have their onclick flunctionality thorough RemoteViews.setOnClickPendingIntent(). This method gets a PendingIntent ap parametes to bound to a button. PendingIntent's can have 3 types created with
getActivity(Context, int, Intent, int)