diff options
Diffstat (limited to 'main/src/cgeo/geocaching')
29 files changed, 268 insertions, 371 deletions
diff --git a/main/src/cgeo/geocaching/AbstractPopupActivity.java b/main/src/cgeo/geocaching/AbstractPopupActivity.java index 82543b0..683579f 100644 --- a/main/src/cgeo/geocaching/AbstractPopupActivity.java +++ b/main/src/cgeo/geocaching/AbstractPopupActivity.java @@ -14,13 +14,12 @@ import cgeo.geocaching.settings.Settings; import cgeo.geocaching.ui.CacheDetailsCreator; import cgeo.geocaching.ui.LoggingUI; import cgeo.geocaching.utils.Log; +import cgeo.geocaching.utils.RxUtils; import org.apache.commons.lang3.StringUtils; import rx.Observable; -import rx.android.observables.AndroidObservable; import rx.functions.Action1; import rx.functions.Func0; -import rx.schedulers.Schedulers; import android.graphics.Rect; import android.os.Bundle; @@ -80,13 +79,13 @@ public abstract class AbstractPopupActivity extends AbstractActivity implements if (!cache.supportsGCVote()) { return; } - AndroidObservable.bindActivity(this, Observable.defer(new Func0<Observable<GCVoteRating>>() { + RxUtils.subscribeOnIOThenUI(Observable.defer(new Func0<Observable<GCVoteRating>>() { @Override public Observable<GCVoteRating> call() { final GCVoteRating rating = GCVote.getRating(cache.getGuid(), geocode); return rating != null ? Observable.just(rating) : Observable.<GCVoteRating>empty(); } - }).subscribeOn(Schedulers.io())).subscribe(new Action1<GCVoteRating>() { + }), new Action1<GCVoteRating>() { @Override public void call(final GCVoteRating rating) { cache.setRating(rating.getRating()); diff --git a/main/src/cgeo/geocaching/CacheDetailActivity.java b/main/src/cgeo/geocaching/CacheDetailActivity.java index f525955..0f86de6 100644 --- a/main/src/cgeo/geocaching/CacheDetailActivity.java +++ b/main/src/cgeo/geocaching/CacheDetailActivity.java @@ -45,6 +45,7 @@ import cgeo.geocaching.utils.CryptUtils; import cgeo.geocaching.utils.ImageUtils; import cgeo.geocaching.utils.Log; import cgeo.geocaching.utils.MatcherWrapper; +import cgeo.geocaching.utils.RxUtils; import cgeo.geocaching.utils.SimpleCancellableHandler; import cgeo.geocaching.utils.SimpleHandler; import cgeo.geocaching.utils.TextUtils; @@ -61,7 +62,6 @@ import rx.Observer; import rx.Scheduler.Inner; import rx.Subscriber; import rx.Subscription; -import rx.android.observables.AndroidObservable; import rx.functions.Action1; import rx.schedulers.Schedulers; @@ -878,7 +878,7 @@ public class CacheDetailActivity extends AbstractViewPagerActivity<CacheDetailAc view = (ScrollView) getLayoutInflater().inflate(R.layout.cachedetail_details_page, null); // Start loading preview map - AndroidObservable.bindActivity(CacheDetailActivity.this, previewMap.subscribeOn(Schedulers.io())).subscribe(new Action1<BitmapDrawable>() { + RxUtils.subscribeOnIOThenUI(previewMap, new Action1<BitmapDrawable>() { @Override public void call(final BitmapDrawable image) { final Bitmap bitmap = image.getBitmap(); @@ -1605,71 +1605,70 @@ public class CacheDetailActivity extends AbstractViewPagerActivity<CacheDetailAc } }); - AndroidObservable.bindActivity(this, producer.subscribeOn(Schedulers.io())) - .subscribe(new Observer<Spanned>() { - @Override - public void onCompleted() { - if (null != loadingIndicatorView) { - loadingIndicatorView.setVisibility(View.GONE); - } - } + RxUtils.subscribeOnIOThenUI(producer, new Observer<Spanned>() { + @Override + public void onCompleted() { + if (null != loadingIndicatorView) { + loadingIndicatorView.setVisibility(View.GONE); + } + } - @Override - public void onError(final Throwable throwable) { - showToast(res.getString(R.string.err_load_descr_failed)); - } + @Override + public void onError(final Throwable throwable) { + showToast(res.getString(R.string.err_load_descr_failed)); + } - @Override - public void onNext(final Spanned description) { - if (StringUtils.isNotBlank(descriptionString)) { - try { - descriptionView.setText(description, TextView.BufferType.SPANNABLE); - } catch (final Exception e) { - // On 4.1, there is sometimes a crash on measuring the layout: https://code.google.com/p/android/issues/detail?id=35412 - Log.e("Android bug setting text: ", e); - // remove the formatting by converting to a simple string - descriptionView.setText(description.toString()); - } - descriptionView.setMovementMethod(AnchorAwareLinkMovementMethod.getInstance()); - fixTextColor(descriptionString); - descriptionView.setVisibility(View.VISIBLE); - registerForContextMenu(descriptionView); + @Override + public void onNext(final Spanned description) { + if (StringUtils.isNotBlank(descriptionString)) { + try { + descriptionView.setText(description, TextView.BufferType.SPANNABLE); + } catch (final Exception e) { + // On 4.1, there is sometimes a crash on measuring the layout: https://code.google.com/p/android/issues/detail?id=35412 + Log.e("Android bug setting text: ", e); + // remove the formatting by converting to a simple string + descriptionView.setText(description.toString()); + } + descriptionView.setMovementMethod(AnchorAwareLinkMovementMethod.getInstance()); + fixTextColor(descriptionString); + descriptionView.setVisibility(View.VISIBLE); + registerForContextMenu(descriptionView); + } + } + + /** + * Handle caches with black font color in dark skin and white font color in light skin + * by changing background color of the view + * + * @param text + * to be checked + */ + private void fixTextColor(final String text) { + int backcolor; + if (Settings.isLightSkin()) { + backcolor = color.white; + + for (final Pattern pattern : LIGHT_COLOR_PATTERNS) { + final MatcherWrapper matcher = new MatcherWrapper(pattern, text); + if (matcher.find()) { + descriptionView.setBackgroundResource(color.darker_gray); + return; } } + } else { + backcolor = color.black; - /** - * Handle caches with black font color in dark skin and white font color in light skin - * by changing background color of the view - * - * @param text - * to be checked - */ - private void fixTextColor(final String text) { - int backcolor; - if (Settings.isLightSkin()) { - backcolor = color.white; - - for (final Pattern pattern : LIGHT_COLOR_PATTERNS) { - final MatcherWrapper matcher = new MatcherWrapper(pattern, text); - if (matcher.find()) { - descriptionView.setBackgroundResource(color.darker_gray); - return; - } - } - } else { - backcolor = color.black; - - for (final Pattern pattern : DARK_COLOR_PATTERNS) { - final MatcherWrapper matcher = new MatcherWrapper(pattern, text); - if (matcher.find()) { - descriptionView.setBackgroundResource(color.darker_gray); - return; - } - } + for (final Pattern pattern : DARK_COLOR_PATTERNS) { + final MatcherWrapper matcher = new MatcherWrapper(pattern, text); + if (matcher.find()) { + descriptionView.setBackgroundResource(color.darker_gray); + return; } - descriptionView.setBackgroundResource(backcolor); } - }); + } + descriptionView.setBackgroundResource(backcolor); + } + }); } private class WaypointsViewCreator extends AbstractCachingPageViewCreator<ListView> { diff --git a/main/src/cgeo/geocaching/CgeoApplication.java b/main/src/cgeo/geocaching/CgeoApplication.java index eda8420..09aee93 100644 --- a/main/src/cgeo/geocaching/CgeoApplication.java +++ b/main/src/cgeo/geocaching/CgeoApplication.java @@ -42,7 +42,7 @@ public class CgeoApplication extends Application { public synchronized Observable<IGeoData> geoDataObservable() { if (geoDataObservable == null) { - final ConnectableObservable<IGeoData> onDemand = GeoDataProvider.create(this).publish(); + final ConnectableObservable<IGeoData> onDemand = GeoDataProvider.create(this).replay(1); onDemand.subscribe(new Action1<IGeoData>() { @Override public void call(final IGeoData geoData) { @@ -56,7 +56,7 @@ public class CgeoApplication extends Application { public synchronized Observable<Float> directionObservable() { if (directionObservable == null) { - final ConnectableObservable<Float> onDemand = DirectionProvider.create(this).publish(); + final ConnectableObservable<Float> onDemand = DirectionProvider.create(this).replay(1); onDemand.subscribe(new Action1<Float>() { @Override public void call(final Float direction) { diff --git a/main/src/cgeo/geocaching/DataStore.java b/main/src/cgeo/geocaching/DataStore.java index f627d7d..ee6c9ef 100644 --- a/main/src/cgeo/geocaching/DataStore.java +++ b/main/src/cgeo/geocaching/DataStore.java @@ -20,16 +20,15 @@ import cgeo.geocaching.settings.Settings; import cgeo.geocaching.ui.dialog.Dialogs; import cgeo.geocaching.utils.FileUtils; import cgeo.geocaching.utils.Log; +import cgeo.geocaching.utils.RxUtils; import org.apache.commons.collections4.CollectionUtils; import org.apache.commons.collections4.MapUtils; import org.apache.commons.lang3.StringUtils; import org.eclipse.jdt.annotation.NonNull; -import rx.android.observables.AndroidObservable; import rx.functions.Action1; import rx.functions.Func0; import rx.functions.Func1; -import rx.schedulers.Schedulers; import rx.util.async.Async; import android.app.Activity; @@ -393,7 +392,7 @@ public class DataStore { */ public static void moveDatabase(final Activity fromActivity) { final ProgressDialog dialog = ProgressDialog.show(fromActivity, fromActivity.getString(R.string.init_dbmove_dbmove), fromActivity.getString(R.string.init_dbmove_running), true, false); - AndroidObservable.bindActivity(fromActivity, Async.fromFunc0(new Func0<Boolean>() { + RxUtils.subscribeOnIOThenUI(Async.fromCallable(new Func0<Boolean>() { @Override public Boolean call() { if (!LocalStorage.isExternalStorageAvailable()) { @@ -418,7 +417,7 @@ public class DataStore { init(); return true; } - })).subscribeOn(Schedulers.io()).subscribe(new Action1<Boolean>() { + }), new Action1<Boolean>() { @Override public void call(final Boolean success) { dialog.dismiss(); diff --git a/main/src/cgeo/geocaching/MainActivity.java b/main/src/cgeo/geocaching/MainActivity.java index 3295d04..b82614b 100644 --- a/main/src/cgeo/geocaching/MainActivity.java +++ b/main/src/cgeo/geocaching/MainActivity.java @@ -21,6 +21,7 @@ import cgeo.geocaching.ui.Formatter; import cgeo.geocaching.ui.dialog.Dialogs; import cgeo.geocaching.utils.DatabaseBackupUtils; import cgeo.geocaching.utils.Log; +import cgeo.geocaching.utils.RxUtils; import cgeo.geocaching.utils.Version; import com.google.zxing.integration.android.IntentIntegrator; @@ -29,9 +30,7 @@ import org.apache.commons.lang3.StringUtils; import rx.Observable; import rx.Observable.OnSubscribe; import rx.Subscriber; -import rx.android.observables.AndroidObservable; import rx.functions.Action1; -import rx.schedulers.Schedulers; import rx.subscriptions.Subscriptions; import android.app.AlertDialog; @@ -551,10 +550,9 @@ public class MainActivity extends AbstractActivity { subscriber.onError(e); } } - }).subscribeOn(Schedulers.io()); - AndroidObservable.bindActivity(MainActivity.this, address) - .onErrorResumeNext(Observable.from(geo.getCoords().toString())) - .subscribe(new Action1<String>() { + }); + RxUtils.subscribeOnIOThenUI(address.onErrorResumeNext(Observable.from(geo.getCoords().toString())), + new Action1<String>() { @Override public void call(final String address) { navLocation.setText(address); diff --git a/main/src/cgeo/geocaching/PocketQueryList.java b/main/src/cgeo/geocaching/PocketQueryList.java index e624808..e748b29 100644 --- a/main/src/cgeo/geocaching/PocketQueryList.java +++ b/main/src/cgeo/geocaching/PocketQueryList.java @@ -2,13 +2,12 @@ package cgeo.geocaching; import cgeo.geocaching.activity.ActivityMixin; import cgeo.geocaching.connector.gc.GCParser; +import cgeo.geocaching.utils.RxUtils; import org.apache.commons.collections4.CollectionUtils; import rx.Observable; import rx.Observable.OnSubscribe; import rx.Subscriber; -import rx.android.observables.AndroidObservable; -import rx.schedulers.Schedulers; import rx.functions.Action1; import android.app.Activity; @@ -46,13 +45,13 @@ public final class PocketQueryList { public static void promptForListSelection(final Activity activity, final Action1<PocketQueryList> runAfterwards) { final Dialog waitDialog = ProgressDialog.show(activity, activity.getString(R.string.search_pocket_title), activity.getString(R.string.search_pocket_loading), true, true); - AndroidObservable.bindActivity(activity, Observable.create(new OnSubscribe<List<PocketQueryList>>() { + RxUtils.subscribeOnIOThenUI(Observable.create(new OnSubscribe<List<PocketQueryList>>() { @Override public void call(final Subscriber<? super List<PocketQueryList>> subscriber) { subscriber.onNext(GCParser.searchPocketQueryList()); subscriber.onCompleted(); } - }).subscribeOn(Schedulers.io())).subscribe(new Action1<List<PocketQueryList>>() { + }), new Action1<List<PocketQueryList>>() { @Override public void call(final List<PocketQueryList> pocketQueryLists) { waitDialog.dismiss(); diff --git a/main/src/cgeo/geocaching/StatusFragment.java b/main/src/cgeo/geocaching/StatusFragment.java index 5229f1e..a59316f 100644 --- a/main/src/cgeo/geocaching/StatusFragment.java +++ b/main/src/cgeo/geocaching/StatusFragment.java @@ -3,9 +3,9 @@ package cgeo.geocaching; import cgeo.geocaching.network.StatusUpdater; import cgeo.geocaching.network.StatusUpdater.Status; import cgeo.geocaching.utils.Log; +import cgeo.geocaching.utils.RxUtils; import rx.Subscription; -import rx.android.observables.AndroidObservable; import rx.functions.Action1; import android.content.Intent; @@ -30,7 +30,7 @@ public class StatusFragment extends Fragment { final ViewGroup statusGroup = (ViewGroup) inflater.inflate(R.layout.status, container, false); final ImageView statusIcon = (ImageView) statusGroup.findViewById(R.id.status_icon); final TextView statusMessage = (TextView) statusGroup.findViewById(R.id.status_message); - statusSubscription = AndroidObservable.bindFragment(this, StatusUpdater.latestStatus).subscribe(new Action1<Status>() { + statusSubscription = RxUtils.subscribeOnIOThenUI(StatusUpdater.latestStatus, new Action1<Status>() { @Override public void call(final Status status) { if (status == null) { diff --git a/main/src/cgeo/geocaching/TrackableActivity.java b/main/src/cgeo/geocaching/TrackableActivity.java index 11f19f5..a14a397 100644 --- a/main/src/cgeo/geocaching/TrackableActivity.java +++ b/main/src/cgeo/geocaching/TrackableActivity.java @@ -20,12 +20,12 @@ import cgeo.geocaching.ui.UserNameClickListener; import cgeo.geocaching.ui.logs.TrackableLogsViewCreator; import cgeo.geocaching.utils.HtmlUtils; import cgeo.geocaching.utils.Log; +import cgeo.geocaching.utils.RxUtils; import cgeo.geocaching.utils.UnknownTagsHandler; import org.apache.commons.lang3.StringUtils; import org.apache.commons.lang3.tuple.ImmutablePair; import org.apache.commons.lang3.tuple.Pair; -import rx.android.observables.AndroidObservable; import rx.android.observables.ViewObservable; import rx.functions.Action1; @@ -524,14 +524,12 @@ public class TrackableActivity extends AbstractViewPagerActivity<TrackableActivi } }); - AndroidObservable.bindActivity(TrackableActivity.this, - new HtmlImage(geocode, true, 0, false).fetchDrawable(trackable.getImage())) - .subscribe(new Action1<BitmapDrawable>() { - @Override - public void call(final BitmapDrawable bitmapDrawable) { - trackableImage.setImageDrawable(bitmapDrawable); - } - }); + RxUtils.subscribeThenUI(new HtmlImage(geocode, true, 0, false).fetchDrawable(trackable.getImage()), new Action1<BitmapDrawable>() { + @Override + public void call(final BitmapDrawable bitmapDrawable) { + trackableImage.setImageDrawable(bitmapDrawable); + } + }); imageView.addView(trackableImage); } diff --git a/main/src/cgeo/geocaching/activity/AbstractActivity.java b/main/src/cgeo/geocaching/activity/AbstractActivity.java index fd83043..1ed9b9b 100644 --- a/main/src/cgeo/geocaching/activity/AbstractActivity.java +++ b/main/src/cgeo/geocaching/activity/AbstractActivity.java @@ -4,10 +4,10 @@ import butterknife.ButterKnife; import cgeo.geocaching.CgeoApplication; import cgeo.geocaching.R; -import cgeo.geocaching.compatibility.Compatibility; import cgeo.geocaching.network.Cookies; import cgeo.geocaching.settings.Settings; import cgeo.geocaching.utils.ClipboardUtils; +import cgeo.geocaching.utils.EditUtils; import cgeo.geocaching.utils.HtmlUtils; import cgeo.geocaching.utils.TranslationUtils; @@ -86,11 +86,16 @@ public abstract class AbstractActivity extends FragmentActivity implements IAbst } protected static void disableSuggestions(final EditText edit) { - Compatibility.disableSuggestions(edit); + EditUtils.disableSuggestions(edit); } protected void restartActivity() { - Compatibility.restartActivity(this); + final Intent intent = getIntent(); + overridePendingTransition(0, 0); + intent.addFlags(Intent.FLAG_ACTIVITY_NO_ANIMATION); + finish(); + overridePendingTransition(0, 0); + startActivity(intent); } @Override diff --git a/main/src/cgeo/geocaching/compatibility/AndroidLevel8.java b/main/src/cgeo/geocaching/compatibility/AndroidLevel8.java deleted file mode 100644 index 1189ff5..0000000 --- a/main/src/cgeo/geocaching/compatibility/AndroidLevel8.java +++ /dev/null @@ -1,41 +0,0 @@ -package cgeo.geocaching.compatibility; - -import cgeo.geocaching.utils.Log; - -import android.annotation.TargetApi; -import android.app.Activity; -import android.app.backup.BackupManager; -import android.os.Environment; -import android.view.Surface; - -import java.io.File; - -@TargetApi(8) -public class AndroidLevel8 implements AndroidLevel8Interface { - - @Override - public void dataChanged(final String name) { - Log.i("Requesting settings backup with settings manager"); - BackupManager.dataChanged(name); - } - - @Override - public int getRotationOffset(final Activity activity) { - switch (activity.getWindowManager().getDefaultDisplay().getRotation()) { - case Surface.ROTATION_90: - return 90; - case Surface.ROTATION_180: - return 180; - case Surface.ROTATION_270: - return 270; - default: - return 0; - } - } - - @Override - public File getExternalPictureDir() { - return Environment.getExternalStoragePublicDirectory( - Environment.DIRECTORY_PICTURES); - } -} diff --git a/main/src/cgeo/geocaching/compatibility/AndroidLevel8Emulation.java b/main/src/cgeo/geocaching/compatibility/AndroidLevel8Emulation.java deleted file mode 100644 index 6d5781f..0000000 --- a/main/src/cgeo/geocaching/compatibility/AndroidLevel8Emulation.java +++ /dev/null @@ -1,38 +0,0 @@ -package cgeo.geocaching.compatibility; - -import android.annotation.TargetApi; -import android.app.Activity; -import android.content.res.Configuration; -import android.os.Environment; -import android.view.Display; - -import java.io.File; - -@TargetApi(value = 7) -public class AndroidLevel8Emulation implements AndroidLevel8Interface { - - @Override - public void dataChanged(final String name) { - // do nothing - } - - @Override - public int getRotationOffset(Activity activity) { - final Display display = activity.getWindowManager().getDefaultDisplay(); - - // the non deprecated method is available in API 8+ only, so we cannot deal better with this - @SuppressWarnings("deprecation") - final int rotation = display.getOrientation(); - - if (rotation == Configuration.ORIENTATION_LANDSCAPE) { - return 90; - } - return 0; - } - - @Override - public File getExternalPictureDir() { - // Use externalStorage/Pictures as default - return new File(Environment.getExternalStorageDirectory(), "Pictures"); - } -} diff --git a/main/src/cgeo/geocaching/compatibility/AndroidLevel8Interface.java b/main/src/cgeo/geocaching/compatibility/AndroidLevel8Interface.java deleted file mode 100644 index 2ba3708..0000000 --- a/main/src/cgeo/geocaching/compatibility/AndroidLevel8Interface.java +++ /dev/null @@ -1,11 +0,0 @@ -package cgeo.geocaching.compatibility; - -import android.app.Activity; - -import java.io.File; - -public interface AndroidLevel8Interface { - public void dataChanged(final String name); - public int getRotationOffset(final Activity activity); - public File getExternalPictureDir(); -}
\ No newline at end of file diff --git a/main/src/cgeo/geocaching/compatibility/Compatibility.java b/main/src/cgeo/geocaching/compatibility/Compatibility.java index 31c9e31..a293cfd 100644 --- a/main/src/cgeo/geocaching/compatibility/Compatibility.java +++ b/main/src/cgeo/geocaching/compatibility/Compatibility.java @@ -1,89 +1,25 @@ package cgeo.geocaching.compatibility; -import cgeo.geocaching.activity.AbstractActivity; -import cgeo.geocaching.utils.AngleUtils; -import cgeo.geocaching.utils.Log; - -import org.apache.commons.lang3.reflect.MethodUtils; import org.eclipse.jdt.annotation.NonNull; import android.app.Activity; -import android.content.Intent; import android.graphics.Point; import android.os.Build; -import android.text.InputType; -import android.widget.EditText; - -import java.io.File; public final class Compatibility { private final static int sdkVersion = Build.VERSION.SDK_INT; - private final static boolean isLevel8 = sdkVersion >= 8; - private final static boolean isLevel5 = sdkVersion >= 5; - private final static AndroidLevel8Interface level8; private final static AndroidLevel11Interface level11; private final static AndroidLevel13Interface level13; private final static AndroidLevel19Interface level19; static { - level8 = isLevel8 ? new AndroidLevel8() : new AndroidLevel8Emulation(); level11 = sdkVersion >= 11 ? new AndroidLevel11() : new AndroidLevel11Emulation(); level13 = sdkVersion >= 13 ? new AndroidLevel13() : new AndroidLevel13Emulation(); level19 = sdkVersion >= 19 ? new AndroidLevel19() : new AndroidLevel19Emulation(); } - /** - * Add 90, 180 or 270 degrees to the given rotation. - * - * @param directionNowPre - * the direction in degrees before adjustment - * @param activity - * the activity whose rotation is used to adjust the direction - * @return the adjusted direction, in the [0, 360[ range - */ - public static float getDirectionNow(final float directionNowPre, final Activity activity) { - return AngleUtils.normalize(directionNowPre + level8.getRotationOffset(activity)); - } - - public static void dataChanged(final String name) { - level8.dataChanged(name); - } - - public static void disableSuggestions(EditText edit) { - if (isLevel5) { - edit.setInputType(edit.getInputType() - | InputType.TYPE_TEXT_FLAG_NO_SUGGESTIONS - | InputType.TYPE_TEXT_VARIATION_FILTER); - } - else { - edit.setInputType(edit.getInputType() - | InputType.TYPE_TEXT_VARIATION_FILTER); - } - } - - private static void overridePendingTransition(final Activity activity, int enterAnim, int exitAnim) { - try { - MethodUtils.invokeMethod(activity, "overridePendingTransition", enterAnim, exitAnim); - } catch (Exception e) { - Log.e("cannot call overridePendingTransition", e); - } - } - - public static void restartActivity(AbstractActivity activity) { - final Intent intent = activity.getIntent(); - if (isLevel5) { - overridePendingTransition(activity, 0, 0); - intent.addFlags(Intent.FLAG_ACTIVITY_NO_ANIMATION); - } - activity.finish(); - if (isLevel5) { - overridePendingTransition(activity, 0, 0); - } - activity.startActivity(intent); - } - public static void invalidateOptionsMenu(final Activity activity) { level11.invalidateOptionsMenu(activity); } @@ -96,10 +32,6 @@ public final class Compatibility { return level13.getDisplaySize(); } - public static File getExternalPictureDir() { - return level8.getExternalPictureDir(); - } - public static void importGpxFromStorageAccessFramework(final @NonNull Activity activity, int requestCodeImportGpx) { level19.importGpxFromStorageAccessFramework(activity, requestCodeImportGpx); } diff --git a/main/src/cgeo/geocaching/connector/gc/RecaptchaHandler.java b/main/src/cgeo/geocaching/connector/gc/RecaptchaHandler.java index 934cc88..280069f 100644 --- a/main/src/cgeo/geocaching/connector/gc/RecaptchaHandler.java +++ b/main/src/cgeo/geocaching/connector/gc/RecaptchaHandler.java @@ -4,12 +4,10 @@ import cgeo.geocaching.R; import cgeo.geocaching.loaders.RecaptchaReceiver; import cgeo.geocaching.network.Network; import cgeo.geocaching.utils.Log; +import cgeo.geocaching.utils.RxUtils; import org.apache.commons.io.IOUtils; - import rx.Observable; -import rx.android.observables.AndroidObservable; -import rx.schedulers.Schedulers; import rx.functions.Action1; import rx.functions.Func0; @@ -39,17 +37,36 @@ public class RecaptchaHandler extends Handler { } private void loadChallenge(final ImageView imageView, final View reloadButton) { - getCaptcha().subscribe(new Action1<Bitmap>() { + final Observable<Bitmap> captcha = Observable.defer(new Func0<Observable<? extends Bitmap>>() { + @Override + public Observable<? extends Bitmap> call() { + final String url = "http://www.google.com/recaptcha/api/image?c=" + recaptchaReceiver.getChallenge(); + final InputStream is = Network.getResponseStream(Network.getRequest(url)); + if (is != null) { + try { + final Bitmap img = BitmapFactory.decodeStream(is); + return Observable.from(img); + } catch (final Exception e) { + Log.e("RecaptchaHandler.getCaptcha", e); + return Observable.error(e); + } finally { + IOUtils.closeQuietly(is); + } + } + return Observable.empty(); + } + }); + RxUtils.subscribeOnIOThenUI(captcha, new Action1<Bitmap>() { @Override public void call(final Bitmap bitmap) { imageView.setImageBitmap(bitmap); } }, new Action1<Throwable>() { - @Override - public void call(final Throwable throwable) { - // Do nothing - } - }); + @Override + public void call(final Throwable throwable) { + // Do nothing + } + }); reloadButton.setEnabled(true); } @@ -88,27 +105,4 @@ public class RecaptchaHandler extends Handler { } } - private Observable<Bitmap> getCaptcha() { - return AndroidObservable.bindActivity(activity, - Observable.defer(new Func0<Observable<? extends Bitmap>>() { - @Override - public Observable<? extends Bitmap> call() { - final String url = "http://www.google.com/recaptcha/api/image?c=" + recaptchaReceiver.getChallenge(); - final InputStream is = Network.getResponseStream(Network.getRequest(url)); - if (is != null) { - try { - final Bitmap img = BitmapFactory.decodeStream(is); - return Observable.from(img); - } catch (final Exception e) { - Log.e("RecaptchaHandler.getCaptcha", e); - return Observable.error(e); - } finally { - IOUtils.closeQuietly(is); - } - } - return Observable.empty(); - } - }).subscribeOn(Schedulers.io())); - } - } diff --git a/main/src/cgeo/geocaching/network/HtmlImage.java b/main/src/cgeo/geocaching/network/HtmlImage.java index 5d713eb..bde85ee 100644 --- a/main/src/cgeo/geocaching/network/HtmlImage.java +++ b/main/src/cgeo/geocaching/network/HtmlImage.java @@ -10,6 +10,7 @@ import cgeo.geocaching.utils.CancellableHandler; import cgeo.geocaching.utils.FileUtils; import cgeo.geocaching.utils.ImageUtils; import cgeo.geocaching.utils.Log; +import cgeo.geocaching.utils.RxUtils; import ch.boye.httpclientandroidlib.HttpResponse; import ch.boye.httpclientandroidlib.androidextra.Base64; @@ -127,9 +128,8 @@ public class HtmlImage implements Html.ImageGetter { return drawable.toBlockingObservable().lastOrDefault(null); } - // Caches are loaded from disk on Schedulers.computation() to avoid using more threads than processors - // on the phone while decoding the image. Downloads happen on downloadScheduler, in parallel with image - // decoding. + // Caches are loaded from disk on a computation scheduler to avoid using more threads than cores while decoding + // the image. Downloads happen on downloadScheduler, in parallel with image decoding. public Observable<BitmapDrawable> fetchDrawable(final String url) { if (StringUtils.isBlank(url) || ImageUtils.containsPattern(url, BLOCKED)) { @@ -143,7 +143,7 @@ public class HtmlImage implements Html.ImageGetter { @Override public void call(final Subscriber<? super BitmapDrawable> subscriber) { subscription.add(subscriber); - subscriber.add(Schedulers.computation().schedule(new Action1<Inner>() { + subscriber.add(RxUtils.computationScheduler.schedule(new Action1<Inner>() { @Override public void call(final Inner inner) { final Pair<BitmapDrawable, Boolean> loaded = loadFromDisk(); @@ -195,7 +195,7 @@ public class HtmlImage implements Html.ImageGetter { if (onlySave) { subscriber.onCompleted(); } else { - Schedulers.computation().schedule(new Action1<Inner>() { + RxUtils.computationScheduler.schedule(new Action1<Inner>() { @Override public void call(final Inner inner) { final Pair<BitmapDrawable, Boolean> loaded = loadFromDisk(); diff --git a/main/src/cgeo/geocaching/search/AutoCompleteAdapter.java b/main/src/cgeo/geocaching/search/AutoCompleteAdapter.java index 885ed48..45559f4 100644 --- a/main/src/cgeo/geocaching/search/AutoCompleteAdapter.java +++ b/main/src/cgeo/geocaching/search/AutoCompleteAdapter.java @@ -1,7 +1,6 @@ package cgeo.geocaching.search; import org.apache.commons.lang3.StringUtils; - import rx.functions.Func1; import android.content.Context; @@ -36,7 +35,7 @@ public class AutoCompleteAdapter extends ArrayAdapter<String> { @Override public Filter getFilter() { - Filter filter = new Filter() { + return new Filter() { @Override protected FilterResults performFiltering(CharSequence constraint) { @@ -67,6 +66,5 @@ public class AutoCompleteAdapter extends ArrayAdapter<String> { } } }; - return filter; } }
\ No newline at end of file diff --git a/main/src/cgeo/geocaching/sensors/DirectionProvider.java b/main/src/cgeo/geocaching/sensors/DirectionProvider.java index 4f11a35..788d5bd 100644 --- a/main/src/cgeo/geocaching/sensors/DirectionProvider.java +++ b/main/src/cgeo/geocaching/sensors/DirectionProvider.java @@ -28,8 +28,8 @@ public class DirectionProvider { static class Listener implements SensorEventListener, StartableHandlerThread.Callback { private int count = 0; - private SensorManager sensorManager; + private SensorManager sensorManager; @Override public void onSensorChanged(final SensorEvent event) { subject.onNext(event.values[0]); @@ -71,10 +71,10 @@ public class DirectionProvider { private static final StartableHandlerThread handlerThread = new StartableHandlerThread("DirectionProvider thread", Process.THREAD_PRIORITY_BACKGROUND, new Listener()); + static { handlerThread.start(); } - static public Observable<Float> create(final Context context) { return Observable.create(new OnSubscribe<Float>() { @Override diff --git a/main/src/cgeo/geocaching/sensors/GeoDirHandler.java b/main/src/cgeo/geocaching/sensors/GeoDirHandler.java index dd61cb1..c10cb48 100644 --- a/main/src/cgeo/geocaching/sensors/GeoDirHandler.java +++ b/main/src/cgeo/geocaching/sensors/GeoDirHandler.java @@ -16,7 +16,7 @@ import rx.subscriptions.CompositeSubscription; * GeoData and Direction handler. * <p> * To use this class, override {@link #updateGeoDir(IGeoData, float)}. You need to start the handler using - * {@link #start()}. A good place to do so might be the {@code onResume} method of the Activity. Stop the Handler + * {@link #start(int)}. A good place to do so might be the {@code onResume} method of the Activity. Stop the Handler * accordingly in {@code onPause}. * * The direction is always relative to the top of the device (natural direction), and that it must diff --git a/main/src/cgeo/geocaching/settings/AbstractCheckCredentialsPreference.java b/main/src/cgeo/geocaching/settings/AbstractCheckCredentialsPreference.java index 8a9d1c7..298270b 100644 --- a/main/src/cgeo/geocaching/settings/AbstractCheckCredentialsPreference.java +++ b/main/src/cgeo/geocaching/settings/AbstractCheckCredentialsPreference.java @@ -5,13 +5,12 @@ import cgeo.geocaching.activity.ActivityMixin; import cgeo.geocaching.enumerations.StatusCode; import cgeo.geocaching.network.Cookies; import cgeo.geocaching.ui.dialog.Dialogs; +import cgeo.geocaching.utils.RxUtils; import org.apache.commons.lang3.StringUtils; import org.apache.commons.lang3.tuple.ImmutablePair; -import rx.android.observables.AndroidObservable; import rx.functions.Action1; import rx.functions.Func0; -import rx.schedulers.Schedulers; import rx.util.async.Async; import android.app.ProgressDialog; @@ -38,7 +37,7 @@ public abstract class AbstractCheckCredentialsPreference extends AbstractClickab protected abstract ImmutablePair<String, String> getCredentials(); - protected abstract ImmutablePair<StatusCode, Drawable> login(); + protected abstract ImmutablePair<StatusCode, ? extends Drawable> login(); private class LoginCheckClickListener implements OnPreferenceClickListener { final private SettingsActivity activity; @@ -65,14 +64,14 @@ public abstract class AbstractCheckCredentialsPreference extends AbstractClickab loginDialog.setCancelable(false); Cookies.clearCookies(); - AndroidObservable.bindActivity(activity, Async.start(new Func0<ImmutablePair<StatusCode, Drawable>>() { + RxUtils.subscribeOnIOThenUI(Async.start(new Func0<ImmutablePair<StatusCode, ? extends Drawable>>() { @Override - public ImmutablePair<StatusCode, Drawable> call() { + public ImmutablePair<StatusCode, ? extends Drawable> call() { return login(); } - }, Schedulers.io())).subscribe(new Action1<ImmutablePair<StatusCode, Drawable>>() { + }), new Action1<ImmutablePair<StatusCode, ? extends Drawable>>() { @Override - public void call(final ImmutablePair<StatusCode, Drawable> loginInfo) { + public void call(final ImmutablePair<StatusCode, ? extends Drawable> loginInfo) { loginDialog.dismiss(); if (loginInfo.getLeft() == StatusCode.NO_ERROR) { Dialogs.message(activity, R.string.init_login_popup, R.string.init_login_popup_ok, loginInfo.getRight()); @@ -81,7 +80,8 @@ public abstract class AbstractCheckCredentialsPreference extends AbstractClickab res.getString(R.string.init_login_popup_failed_reason) + " " + loginInfo.getLeft().getErrorString(res) - + "."); + + "." + ); } activity.initBasicMemberPreferences(); } diff --git a/main/src/cgeo/geocaching/settings/CheckGcCredentialsPreference.java b/main/src/cgeo/geocaching/settings/CheckGcCredentialsPreference.java index 8257fdd..2a05f47 100644 --- a/main/src/cgeo/geocaching/settings/CheckGcCredentialsPreference.java +++ b/main/src/cgeo/geocaching/settings/CheckGcCredentialsPreference.java @@ -25,14 +25,14 @@ public class CheckGcCredentialsPreference extends AbstractCheckCredentialsPrefer } @Override - protected ImmutablePair<StatusCode, Drawable> login() { + protected ImmutablePair<StatusCode, ? extends Drawable> login() { final StatusCode loginResult = GCLogin.getInstance().login(); switch (loginResult) { case NO_ERROR: GCLogin.detectGcCustomDate(); - return new ImmutablePair<StatusCode, Drawable>(StatusCode.NO_ERROR, GCLogin.getInstance().downloadAvatarAndGetMemberStatus()); + return ImmutablePair.of(StatusCode.NO_ERROR, GCLogin.getInstance().downloadAvatarAndGetMemberStatus()); default: - return new ImmutablePair<StatusCode, Drawable>(loginResult, null); + return ImmutablePair.of(loginResult, null); } } } diff --git a/main/src/cgeo/geocaching/settings/RegisterSend2CgeoPreference.java b/main/src/cgeo/geocaching/settings/RegisterSend2CgeoPreference.java index 49239bc..1b18438 100644 --- a/main/src/cgeo/geocaching/settings/RegisterSend2CgeoPreference.java +++ b/main/src/cgeo/geocaching/settings/RegisterSend2CgeoPreference.java @@ -6,14 +6,13 @@ import cgeo.geocaching.network.Network; import cgeo.geocaching.network.Parameters; import cgeo.geocaching.ui.dialog.Dialogs; import cgeo.geocaching.utils.Log; +import cgeo.geocaching.utils.RxUtils; import ch.boye.httpclientandroidlib.HttpResponse; import org.apache.commons.lang3.StringUtils; import rx.Observable; -import rx.android.observables.AndroidObservable; import rx.functions.Action1; import rx.functions.Func0; -import rx.schedulers.Schedulers; import android.app.ProgressDialog; import android.content.Context; @@ -53,30 +52,29 @@ public class RegisterSend2CgeoPreference extends AbstractClickablePreference { activity.getString(R.string.init_sendToCgeo_registering), true); progressDialog.setCancelable(false); - AndroidObservable.bindActivity(activity, - Observable.defer(new Func0<Observable<Integer>>() { - @Override - public Observable<Integer> call() { - final String nam = StringUtils.defaultString(deviceName); - final String cod = StringUtils.defaultString(deviceCode); - - final Parameters params = new Parameters("name", nam, "code", cod); - HttpResponse response = Network.getRequest("http://send2.cgeo.org/auth.html", params); - - if (response != null && response.getStatusLine().getStatusCode() == 200) { - //response was OK - final String[] strings = StringUtils.split(Network.getResponseData(response), ','); - Settings.setWebNameCode(nam, strings[0]); - try { - return Observable.from(Integer.parseInt(strings[1].trim())); - } catch (final Exception e) { - Log.e("RegisterSend2CgeoPreference", e); - } - } - - return Observable.empty(); + RxUtils.subscribeOnIOThenUI(Observable.defer(new Func0<Observable<Integer>>() { + @Override + public Observable<Integer> call() { + final String nam = StringUtils.defaultString(deviceName); + final String cod = StringUtils.defaultString(deviceCode); + + final Parameters params = new Parameters("name", nam, "code", cod); + HttpResponse response = Network.getRequest("http://send2.cgeo.org/auth.html", params); + + if (response != null && response.getStatusLine().getStatusCode() == 200) { + //response was OK + final String[] strings = StringUtils.split(Network.getResponseData(response), ','); + Settings.setWebNameCode(nam, strings[0]); + try { + return Observable.from(Integer.parseInt(strings[1].trim())); + } catch (final Exception e) { + Log.e("RegisterSend2CgeoPreference", e); } - }).firstOrDefault(0).subscribeOn(Schedulers.io())).subscribe(new Action1<Integer>() { + } + + return Observable.empty(); + } + }).firstOrDefault(0), new Action1<Integer>() { @Override public void call(final Integer pin) { progressDialog.dismiss(); diff --git a/main/src/cgeo/geocaching/settings/Settings.java b/main/src/cgeo/geocaching/settings/Settings.java index 6c3c984..59140ba 100644 --- a/main/src/cgeo/geocaching/settings/Settings.java +++ b/main/src/cgeo/geocaching/settings/Settings.java @@ -462,7 +462,7 @@ public class Settings { } public static CoordInputFormatEnum getCoordInputFormat() { - return CoordInputFormatEnum.fromInt(getInt(R.string.pref_coordinputformat, 0)); + return CoordInputFormatEnum.fromInt(getInt(R.string.pref_coordinputformat, CoordInputFormatEnum.Min.ordinal())); } public static void setCoordInputFormat(final CoordInputFormatEnum format) { diff --git a/main/src/cgeo/geocaching/settings/SettingsActivity.java b/main/src/cgeo/geocaching/settings/SettingsActivity.java index 76f48e2..8834a3b 100644 --- a/main/src/cgeo/geocaching/settings/SettingsActivity.java +++ b/main/src/cgeo/geocaching/settings/SettingsActivity.java @@ -8,7 +8,6 @@ import cgeo.geocaching.SelectMapfileActivity; import cgeo.geocaching.activity.ActivityMixin; import cgeo.geocaching.apps.cache.navi.NavigationAppFactory; import cgeo.geocaching.apps.cache.navi.NavigationAppFactory.NavigationAppsEnum; -import cgeo.geocaching.compatibility.Compatibility; import cgeo.geocaching.connector.gc.GCConnector; import cgeo.geocaching.connector.gc.GCLogin; import cgeo.geocaching.files.SimpleDirChooser; @@ -21,6 +20,7 @@ import org.apache.commons.lang3.StringUtils; import org.openintents.intents.FileManagerIntents; import android.app.ProgressDialog; +import android.app.backup.BackupManager; import android.content.Context; import android.content.Intent; import android.content.res.Resources; @@ -111,7 +111,8 @@ public class SettingsActivity extends PreferenceActivity { @Override protected void onPause() { - Compatibility.dataChanged(getPackageName()); + Log.i("Requesting settings backup with settings manager"); + BackupManager.dataChanged(getPackageName()); super.onPause(); } diff --git a/main/src/cgeo/geocaching/ui/CompassView.java b/main/src/cgeo/geocaching/ui/CompassView.java index eaaf711..f7111f7 100644 --- a/main/src/cgeo/geocaching/ui/CompassView.java +++ b/main/src/cgeo/geocaching/ui/CompassView.java @@ -16,7 +16,6 @@ import android.graphics.Canvas; import android.graphics.Paint; import android.graphics.PaintFlagsDrawFilter; import android.util.AttributeSet; -import android.util.FloatMath; import android.view.View; import java.util.concurrent.TimeUnit; @@ -158,19 +157,19 @@ public class CompassView extends View { * @return the new value */ static protected float smoothUpdate(float goal, float actual) { - final float diff = AngleUtils.difference(actual, goal); + final double diff = AngleUtils.difference(actual, goal); - float offset = 0; + double offset = 0; // If the difference is smaller than 1 degree, do nothing as it // causes the arrow to vibrate. Round away from 0. if (diff > 1.0) { - offset = FloatMath.ceil(diff / 10.0f); // for larger angles, rotate faster + offset = Math.ceil(diff / 10.0); // for larger angles, rotate faster } else if (diff < 1.0) { - offset = FloatMath.floor(diff / 10.0f); + offset = Math.floor(diff / 10.0); } - return AngleUtils.normalize(actual + offset); + return AngleUtils.normalize((float) (actual + offset)); } @Override diff --git a/main/src/cgeo/geocaching/ui/ImagesList.java b/main/src/cgeo/geocaching/ui/ImagesList.java index 31a61b5..d1b2a64 100644 --- a/main/src/cgeo/geocaching/ui/ImagesList.java +++ b/main/src/cgeo/geocaching/ui/ImagesList.java @@ -6,11 +6,11 @@ import cgeo.geocaching.files.LocalStorage; import cgeo.geocaching.list.StoredList; import cgeo.geocaching.network.HtmlImage; import cgeo.geocaching.utils.Log; +import cgeo.geocaching.utils.RxUtils; import org.apache.commons.io.IOUtils; import org.apache.commons.lang3.StringUtils; import rx.Subscription; -import rx.android.observables.AndroidObservable; import rx.functions.Action0; import rx.functions.Action1; import rx.subscriptions.CompositeSubscription; @@ -30,12 +30,14 @@ import android.view.ContextMenu; import android.view.LayoutInflater; import android.view.MenuItem; import android.view.View; +import android.webkit.MimeTypeMap; import android.widget.ImageView; import android.widget.LinearLayout; import android.widget.TextView; import java.io.BufferedOutputStream; import java.io.File; +import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.util.Collection; import java.util.LinkedList; @@ -116,13 +118,12 @@ public class ImagesList { final ImageView imageView = (ImageView) inflater.inflate(R.layout.image_item, null); assert(imageView != null); - subscriptions.add(AndroidObservable.bindActivity(activity, imgGetter.fetchDrawable(img.getUrl())) - .subscribe(new Action1<BitmapDrawable>() { - @Override - public void call(final BitmapDrawable image) { - display(imageView, image, img, rowView); - } - })); + subscriptions.add(RxUtils.subscribeThenUI(imgGetter.fetchDrawable(img.getUrl()), new Action1<BitmapDrawable>() { + @Override + public void call(final BitmapDrawable image) { + display(imageView, image, img, rowView); + } + })); rowView.addView(imageView); imagesView.addView(rowView); } @@ -141,7 +142,7 @@ public class ImagesList { imageView.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View arg0) { - viewImageInStandardApp(image); + viewImageInStandardApp(img, image); } }); activity.registerForContextMenu(imageView); @@ -181,7 +182,7 @@ public class ImagesList { public boolean onContextItemSelected(MenuItem item) { switch (item.getItemId()) { case R.id.image_open_file: - viewImageInStandardApp(currentDrawable); + viewImageInStandardApp(currentImage, currentDrawable); return true; case R.id.image_open_browser: if (currentImage != null) { @@ -193,26 +194,35 @@ public class ImagesList { } } - private void viewImageInStandardApp(final BitmapDrawable image) { + private static String mimeTypeForUrl(final String url) { + return StringUtils.defaultString(MimeTypeMap.getSingleton().getMimeTypeFromExtension(MimeTypeMap.getFileExtensionFromUrl(url)), "image/*"); + } + + private static File saveToTemporaryJPGFile(final BitmapDrawable image) throws FileNotFoundException { final File file = LocalStorage.getStorageFile(null, "temp.jpg", false, true); BufferedOutputStream stream = null; try { stream = new BufferedOutputStream(new FileOutputStream(file)); image.getBitmap().compress(CompressFormat.JPEG, 100, stream); - } catch (Exception e) { - Log.e("ImagesList.viewImageInStandardApp", e); - return; } finally { IOUtils.closeQuietly(stream); } + file.deleteOnExit(); + return file; + } - final Intent intent = new Intent(); - intent.setAction(android.content.Intent.ACTION_VIEW); - intent.setDataAndType(Uri.fromFile(file), "image/jpeg"); - activity.startActivity(intent); - - if (file.exists()) { - file.deleteOnExit(); + private void viewImageInStandardApp(final Image img, final BitmapDrawable image) { + try { + final Intent intent = new Intent().setAction(android.content.Intent.ACTION_VIEW); + final File file = LocalStorage.getStorageFile(geocode, img.getUrl(), true, true); + if (file.exists()) { + intent.setDataAndType(Uri.fromFile(file), mimeTypeForUrl(img.getUrl())); + } else { + intent.setDataAndType(Uri.fromFile(saveToTemporaryJPGFile(image)), "image/jpeg"); + } + activity.startActivity(intent); + } catch (Exception e) { + Log.e("ImagesList.viewImageInStandardApp", e); } } diff --git a/main/src/cgeo/geocaching/ui/dialog/CoordinatesInputDialog.java b/main/src/cgeo/geocaching/ui/dialog/CoordinatesInputDialog.java index c150434..cb52319 100644 --- a/main/src/cgeo/geocaching/ui/dialog/CoordinatesInputDialog.java +++ b/main/src/cgeo/geocaching/ui/dialog/CoordinatesInputDialog.java @@ -5,11 +5,11 @@ import cgeo.geocaching.sensors.IGeoData; import cgeo.geocaching.R; import cgeo.geocaching.activity.AbstractActivity; import cgeo.geocaching.activity.ActivityMixin; -import cgeo.geocaching.compatibility.Compatibility; import cgeo.geocaching.geopoint.Geopoint; import cgeo.geocaching.geopoint.GeopointFormatter; import cgeo.geocaching.settings.Settings; import cgeo.geocaching.settings.Settings.CoordInputFormatEnum; +import cgeo.geocaching.utils.EditUtils; import org.apache.commons.lang3.StringUtils; @@ -103,14 +103,14 @@ public class CoordinatesInputDialog extends NoTitleDialog { eLonSec.addTextChangedListener(new TextChanged(eLonSec)); eLonSub.addTextChangedListener(new TextChanged(eLonSub)); - Compatibility.disableSuggestions(eLatDeg); - Compatibility.disableSuggestions(eLatMin); - Compatibility.disableSuggestions(eLatSec); - Compatibility.disableSuggestions(eLatSub); - Compatibility.disableSuggestions(eLonDeg); - Compatibility.disableSuggestions(eLonMin); - Compatibility.disableSuggestions(eLonSec); - Compatibility.disableSuggestions(eLonSub); + EditUtils.disableSuggestions(eLatDeg); + EditUtils.disableSuggestions(eLatMin); + EditUtils.disableSuggestions(eLatSec); + EditUtils.disableSuggestions(eLatSub); + EditUtils.disableSuggestions(eLonDeg); + EditUtils.disableSuggestions(eLonMin); + EditUtils.disableSuggestions(eLonSec); + EditUtils.disableSuggestions(eLonSub); bLat.setOnClickListener(new ButtonClickListener()); bLon.setOnClickListener(new ButtonClickListener()); diff --git a/main/src/cgeo/geocaching/utils/EditUtils.java b/main/src/cgeo/geocaching/utils/EditUtils.java index d975df9..0bfe2ea 100644 --- a/main/src/cgeo/geocaching/utils/EditUtils.java +++ b/main/src/cgeo/geocaching/utils/EditUtils.java @@ -1,5 +1,6 @@ package cgeo.geocaching.utils; +import android.text.InputType; import android.view.KeyEvent; import android.view.View; import android.view.inputmethod.EditorInfo; @@ -41,4 +42,9 @@ public final class EditUtils { } + public static void disableSuggestions(EditText edit) { + edit.setInputType(edit.getInputType() + | InputType.TYPE_TEXT_FLAG_NO_SUGGESTIONS + | InputType.TYPE_TEXT_VARIATION_FILTER); + } } diff --git a/main/src/cgeo/geocaching/utils/ImageUtils.java b/main/src/cgeo/geocaching/utils/ImageUtils.java index 0d8bec8..aae0f14 100644 --- a/main/src/cgeo/geocaching/utils/ImageUtils.java +++ b/main/src/cgeo/geocaching/utils/ImageUtils.java @@ -15,6 +15,7 @@ import android.graphics.Rect; import android.graphics.drawable.BitmapDrawable; import android.media.ExifInterface; import android.net.Uri; +import android.os.Environment; import java.io.BufferedOutputStream; import java.io.File; @@ -202,8 +203,8 @@ public final class ImageUtils { public static File getOutputImageFile() { // To be safe, you should check that the SDCard is mounted // using Environment.getExternalStorageState() before doing this. + final File mediaStorageDir = new File(Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES), "cgeo"); - File mediaStorageDir = new File(Compatibility.getExternalPictureDir(), "cgeo"); // This location works best if you want the created images to be shared // between applications and persist after your app has been uninstalled. diff --git a/main/src/cgeo/geocaching/utils/RxUtils.java b/main/src/cgeo/geocaching/utils/RxUtils.java new file mode 100644 index 0000000..9926bab --- /dev/null +++ b/main/src/cgeo/geocaching/utils/RxUtils.java @@ -0,0 +1,51 @@ +package cgeo.geocaching.utils; + +import rx.Observable; +import rx.Observer; +import rx.Scheduler; +import rx.Subscription; +import rx.android.schedulers.AndroidSchedulers; +import rx.functions.Action1; +import rx.schedulers.Schedulers; + +import java.util.concurrent.LinkedBlockingQueue; +import java.util.concurrent.ThreadPoolExecutor; +import java.util.concurrent.TimeUnit; + +public class RxUtils { + + // Utility class, not to be instanciated + private RxUtils() {} + + final static private int cores = Runtime.getRuntime().availableProcessors(); + public final static Scheduler computationScheduler = Schedulers.executor(new ThreadPoolExecutor(1, cores, 5, TimeUnit.SECONDS, new LinkedBlockingQueue<Runnable>())); + + public static <T> Subscription subscribeThenUI(final Observable<T> observable, final Observer<T> observer) { + return observable.observeOn(AndroidSchedulers.mainThread()).subscribe(observer); + } + + public static <T> Subscription subscribeThenUI(final Observable<T> observable, final Action1<T> action) { + return observable.observeOn(AndroidSchedulers.mainThread()).subscribe(action); + } + + public static <T> Subscription subscribeThenUI(final Observable<T> observable, final Action1<T> action, final Action1<Throwable> onError) { + return observable.observeOn(AndroidSchedulers.mainThread()).subscribe(action, onError); + } + + public static <T> Observable<T> onIO(final Observable<T> observable) { + return observable.subscribeOn(Schedulers.io()); + } + + public static <T> Subscription subscribeOnIOThenUI(final Observable<T> observable, final Observer<T> observer) { + return subscribeThenUI(onIO(observable), observer); + } + + public static <T> Subscription subscribeOnIOThenUI(final Observable<T> observable, final Action1<T> action) { + return subscribeThenUI(onIO(observable), action); + } + + public static <T> Subscription subscribeOnIOThenUI(final Observable<T> observable, final Action1<T> action, final Action1<Throwable> onError) { + return subscribeThenUI(onIO(observable), action, onError); + } + +} |
