19066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project/*
29066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Copyright (C) 2008 The Android Open Source Project
39066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
49066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License");
59066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * you may not use this file except in compliance with the License.
69066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * You may obtain a copy of the License at
79066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
89066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *      http://www.apache.org/licenses/LICENSE-2.0
99066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Unless required by applicable law or agreed to in writing, software
119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS,
129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * See the License for the specific language governing permissions and
149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * limitations under the License.
159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project */
169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectpackage android.os;
189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1981de61bfddceba0eb77b3aacea317594b0f1de49Joe Onoratoimport java.util.ArrayDeque;
209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport java.util.concurrent.BlockingQueue;
219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport java.util.concurrent.Callable;
227f4b6842ce2388b8e60cd31bdc3273f80472f632Gilles Debunneimport java.util.concurrent.CancellationException;
2381de61bfddceba0eb77b3aacea317594b0f1de49Joe Onoratoimport java.util.concurrent.Executor;
249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport java.util.concurrent.ExecutionException;
257f4b6842ce2388b8e60cd31bdc3273f80472f632Gilles Debunneimport java.util.concurrent.FutureTask;
267f4b6842ce2388b8e60cd31bdc3273f80472f632Gilles Debunneimport java.util.concurrent.LinkedBlockingQueue;
277f4b6842ce2388b8e60cd31bdc3273f80472f632Gilles Debunneimport java.util.concurrent.ThreadFactory;
287f4b6842ce2388b8e60cd31bdc3273f80472f632Gilles Debunneimport java.util.concurrent.ThreadPoolExecutor;
297f4b6842ce2388b8e60cd31bdc3273f80472f632Gilles Debunneimport java.util.concurrent.TimeUnit;
309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport java.util.concurrent.TimeoutException;
315ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guyimport java.util.concurrent.atomic.AtomicBoolean;
329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectimport java.util.concurrent.atomic.AtomicInteger;
339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project/**
350bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy * <p>AsyncTask enables proper and easy use of the UI thread. This class allows to
360bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy * perform background operations and publish results on the UI thread without
370bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy * having to manipulate threads and/or handlers.</p>
389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
392c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy * <p>AsyncTask is designed to be a helper class around {@link Thread} and {@link Handler}
402c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy * and does not constitute a generic threading framework. AsyncTasks should ideally be
412c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy * used for short operations (a few seconds at the most.) If you need to keep threads
422c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy * running for long periods of time, it is highly recommended you use the various APIs
432c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy * provided by the <code>java.util.concurrent</code> pacakge such as {@link Executor},
442c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy * {@link ThreadPoolExecutor} and {@link FutureTask}.</p>
452c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy *
469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <p>An asynchronous task is defined by a computation that runs on a background thread and
470bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy * whose result is published on the UI thread. An asynchronous task is defined by 3 generic
489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * types, called <code>Params</code>, <code>Progress</code> and <code>Result</code>,
497f4b6842ce2388b8e60cd31bdc3273f80472f632Gilles Debunne * and 4 steps, called <code>onPreExecute</code>, <code>doInBackground</code>,
507f4b6842ce2388b8e60cd31bdc3273f80472f632Gilles Debunne * <code>onProgressUpdate</code> and <code>onPostExecute</code>.</p>
519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
52b54e7a3d9f60ac605f404f9eb3c5e92ca51bbd23Joe Fernandez * <div class="special reference">
53b54e7a3d9f60ac605f404f9eb3c5e92ca51bbd23Joe Fernandez * <h3>Developer Guides</h3>
54b54e7a3d9f60ac605f404f9eb3c5e92ca51bbd23Joe Fernandez * <p>For more information about using tasks and threads, read the
55b54e7a3d9f60ac605f404f9eb3c5e92ca51bbd23Joe Fernandez * <a href="{@docRoot}guide/topics/fundamentals/processes-and-threads.html">Processes and
56b54e7a3d9f60ac605f404f9eb3c5e92ca51bbd23Joe Fernandez * Threads</a> developer guide.</p>
57b54e7a3d9f60ac605f404f9eb3c5e92ca51bbd23Joe Fernandez * </div>
58b54e7a3d9f60ac605f404f9eb3c5e92ca51bbd23Joe Fernandez *
599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <h2>Usage</h2>
609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <p>AsyncTask must be subclassed to be used. The subclass will override at least
619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * one method ({@link #doInBackground}), and most often will override a
629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * second one ({@link #onPostExecute}.)</p>
639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <p>Here is an example of subclassing:</p>
659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <pre class="prettyprint">
669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * private class DownloadFilesTask extends AsyncTask&lt;URL, Integer, Long&gt; {
679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     protected Long doInBackground(URL... urls) {
689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *         int count = urls.length;
699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *         long totalSize = 0;
709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *         for (int i = 0; i < count; i++) {
719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *             totalSize += Downloader.downloadFile(urls[i]);
729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *             publishProgress((int) ((i / (float) count) * 100));
732c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy *             // Escape early if cancel() is called
742c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy *             if (isCancelled()) break;
759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *         }
769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *         return totalSize;
779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     }
789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     protected void onProgressUpdate(Integer... progress) {
809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *         setProgressPercent(progress[0]);
819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     }
829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     protected void onPostExecute(Long result) {
849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *         showDialog("Downloaded " + result + " bytes");
859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     }
869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * }
879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * </pre>
889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <p>Once created, a task is executed very simply:</p>
909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <pre class="prettyprint">
919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * new DownloadFilesTask().execute(url1, url2, url3);
929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * </pre>
939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <h2>AsyncTask's generic types</h2>
959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <p>The three types used by an asynchronous task are the following:</p>
969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <ol>
979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     <li><code>Params</code>, the type of the parameters sent to the task upon
989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     execution.</li>
999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     <li><code>Progress</code>, the type of the progress units published during
1009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     the background computation.</li>
1019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     <li><code>Result</code>, the type of the result of the background
1029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     computation.</li>
1039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * </ol>
104202f560f85446008808e443ad28e438622bca49fOwen Lin * <p>Not all types are always used by an asynchronous task. To mark a type as unused,
1059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * simply use the type {@link Void}:</p>
1069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <pre>
1076a1ae64f7735a3817713a223096bf8034f78a620Romain Guy * private class MyTask extends AsyncTask&lt;Void, Void, Void&gt; { ... }
1089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * </pre>
1099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
1109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <h2>The 4 steps</h2>
1119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <p>When an asynchronous task is executed, the task goes through 4 steps:</p>
1129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <ol>
1136f931ccd31bc0a8a402072c1d87e682c8a30a404Romain Guy *     <li>{@link #onPreExecute()}, invoked on the UI thread before the task
1149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     is executed. This step is normally used to setup the task, for instance by
1159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     showing a progress bar in the user interface.</li>
1169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     <li>{@link #doInBackground}, invoked on the background thread
1179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     immediately after {@link #onPreExecute()} finishes executing. This step is used
1189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     to perform background computation that can take a long time. The parameters
1199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     of the asynchronous task are passed to this step. The result of the computation must
1209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     be returned by this step and will be passed back to the last step. This step
1219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     can also use {@link #publishProgress} to publish one or more units
1220bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy *     of progress. These values are published on the UI thread, in the
1239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     {@link #onProgressUpdate} step.</li>
1240bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy *     <li>{@link #onProgressUpdate}, invoked on the UI thread after a
1259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     call to {@link #publishProgress}. The timing of the execution is
1269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     undefined. This method is used to display any form of progress in the user
1279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     interface while the background computation is still executing. For instance,
1289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     it can be used to animate a progress bar or show logs in a text field.</li>
1290bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy *     <li>{@link #onPostExecute}, invoked on the UI thread after the background
1309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     computation finishes. The result of the background computation is passed to
1319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     this step as a parameter.</li>
1329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * </ol>
133e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy *
134e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy * <h2>Cancelling a task</h2>
135e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy * <p>A task can be cancelled at any time by invoking {@link #cancel(boolean)}. Invoking
136e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy * this method will cause subsequent calls to {@link #isCancelled()} to return true.
1375ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy * After invoking this method, {@link #onCancelled(Object)}, instead of
1385ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy * {@link #onPostExecute(Object)} will be invoked after {@link #doInBackground(Object[])}
1395ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy * returns. To ensure that a task is cancelled as quickly as possible, you should always
1405ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy * check the return value of {@link #isCancelled()} periodically from
1415ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy * {@link #doInBackground(Object[])}, if possible (inside a loop for instance.)</p>
1429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
1439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <h2>Threading rules</h2>
1449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <p>There are a few threading rules that must be followed for this class to
1459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * work properly:</p>
1469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * <ul>
1475e9120d4adfb07aeeadb0e0de1de2eb9ebbd80e0Romain Guy *     <li>The AsyncTask class must be loaded on the UI thread. This is done
1485e9120d4adfb07aeeadb0e0de1de2eb9ebbd80e0Romain Guy *     automatically as of {@link android.os.Build.VERSION_CODES#JELLY_BEAN}.</li>
1490bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy *     <li>The task instance must be created on the UI thread.</li>
1500bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy *     <li>{@link #execute} must be invoked on the UI thread.</li>
1519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     <li>Do not call {@link #onPreExecute()}, {@link #onPostExecute},
1529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     {@link #doInBackground}, {@link #onProgressUpdate} manually.</li>
1539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     <li>The task can be executed only once (an exception will be thrown if
1549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *     a second execution is attempted.)</li>
1559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * </ul>
156aa60a02f7934ac23cb88f16ed2d726157bc9f31cMakoto Onuki *
157aa60a02f7934ac23cb88f16ed2d726157bc9f31cMakoto Onuki * <h2>Memory observability</h2>
158aa60a02f7934ac23cb88f16ed2d726157bc9f31cMakoto Onuki * <p>AsyncTask guarantees that all callback calls are synchronized in such a way that the following
159aa60a02f7934ac23cb88f16ed2d726157bc9f31cMakoto Onuki * operations are safe without explicit synchronizations.</p>
160aa60a02f7934ac23cb88f16ed2d726157bc9f31cMakoto Onuki * <ul>
161aa60a02f7934ac23cb88f16ed2d726157bc9f31cMakoto Onuki *     <li>Set member fields in the constructor or {@link #onPreExecute}, and refer to them
162aa60a02f7934ac23cb88f16ed2d726157bc9f31cMakoto Onuki *     in {@link #doInBackground}.
163aa60a02f7934ac23cb88f16ed2d726157bc9f31cMakoto Onuki *     <li>Set member fields in {@link #doInBackground}, and refer to them in
164aa60a02f7934ac23cb88f16ed2d726157bc9f31cMakoto Onuki *     {@link #onProgressUpdate} and {@link #onPostExecute}.
165aa60a02f7934ac23cb88f16ed2d726157bc9f31cMakoto Onuki * </ul>
1662c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy *
1672c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy * <h2>Order of execution</h2>
1682c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy * <p>When first introduced, AsyncTasks were executed serially on a single background
1692c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy * thread. Starting with {@link android.os.Build.VERSION_CODES#DONUT}, this was changed
1702c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy * to a pool of threads allowing multiple tasks to operate in parallel. Starting with
1712c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy * {@link android.os.Build.VERSION_CODES#HONEYCOMB}, tasks are executed on a single
1722c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy * thread to avoid common application errors caused by parallel execution.</p>
1732c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy * <p>If you truly want parallel execution, you can invoke
1742c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy * {@link #executeOnExecutor(java.util.concurrent.Executor, Object[])} with
1752c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy * {@link #THREAD_POOL_EXECUTOR}.</p>
1769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project */
1779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectpublic abstract class AsyncTask<Params, Progress, Result> {
1789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private static final String LOG_TAG = "AsyncTask";
1799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
180a9be47cea45c19f2869732252e9922bf88fa4d86Romain Guy    private static final int CORE_POOL_SIZE = 5;
181a9be47cea45c19f2869732252e9922bf88fa4d86Romain Guy    private static final int MAXIMUM_POOL_SIZE = 128;
1826b424f4770e1c4fe3e4c2a44d08447b0e9203dd4Romain Guy    private static final int KEEP_ALIVE = 1;
1839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private static final ThreadFactory sThreadFactory = new ThreadFactory() {
1859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        private final AtomicInteger mCount = new AtomicInteger(1);
1869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        public Thread newThread(Runnable r) {
1889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return new Thread(r, "AsyncTask #" + mCount.getAndIncrement());
1899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
1909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    };
1919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
19281de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato    private static final BlockingQueue<Runnable> sPoolWorkQueue =
19381de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato            new LinkedBlockingQueue<Runnable>(10);
19481de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato
19581de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato    /**
19696438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * An {@link Executor} that can be used to execute tasks in parallel.
19781de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato     */
19896438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn    public static final Executor THREAD_POOL_EXECUTOR
19981de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato            = new ThreadPoolExecutor(CORE_POOL_SIZE, MAXIMUM_POOL_SIZE, KEEP_ALIVE,
20081de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato                    TimeUnit.SECONDS, sPoolWorkQueue, sThreadFactory);
20181de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato
20296438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn    /**
20396438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * An {@link Executor} that executes tasks one at a time in serial
20496438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * order.  This serialization is global to a particular process.
20596438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     */
20696438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn    public static final Executor SERIAL_EXECUTOR = new SerialExecutor();
2079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private static final int MESSAGE_POST_RESULT = 0x1;
2099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private static final int MESSAGE_POST_PROGRESS = 0x2;
2109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2110bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy    private static final InternalHandler sHandler = new InternalHandler();
2129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
213d630f105e8bc0021541aacb4dc6498a49048eceaJoe Onorato    private static volatile Executor sDefaultExecutor = SERIAL_EXECUTOR;
2149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private final WorkerRunnable<Params, Result> mWorker;
2159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private final FutureTask<Result> mFuture;
2169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private volatile Status mStatus = Status.PENDING;
2185ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy
219657f51371cc631a82a8d30cd4a796c48077d474bRomain Guy    private final AtomicBoolean mCancelled = new AtomicBoolean();
2205ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy    private final AtomicBoolean mTaskInvoked = new AtomicBoolean();
2219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
22281de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato    private static class SerialExecutor implements Executor {
22381de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato        final ArrayDeque<Runnable> mTasks = new ArrayDeque<Runnable>();
22481de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato        Runnable mActive;
22581de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato
22681de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato        public synchronized void execute(final Runnable r) {
22781de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato            mTasks.offer(new Runnable() {
22881de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato                public void run() {
22981de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato                    try {
23081de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato                        r.run();
23181de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato                    } finally {
23281de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato                        scheduleNext();
23381de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato                    }
23481de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato                }
23581de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato            });
23681de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato            if (mActive == null) {
23781de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato                scheduleNext();
23881de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato            }
23981de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato        }
24081de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato
24181de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato        protected synchronized void scheduleNext() {
24281de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato            if ((mActive = mTasks.poll()) != null) {
24381de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato                THREAD_POOL_EXECUTOR.execute(mActive);
24481de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato            }
24581de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato        }
24681de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato    }
24781de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato
2489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
2499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * Indicates the current status of the task. Each status will be set only once
2509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * during the lifetime of a task.
2519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
2529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public enum Status {
2539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        /**
2549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project         * Indicates that the task has not been executed yet.
2559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project         */
2569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        PENDING,
2579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        /**
2589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project         * Indicates that the task is running.
2599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project         */
2609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        RUNNING,
2619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        /**
2629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project         * Indicates that {@link AsyncTask#onPostExecute} has finished.
2639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project         */
2649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        FINISHED,
2659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2670bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy    /** @hide Used to force static handler to be created. */
26823fdaf6fb62a9b5154b2508916a21c678462c5d0Dianne Hackborn    public static void init() {
2690bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy        sHandler.getLooper();
27023fdaf6fb62a9b5154b2508916a21c678462c5d0Dianne Hackborn    }
27123fdaf6fb62a9b5154b2508916a21c678462c5d0Dianne Hackborn
272d630f105e8bc0021541aacb4dc6498a49048eceaJoe Onorato    /** @hide */
273d630f105e8bc0021541aacb4dc6498a49048eceaJoe Onorato    public static void setDefaultExecutor(Executor exec) {
274d630f105e8bc0021541aacb4dc6498a49048eceaJoe Onorato        sDefaultExecutor = exec;
275d630f105e8bc0021541aacb4dc6498a49048eceaJoe Onorato    }
276d630f105e8bc0021541aacb4dc6498a49048eceaJoe Onorato
2779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
2780bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy     * Creates a new asynchronous task. This constructor must be invoked on the UI thread.
2799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
2809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public AsyncTask() {
2819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mWorker = new WorkerRunnable<Params, Result>() {
2829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            public Result call() throws Exception {
2835ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy                mTaskInvoked.set(true);
284e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy
2855ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy                Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
286657f51371cc631a82a8d30cd4a796c48077d474bRomain Guy                //noinspection unchecked
2875ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy                return postResult(doInBackground(mParams));
288bef9c7a59dc020c5cdcbd555b5212ae5a10e8045Dmitri Plotnikov            }
289e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy        };
290bef9c7a59dc020c5cdcbd555b5212ae5a10e8045Dmitri Plotnikov
291e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy        mFuture = new FutureTask<Result>(mWorker) {
2929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            @Override
2939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            protected void done() {
2949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                try {
295657f51371cc631a82a8d30cd4a796c48077d474bRomain Guy                    postResultIfNotInvoked(get());
2969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                } catch (InterruptedException e) {
2979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    android.util.Log.w(LOG_TAG, e);
2989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                } catch (ExecutionException e) {
2999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    throw new RuntimeException("An error occured while executing doInBackground()",
3009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                            e.getCause());
3019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                } catch (CancellationException e) {
3025ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy                    postResultIfNotInvoked(null);
3039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                }
3049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
3059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        };
3069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3085ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy    private void postResultIfNotInvoked(Result result) {
3095ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy        final boolean wasTaskInvoked = mTaskInvoked.get();
3105ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy        if (!wasTaskInvoked) {
3115ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy            postResult(result);
3125ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy        }
3135ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy    }
3145ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy
3155ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy    private Result postResult(Result result) {
316657f51371cc631a82a8d30cd4a796c48077d474bRomain Guy        @SuppressWarnings("unchecked")
3175e7f2d0b227df38f6dbc2313ac8b5c9f225c135eRomain Guy        Message message = sHandler.obtainMessage(MESSAGE_POST_RESULT,
3185ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy                new AsyncTaskResult<Result>(this, result));
3195ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy        message.sendToTarget();
3205ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy        return result;
3215ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy    }
3225ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy
3239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
3249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * Returns the current status of this task.
3259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
3269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @return The current status.
3279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
3289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public final Status getStatus() {
3299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return mStatus;
3309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
3339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * Override this method to perform a computation on a background thread. The
3349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * specified parameters are the parameters passed to {@link #execute}
3359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * by the caller of this task.
3369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
3379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * This method can call {@link #publishProgress} to publish updates
3380bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy     * on the UI thread.
3399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
3409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @param params The parameters of the task.
3419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
3429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @return A result, defined by the subclass of this task.
3439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
3449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see #onPreExecute()
3459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see #onPostExecute
3469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see #publishProgress
3479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
3489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    protected abstract Result doInBackground(Params... params);
3499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
3510bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy     * Runs on the UI thread before {@link #doInBackground}.
3529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
3539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see #onPostExecute
3549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see #doInBackground
3559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
3569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    protected void onPreExecute() {
3579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
3600bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy     * <p>Runs on the UI thread after {@link #doInBackground}. The
361e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy     * specified result is the value returned by {@link #doInBackground}.</p>
362e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy     *
363e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy     * <p>This method won't be invoked if the task was cancelled.</p>
3649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
3659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @param result The result of the operation computed by {@link #doInBackground}.
3669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
3679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see #onPreExecute
3689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see #doInBackground
3695ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     * @see #onCancelled(Object)
3709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
3719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @SuppressWarnings({"UnusedDeclaration"})
3729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    protected void onPostExecute(Result result) {
3739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
3760bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy     * Runs on the UI thread after {@link #publishProgress} is invoked.
3779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * The specified values are the values passed to {@link #publishProgress}.
3789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
3799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @param values The values indicating progress.
3809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
3819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see #publishProgress
3829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see #doInBackground
3839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
3849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @SuppressWarnings({"UnusedDeclaration"})
3859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    protected void onProgressUpdate(Progress... values) {
3869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
3890bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy     * <p>Runs on the UI thread after {@link #cancel(boolean)} is invoked and
3905ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     * {@link #doInBackground(Object[])} has finished.</p>
3915ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     *
3925ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     * <p>The default implementation simply invokes {@link #onCancelled()} and
3935ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     * ignores the result. If you write your own implementation, do not call
3945ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     * <code>super.onCancelled(result)</code>.</p>
3955ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     *
3965ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     * @param result The result, if any, computed in
3975ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     *               {@link #doInBackground(Object[])}, can be null
3985ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     *
3995ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     * @see #cancel(boolean)
4005ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     * @see #isCancelled()
4015ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     */
4025ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy    @SuppressWarnings({"UnusedParameters"})
4035ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy    protected void onCancelled(Result result) {
4045ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy        onCancelled();
4055ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy    }
4065ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy
4075ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy    /**
4085ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     * <p>Applications should preferably override {@link #onCancelled(Object)}.
4095ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     * This method is invoked by the default implementation of
4105ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     * {@link #onCancelled(Object)}.</p>
4115ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     *
4120bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy     * <p>Runs on the UI thread after {@link #cancel(boolean)} is invoked and
4135ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     * {@link #doInBackground(Object[])} has finished.</p>
4149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
4155ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     * @see #onCancelled(Object)
4169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see #cancel(boolean)
4179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see #isCancelled()
4189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
4199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    protected void onCancelled() {
4209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
4239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * Returns <tt>true</tt> if this task was cancelled before it completed
424e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy     * normally. If you are calling {@link #cancel(boolean)} on the task,
425e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy     * the value returned by this method should be checked periodically from
426e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy     * {@link #doInBackground(Object[])} to end the task as soon as possible.
4279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
4289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @return <tt>true</tt> if task was cancelled before it completed
4299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
4309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see #cancel(boolean)
4319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
4329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public final boolean isCancelled() {
433657f51371cc631a82a8d30cd4a796c48077d474bRomain Guy        return mCancelled.get();
4349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
437e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy     * <p>Attempts to cancel execution of this task.  This attempt will
4389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * fail if the task has already completed, already been cancelled,
4399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * or could not be cancelled for some other reason. If successful,
4409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * and this task has not started when <tt>cancel</tt> is called,
441e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy     * this task should never run. If the task has already started,
4429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * then the <tt>mayInterruptIfRunning</tt> parameter determines
4439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * whether the thread executing this task should be interrupted in
444e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy     * an attempt to stop the task.</p>
445e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy     *
4465ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     * <p>Calling this method will result in {@link #onCancelled(Object)} being
4470bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy     * invoked on the UI thread after {@link #doInBackground(Object[])}
448e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy     * returns. Calling this method guarantees that {@link #onPostExecute(Object)}
449e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy     * is never invoked. After invoking this method, you should check the
450e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy     * value returned by {@link #isCancelled()} periodically from
451e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy     * {@link #doInBackground(Object[])} to finish the task as early as
452e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy     * possible.</p>
4539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
4549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @param mayInterruptIfRunning <tt>true</tt> if the thread executing this
4559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *        task should be interrupted; otherwise, in-progress tasks are allowed
4569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *        to complete.
4579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
4589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @return <tt>false</tt> if the task could not be cancelled,
4599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *         typically because it has already completed normally;
4609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *         <tt>true</tt> otherwise
4619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
4629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see #isCancelled()
4635ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy     * @see #onCancelled(Object)
4649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
4659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public final boolean cancel(boolean mayInterruptIfRunning) {
466657f51371cc631a82a8d30cd4a796c48077d474bRomain Guy        mCancelled.set(true);
4679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return mFuture.cancel(mayInterruptIfRunning);
4689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
4719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * Waits if necessary for the computation to complete, and then
4729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * retrieves its result.
4739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
4749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @return The computed result.
4759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
4769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @throws CancellationException If the computation was cancelled.
4779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @throws ExecutionException If the computation threw an exception.
4789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @throws InterruptedException If the current thread was interrupted
4799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *         while waiting.
4809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
4819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public final Result get() throws InterruptedException, ExecutionException {
4829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return mFuture.get();
4839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
4869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * Waits if necessary for at most the given time for the computation
4879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * to complete, and then retrieves its result.
4889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
4899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @param timeout Time to wait before cancelling the operation.
4909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @param unit The time unit for the timeout.
4919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
4929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @return The computed result.
4939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
4949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @throws CancellationException If the computation was cancelled.
4959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @throws ExecutionException If the computation threw an exception.
4969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @throws InterruptedException If the current thread was interrupted
4979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *         while waiting.
4989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @throws TimeoutException If the wait timed out.
4999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
5009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public final Result get(long timeout, TimeUnit unit) throws InterruptedException,
5019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            ExecutionException, TimeoutException {
5029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return mFuture.get(timeout, unit);
5039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
5049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
5069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * Executes the task with the specified parameters. The task returns
50796438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * itself (this) so that the caller can keep a reference to it.
50896438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     *
50996438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * <p>Note: this function schedules the task on a queue for a single background
51096438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * thread or pool of threads depending on the platform version.  When first
51196438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * introduced, AsyncTasks were executed serially on a single background thread.
51296438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * Starting with {@link android.os.Build.VERSION_CODES#DONUT}, this was changed
5132c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy     * to a pool of threads allowing multiple tasks to operate in parallel. Starting
5142c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy     * {@link android.os.Build.VERSION_CODES#HONEYCOMB}, tasks are back to being
5152c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy     * executed on a single thread to avoid common application errors caused
51696438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * by parallel execution.  If you truly want parallel execution, you can use
51796438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * the {@link #executeOnExecutor} version of this method
5182c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy     * with {@link #THREAD_POOL_EXECUTOR}; however, see commentary there for warnings
5192c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy     * on its use.
5209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
5210bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy     * <p>This method must be invoked on the UI thread.
5229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
5239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @param params The parameters of the task.
5249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
5259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @return This instance of AsyncTask.
5269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
5279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @throws IllegalStateException If {@link #getStatus()} returns either
5280bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy     *         {@link AsyncTask.Status#RUNNING} or {@link AsyncTask.Status#FINISHED}.
5292c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy     *
5302c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy     * @see #executeOnExecutor(java.util.concurrent.Executor, Object[])
5312c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy     * @see #execute(Runnable)
5329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
5339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    public final AsyncTask<Params, Progress, Result> execute(Params... params) {
534d630f105e8bc0021541aacb4dc6498a49048eceaJoe Onorato        return executeOnExecutor(sDefaultExecutor, params);
53581de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato    }
53681de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato
53781de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato    /**
53881de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato     * Executes the task with the specified parameters. The task returns
53981de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato     * itself (this) so that the caller can keep a reference to it.
54096438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     *
54196438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * <p>This method is typically used with {@link #THREAD_POOL_EXECUTOR} to
54296438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * allow multiple tasks to run in parallel on a pool of threads managed by
54396438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * AsyncTask, however you can also use your own {@link Executor} for custom
54496438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * behavior.
54596438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     *
54696438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * <p><em>Warning:</em> Allowing multiple tasks to run in parallel from
54796438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * a thread pool is generally <em>not</em> what one wants, because the order
54896438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * of their operation is not defined.  For example, if these tasks are used
54996438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * to modify any state in common (such as writing a file due to a button click),
55096438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * there are no guarantees on the order of the modifications.
55196438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * Without careful work it is possible in rare cases for the newer version
55296438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * of the data to be over-written by an older one, leading to obscure data
55396438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * loss and stability issues.  Such changes are best
55496438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * executed in serial; to guarantee such work is serialized regardless of
55596438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * platform version you can use this function with {@link #SERIAL_EXECUTOR}.
55681de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato     *
5570bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy     * <p>This method must be invoked on the UI thread.
55881de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato     *
55981de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato     * @param exec The executor to use.  {@link #THREAD_POOL_EXECUTOR} is available as a
56081de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato     *              convenient process-wide thread pool for tasks that are loosely coupled.
56181de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato     * @param params The parameters of the task.
56281de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato     *
56381de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato     * @return This instance of AsyncTask.
56481de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato     *
56581de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato     * @throws IllegalStateException If {@link #getStatus()} returns either
5660bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy     *         {@link AsyncTask.Status#RUNNING} or {@link AsyncTask.Status#FINISHED}.
5672c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy     *
5682c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy     * @see #execute(Object[])
56981de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato     */
57081de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato    public final AsyncTask<Params, Progress, Result> executeOnExecutor(Executor exec,
57181de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato            Params... params) {
5729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (mStatus != Status.PENDING) {
5739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            switch (mStatus) {
5749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                case RUNNING:
5759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    throw new IllegalStateException("Cannot execute task:"
5769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                            + " the task is already running.");
5779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                case FINISHED:
5789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    throw new IllegalStateException("Cannot execute task:"
5799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                            + " the task has already been executed "
5809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                            + "(a task can be executed only once)");
5819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
5829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
5839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mStatus = Status.RUNNING;
5859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        onPreExecute();
5879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mWorker.mParams = params;
58981de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato        exec.execute(mFuture);
5909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return this;
5929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
5939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /**
59596438cd658f91fed9d8fc651c4eb1e55dc6dbf80Dianne Hackborn     * Convenience version of {@link #execute(Object...)} for use with
5962c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy     * a simple Runnable object. See {@link #execute(Object[])} for more
5972c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy     * information on the order of execution.
5982c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy     *
5992c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy     * @see #execute(Object[])
6002c1b8c744daf1dfb3cc545effaf9a43e342a3d38Romain Guy     * @see #executeOnExecutor(java.util.concurrent.Executor, Object[])
60181de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato     */
60281de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato    public static void execute(Runnable runnable) {
603d630f105e8bc0021541aacb4dc6498a49048eceaJoe Onorato        sDefaultExecutor.execute(runnable);
60481de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato    }
60581de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato
60681de61bfddceba0eb77b3aacea317594b0f1de49Joe Onorato    /**
6079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * This method can be invoked from {@link #doInBackground} to
6080bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy     * publish updates on the UI thread while the background computation is
6099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * still running. Each call to this method will trigger the execution of
6100bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy     * {@link #onProgressUpdate} on the UI thread.
611bef9c7a59dc020c5cdcbd555b5212ae5a10e8045Dmitri Plotnikov     *
6124aaf8ec9dfb9a9e0f3d84e8ee95d7ac2ebca8d92Romain Guy     * {@link #onProgressUpdate} will note be called if the task has been
6134aaf8ec9dfb9a9e0f3d84e8ee95d7ac2ebca8d92Romain Guy     * canceled.
6149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
6159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @param values The progress values to update the UI with.
6169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     *
6179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see #onProgressUpdate
6189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     * @see #doInBackground
6199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project     */
6209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    protected final void publishProgress(Progress... values) {
6214aaf8ec9dfb9a9e0f3d84e8ee95d7ac2ebca8d92Romain Guy        if (!isCancelled()) {
6220bbd8d8273c1dde9e0504f67bd8eb159bef2406aRomain Guy            sHandler.obtainMessage(MESSAGE_POST_PROGRESS,
6234aaf8ec9dfb9a9e0f3d84e8ee95d7ac2ebca8d92Romain Guy                    new AsyncTaskResult<Progress>(this, values)).sendToTarget();
6244aaf8ec9dfb9a9e0f3d84e8ee95d7ac2ebca8d92Romain Guy        }
6259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
6269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private void finish(Result result) {
628e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy        if (isCancelled()) {
6295ba812b9e9c886425a5736c2ae6fbe0fc94afd8bRomain Guy            onCancelled(result);
630e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy        } else {
631e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy            onPostExecute(result);
632e95003e4a15eea2d5f93950fc46f99ff2b9c973aRomain Guy        }
6339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        mStatus = Status.FINISHED;
6349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
6359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private static class InternalHandler extends Handler {
6379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        @SuppressWarnings({"unchecked", "RawUseOfParameterizedType"})
6389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        @Override
6399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        public void handleMessage(Message msg) {
6409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            AsyncTaskResult result = (AsyncTaskResult) msg.obj;
6419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            switch (msg.what) {
6429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                case MESSAGE_POST_RESULT:
6439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    // There is only one result
6449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    result.mTask.finish(result.mData[0]);
6459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    break;
6469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                case MESSAGE_POST_PROGRESS:
6479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    result.mTask.onProgressUpdate(result.mData);
6489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    break;
6499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
6509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
6519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
6529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private static abstract class WorkerRunnable<Params, Result> implements Callable<Result> {
6549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        Params[] mParams;
6559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
6569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    @SuppressWarnings({"RawUseOfParameterizedType"})
6589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    private static class AsyncTaskResult<Data> {
6599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        final AsyncTask mTask;
6609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        final Data[] mData;
6619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        AsyncTaskResult(AsyncTask task, Data... data) {
6639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            mTask = task;
6649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            mData = data;
6659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
6669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
6679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
668