Question

Formalities

Hello...

Prerequisites

I'm using a Service to listen to the Wi-Fi and Bluetooth adapters (continiously in a specific scenario, detecting SSID's and bluetooth beacons) and other tasks that need to be executed in the background such as downloading. I maintain an ExecutorService in this Service for executing runnables and asynctasks.

I detect changes in the Wi-Fi states, GCM messages etc. with broadcastreceivers.

I need to be able to write data to cache, internal and external storage. Having read that the DownloadManager class only allows for writing to the external storage, this kind of prevented me from using it. (Writing my own and using DownloadManager seemed less than ideal).

I have tested using Volley and OkHttp for my networking needs, but they seemed WAY slower than my AsyncTask solution, though Volley provides my with an easy to use NetworkImageView (or whatever it's name was). I have tested downloading an 26mb file and 100 <60kb files. Might have been my implementation, but AsyncTask was faster.

I have to download audio files as well and would therefor have to write a download class still, if I would be using a library for loading the images. I would therefor like to combine the code for the downloading of files into a single class.

Scenario

With the above information in mind I decided to use an AsyncTask to lazy load images in my listviews. I'm looking for a good way to send a broadcast back to the activity and update the ImageView for which the download was executed. Does anyone know an alternative solution to iterating the list items in the ListView Adapter?

Currently I would register a broadcastreceiver in my activity and iterate over my adapter's collection and then match the id of the image with the id in the model stored in the collection. I was wondering if there was a way to directly make a call to the model/listitem to update the representation of the image.

Code

CoreManagerService:

public class CoreManagerService extends Service {

/**
 * TODO Create separate running threads using this ExecutorService.
 * To be used for spawning threads that handle scanning for Bluetooth, Wi-Fi etc.
 * Creates a thread pool with a dynamic number of workers.
 * @see ExecutorService {@link java.util.concurrent.Executors#newCachedThreadPool()}
 */
public ExecutorService mThreadPool = Executors.newCachedThreadPool();

StartDownloadReceiver:

@Override
public void onReceive(Context context, Intent intent) {
    DownloadImagesTask task = new DownloadImagesTask(context);
    task.executeOnExecutor(service.mThreadPool, intent);
}

DownloadImagesTask:

public class DownloadImagesTask extends AsyncTask<Intent, Integer, FileTransferJavaBean> {

I don't think you need the source here to get the general idea. I use a Java Bean to store my values and send them activity->service and service->activity. I know Intent can do it all for me, but creating a class for this seemed cleaner. The Java Bean implements Parcelable.

I hope you guys can provide me with an answer to my query.

Was it helpful?

Solution 3

Anyone facing the same issue that I've faced here should take a look at: https://www.youtube.com/watch?v=xHXn3Kg2IQE.

While my question was about downloading which was easily solved with broadcasts, but requires you to manually keep track of your broadcast receivers etc. Now REST came looking around the corner and I quickly realised that broadcasts wouldn't cut it.

I can still use my AsyncTasks within pattern C, that's described in the video and create a contentprovider for the downloading of images, audio etc.

The advantages that the pattern provide are significant. While some advantages might not be relevant with current phones (automatic checking if other apps are syncing etc. to reduce load on the phone).

I will create a new question here to get an answer to my question on how to correctly implement a contentprovider and ORMLite.

OTHER TIPS

Universal image loader is just what you need.

https://github.com/nostra13/Android-Universal-Image-Loader

You can also callback to your activity from an asynctask's onPostExecute method like this :

    getActivity().runOnUiThread(new Runnable() {
        @Override
        public void run() {
            myImageView.setImageBitmap(myimage.getBitmap());
        }
    });

Try Picasso to download and cache images. It works perfectly with adapters out of the box.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top