diff --git a/app/src/main/java/com/fox2code/mmm/MainActivity.java b/app/src/main/java/com/fox2code/mmm/MainActivity.java index 147169a..3641747 100644 --- a/app/src/main/java/com/fox2code/mmm/MainActivity.java +++ b/app/src/main/java/com/fox2code/mmm/MainActivity.java @@ -1,6 +1,7 @@ package com.fox2code.mmm; import android.Manifest; +import android.content.SharedPreferences; import android.content.pm.PackageManager; import android.content.res.Configuration; import android.content.res.Resources; @@ -20,6 +21,7 @@ import androidx.appcompat.widget.SearchView; import androidx.cardview.widget.CardView; import androidx.core.content.ContextCompat; import androidx.core.graphics.ColorUtils; +import androidx.preference.PreferenceManager; import androidx.recyclerview.widget.LinearLayoutManager; import androidx.recyclerview.widget.RecyclerView; import androidx.swiperefreshlayout.widget.SwipeRefreshLayout; @@ -39,12 +41,10 @@ import com.fox2code.mmm.utils.ExternalHelper; import com.fox2code.mmm.utils.Http; import com.fox2code.mmm.utils.IntentHelper; import com.fox2code.mmm.utils.NoodleDebug; +import com.google.android.material.dialog.MaterialAlertDialogBuilder; import com.google.android.material.progressindicator.LinearProgressIndicator; -import com.topjohnwu.superuser.Shell; import eightbitlab.com.blurview.BlurView; -import eightbitlab.com.blurview.RenderEffectBlur; -import eightbitlab.com.blurview.RenderScriptBlur; public class MainActivity extends FoxActivity implements SwipeRefreshLayout.OnRefreshListener, SearchView.OnQueryTextListener, SearchView.OnCloseListener, @@ -87,10 +87,10 @@ public class MainActivity extends FoxActivity implements SwipeRefreshLayout.OnRe noodleDebugState = MainApplication.isDeveloper(); BackgroundUpdateChecker.onMainActivityCreate(this); super.onCreate(savedInstanceState); - this.setActionBarExtraMenuButton(R.drawable.ic_baseline_settings_24, v -> { + this.setActionBarExtraMenuButton(R.drawable.ic_baseline_settings_24, v -> { IntentHelper.startActivity(this, SettingsActivity.class); - return true; - }, R.string.pref_category_settings); + return true; + }, R.string.pref_category_settings); setContentView(R.layout.activity_main); this.setTitle(R.string.app_name); this.getWindow().setFlags( @@ -208,7 +208,7 @@ public class MainActivity extends FoxActivity implements SwipeRefreshLayout.OnRe noodleDebug.replace("Check Update"); RepoManager.getINSTANCE().update(value -> runOnUiThread(max == 0 ? () -> progressIndicator.setProgressCompat( - (int) (value * PRECISION), true) :() -> + (int) (value * PRECISION), true) : () -> progressIndicator.setProgressCompat( (int) (value * PRECISION * 0.75F), true))); NotificationType.NEED_CAPTCHA_ANDROIDACY.autoAdd(moduleViewListBuilder); @@ -432,7 +432,7 @@ public class MainActivity extends FoxActivity implements SwipeRefreshLayout.OnRe final int max = ModuleManager.getINSTANCE().getUpdatableModuleCount(); RepoManager.getINSTANCE().update(value -> runOnUiThread(max == 0 ? () -> progressIndicator.setProgressCompat( - (int) (value * PRECISION), true) :() -> + (int) (value * PRECISION), true) : () -> progressIndicator.setProgressCompat( (int) (value * PRECISION * 0.75F), true))); NotificationType.NEED_CAPTCHA_ANDROIDACY.autoAdd(moduleViewListBuilder); @@ -483,7 +483,7 @@ public class MainActivity extends FoxActivity implements SwipeRefreshLayout.OnRe this.moduleViewListBuilder.applyTo(moduleList, moduleViewAdapter); noodleDebug.pop(); noodleDebug.unbind(); - },"Repo update thread").start(); + }, "Repo update thread").start(); } @Override @@ -532,9 +532,22 @@ public class MainActivity extends FoxActivity implements SwipeRefreshLayout.OnRe ContextCompat.checkSelfPermission(this, Manifest.permission.POST_NOTIFICATIONS) != PackageManager.PERMISSION_GRANTED) { - // TODO Use standard Android API to ask for permissions - Shell.cmd("pm grant " + this.getPackageName() + " " + - Manifest.permission.POST_NOTIFICATIONS); + // Show a dialog explaining why we need this permission, which is to show + // notifications for updates + runOnUiThread(() -> { + MaterialAlertDialogBuilder builder = new MaterialAlertDialogBuilder(this); + builder.setTitle(R.string.permission_notification_title); + builder.setMessage(R.string.permission_notification_message); + builder.setPositiveButton(R.string.permission_notification_grant, (dialog, which) -> this.requestPermissions(new String[]{ + Manifest.permission.POST_NOTIFICATIONS}, 0)); + builder.setNegativeButton(R.string.cancel, (dialog, which) -> { + // Set pref_background_update_check to false and dismiss dialog + SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(this); + prefs.edit().putBoolean("pref_background_update_check", false).apply(); + dialog.dismiss(); + }); + builder.show(); + }); } } } \ No newline at end of file diff --git a/app/src/main/java/com/fox2code/mmm/MainApplication.java b/app/src/main/java/com/fox2code/mmm/MainApplication.java index 5133a51..75a5c21 100644 --- a/app/src/main/java/com/fox2code/mmm/MainApplication.java +++ b/app/src/main/java/com/fox2code/mmm/MainApplication.java @@ -15,6 +15,7 @@ import android.util.Log; import androidx.annotation.NonNull; import androidx.annotation.StyleRes; +import androidx.core.app.NotificationManagerCompat; import androidx.emoji2.text.DefaultEmojiCompatConfig; import androidx.emoji2.text.EmojiCompat; import androidx.emoji2.text.FontRequestEmojiCompatConfig; @@ -207,6 +208,10 @@ public class MainApplication extends FoxApplication private FoxThemeWrapper markwonThemeContext; private Markwon markwon; + public static boolean isNotificationPermissionGranted() { + return NotificationManagerCompat.from(INSTANCE).areNotificationsEnabled(); + } + public Markwon getMarkwon() { if (this.markwon != null) return this.markwon; diff --git a/app/src/main/java/com/fox2code/mmm/repo/CustomRepoManager.java b/app/src/main/java/com/fox2code/mmm/repo/CustomRepoManager.java index a59003a..f983686 100644 --- a/app/src/main/java/com/fox2code/mmm/repo/CustomRepoManager.java +++ b/app/src/main/java/com/fox2code/mmm/repo/CustomRepoManager.java @@ -3,6 +3,8 @@ package com.fox2code.mmm.repo; import android.content.Context; import android.content.SharedPreferences; +import androidx.annotation.NonNull; + import com.fox2code.mmm.MainApplication; import com.fox2code.mmm.utils.PropUtils; @@ -65,6 +67,8 @@ public class CustomRepoManager { CustomRepoData customRepoData = (CustomRepoData) this.repoManager.addOrGet(repo); customRepoData.override = "custom_repo_" + i; + // Set the enabled state to true + customRepoData.setEnabled(true); customRepoData.updateEnabledState(); return customRepoData; } diff --git a/app/src/main/java/com/fox2code/mmm/settings/SettingsActivity.java b/app/src/main/java/com/fox2code/mmm/settings/SettingsActivity.java index b671d0e..15dfcd8 100644 --- a/app/src/main/java/com/fox2code/mmm/settings/SettingsActivity.java +++ b/app/src/main/java/com/fox2code/mmm/settings/SettingsActivity.java @@ -262,12 +262,18 @@ public class SettingsActivity extends FoxActivity implements LanguageActivity { Preference debugNotification = findPreference("pref_background_update_check_debug"); debugNotification.setEnabled(MainApplication.isBackgroundUpdateCheckEnabled()); debugNotification.setVisible(MainApplication.isDeveloper() && !MainApplication.isWrapped()); + debugNotification.setVisible(MainApplication.isDeveloper() && !MainApplication.isWrapped()); debugNotification.setOnPreferenceClickListener(preference -> { BackgroundUpdateChecker.postNotification(this.requireContext(), new Random().nextInt(4) + 2); return true; }); Preference backgroundUpdateCheck = findPreference("pref_background_update_check"); backgroundUpdateCheck.setVisible(!MainApplication.isWrapped()); + // Make uncheckable if POST_NOTIFICATIONS permission is not granted + if (!MainApplication.isNotificationPermissionGranted()) { + backgroundUpdateCheck.setSummary(R.string.background_update_check_permission_required); + backgroundUpdateCheck.setEnabled(false); + } backgroundUpdateCheck.setOnPreferenceChangeListener((preference, newValue) -> { boolean enabled = Boolean.parseBoolean(String.valueOf(newValue)); debugNotification.setEnabled(enabled); @@ -651,7 +657,7 @@ public class SettingsActivity extends FoxActivity implements LanguageActivity { if (preference == null) continue; final int index = i; preference.setOnPreferenceClickListener(preference1 -> { - sharedPreferences.edit().putBoolean("pref_custom_repo_" + index + "_enabled", false).apply(); + sharedPreferences.edit().remove("pref_custom_repo_" + index + "_enabled").apply(); customRepoManager.removeRepo(index); updateCustomRepoList(false); return true; @@ -677,7 +683,6 @@ public class SettingsActivity extends FoxActivity implements LanguageActivity { String text = String.valueOf(input.getText()); if (customRepoManager.canAddRepo(text)) { final CustomRepoData customRepoData = customRepoManager.addRepo(text); - customRepoData.setEnabled(true); new Thread("Add Custom Repo Thread") { @Override public void run() { diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 8b44069..c41ad95 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -183,4 +183,8 @@ Androidacy update blocked by Captcha API key has been changed. Restart the app to apply changes. The API key you input is the same as the one already in use. + Allow notifications? + We need the notifications permission to notify you on app and module updates. If you don\'t grant this permission, background update checks will not run. + Grant permission + Please enable notifications to enable this option.