From ca480d054dfa226e9904d4807ca1aba7b65b0bc1 Mon Sep 17 00:00:00 2001 From: M66B Date: Tue, 13 Aug 2019 10:27:17 +0200 Subject: [PATCH] Refactoring --- app/src/main/AndroidManifest.xml | 6 + .../eu/faircode/email/ActivityBilling.java | 126 ++++++++++-------- .../eu/faircode/email/ActivityCompose.java | 43 +----- .../java/eu/faircode/email/ActivitySetup.java | 23 ++-- .../java/eu/faircode/email/ActivityView.java | 32 ++--- .../eu/faircode/email/AdapterAccount.java | 2 +- .../java/eu/faircode/email/AdapterFolder.java | 7 +- .../eu/faircode/email/AdapterIdentity.java | 2 +- .../eu/faircode/email/AdapterMessage.java | 48 +++---- .../eu/faircode/email/AdapterNavFolder.java | 2 +- .../java/eu/faircode/email/AdapterRule.java | 2 +- app/src/main/java/eu/faircode/email/Core.java | 6 +- .../eu/faircode/email/FragmentAccount.java | 9 +- .../eu/faircode/email/FragmentCompose.java | 13 +- .../eu/faircode/email/FragmentIdentity.java | 8 +- .../eu/faircode/email/FragmentMessages.java | 28 ++-- .../faircode/email/FragmentOptionsMisc.java | 2 +- .../email/FragmentOptionsNotifications.java | 2 +- .../email/FragmentOptionsSynchronize.java | 2 +- .../java/eu/faircode/email/FragmentRule.java | 11 +- .../main/java/eu/faircode/email/Helper.java | 28 ++-- app/src/main/java/eu/faircode/email/Log.java | 2 +- .../eu/faircode/email/ServiceExternal.java | 2 +- .../eu/faircode/email/ServiceSynchronize.java | 2 +- .../java/eu/faircode/email/WidgetUnified.java | 4 +- app/src/main/res/layout/activity_billing.xml | 6 + 26 files changed, 183 insertions(+), 235 deletions(-) create mode 100644 app/src/main/res/layout/activity_billing.xml diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index 3c33dba1a7..0be02c078b 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -207,6 +207,12 @@ + + diff --git a/app/src/main/java/eu/faircode/email/ActivityBilling.java b/app/src/main/java/eu/faircode/email/ActivityBilling.java index 0a592d0bc4..2f93f84b3c 100644 --- a/app/src/main/java/eu/faircode/email/ActivityBilling.java +++ b/app/src/main/java/eu/faircode/email/ActivityBilling.java @@ -19,6 +19,7 @@ package eu.faircode.email; Copyright 2018-2019 by Marcel Bokhorst (M66B) */ +import android.annotation.SuppressLint; import android.content.BroadcastReceiver; import android.content.Context; import android.content.Intent; @@ -33,6 +34,8 @@ import android.widget.Toast; import androidx.annotation.NonNull; import androidx.annotation.Nullable; +import androidx.fragment.app.FragmentManager; +import androidx.fragment.app.FragmentTransaction; import androidx.lifecycle.Lifecycle; import androidx.lifecycle.LifecycleObserver; import androidx.lifecycle.LifecycleOwner; @@ -67,21 +70,35 @@ import java.util.HashMap; import java.util.List; import java.util.Map; -abstract class ActivityBilling extends ActivityBase implements PurchasesUpdatedListener { +public class ActivityBilling extends ActivityBase implements PurchasesUpdatedListener, FragmentManager.OnBackStackChangedListener { private BillingClient billingClient = null; private Map skuDetails = new HashMap<>(); private List listeners = new ArrayList<>(); static final String ACTION_PURCHASE = BuildConfig.APPLICATION_ID + ".ACTION_PURCHASE"; static final String ACTION_PURCHASE_CHECK = BuildConfig.APPLICATION_ID + ".ACTION_PURCHASE_CHECK"; - static final String ACTION_ACTIVATE_PRO = BuildConfig.APPLICATION_ID + ".ACTIVATE_PRO"; final static long MAX_SKU_CACHE_DURATION = 24 * 3600 * 1000L; // milliseconds @Override + @SuppressLint("MissingSuperCall") protected void onCreate(Bundle savedInstanceState) { + onCreate(savedInstanceState, true); + } + + protected void onCreate(Bundle savedInstanceState, boolean standalone) { super.onCreate(savedInstanceState); + if (standalone) { + setContentView(R.layout.activity_billing); + + FragmentTransaction fragmentTransaction = getSupportFragmentManager().beginTransaction(); + fragmentTransaction.replace(R.id.content_frame, new FragmentPro()).addToBackStack("pro"); + fragmentTransaction.commit(); + + getSupportFragmentManager().addOnBackStackChangedListener(this); + } + if (Helper.isPlayStoreInstall(this)) { Log.i("IAB start"); billingClient = BillingClient.newBuilder(this) @@ -92,6 +109,13 @@ abstract class ActivityBilling extends ActivityBase implements PurchasesUpdatedL } } + @Override + public void onBackStackChanged() { + int count = getSupportFragmentManager().getBackStackEntryCount(); + if (count == 0) + finish(); + } + @Override protected void onResume() { super.onResume(); @@ -100,7 +124,6 @@ abstract class ActivityBilling extends ActivityBase implements PurchasesUpdatedL IntentFilter iff = new IntentFilter(); iff.addAction(ACTION_PURCHASE); iff.addAction(ACTION_PURCHASE_CHECK); - iff.addAction(ACTION_ACTIVATE_PRO); lbm.registerReceiver(receiver, iff); if (billingClient != null && billingClient.isReady()) @@ -110,6 +133,7 @@ abstract class ActivityBilling extends ActivityBase implements PurchasesUpdatedL @Override protected void onPause() { super.onPause(); + LocalBroadcastManager lbm = LocalBroadcastManager.getInstance(this); lbm.unregisterReceiver(receiver); } @@ -118,6 +142,7 @@ abstract class ActivityBilling extends ActivityBase implements PurchasesUpdatedL protected void onDestroy() { if (billingClient != null) billingClient.endConnection(); + super.onDestroy(); } @@ -129,27 +154,42 @@ abstract class ActivityBilling extends ActivityBase implements PurchasesUpdatedL return BuildConfig.APPLICATION_ID + ".pro"; } - protected Intent getIntentPro() { - if (Helper.isPlayStoreInstall(this)) - return null; - - try { - Intent intent = new Intent(Intent.ACTION_VIEW); - intent.setData(Uri.parse(BuildConfig.PRO_FEATURES_URI + "?challenge=" + getChallenge())); - return intent; - } catch (NoSuchAlgorithmException ex) { - Log.e(ex); - return null; - } - } - - private String getChallenge() throws NoSuchAlgorithmException { - String android_id = Settings.Secure.getString(getContentResolver(), Settings.Secure.ANDROID_ID); + private static String getChallenge(Context context) throws NoSuchAlgorithmException { + String android_id = Settings.Secure.getString(context.getContentResolver(), Settings.Secure.ANDROID_ID); return Helper.sha256(android_id); } - private String getResponse() throws NoSuchAlgorithmException { - return Helper.sha256(BuildConfig.APPLICATION_ID + getChallenge()); + private static String getResponse(Context context) throws NoSuchAlgorithmException { + return Helper.sha256(BuildConfig.APPLICATION_ID + getChallenge(context)); + } + + static boolean activatePro(Context context, Uri data) throws NoSuchAlgorithmException { + String challenge = getChallenge(context); + String response = data.getQueryParameter("response"); + Log.i("IAB challenge=" + challenge); + Log.i("IAB response=" + response); + String expected = getResponse(context); + if (expected.equals(response)) { + Log.i("IAB response valid"); + + SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context); + prefs.edit() + .putBoolean("pro", true) + .putBoolean("play_store", false) + .apply(); + + WidgetUnified.update(context); + return true; + } else { + Log.i("IAB response invalid"); + return false; + } + } + + static boolean isPro(Context context) { + if (false && BuildConfig.DEBUG) + return true; + return PreferenceManager.getDefaultSharedPreferences(context).getBoolean("pro", false); } private BroadcastReceiver receiver = new BroadcastReceiver() { @@ -160,8 +200,6 @@ abstract class ActivityBilling extends ActivityBase implements PurchasesUpdatedL onPurchase(intent); else if (ACTION_PURCHASE_CHECK.equals(intent.getAction())) onPurchaseCheck(intent); - else if (ACTION_ACTIVATE_PRO.equals(intent.getAction())) - onActivatePro(intent); } } }; @@ -179,7 +217,14 @@ abstract class ActivityBilling extends ActivityBase implements PurchasesUpdatedL if (result.getResponseCode() != BillingClient.BillingResponseCode.OK) notifyError(text); } else - Helper.view(this, getIntentPro()); + try { + Intent view = new Intent(Intent.ACTION_VIEW); + view.setData(Uri.parse(BuildConfig.PRO_FEATURES_URI + "?challenge=" + getChallenge(this))); + Helper.view(this, view); + } catch (NoSuchAlgorithmException ex) { + Log.e(ex); + Helper.unexpectedError(getSupportFragmentManager(), ex); + } } private void onPurchaseCheck(Intent intent) { @@ -200,35 +245,6 @@ abstract class ActivityBilling extends ActivityBase implements PurchasesUpdatedL }); } - private void onActivatePro(Intent intent) { - try { - Uri data = intent.getParcelableExtra("uri"); - String challenge = getChallenge(); - String response = data.getQueryParameter("response"); - Log.i("IAB challenge=" + challenge); - Log.i("IAB response=" + response); - String expected = getResponse(); - if (expected.equals(response)) { - SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(this); - prefs.edit() - .putBoolean("pro", true) - .putBoolean("play_store", false) - .apply(); - - Log.i("IAB response valid"); - ToastEx.makeText(this, R.string.title_pro_valid, Toast.LENGTH_LONG).show(); - - WidgetUnified.update(this); - } else { - Log.i("IAB response invalid"); - ToastEx.makeText(this, R.string.title_pro_invalid, Toast.LENGTH_LONG).show(); - } - } catch (NoSuchAlgorithmException ex) { - Log.e(ex); - Helper.unexpectedError(getSupportFragmentManager(), ex); - } - } - private BillingClientStateListener billingClientStateListener = new BillingClientStateListener() { private int backoff = 4; // seconds @@ -303,10 +319,8 @@ abstract class ActivityBilling extends ActivityBase implements PurchasesUpdatedL if (billingClient.isReady()) { listener.onConnected(); queryPurchases(); - } else { + } else listener.onDisconnected(); - billingClient.startConnection(billingClientStateListener); - } owner.getLifecycle().addObserver(new LifecycleObserver() { @OnLifecycleEvent(Lifecycle.Event.ON_DESTROY) diff --git a/app/src/main/java/eu/faircode/email/ActivityCompose.java b/app/src/main/java/eu/faircode/email/ActivityCompose.java index f073642e3f..ed7b5120bc 100644 --- a/app/src/main/java/eu/faircode/email/ActivityCompose.java +++ b/app/src/main/java/eu/faircode/email/ActivityCompose.java @@ -19,10 +19,7 @@ package eu.faircode.email; Copyright 2018-2019 by Marcel Bokhorst (M66B) */ -import android.content.BroadcastReceiver; -import android.content.Context; import android.content.Intent; -import android.content.IntentFilter; import android.net.MailTo; import android.net.Uri; import android.os.Bundle; @@ -34,7 +31,6 @@ import androidx.core.app.TaskStackBuilder; import androidx.fragment.app.FragmentManager; import androidx.fragment.app.FragmentTransaction; import androidx.lifecycle.Lifecycle; -import androidx.localbroadcastmanager.content.LocalBroadcastManager; import org.jsoup.Jsoup; import org.jsoup.safety.Whitelist; @@ -44,11 +40,9 @@ import java.util.ArrayList; import javax.mail.internet.AddressException; import javax.mail.internet.InternetAddress; -public class ActivityCompose extends ActivityBilling implements FragmentManager.OnBackStackChangedListener { +public class ActivityCompose extends ActivityBase implements FragmentManager.OnBackStackChangedListener { static final int PI_REPLY = 1; - static final String ACTION_SHOW_PRO = BuildConfig.APPLICATION_ID + ".SHOW_PRO"; - @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); @@ -214,39 +208,4 @@ public class ActivityCompose extends ActivityBilling implements FragmentManager. return false; } } - - @Override - protected void onResume() { - super.onResume(); - LocalBroadcastManager lbm = LocalBroadcastManager.getInstance(this); - IntentFilter iff = new IntentFilter(); - iff.addAction(ACTION_SHOW_PRO); - lbm.registerReceiver(receiver, iff); - } - - @Override - protected void onPause() { - super.onPause(); - LocalBroadcastManager lbm = LocalBroadcastManager.getInstance(this); - lbm.unregisterReceiver(receiver); - } - - private BroadcastReceiver receiver = new BroadcastReceiver() { - @Override - public void onReceive(Context context, Intent intent) { - if (getLifecycle().getCurrentState().isAtLeast(Lifecycle.State.STARTED)) { - if (ACTION_SHOW_PRO.equals(intent.getAction())) - onShowPro(intent); - } - } - }; - - private void onShowPro(Intent intent) { - if (getLifecycle().getCurrentState().isAtLeast(Lifecycle.State.STARTED)) - getSupportFragmentManager().popBackStack("pro", FragmentManager.POP_BACK_STACK_INCLUSIVE); - - FragmentTransaction fragmentTransaction = getSupportFragmentManager().beginTransaction(); - fragmentTransaction.replace(R.id.content_frame, new FragmentPro()).addToBackStack("pro"); - fragmentTransaction.commit(); - } } diff --git a/app/src/main/java/eu/faircode/email/ActivitySetup.java b/app/src/main/java/eu/faircode/email/ActivitySetup.java index 48f74beef0..3acbccc47d 100644 --- a/app/src/main/java/eu/faircode/email/ActivitySetup.java +++ b/app/src/main/java/eu/faircode/email/ActivitySetup.java @@ -409,7 +409,7 @@ public class ActivitySetup extends ActivityBase implements FragmentManager.OnBac } private void onMenuExport() { - if (Helper.isPro(this)) { + if (ActivityBilling.isPro(this)) { try { askPassword(true); } catch (Throwable ex) { @@ -417,7 +417,7 @@ public class ActivitySetup extends ActivityBase implements FragmentManager.OnBac Helper.unexpectedError(getSupportFragmentManager(), ex); } } else - ToastEx.makeText(this, R.string.title_pro_feature, Toast.LENGTH_LONG).show(); + startActivity(new Intent(this, ActivityBilling.class)); } private void onMenuImport() { @@ -457,21 +457,20 @@ public class ActivitySetup extends ActivityBase implements FragmentManager.OnBac private void onMenuBiometrics() { final SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(ActivitySetup.this); final boolean biometrics = prefs.getBoolean("biometrics", false); - final boolean pro = Helper.isPro(this); + final boolean pro = ActivityBilling.isPro(this); Helper.authenticate(this, biometrics, new Runnable() { @Override public void run() { - if (pro) + if (pro) { prefs.edit().putBoolean("biometrics", !biometrics).apply(); - - ToastEx.makeText(ActivitySetup.this, - pro - ? biometrics - ? R.string.title_setup_biometrics_disable - : R.string.title_setup_biometrics_enable - : R.string.title_pro_feature, - Toast.LENGTH_LONG).show(); + ToastEx.makeText(ActivitySetup.this, + biometrics + ? R.string.title_setup_biometrics_disable + : R.string.title_setup_biometrics_enable, + Toast.LENGTH_LONG).show(); + } else + startActivity(new Intent(ActivitySetup.this, ActivityBilling.class)); } }, new Runnable() { @Override diff --git a/app/src/main/java/eu/faircode/email/ActivityView.java b/app/src/main/java/eu/faircode/email/ActivityView.java index 6466290149..a20463afc3 100644 --- a/app/src/main/java/eu/faircode/email/ActivityView.java +++ b/app/src/main/java/eu/faircode/email/ActivityView.java @@ -19,6 +19,7 @@ package eu.faircode.email; Copyright 2018-2019 by Marcel Bokhorst (M66B) */ +import android.annotation.SuppressLint; import android.app.Dialog; import android.app.NotificationManager; import android.app.PendingIntent; @@ -114,14 +115,14 @@ public class ActivityView extends ActivityBilling implements FragmentManager.OnB static final String ACTION_EDIT_ANSWER = BuildConfig.APPLICATION_ID + ".EDIT_ANSWER"; static final String ACTION_EDIT_RULES = BuildConfig.APPLICATION_ID + ".EDIT_RULES"; static final String ACTION_EDIT_RULE = BuildConfig.APPLICATION_ID + ".EDIT_RULE"; - static final String ACTION_SHOW_PRO = BuildConfig.APPLICATION_ID + ".SHOW_PRO"; private static final long EXIT_DELAY = 2500L; // milliseconds static final long UPDATE_INTERVAL = (BuildConfig.BETA_RELEASE ? 4 : 12) * 3600 * 1000L; // milliseconds @Override + @SuppressLint("MissingSuperCall") protected void onCreate(Bundle savedInstanceState) { - super.onCreate(savedInstanceState); + super.onCreate(savedInstanceState, false); if (savedInstanceState != null) searching = savedInstanceState.getBoolean("fair:searching"); @@ -341,14 +342,13 @@ public class ActivityView extends ActivityBilling implements FragmentManager.OnB } }).setSeparated()); - if (getIntentPro() == null || getIntentPro().resolveActivity(pm) != null) - extra.add(new NavMenuItem(R.drawable.baseline_monetization_on_24, R.string.menu_pro, new Runnable() { - @Override - public void run() { - drawerLayout.closeDrawer(drawerContainer); - onShowPro(null); - } - })); + extra.add(new NavMenuItem(R.drawable.baseline_monetization_on_24, R.string.menu_pro, new Runnable() { + @Override + public void run() { + drawerLayout.closeDrawer(drawerContainer); + startActivity(new Intent(ActivityView.this, ActivityBilling.class)); + } + })); if ((getIntentInvite(this).resolveActivity(pm) != null)) extra.add(new NavMenuItem(R.drawable.baseline_people_24, R.string.menu_invite, new Runnable() { @@ -560,7 +560,6 @@ public class ActivityView extends ActivityBilling implements FragmentManager.OnB iff.addAction(ACTION_EDIT_ANSWER); iff.addAction(ACTION_EDIT_RULES); iff.addAction(ACTION_EDIT_RULE); - iff.addAction(ACTION_SHOW_PRO); lbm.registerReceiver(receiver, iff); checkUpdate(false); @@ -990,8 +989,6 @@ public class ActivityView extends ActivityBilling implements FragmentManager.OnB onEditRules(intent); else if (ACTION_EDIT_RULE.equals(action)) onEditRule(intent); - else if (ACTION_SHOW_PRO.equals(action)) - onShowPro(intent); } } }; @@ -1093,15 +1090,6 @@ public class ActivityView extends ActivityBilling implements FragmentManager.OnB fragmentTransaction.commit(); } - private void onShowPro(Intent intent) { - if (getLifecycle().getCurrentState().isAtLeast(Lifecycle.State.STARTED)) - getSupportFragmentManager().popBackStack("pro", FragmentManager.POP_BACK_STACK_INCLUSIVE); - - FragmentTransaction fragmentTransaction = getSupportFragmentManager().beginTransaction(); - fragmentTransaction.replace(R.id.content_frame, new FragmentPro()).addToBackStack("pro"); - fragmentTransaction.commit(); - } - private class UpdateInfo { String tag_name; // version String html_url; diff --git a/app/src/main/java/eu/faircode/email/AdapterAccount.java b/app/src/main/java/eu/faircode/email/AdapterAccount.java index 7cd590d3dd..0e69015be4 100644 --- a/app/src/main/java/eu/faircode/email/AdapterAccount.java +++ b/app/src/main/java/eu/faircode/email/AdapterAccount.java @@ -125,7 +125,7 @@ public class AdapterAccount extends RecyclerView.Adapter 0) @@ -600,9 +600,8 @@ public class AdapterFolder extends RecyclerView.Adapter 0 ? R.drawable.baseline_star_24 : R.drawable.baseline_star_border_24); ivFlagged.setImageTintList(ColorStateList.valueOf(flagged > 0 - ? message.color == null || !Helper.isPro(context) + ? message.color == null || !ActivityBilling.isPro(context) ? colorAccent : message.color : textColorSecondary)); ivFlagged.setVisibility(flags && !message.folderReadOnly ? (message.uid == null ? View.INVISIBLE : View.VISIBLE) @@ -1319,9 +1321,8 @@ public class AdapterMessage extends RecyclerView.Adapter 0); popupMenu.getMenu().findItem(R.id.menu_reply_list).setVisible(data.message.list_post != null); popupMenu.getMenu().findItem(R.id.menu_reply_receipt).setVisible(data.message.receipt_to != null); - popupMenu.getMenu().findItem(R.id.menu_reply_answer).setVisible(answers != 0 || !Helper.isPro(context)); + popupMenu.getMenu().findItem(R.id.menu_reply_answer).setVisible(answers != 0 || !ActivityBilling.isPro(context)); popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() { @Override @@ -2908,9 +2913,8 @@ public class AdapterMessage extends RecyclerView.Adapter { popupMenu.getMenu().add(Menu.NONE, R.string.title_rule_enabled, 1, R.string.title_rule_enabled) .setCheckable(true).setChecked(rule.enabled); popupMenu.getMenu().add(Menu.NONE, R.string.title_rule_execute, 2, R.string.title_rule_execute) - .setEnabled(Helper.isPro(context)); + .setEnabled(ActivityBilling.isPro(context)); popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() { @Override diff --git a/app/src/main/java/eu/faircode/email/Core.java b/app/src/main/java/eu/faircode/email/Core.java index 0b801f997e..b9776e23bc 100644 --- a/app/src/main/java/eu/faircode/email/Core.java +++ b/app/src/main/java/eu/faircode/email/Core.java @@ -1737,7 +1737,7 @@ class Core { } private static void runRules(Context context, Message imessage, EntityMessage message, List rules) { - if (!Helper.isPro(context)) + if (!ActivityBilling.isPro(context)) return; DB db = DB.getInstance(context); @@ -1938,7 +1938,7 @@ class Core { SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context); boolean badge = prefs.getBoolean("badge", true); - boolean pro = Helper.isPro(context); + boolean pro = ActivityBilling.isPro(context); // Current int unseen = 0; @@ -2057,7 +2057,7 @@ class Core { if (messages == null || messages.size() == 0 || nm == null) return notifications; - boolean pro = Helper.isPro(context); + boolean pro = ActivityBilling.isPro(context); SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context); boolean biometrics = prefs.getBoolean("biometrics", false); diff --git a/app/src/main/java/eu/faircode/email/FragmentAccount.java b/app/src/main/java/eu/faircode/email/FragmentAccount.java index d48e5c3b3a..c580d12f06 100644 --- a/app/src/main/java/eu/faircode/email/FragmentAccount.java +++ b/app/src/main/java/eu/faircode/email/FragmentAccount.java @@ -49,7 +49,6 @@ import android.widget.RadioGroup; import android.widget.ScrollView; import android.widget.Spinner; import android.widget.TextView; -import android.widget.Toast; import androidx.annotation.NonNull; import androidx.annotation.Nullable; @@ -762,7 +761,7 @@ public class FragmentAccount extends FragmentBase { EntityFolder left = (EntityFolder) args.getSerializable("left"); EntityFolder right = (EntityFolder) args.getSerializable("right"); - boolean pro = Helper.isPro(context); + boolean pro = ActivityBilling.isPro(context); boolean should = args.getBoolean("should"); if (host.contains(":")) { @@ -1167,7 +1166,7 @@ public class FragmentAccount extends FragmentBase { etName.setText(account == null ? null : account.name); - boolean pro = Helper.isPro(getContext()); + boolean pro = ActivityBilling.isPro(getContext()); cbNotify.setChecked(account != null && account.notify && pro); cbNotify.setEnabled(pro); @@ -1292,11 +1291,11 @@ public class FragmentAccount extends FragmentBase { switch (requestCode) { case REQUEST_COLOR: if (resultCode == RESULT_OK && data != null) { - if (Helper.isPro(getContext())) { + if (ActivityBilling.isPro(getContext())) { Bundle args = data.getBundleExtra("args"); setColor(args.getInt("color")); } else - ToastEx.makeText(getContext(), R.string.title_pro_feature, Toast.LENGTH_LONG).show(); + startActivity(new Intent(getContext(), ActivityBilling.class)); } break; case REQUEST_SAVE: diff --git a/app/src/main/java/eu/faircode/email/FragmentCompose.java b/app/src/main/java/eu/faircode/email/FragmentCompose.java index 0bac6e84f9..0300ae5cb5 100644 --- a/app/src/main/java/eu/faircode/email/FragmentCompose.java +++ b/app/src/main/java/eu/faircode/email/FragmentCompose.java @@ -99,7 +99,6 @@ import androidx.core.content.FileProvider; import androidx.cursoradapter.widget.SimpleCursorAdapter; import androidx.lifecycle.Lifecycle; import androidx.lifecycle.Observer; -import androidx.localbroadcastmanager.content.LocalBroadcastManager; import androidx.preference.PreferenceManager; import androidx.recyclerview.widget.LinearLayoutManager; import androidx.recyclerview.widget.RecyclerView; @@ -903,9 +902,8 @@ public class FragmentCompose extends FragmentBase { } private void onMenuAnswer() { - if (!Helper.isPro(getContext())) { - LocalBroadcastManager lbm = LocalBroadcastManager.getInstance(getContext()); - lbm.sendBroadcast(new Intent(ActivityCompose.ACTION_SHOW_PRO)); + if (!ActivityBilling.isPro(getContext())) { + getContext().startActivity(new Intent(getContext(), ActivityBilling.class)); return; } @@ -1542,9 +1540,8 @@ public class FragmentCompose extends FragmentBase { } private void onSendAfter(long time) { - if (!Helper.isPro(getContext())) { - LocalBroadcastManager lbm = LocalBroadcastManager.getInstance(getContext()); - lbm.sendBroadcast(new Intent(ActivityCompose.ACTION_SHOW_PRO)); + if (!ActivityBilling.isPro(getContext())) { + getContext().startActivity(new Intent(getContext(), ActivityBilling.class)); return; } @@ -2499,7 +2496,7 @@ public class FragmentCompose extends FragmentBase { } }); } - }else { + } else { // Move draft to new account if (draft.account != aid && aid >= 0) { Log.i("Account changed"); diff --git a/app/src/main/java/eu/faircode/email/FragmentIdentity.java b/app/src/main/java/eu/faircode/email/FragmentIdentity.java index 80ece60d31..b350a37932 100644 --- a/app/src/main/java/eu/faircode/email/FragmentIdentity.java +++ b/app/src/main/java/eu/faircode/email/FragmentIdentity.java @@ -31,7 +31,6 @@ import android.os.Bundle; import android.os.Handler; import android.text.Editable; import android.text.SpannableStringBuilder; -import android.text.Spanned; import android.text.TextUtils; import android.text.TextWatcher; import android.text.method.LinkMovementMethod; @@ -53,7 +52,6 @@ import android.widget.RadioGroup; import android.widget.ScrollView; import android.widget.Spinner; import android.widget.TextView; -import android.widget.Toast; import androidx.annotation.NonNull; import androidx.annotation.Nullable; @@ -594,7 +592,7 @@ public class FragmentIdentity extends FragmentBase { if (TextUtils.isEmpty(bcc)) bcc = null; - if (color == Color.TRANSPARENT || !Helper.isPro(context)) + if (color == Color.TRANSPARENT || !ActivityBilling.isPro(context)) color = null; if (TextUtils.isEmpty(signature)) signature = null; @@ -1005,11 +1003,11 @@ public class FragmentIdentity extends FragmentBase { switch (requestCode) { case REQUEST_COLOR: if (resultCode == RESULT_OK && data != null) { - if (Helper.isPro(getContext())) { + if (ActivityBilling.isPro(getContext())) { Bundle args = data.getBundleExtra("args"); setColor(args.getInt("color")); } else - ToastEx.makeText(getContext(), R.string.title_pro_feature, Toast.LENGTH_LONG).show(); + startActivity(new Intent(getContext(), ActivityBilling.class)); } break; case REQUEST_SAVE: diff --git a/app/src/main/java/eu/faircode/email/FragmentMessages.java b/app/src/main/java/eu/faircode/email/FragmentMessages.java index 5c23eb9c2c..878ae2e919 100644 --- a/app/src/main/java/eu/faircode/email/FragmentMessages.java +++ b/app/src/main/java/eu/faircode/email/FragmentMessages.java @@ -372,8 +372,7 @@ public class FragmentMessages extends FragmentBase implements SharedPreferences. tvSupport.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { - LocalBroadcastManager lbm = LocalBroadcastManager.getInstance(getContext()); - lbm.sendBroadcast(new Intent(ActivityView.ACTION_SHOW_PRO)); + getContext().startActivity(new Intent(getContext(), ActivityBilling.class)); } }); @@ -3408,9 +3407,8 @@ public class FragmentMessages extends FragmentBase implements SharedPreferences. break; case REQUEST_MESSAGES_COLOR: if (resultCode == RESULT_OK && data != null) { - if (!Helper.isPro(getContext())) { - LocalBroadcastManager lbm = LocalBroadcastManager.getInstance(getContext()); - lbm.sendBroadcast(new Intent(ActivityView.ACTION_SHOW_PRO)); + if (!ActivityBilling.isPro(getContext())) { + getContext().startActivity(new Intent(getContext(), ActivityBilling.class)); return; } @@ -4007,9 +4005,8 @@ public class FragmentMessages extends FragmentBase implements SharedPreferences. } private void onColor(long id, int color) { - if (!Helper.isPro(getContext())) { - LocalBroadcastManager lbm = LocalBroadcastManager.getInstance(getContext()); - lbm.sendBroadcast(new Intent(ActivityView.ACTION_SHOW_PRO)); + if (!ActivityBilling.isPro(getContext())) { + getContext().startActivity(new Intent(getContext(), ActivityBilling.class)); return; } @@ -4045,9 +4042,8 @@ public class FragmentMessages extends FragmentBase implements SharedPreferences. } private void onSnooze(Bundle args) { - if (!Helper.isPro(getContext())) { - LocalBroadcastManager lbm = LocalBroadcastManager.getInstance(getContext()); - lbm.sendBroadcast(new Intent(ActivityView.ACTION_SHOW_PRO)); + if (!ActivityBilling.isPro(getContext())) { + getContext().startActivity(new Intent(getContext(), ActivityBilling.class)); return; } @@ -4099,9 +4095,8 @@ public class FragmentMessages extends FragmentBase implements SharedPreferences. } private void onSnoozeSelection(Bundle args) { - if (!Helper.isPro(getContext())) { - LocalBroadcastManager lbm = LocalBroadcastManager.getInstance(getContext()); - lbm.sendBroadcast(new Intent(ActivityView.ACTION_SHOW_PRO)); + if (!ActivityBilling.isPro(getContext())) { + getContext().startActivity(new Intent(getContext(), ActivityBilling.class)); return; } @@ -4322,9 +4317,8 @@ public class FragmentMessages extends FragmentBase implements SharedPreferences. static void search( final Context context, final LifecycleOwner owner, final FragmentManager manager, long folder, boolean server, String query) { - if (!Helper.isPro(context)) { - LocalBroadcastManager lbm = LocalBroadcastManager.getInstance(context); - lbm.sendBroadcast(new Intent(ActivityView.ACTION_SHOW_PRO)); + if (!ActivityBilling.isPro(context)) { + context.startActivity(new Intent(context, ActivityBilling.class)); return; } diff --git a/app/src/main/java/eu/faircode/email/FragmentOptionsMisc.java b/app/src/main/java/eu/faircode/email/FragmentOptionsMisc.java index bd9ee1a397..1433af99af 100644 --- a/app/src/main/java/eu/faircode/email/FragmentOptionsMisc.java +++ b/app/src/main/java/eu/faircode/email/FragmentOptionsMisc.java @@ -289,7 +289,7 @@ public class FragmentOptionsMisc extends FragmentBase implements SharedPreferenc swBadge.setChecked(prefs.getBoolean("badge", true)); - boolean pro = Helper.isPro(getContext()); + boolean pro = ActivityBilling.isPro(getContext()); swSubscriptions.setChecked(prefs.getBoolean("subscriptions", false) && pro); swSubscriptions.setEnabled(pro); swSubscribedOnly.setChecked(prefs.getBoolean("subscribed_only", false)); diff --git a/app/src/main/java/eu/faircode/email/FragmentOptionsNotifications.java b/app/src/main/java/eu/faircode/email/FragmentOptionsNotifications.java index 6a48c36520..bacfef5356 100644 --- a/app/src/main/java/eu/faircode/email/FragmentOptionsNotifications.java +++ b/app/src/main/java/eu/faircode/email/FragmentOptionsNotifications.java @@ -232,7 +232,7 @@ public class FragmentOptionsNotifications extends FragmentBase implements Shared } private void setOptions() { - boolean pro = Helper.isPro(getContext()); + boolean pro = ActivityBilling.isPro(getContext()); SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(getContext()); swNotifyPreview.setChecked(prefs.getBoolean("notify_preview", true)); diff --git a/app/src/main/java/eu/faircode/email/FragmentOptionsSynchronize.java b/app/src/main/java/eu/faircode/email/FragmentOptionsSynchronize.java index 0f432052a8..25afdc59f8 100644 --- a/app/src/main/java/eu/faircode/email/FragmentOptionsSynchronize.java +++ b/app/src/main/java/eu/faircode/email/FragmentOptionsSynchronize.java @@ -264,7 +264,7 @@ public class FragmentOptionsSynchronize extends FragmentBase implements SharedPr break; } - boolean pro = Helper.isPro(getContext()); + boolean pro = ActivityBilling.isPro(getContext()); swSchedule.setChecked(prefs.getBoolean("schedule", false) && pro); swSchedule.setEnabled(pro); tvScheduleStart.setText(formatHour(getContext(), prefs.getInt("schedule_start", 0))); diff --git a/app/src/main/java/eu/faircode/email/FragmentRule.java b/app/src/main/java/eu/faircode/email/FragmentRule.java index 90a4658fd5..e0be0950e1 100644 --- a/app/src/main/java/eu/faircode/email/FragmentRule.java +++ b/app/src/main/java/eu/faircode/email/FragmentRule.java @@ -57,7 +57,6 @@ import androidx.constraintlayout.widget.ConstraintLayout; import androidx.constraintlayout.widget.Group; import androidx.fragment.app.DialogFragment; import androidx.fragment.app.Fragment; -import androidx.localbroadcastmanager.content.LocalBroadcastManager; import androidx.recyclerview.widget.LinearLayoutManager; import androidx.recyclerview.widget.RecyclerView; @@ -494,9 +493,8 @@ public class FragmentRule extends FragmentBase { break; case REQUEST_COLOR: if (resultCode == RESULT_OK && data != null) { - if (!Helper.isPro(getContext())) { - LocalBroadcastManager lbm = LocalBroadcastManager.getInstance(getContext()); - lbm.sendBroadcast(new Intent(ActivityView.ACTION_SHOW_PRO)); + if (!ActivityBilling.isPro(getContext())) { + getContext().startActivity(new Intent(getContext(), ActivityBilling.class)); return; } @@ -770,9 +768,8 @@ public class FragmentRule extends FragmentBase { } private void onActionSave() { - if (!Helper.isPro(getContext())) { - LocalBroadcastManager lbm = LocalBroadcastManager.getInstance(getContext()); - lbm.sendBroadcast(new Intent(ActivityView.ACTION_SHOW_PRO)); + if (!ActivityBilling.isPro(getContext())) { + getContext().startActivity(new Intent(getContext(), ActivityBilling.class)); return; } diff --git a/app/src/main/java/eu/faircode/email/Helper.java b/app/src/main/java/eu/faircode/email/Helper.java index 968fc05e72..1ac3660495 100644 --- a/app/src/main/java/eu/faircode/email/Helper.java +++ b/app/src/main/java/eu/faircode/email/Helper.java @@ -230,7 +230,7 @@ public class Helper { (Helper.hasValidFingerprint(context) ? "1" : "3") + (BuildConfig.PLAY_STORE_RELEASE ? "p" : "") + (BuildConfig.DEBUG ? "d" : "") + - (Helper.isPro(context) ? "+" : ""); + (ActivityBilling.isPro(context) ? "+" : ""); Intent intent = new Intent(Intent.ACTION_SEND); intent.setPackage(BuildConfig.APPLICATION_ID); intent.setType("text/plain"); @@ -812,27 +812,17 @@ public class Helper { return BuildConfig.PLAY_STORE_RELEASE; } - static boolean isPro(Context context) { - if (false && BuildConfig.DEBUG) - return true; - return PreferenceManager.getDefaultSharedPreferences(context).getBoolean("pro", false); - } - static void linkPro(final TextView tv) { - if (isPro(tv.getContext()) && !BuildConfig.DEBUG) + if (ActivityBilling.isPro(tv.getContext()) && !BuildConfig.DEBUG) hide(tv); else { - final Intent pro = new Intent(Intent.ACTION_VIEW, Uri.parse(BuildConfig.PRO_FEATURES_URI)); - PackageManager pm = tv.getContext().getPackageManager(); - if (pro.resolveActivity(pm) != null) { - tv.getPaint().setUnderlineText(true); - tv.setOnClickListener(new View.OnClickListener() { - @Override - public void onClick(View view) { - tv.getContext().startActivity(pro); - } - }); - } + tv.getPaint().setUnderlineText(true); + tv.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + tv.getContext().startActivity(new Intent(tv.getContext(), ActivityBilling.class)); + } + }); } } diff --git a/app/src/main/java/eu/faircode/email/Log.java b/app/src/main/java/eu/faircode/email/Log.java index d17a7c8589..7f292672b3 100644 --- a/app/src/main/java/eu/faircode/email/Log.java +++ b/app/src/main/java/eu/faircode/email/Log.java @@ -459,7 +459,7 @@ public class Log { Helper.hasValidFingerprint(context) ? "1" : "3", BuildConfig.PLAY_STORE_RELEASE ? "p" : "", BuildConfig.DEBUG ? "d" : "", - Helper.isPro(context) ? "+" : "")); + ActivityBilling.isPro(context) ? "+" : "")); sb.append(String.format("Android: %s (SDK %d)\r\n", Build.VERSION.RELEASE, Build.VERSION.SDK_INT)); sb.append("\r\n"); diff --git a/app/src/main/java/eu/faircode/email/ServiceExternal.java b/app/src/main/java/eu/faircode/email/ServiceExternal.java index 60ccaef50e..552335259f 100644 --- a/app/src/main/java/eu/faircode/email/ServiceExternal.java +++ b/app/src/main/java/eu/faircode/email/ServiceExternal.java @@ -60,7 +60,7 @@ public class ServiceExternal extends Service { if (intent == null) return START_NOT_STICKY; - if (!Helper.isPro(this)) + if (!ActivityBilling.isPro(this)) return START_NOT_STICKY; final Boolean enabled; diff --git a/app/src/main/java/eu/faircode/email/ServiceSynchronize.java b/app/src/main/java/eu/faircode/email/ServiceSynchronize.java index 309fcfa4cb..fa5056fb66 100644 --- a/app/src/main/java/eu/faircode/email/ServiceSynchronize.java +++ b/app/src/main/java/eu/faircode/email/ServiceSynchronize.java @@ -1488,7 +1488,7 @@ public class ServiceSynchronize extends ServiceBase { am.cancel(piAlarm); SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context); - if (!prefs.getBoolean("schedule", false) || !Helper.isPro(context)) + if (!prefs.getBoolean("schedule", false) || !ActivityBilling.isPro(context)) return; int minuteStart = prefs.getInt("schedule_start", 0); diff --git a/app/src/main/java/eu/faircode/email/WidgetUnified.java b/app/src/main/java/eu/faircode/email/WidgetUnified.java index eb1f397c4a..d806a618ee 100644 --- a/app/src/main/java/eu/faircode/email/WidgetUnified.java +++ b/app/src/main/java/eu/faircode/email/WidgetUnified.java @@ -43,7 +43,7 @@ public class WidgetUnified extends AppWidgetProvider { static void update(Context context) { Log.i("Widget unified update"); - if (Helper.isPro(context)) { + if (ActivityBilling.isPro(context)) { AppWidgetManager appWidgetManager = AppWidgetManager.getInstance(context); int[] appWidgetIds = appWidgetManager.getAppWidgetIds(new ComponentName(context, WidgetUnified.class)); appWidgetManager.notifyAppWidgetViewDataChanged(appWidgetIds, R.id.lv); @@ -56,7 +56,7 @@ public class WidgetUnified extends AppWidgetProvider { view.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); PendingIntent pi = PendingIntent.getActivity(context, ActivityView.REQUEST_UNIFIED, view, PendingIntent.FLAG_UPDATE_CURRENT); - boolean pro = Helper.isPro(context); + boolean pro = ActivityBilling.isPro(context); for (int id : appWidgetIds) { RemoteViews views = new RemoteViews(context.getPackageName(), R.layout.widget_unified); diff --git a/app/src/main/res/layout/activity_billing.xml b/app/src/main/res/layout/activity_billing.xml new file mode 100644 index 0000000000..5e96726ae2 --- /dev/null +++ b/app/src/main/res/layout/activity_billing.xml @@ -0,0 +1,6 @@ + \ No newline at end of file