allow canceling offline download task

This commit is contained in:
Andrew Dolgov 2012-06-20 09:49:30 +04:00
parent e1afe38ef3
commit 4fb366178c
3 changed files with 102 additions and 26 deletions

View File

@ -133,4 +133,6 @@
<string name="attachment_view">View</string> <string name="attachment_view">View</string>
<string name="attachment_copy">Copy URL</string> <string name="attachment_copy">Copy URL</string>
<string name="justify_article_text">Justify article text</string> <string name="justify_article_text">Justify article text</string>
<string name="dialog_offline_sync_in_progress">Offline sync in progress</string>
<string name="dialog_offline_sync_stop">Stop syncing</string>
</resources> </resources>

View File

@ -49,7 +49,6 @@ import android.view.MenuItem;
import android.view.View; import android.view.View;
import android.view.ViewGroup; import android.view.ViewGroup;
import android.view.Window; import android.view.Window;
import android.view.animation.AnimationUtils;
import android.widget.AdapterView.AdapterContextMenuInfo; import android.widget.AdapterView.AdapterContextMenuInfo;
import android.widget.EditText; import android.widget.EditText;
import android.widget.SearchView; import android.widget.SearchView;
@ -87,7 +86,7 @@ public class MainActivity extends FragmentActivity implements OnlineServices {
private int m_apiLevel = 0; private int m_apiLevel = 0;
private boolean m_isLoggingIn = false; private boolean m_isLoggingIn = false;
private boolean m_isOffline = false; private boolean m_isOffline = false;
private boolean m_offlineModeReady = false; private int m_offlineModeStatus = 0;
private int m_selectedProduct = -1; private int m_selectedProduct = -1;
private SQLiteDatabase m_readableDb; private SQLiteDatabase m_readableDb;
@ -132,7 +131,7 @@ public class MainActivity extends FragmentActivity implements OnlineServices {
if (intent.getAction().equals(OfflineDownloadService.INTENT_ACTION_SUCCESS)) { if (intent.getAction().equals(OfflineDownloadService.INTENT_ACTION_SUCCESS)) {
m_offlineModeReady = true; m_offlineModeStatus = 2;
switchOffline(); switchOffline();
@ -381,7 +380,7 @@ public class MainActivity extends FragmentActivity implements OnlineServices {
} }
} }
private synchronized void refreshHeadlines() { /* private synchronized void refreshHeadlines() {
if (m_sessionId != null) { if (m_sessionId != null) {
HeadlinesFragment frag = (HeadlinesFragment) getSupportFragmentManager() HeadlinesFragment frag = (HeadlinesFragment) getSupportFragmentManager()
.findFragmentByTag(FRAG_HEADLINES); .findFragmentByTag(FRAG_HEADLINES);
@ -392,7 +391,7 @@ public class MainActivity extends FragmentActivity implements OnlineServices {
frag.refresh(true); frag.refresh(true);
} }
} }
} } */
private synchronized void refreshCategories() { private synchronized void refreshCategories() {
if (m_sessionId != null) { if (m_sessionId != null) {
@ -453,6 +452,12 @@ public class MainActivity extends FragmentActivity implements OnlineServices {
super.onCreate(savedInstanceState); super.onCreate(savedInstanceState);
if (OfflineDownloadService.INTENT_ACTION_CANCEL.equals(getIntent().getAction())) {
cancelOfflineSync();
}
//Log.d(TAG, "started with intent action=" + intentAction);
requestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS); requestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS);
m_themeName = m_prefs.getString("theme", "THEME_DARK"); m_themeName = m_prefs.getString("theme", "THEME_DARK");
@ -468,7 +473,7 @@ public class MainActivity extends FragmentActivity implements OnlineServices {
m_activeCategory = savedInstanceState m_activeCategory = savedInstanceState
.getParcelable("activeCategory"); .getParcelable("activeCategory");
m_apiLevel = savedInstanceState.getInt("apiLevel"); m_apiLevel = savedInstanceState.getInt("apiLevel");
m_offlineModeReady = savedInstanceState.getBoolean("offlineModeReady"); m_offlineModeStatus = savedInstanceState.getInt("offlineModeStatus");
} }
m_enableCats = m_prefs.getBoolean("enable_cats", false); m_enableCats = m_prefs.getBoolean("enable_cats", false);
@ -537,9 +542,8 @@ public class MainActivity extends FragmentActivity implements OnlineServices {
return m_writableDb; return m_writableDb;
} }
@SuppressWarnings("unchecked")
private void switchOffline() { private void switchOffline() {
if (m_offlineModeReady) { if (m_offlineModeStatus == 2) {
AlertDialog.Builder builder = new AlertDialog.Builder( AlertDialog.Builder builder = new AlertDialog.Builder(
MainActivity.this) MainActivity.this)
@ -549,6 +553,8 @@ public class MainActivity extends FragmentActivity implements OnlineServices {
public void onClick(DialogInterface dialog, public void onClick(DialogInterface dialog,
int which) { int which) {
m_offlineModeStatus = 0;
SharedPreferences localPrefs = getSharedPreferences("localprefs", Context.MODE_PRIVATE); SharedPreferences localPrefs = getSharedPreferences("localprefs", Context.MODE_PRIVATE);
SharedPreferences.Editor editor = localPrefs.edit(); SharedPreferences.Editor editor = localPrefs.edit();
editor.putBoolean("offline_mode_active", true); editor.putBoolean("offline_mode_active", true);
@ -565,14 +571,16 @@ public class MainActivity extends FragmentActivity implements OnlineServices {
new Dialog.OnClickListener() { new Dialog.OnClickListener() {
public void onClick(DialogInterface dialog, public void onClick(DialogInterface dialog,
int which) { int which) {
//
m_offlineModeStatus = 0;
} }
}); });
AlertDialog dlg = builder.create(); AlertDialog dlg = builder.create();
dlg.show(); dlg.show();
} else { } else if (m_offlineModeStatus == 0) {
AlertDialog.Builder builder = new AlertDialog.Builder(this) AlertDialog.Builder builder = new AlertDialog.Builder(this)
.setMessage(R.string.dialog_offline_switch_prompt) .setMessage(R.string.dialog_offline_switch_prompt)
@ -584,6 +592,8 @@ public class MainActivity extends FragmentActivity implements OnlineServices {
if (m_sessionId != null) { if (m_sessionId != null) {
Log.d(TAG, "offline: starting"); Log.d(TAG, "offline: starting");
m_offlineModeStatus = 1;
Intent intent = new Intent( Intent intent = new Intent(
MainActivity.this, MainActivity.this,
OfflineDownloadService.class); OfflineDownloadService.class);
@ -603,9 +613,44 @@ public class MainActivity extends FragmentActivity implements OnlineServices {
AlertDialog dlg = builder.create(); AlertDialog dlg = builder.create();
dlg.show(); dlg.show();
} else if (m_offlineModeStatus == 1) {
cancelOfflineSync();
} }
} }
private void cancelOfflineSync() {
AlertDialog.Builder builder = new AlertDialog.Builder(this)
.setMessage(R.string.dialog_offline_sync_in_progress)
.setPositiveButton(R.string.dialog_offline_sync_stop,
new Dialog.OnClickListener() {
public void onClick(DialogInterface dialog,
int which) {
if (m_sessionId != null) {
Log.d(TAG, "offline: stopping");
m_offlineModeStatus = 0;
Intent intent = new Intent(
MainActivity.this,
OfflineDownloadService.class);
stopService(intent);
}
}
})
.setNegativeButton(R.string.dialog_cancel,
new Dialog.OnClickListener() {
public void onClick(DialogInterface dialog,
int which) {
//
}
});
AlertDialog dlg = builder.create();
dlg.show();
}
private void switchOfflineSuccess() { private void switchOfflineSuccess() {
logout(); logout();
// setLoadingStatus(R.string.blank, false); // setLoadingStatus(R.string.blank, false);
@ -641,7 +686,7 @@ public class MainActivity extends FragmentActivity implements OnlineServices {
out.putBoolean("unreadArticlesOnly", m_unreadArticlesOnly); out.putBoolean("unreadArticlesOnly", m_unreadArticlesOnly);
out.putParcelable("activeCategory", m_activeCategory); out.putParcelable("activeCategory", m_activeCategory);
out.putInt("apiLevel", m_apiLevel); out.putInt("apiLevel", m_apiLevel);
out.putBoolean("offlineModeReady", m_offlineModeReady); out.putInt("offlineModeStatus", m_offlineModeStatus);
} }
@Override @Override
@ -1601,13 +1646,13 @@ public class MainActivity extends FragmentActivity implements OnlineServices {
ft.commit(); ft.commit();
} }
private Feed getActiveFeed() { /* private Feed getActiveFeed() {
return m_activeFeed; return m_activeFeed;
} }
private FeedCategory getActiveCategory() { private FeedCategory getActiveCategory() {
return m_activeCategory; return m_activeCategory;
} } */
private void logout() { private void logout() {
if (m_refreshTask != null) { if (m_refreshTask != null) {

View File

@ -24,13 +24,16 @@ import android.app.IntentService;
import android.app.Notification; import android.app.Notification;
import android.app.NotificationManager; import android.app.NotificationManager;
import android.app.PendingIntent; import android.app.PendingIntent;
import android.app.Service;
import android.content.Context; import android.content.Context;
import android.content.Intent; import android.content.Intent;
import android.content.SharedPreferences; import android.content.SharedPreferences;
import android.database.sqlite.SQLiteDatabase; import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteStatement; import android.database.sqlite.SQLiteStatement;
import android.os.Binder;
import android.os.Bundle; import android.os.Bundle;
import android.os.Environment; import android.os.Environment;
import android.os.IBinder;
import android.preference.PreferenceManager; import android.preference.PreferenceManager;
import android.provider.BaseColumns; import android.provider.BaseColumns;
import android.util.Log; import android.util.Log;
@ -39,14 +42,15 @@ import com.google.gson.Gson;
import com.google.gson.JsonElement; import com.google.gson.JsonElement;
import com.google.gson.reflect.TypeToken; import com.google.gson.reflect.TypeToken;
public class OfflineDownloadService extends IntentService { public class OfflineDownloadService extends Service {
private final String TAG = this.getClass().getSimpleName(); private final String TAG = this.getClass().getSimpleName();
public static final int NOTIFY_DOWNLOADING = 1; public static final int NOTIFY_DOWNLOADING = 1;
public static final String INTENT_ACTION_SUCCESS = "org.fox.ttrss.intent.action.DownloadComplete"; public static final String INTENT_ACTION_SUCCESS = "org.fox.ttrss.intent.action.DownloadComplete";
public static final String INTENT_ACTION_CANCEL = "org.fox.ttrss.intent.action.Cancel";
private static final int OFFLINE_SYNC_SEQ = 60; private static final int OFFLINE_SYNC_SEQ = 40;
private static final int OFFLINE_SYNC_MAX = 500; private static final int OFFLINE_SYNC_MAX = 500;
private SQLiteDatabase m_writableDb; private SQLiteDatabase m_writableDb;
@ -59,10 +63,20 @@ public class OfflineDownloadService extends IntentService {
private boolean m_downloadImages = false; private boolean m_downloadImages = false;
private int m_syncMax; private int m_syncMax;
private SharedPreferences m_prefs; private SharedPreferences m_prefs;
private boolean m_canProceed = true;
public OfflineDownloadService() { private final IBinder m_binder = new LocalBinder();
super("OfflineDownloadService");
} public class LocalBinder extends Binder {
OfflineDownloadService getService() {
return OfflineDownloadService.this;
}
}
@Override
public IBinder onBind(Intent intent) {
return m_binder;
}
@Override @Override
public void onCreate() { public void onCreate() {
@ -81,8 +95,11 @@ public class OfflineDownloadService extends IntentService {
Notification notification = new Notification(R.drawable.icon, Notification notification = new Notification(R.drawable.icon,
getString(R.string.notify_downloading_title), System.currentTimeMillis()); getString(R.string.notify_downloading_title), System.currentTimeMillis());
Intent intent = new Intent(this, MainActivity.class);
intent.setAction(INTENT_ACTION_CANCEL);
PendingIntent contentIntent = PendingIntent.getActivity(this, 0, PendingIntent contentIntent = PendingIntent.getActivity(this, 0,
new Intent(this, MainActivity.class), 0); intent, 0);
notification.flags |= Notification.FLAG_ONGOING_EVENT; notification.flags |= Notification.FLAG_ONGOING_EVENT;
notification.flags |= Notification.FLAG_ONLY_ALERT_ONCE; notification.flags |= Notification.FLAG_ONLY_ALERT_ONCE;
@ -100,6 +117,8 @@ public class OfflineDownloadService extends IntentService {
m_readableDb.close(); m_readableDb.close();
m_writableDb.close(); m_writableDb.close();
m_nmgr.cancel(NOTIFY_DOWNLOADING);
// TODO send notification to activity? // TODO send notification to activity?
m_downloadInProgress = false; m_downloadInProgress = false;
@ -209,7 +228,11 @@ public class OfflineDownloadService extends IntentService {
getWritableDb().execSQL("DELETE FROM articles;"); getWritableDb().execSQL("DELETE FROM articles;");
downloadArticles(); if (m_canProceed) {
downloadArticles();
} else {
downloadFailed();
}
} catch (Exception e) { } catch (Exception e) {
e.printStackTrace(); e.printStackTrace();
updateNotification(R.string.offline_switch_error); updateNotification(R.string.offline_switch_error);
@ -240,9 +263,11 @@ public class OfflineDownloadService extends IntentService {
@Override @Override
public void onDestroy() { public void onDestroy() {
super.onDestroy(); super.onDestroy();
m_nmgr.cancel(NOTIFY_DOWNLOADING); m_nmgr.cancel(NOTIFY_DOWNLOADING);
m_canProceed = false;
Log.d(TAG, "onDestroy");
//m_readableDb.close(); //m_readableDb.close();
//m_writableDb.close(); //m_writableDb.close();
} }
@ -320,12 +345,16 @@ public class OfflineDownloadService extends IntentService {
//m_canGetMoreArticles = articles.size() == 30; //m_canGetMoreArticles = articles.size() == 30;
m_articleOffset += articles.size(); m_articleOffset += articles.size();
Log.d(TAG, "offline: received " + articles.size() + " articles"); Log.d(TAG, "offline: received " + articles.size() + " articles; canProc=" + m_canProceed);
if (articles.size() == OFFLINE_SYNC_SEQ && m_articleOffset < m_syncMax) { if (m_canProceed) {
downloadArticles(); if (articles.size() == OFFLINE_SYNC_SEQ && m_articleOffset < m_syncMax) {
downloadArticles();
} else {
downloadComplete();
}
} else { } else {
downloadComplete(); downloadFailed();
} }
return; return;
@ -346,7 +375,7 @@ public class OfflineDownloadService extends IntentService {
} }
@Override @Override
protected void onHandleIntent(Intent intent) { public void onStart(Intent intent, int startId) {
m_sessionId = intent.getStringExtra("sessionId"); m_sessionId = intent.getStringExtra("sessionId");
if (!m_downloadInProgress) { if (!m_downloadInProgress) {