Implement background module update check & improve translator utils. (New strings)

pull/27/head
Fox2Code 3 years ago
parent 54879213bd
commit 58a29f006d

@ -97,6 +97,7 @@ dependencies {
implementation 'com.github.Fox2Code:FoxCompat:0.0.2' implementation 'com.github.Fox2Code:FoxCompat:0.0.2'
// Utils // Utils
implementation 'androidx.work:work-runtime:2.7.1'
implementation 'com.squareup.okhttp3:okhttp-dnsoverhttps:4.9.3' implementation 'com.squareup.okhttp3:okhttp-dnsoverhttps:4.9.3'
implementation 'com.squareup.okhttp3:okhttp-brotli:4.9.3' implementation 'com.squareup.okhttp3:okhttp-brotli:4.9.3'
implementation 'com.github.topjohnwu.libsu:io:5.0.1' implementation 'com.github.topjohnwu.libsu:io:5.0.1'

@ -11,6 +11,8 @@
<uses-permission android:name="android.permission.INTERNET" /> <uses-permission android:name="android.permission.INTERNET" />
<!-- WebView offline webpage support --> <!-- WebView offline webpage support -->
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /> <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<!-- Check if there is modules updates on boot -->
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
<!-- Open config apps for applications --> <!-- Open config apps for applications -->
<uses-permission-sdk-23 android:name="android.permission.QUERY_ALL_PACKAGES" /> <uses-permission-sdk-23 android:name="android.permission.QUERY_ALL_PACKAGES" />
<!-- Supposed to fix bugs with old firmware, only requested on pre Marshmallow --> <!-- Supposed to fix bugs with old firmware, only requested on pre Marshmallow -->
@ -31,7 +33,14 @@
android:networkSecurityConfig="@xml/network_security_config" android:networkSecurityConfig="@xml/network_security_config"
android:usesCleartextTraffic="false" android:usesCleartextTraffic="false"
tools:targetApi="s" tools:targetApi="s"
tools:replace="android:supportsRtl"> tools:replace="android:supportsRtl"
tools:ignore="ManifestResource">
<receiver android:name="com.fox2code.mmm.background.BackgroundBootListener"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.BOOT_COMPLETED" />
</intent-filter>
</receiver>
<activity <activity
android:name=".settings.SettingsActivity" android:name=".settings.SettingsActivity"
android:parentActivityName=".MainActivity" android:parentActivityName=".MainActivity"

@ -16,6 +16,7 @@ import android.widget.TextView;
import androidx.annotation.NonNull; import androidx.annotation.NonNull;
import androidx.appcompat.widget.SearchView; import androidx.appcompat.widget.SearchView;
import androidx.cardview.widget.CardView; import androidx.cardview.widget.CardView;
import androidx.core.app.NotificationManagerCompat;
import androidx.core.graphics.ColorUtils; import androidx.core.graphics.ColorUtils;
import androidx.recyclerview.widget.LinearLayoutManager; import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView; import androidx.recyclerview.widget.RecyclerView;
@ -23,6 +24,7 @@ import androidx.swiperefreshlayout.widget.SwipeRefreshLayout;
import com.fox2code.foxcompat.FoxActivity; import com.fox2code.foxcompat.FoxActivity;
import com.fox2code.foxcompat.FoxDisplay; import com.fox2code.foxcompat.FoxDisplay;
import com.fox2code.mmm.background.BackgroundUpdateChecker;
import com.fox2code.mmm.installer.InstallerInitializer; import com.fox2code.mmm.installer.InstallerInitializer;
import com.fox2code.mmm.manager.LocalModuleInfo; import com.fox2code.mmm.manager.LocalModuleInfo;
import com.fox2code.mmm.manager.ModuleManager; import com.fox2code.mmm.manager.ModuleManager;
@ -64,9 +66,16 @@ public class MainActivity extends FoxActivity implements SwipeRefreshLayout.OnRe
this.moduleViewListBuilder.addNotification(NotificationType.INSTALL_FROM_STORAGE); this.moduleViewListBuilder.addNotification(NotificationType.INSTALL_FROM_STORAGE);
} }
@Override
protected void onResume() {
BackgroundUpdateChecker.onMainActivityResume(this);
super.onResume();
}
@Override @Override
protected void onCreate(Bundle savedInstanceState) { protected void onCreate(Bundle savedInstanceState) {
this.initMode = true; this.initMode = true;
BackgroundUpdateChecker.onMainActivityCreate(this);
super.onCreate(savedInstanceState); 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); IntentHelper.startActivity(this, SettingsActivity.class);
@ -395,7 +404,8 @@ public class MainActivity extends FoxActivity implements SwipeRefreshLayout.OnRe
this.searchView.clearFocus(); this.searchView.clearFocus();
if (this.initMode) return false; if (this.initMode) return false;
if (this.moduleViewListBuilder.setQueryChange(query)) { if (this.moduleViewListBuilder.setQueryChange(query)) {
new Thread(() -> this.moduleViewListBuilder.applyTo(moduleList, moduleViewAdapter), "Query update thread").start(); new Thread(() -> this.moduleViewListBuilder.applyTo(
moduleList, moduleViewAdapter), "Query update thread").start();
} }
return true; return true;
} }
@ -404,7 +414,8 @@ public class MainActivity extends FoxActivity implements SwipeRefreshLayout.OnRe
public boolean onQueryTextChange(String query) { public boolean onQueryTextChange(String query) {
if (this.initMode) return false; if (this.initMode) return false;
if (this.moduleViewListBuilder.setQueryChange(query)) { if (this.moduleViewListBuilder.setQueryChange(query)) {
new Thread(() -> this.moduleViewListBuilder.applyTo(moduleList, moduleViewAdapter), "Query update thread").start(); new Thread(() -> this.moduleViewListBuilder.applyTo(
moduleList, moduleViewAdapter), "Query update thread").start();
} }
return false; return false;
} }
@ -413,7 +424,8 @@ public class MainActivity extends FoxActivity implements SwipeRefreshLayout.OnRe
public boolean onClose() { public boolean onClose() {
if (this.initMode) return false; if (this.initMode) return false;
if (this.moduleViewListBuilder.setQueryChange(null)) { if (this.moduleViewListBuilder.setQueryChange(null)) {
new Thread(() -> this.moduleViewListBuilder.applyTo(moduleList, moduleViewAdapter), "Query update thread").start(); new Thread(() -> this.moduleViewListBuilder.applyTo(
moduleList, moduleViewAdapter), "Query update thread").start();
} }
return false; return false;
} }

@ -17,10 +17,16 @@ import androidx.annotation.StyleRes;
import androidx.emoji2.text.DefaultEmojiCompatConfig; import androidx.emoji2.text.DefaultEmojiCompatConfig;
import androidx.emoji2.text.EmojiCompat; import androidx.emoji2.text.EmojiCompat;
import androidx.emoji2.text.FontRequestEmojiCompatConfig; import androidx.emoji2.text.FontRequestEmojiCompatConfig;
import androidx.work.Constraints;
import androidx.work.ExistingPeriodicWorkPolicy;
import androidx.work.NetworkType;
import androidx.work.PeriodicWorkRequest;
import androidx.work.WorkManager;
import com.fox2code.foxcompat.FoxActivity; import com.fox2code.foxcompat.FoxActivity;
import com.fox2code.foxcompat.FoxApplication; import com.fox2code.foxcompat.FoxApplication;
import com.fox2code.foxcompat.FoxThemeWrapper; import com.fox2code.foxcompat.FoxThemeWrapper;
import com.fox2code.mmm.background.BackgroundUpdateChecker;
import com.fox2code.mmm.installer.InstallerInitializer; import com.fox2code.mmm.installer.InstallerInitializer;
import com.fox2code.mmm.utils.GMSProviderInstaller; import com.fox2code.mmm.utils.GMSProviderInstaller;
import com.fox2code.mmm.utils.Http; import com.fox2code.mmm.utils.Http;
@ -31,6 +37,7 @@ import java.text.SimpleDateFormat;
import java.util.Date; import java.util.Date;
import java.util.Locale; import java.util.Locale;
import java.util.Random; import java.util.Random;
import java.util.concurrent.TimeUnit;
import io.noties.markwon.Markwon; import io.noties.markwon.Markwon;
import io.noties.markwon.html.HtmlPlugin; import io.noties.markwon.html.HtmlPlugin;
@ -47,7 +54,8 @@ import io.noties.prism4j.annotations.PrismBundle;
includeAll = true, includeAll = true,
grammarLocatorClassName = ".Prism4jGrammarLocator" grammarLocatorClassName = ".Prism4jGrammarLocator"
) )
public class MainApplication extends FoxApplication { public class MainApplication extends FoxApplication
implements androidx.work.Configuration.Provider {
private static final String timeFormatString = "dd MMM yyyy"; // Example: 13 july 2001 private static final String timeFormatString = "dd MMM yyyy"; // Example: 13 july 2001
private static Locale timeFormatLocale = private static Locale timeFormatLocale =
Resources.getSystem().getConfiguration().locale; Resources.getSystem().getConfiguration().locale;
@ -146,6 +154,10 @@ public class MainApplication extends FoxApplication {
&& isDeveloper(); && isDeveloper();
} }
public static boolean isBackgroundUpdateCheckEnabled() {
return getSharedPreferences().getBoolean("pref_background_update_check", true);
}
public static boolean isFirstBoot() { public static boolean isFirstBoot() {
return firstBoot; return firstBoot;
} }
@ -196,6 +208,12 @@ public class MainApplication extends FoxApplication {
return this.markwonThemeContext; return this.markwonThemeContext;
} }
@NonNull
@Override
public androidx.work.Configuration getWorkManagerConfiguration() {
return new androidx.work.Configuration.Builder().build();
}
private class Prism4jSwitchTheme implements Prism4jTheme { private class Prism4jSwitchTheme implements Prism4jTheme {
private final Prism4jTheme light = new Prism4jThemeDefault(Color.TRANSPARENT); private final Prism4jTheme light = new Prism4jThemeDefault(Color.TRANSPARENT);
private final Prism4jTheme dark = new Prism4jThemeDarkula(Color.TRANSPARENT); private final Prism4jTheme dark = new Prism4jThemeDarkula(Color.TRANSPARENT);

@ -0,0 +1,19 @@
package com.fox2code.mmm.background;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import com.fox2code.mmm.MainApplication;
public class BackgroundBootListener extends BroadcastReceiver {
private static final String BOOT_COMPLETED = "android.intent.action.BOOT_COMPLETED";
@Override
public void onReceive(Context context, Intent intent) {
if (!BOOT_COMPLETED.equals(intent.getAction())) return;
if (!MainApplication.isBackgroundUpdateCheckEnabled()) return;
BackgroundUpdateChecker.onMainActivityCreate(context);
BackgroundUpdateChecker.doCheck(context);
}
}

@ -0,0 +1,115 @@
package com.fox2code.mmm.background;
import android.app.PendingIntent;
import android.content.Context;
import android.content.Intent;
import android.os.Build;
import androidx.annotation.NonNull;
import androidx.core.app.NotificationChannelCompat;
import androidx.core.app.NotificationCompat;
import androidx.core.app.NotificationManagerCompat;
import androidx.work.Constraints;
import androidx.work.ExistingPeriodicWorkPolicy;
import androidx.work.NetworkType;
import androidx.work.PeriodicWorkRequest;
import androidx.work.WorkManager;
import androidx.work.Worker;
import androidx.work.WorkerParameters;
import com.fox2code.mmm.MainActivity;
import com.fox2code.mmm.MainApplication;
import com.fox2code.mmm.R;
import com.fox2code.mmm.manager.LocalModuleInfo;
import com.fox2code.mmm.manager.ModuleManager;
import com.fox2code.mmm.repo.RepoManager;
import com.fox2code.mmm.repo.RepoModule;
import java.util.Random;
import java.util.concurrent.TimeUnit;
public class BackgroundUpdateChecker extends Worker {
private static boolean easterEggActive = false;
public static final String NOTIFICATION_CHANNEL_ID = "background_update";
public static final int NOTIFICATION_ID = 1;
public BackgroundUpdateChecker(@NonNull Context context,
@NonNull WorkerParameters workerParams) {
super(context, workerParams);
}
@NonNull
@Override
public Result doWork() {
if (!NotificationManagerCompat.from(this.getApplicationContext()).areNotificationsEnabled()
|| !MainApplication.isBackgroundUpdateCheckEnabled()) return Result.success();
doCheck(this.getApplicationContext());
return Result.success();
}
static void doCheck(Context context) {
Thread.currentThread().setPriority(Thread.MIN_PRIORITY);
RepoManager.getINSTANCE().update(null);
ModuleManager.getINSTANCE().scan();
ModuleManager.getINSTANCE().scan();
int moduleUpdateCount = 0;
for (LocalModuleInfo localModuleInfo :
ModuleManager.getINSTANCE().getModules().values()) {
RepoModule repoModule = RepoManager.getINSTANCE()
.getModules().get(localModuleInfo.id);
localModuleInfo.checkModuleUpdate();
if (localModuleInfo.updateVersionCode > localModuleInfo.versionCode) {
moduleUpdateCount++;
} else if (repoModule != null &&
repoModule.moduleInfo.versionCode > localModuleInfo.versionCode) {
moduleUpdateCount++;
}
}
if (moduleUpdateCount != 0) {
postNotification(context, moduleUpdateCount);
}
}
public static void postNotification(Context context, int updateCount) {
if (!easterEggActive) easterEggActive = new Random().nextInt(100) <= updateCount;
NotificationCompat.Builder builder = new NotificationCompat.Builder(
context, NOTIFICATION_CHANNEL_ID)
.setContentTitle(context.getString(easterEggActive ?
R.string.notification_update_title_easter_egg :
R.string.notification_update_title)
.replace("%i", String.valueOf(updateCount)))
.setContentText(context.getString(R.string.notification_update_subtitle))
.setSmallIcon(R.drawable.ic_baseline_extension_24)
.setPriority(NotificationCompat.PRIORITY_HIGH)
.setContentIntent(PendingIntent.getActivity(context, 0,
new Intent(context, MainActivity.class).setFlags(
Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK),
Build.VERSION.SDK_INT >= Build.VERSION_CODES.M ?
PendingIntent.FLAG_IMMUTABLE : 0)).setAutoCancel(true);
NotificationManagerCompat.from(context).notify(NOTIFICATION_ID, builder.build());
}
public static void onMainActivityCreate(Context context) {
NotificationManagerCompat notificationManagerCompat =
NotificationManagerCompat.from(context);
notificationManagerCompat.createNotificationChannel(
new NotificationChannelCompat.Builder(NOTIFICATION_CHANNEL_ID,
NotificationManagerCompat.IMPORTANCE_HIGH).setShowBadge(true)
.setName(context.getString(R.string.notification_update_pref)).build());
notificationManagerCompat.cancel(BackgroundUpdateChecker.NOTIFICATION_ID);
BackgroundUpdateChecker.easterEggActive = false;
WorkManager.getInstance(context).enqueueUniquePeriodicWork("background_checker",
ExistingPeriodicWorkPolicy.REPLACE, new PeriodicWorkRequest.Builder(
BackgroundUpdateChecker.class, 6, TimeUnit.HOURS)
.setConstraints(new Constraints.Builder().setRequiresBatteryNotLow(true)
.setRequiredNetworkType(NetworkType.UNMETERED).build()).build());
}
public static void onMainActivityResume(Context context) {
NotificationManagerCompat.from(context).cancel(
BackgroundUpdateChecker.NOTIFICATION_ID);
BackgroundUpdateChecker.easterEggActive = false;
}
}

@ -253,7 +253,8 @@ public enum ActionButtonType {
if (url.startsWith("https://www.paypal.me/") || if (url.startsWith("https://www.paypal.me/") ||
url.startsWith("https://www.paypal.com/paypalme/")) { url.startsWith("https://www.paypal.com/paypalme/")) {
icon = R.drawable.ic_baseline_paypal_24; icon = R.drawable.ic_baseline_paypal_24;
} else if (url.startsWith("https://www.patreon.com/")) { } else if (url.startsWith("https://patreon.com/") ||
url.startsWith("https://www.patreon.com/")) {
icon = R.drawable.ic_patreon; icon = R.drawable.ic_patreon;
} }
return icon; return icon;

@ -212,11 +212,14 @@ public class RepoData extends XRepo {
return this.id; return this.id;
} }
private static boolean isNonNull(String str) {
return str != null && !str.isEmpty() && !"null".equals(str);
}
// Repo data info getters // Repo data info getters
@NonNull @NonNull
public String getName() { public String getName() {
if (this.name != null && if (isNonNull(this.name))
!this.name.isEmpty())
return this.name; return this.name;
if (this.defaultName != null) if (this.defaultName != null)
return this.defaultName; return this.defaultName;
@ -225,8 +228,7 @@ public class RepoData extends XRepo {
@NonNull @NonNull
public String getWebsite() { public String getWebsite() {
if (this.website != null && if (isNonNull(this.website))
!this.website.isEmpty())
return this.website; return this.website;
if (this.defaultWebsite != null) if (this.defaultWebsite != null)
return this.defaultWebsite; return this.defaultWebsite;
@ -234,22 +236,19 @@ public class RepoData extends XRepo {
} }
public String getSupport() { public String getSupport() {
if (this.support != null && if (isNonNull(this.support))
!this.support.isEmpty())
return this.support; return this.support;
return this.defaultSupport; return this.defaultSupport;
} }
public String getDonate() { public String getDonate() {
if (this.donate != null && if (isNonNull(this.donate))
!this.donate.isEmpty())
return this.donate; return this.donate;
return this.defaultDonate; return this.defaultDonate;
} }
public String getSubmitModule() { public String getSubmitModule() {
if (this.submitModule != null && if (isNonNull(this.submitModule))
!this.submitModule.isEmpty())
return this.submitModule; return this.submitModule;
return this.defaultSubmitModule; return this.defaultSubmitModule;
} }

@ -6,7 +6,6 @@ import android.app.PendingIntent;
import android.content.Context; import android.content.Context;
import android.content.Intent; import android.content.Intent;
import android.content.SharedPreferences; import android.content.SharedPreferences;
import android.content.res.Configuration;
import android.os.Build; import android.os.Build;
import android.os.Bundle; import android.os.Bundle;
import android.util.Log; import android.util.Log;
@ -33,6 +32,7 @@ import com.fox2code.mmm.Constants;
import com.fox2code.mmm.MainActivity; import com.fox2code.mmm.MainActivity;
import com.fox2code.mmm.MainApplication; import com.fox2code.mmm.MainApplication;
import com.fox2code.mmm.R; import com.fox2code.mmm.R;
import com.fox2code.mmm.background.BackgroundUpdateChecker;
import com.fox2code.mmm.installer.InstallerInitializer; import com.fox2code.mmm.installer.InstallerInitializer;
import com.fox2code.mmm.module.ActionButtonType; import com.fox2code.mmm.module.ActionButtonType;
import com.fox2code.mmm.repo.CustomRepoData; import com.fox2code.mmm.repo.CustomRepoData;
@ -54,8 +54,10 @@ import org.json.JSONException;
import java.io.IOException; import java.io.IOException;
import java.util.HashSet; import java.util.HashSet;
import java.util.Objects; import java.util.Objects;
import java.util.Random;
public class SettingsActivity extends FoxActivity implements LanguageActivity { public class SettingsActivity extends FoxActivity implements LanguageActivity {
private static final int LANGUAGE_SUPPORT_LEVEL = 1;
private static final String TAG = "SettingsActivity"; private static final String TAG = "SettingsActivity";
private static int devModeStep = 0; private static int devModeStep = 0;
@ -88,6 +90,12 @@ public class SettingsActivity extends FoxActivity implements LanguageActivity {
System.exit(0); // Exit app process System.exit(0); // Exit app process
} }
@Override
protected void onPause() {
BackgroundUpdateChecker.onMainActivityResume(this);
super.onPause();
}
public static class SettingsFragment extends PreferenceFragmentCompat public static class SettingsFragment extends PreferenceFragmentCompat
implements FoxActivity.OnBackPressedCallback { implements FoxActivity.OnBackPressedCallback {
@Override @Override
@ -145,10 +153,12 @@ public class SettingsActivity extends FoxActivity implements LanguageActivity {
HashSet<String> supportedLocales = new HashSet<>(); HashSet<String> supportedLocales = new HashSet<>();
supportedLocales.add("cs"); supportedLocales.add("cs");
supportedLocales.add("de"); supportedLocales.add("de");
supportedLocales.add("el");
supportedLocales.add("es-rMX"); supportedLocales.add("es-rMX");
supportedLocales.add("et"); supportedLocales.add("et");
supportedLocales.add("fr"); supportedLocales.add("fr");
supportedLocales.add("id"); supportedLocales.add("id");
supportedLocales.add("it");
supportedLocales.add("ja"); supportedLocales.add("ja");
supportedLocales.add("nb-rNO"); supportedLocales.add("nb-rNO");
supportedLocales.add("pl"); supportedLocales.add("pl");
@ -170,18 +180,20 @@ public class SettingsActivity extends FoxActivity implements LanguageActivity {
return true; return true;
}); });
int nightModeFlags = int level = this.currentLanguageLevel();
getContext().getResources().getConfiguration().uiMode & if (level != LANGUAGE_SUPPORT_LEVEL) {
Configuration.UI_MODE_NIGHT_MASK; Log.e(TAG, "Detected language level " + level +
switch (nightModeFlags) { ", latest is " + LANGUAGE_SUPPORT_LEVEL);
case Configuration.UI_MODE_NIGHT_YES: languageSelector.setSummary(R.string.language_support_outdated);
findPreference("pref_force_dark_terminal").setEnabled(false); } else {
break; if (!"Translated by Fox2Code".equals( // I don't "translate" english
case Configuration.UI_MODE_NIGHT_NO: this.getString(R.string.language_translated_by))) {
case Configuration.UI_MODE_NIGHT_UNDEFINED: languageSelector.setSummary(R.string.language_translated_by);
findPreference("pref_force_dark_terminal").setEnabled(true); } else {
break; languageSelector.setSummary(null);
}
} }
if (!MainApplication.isDeveloper()) { if (!MainApplication.isDeveloper()) {
findPreference("pref_disable_low_quality_module_filter").setVisible(false); findPreference("pref_disable_low_quality_module_filter").setVisible(false);
} }
@ -189,6 +201,23 @@ public class SettingsActivity extends FoxActivity implements LanguageActivity {
|| !MainApplication.isDeveloper()) { || !MainApplication.isDeveloper()) {
findPreference("pref_use_magisk_install_command").setVisible(false); findPreference("pref_use_magisk_install_command").setVisible(false);
} }
Preference debugNotification = findPreference("pref_background_update_check_debug");
debugNotification.setEnabled(MainApplication.isBackgroundUpdateCheckEnabled());
debugNotification.setVisible(MainApplication.isDeveloper());
debugNotification.setOnPreferenceClickListener(preference -> {
BackgroundUpdateChecker.postNotification(
this.requireContext(), new Random().nextInt(4) + 2);
return true;
});
findPreference("pref_background_update_check").setOnPreferenceChangeListener((preference, newValue) -> {
boolean enabled = Boolean.parseBoolean(String.valueOf(newValue));
debugNotification.setEnabled(enabled);
if (!enabled) {
BackgroundUpdateChecker.onMainActivityResume(
this.requireContext());
}
return true;
});
final LibsBuilder libsBuilder = new LibsBuilder().withShowLoadingProgress(false) final LibsBuilder libsBuilder = new LibsBuilder().withShowLoadingProgress(false)
.withLicenseShown(true).withAboutMinimalDesign(false); .withLicenseShown(true).withAboutMinimalDesign(false);
@ -201,13 +230,30 @@ public class SettingsActivity extends FoxActivity implements LanguageActivity {
"https://github.com/Fox2Code/FoxMagiskModuleManager/releases"); "https://github.com/Fox2Code/FoxMagiskModuleManager/releases");
return true; return true;
}); });
if (BuildConfig.DEBUG || BuildConfig.ENABLE_AUTO_UPDATER) {
findPreference("pref_report_bug").setOnPreferenceClickListener(p -> {
devModeStep = 0;
IntentHelper.openUrl(p.getContext(),
"https://github.com/Fox2Code/FoxMagiskModuleManager/issues");
return true;
});
} else {
findPreference("pref_report_bug").setVisible(false);
}
findPreference("pref_source_code").setOnPreferenceClickListener(p -> { findPreference("pref_source_code").setOnPreferenceClickListener(p -> {
if (devModeStep == 2 && (BuildConfig.DEBUG || !MainApplication.isDeveloper())) { if (devModeStep == 2) {
devModeStep = 0; devModeStep = 0;
if (MainApplication.isDeveloper() && !BuildConfig.DEBUG) {
MainApplication.getSharedPreferences().edit()
.putBoolean("developer", false).apply();
Toast.makeText(getContext(), // Tell the user something changed
R.string.dev_mode_disabled, Toast.LENGTH_SHORT).show();
} else {
MainApplication.getSharedPreferences().edit() MainApplication.getSharedPreferences().edit()
.putBoolean("developer", true).apply(); .putBoolean("developer", true).apply();
Toast.makeText(getContext(), // Tell the user something changed Toast.makeText(getContext(), // Tell the user something changed
R.string.dev_mode_enabled, Toast.LENGTH_SHORT).show(); R.string.dev_mode_enabled, Toast.LENGTH_SHORT).show();
}
return true; return true;
} }
IntentHelper.openUrl(p.getContext(), IntentHelper.openUrl(p.getContext(),
@ -221,6 +267,7 @@ public class SettingsActivity extends FoxActivity implements LanguageActivity {
}); });
findPreference("pref_show_licenses").setOnPreferenceClickListener(p -> { findPreference("pref_show_licenses").setOnPreferenceClickListener(p -> {
devModeStep = devModeStep == 1 ? 2 : 0; devModeStep = devModeStep == 1 ? 2 : 0;
BackgroundUpdateChecker.onMainActivityResume(this.requireContext());
openFragment(libsBuilder.supportFragment(), R.string.licenses); openFragment(libsBuilder.supportFragment(), R.string.licenses);
return true; return true;
}); });
@ -250,6 +297,21 @@ public class SettingsActivity extends FoxActivity implements LanguageActivity {
.commit(); .commit();
return true; return true;
} }
private int currentLanguageLevel() {
int declaredLanguageLevel =
this.getResources().getInteger(R.integer.language_support_level);
if (declaredLanguageLevel != LANGUAGE_SUPPORT_LEVEL)
return declaredLanguageLevel;
if (!this.getResources().getConfiguration().locale.getLanguage().equals("en") &&
this.getResources().getString(R.string.notification_update_pref)
.equals("Background modules update check") &&
this.getResources().getString(R.string.notification_update_desc)
.equals("May increase battery usage")) {
return 0;
}
return LANGUAGE_SUPPORT_LEVEL;
}
} }
public static class RepoFragment extends PreferenceFragmentCompat { public static class RepoFragment extends PreferenceFragmentCompat {

@ -0,0 +1,10 @@
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp"
android:height="24dp"
android:viewportWidth="24"
android:viewportHeight="24"
android:tint="?attr/colorControlNormal">
<path
android:fillColor="@android:color/white"
android:pathData="M12,22c1.1,0 2,-0.9 2,-2h-4c0,1.1 0.89,2 2,2zM18,16v-5c0,-3.07 -1.64,-5.64 -4.5,-6.32L13.5,4c0,-0.83 -0.67,-1.5 -1.5,-1.5s-1.5,0.67 -1.5,1.5v0.68C7.63,5.36 6,7.92 6,11v5l-2,2v1h16v-1l-2,-2z"/>
</vector>

@ -27,6 +27,10 @@
<string name="description">Description</string> <string name="description">Description</string>
<string name="uninstall">Uninstall</string> <string name="uninstall">Uninstall</string>
<string name="config">Config</string> <string name="config">Config</string>
<string name="favourite">Favourite</string>
<string name="report_bugs">Report bugs</string>
<string name="sniffed_modules">Sniffed modules</string>
<string name="sniffing_modules">Sniffing modules</string>
<string name="submit_modules">Submit a module</string> <string name="submit_modules">Submit a module</string>
<string name="require_android_6">Requires Android 6.0+</string> <string name="require_android_6">Requires Android 6.0+</string>
<string name="require_android_12">Requires Android 12+</string> <string name="require_android_12">Requires Android 12+</string>
@ -96,6 +100,7 @@
so this option behind is hidden behind developer mode.\nTurn this on at your own risk! so this option behind is hidden behind developer mode.\nTurn this on at your own risk!
</string> </string>
<string name="dev_mode_enabled">Developer mode on</string> <string name="dev_mode_enabled">Developer mode on</string>
<string name="dev_mode_disabled">Developer mode off</string>
<string name="force_english_pref">English app language</string> <string name="force_english_pref">English app language</string>
<string name="disable_low_quality_module_filter_pref">Show low-quality modules</string> <string name="disable_low_quality_module_filter_pref">Show low-quality modules</string>
<string name="disable_low_quality_module_filter_desc"> <string name="disable_low_quality_module_filter_desc">
@ -128,6 +133,21 @@
<string name="backup_module_list">Backup modules</string> <string name="backup_module_list">Backup modules</string>
<string name="restore_module_list">Restore modules</string> <string name="restore_module_list">Restore modules</string>
<string name="require_internet">This operation require an internet connection</string> <string name="require_internet">This operation require an internet connection</string>
<!-- Background Notification translation -->
<string name="notification_update_title">Found %i module updates</string>
<string name="notification_update_title_easter_egg">Sniffed %i module updates</string>
<string name="notification_update_subtitle">Click to open the app</string>
<string name="notification_update_pref">Background modules update check</string>
<string name="notification_update_desc">May increase battery usage</string>
<string name="notification_update_debug_pref">Test Notification</string>
<!-- Set to true in translation file if your language is right to left --> <!-- Set to true in translation file if your language is right to left -->
<bool name="lang_support_rtl">false</bool> <bool name="lang_support_rtl">false</bool>
<!-- Always copy language_support_level when translating -->
<integer name="language_support_level">1</integer>
<string name="language_support_outdated">Some translations for the current language are
not up-to-date, please consider contributing to the app translations on GitHub</string>
<!-- Replace with your own username when translating -->
<string name="language_translated_by">Translated by Fox2Code</string>
</resources> </resources>

@ -31,6 +31,19 @@
app:title="@string/use_magisk_install_command_pref" app:title="@string/use_magisk_install_command_pref"
app:summary="@string/use_magisk_install_command_desc" app:summary="@string/use_magisk_install_command_desc"
app:singleLineTitle="false" /> app:singleLineTitle="false" />
<SwitchPreferenceCompat
app:defaultValue="true"
app:key="pref_background_update_check"
app:icon="@drawable/ic_baseline_notifications_24"
app:title="@string/notification_update_pref"
app:summary="@string/notification_update_desc"
app:singleLineTitle="false" />
<Preference
app:key="pref_background_update_check_debug"
app:title="@string/notification_update_debug_pref"
app:singleLineTitle="false" />
</PreferenceCategory> </PreferenceCategory>
<PreferenceCategory app:title="@string/pref_category_appearance"> <PreferenceCategory app:title="@string/pref_category_appearance">
@ -111,6 +124,11 @@
app:icon="@drawable/ic_baseline_system_update_24" app:icon="@drawable/ic_baseline_system_update_24"
app:title="@string/app_update" app:title="@string/app_update"
app:singleLineTitle="false" /> app:singleLineTitle="false" />
<Preference
app:key="pref_report_bug"
app:icon="@drawable/ic_baseline_bug_report_24"
app:title="@string/report_bugs"
app:singleLineTitle="false" />
<Preference <Preference
app:key="pref_source_code" app:key="pref_source_code"
app:icon="@drawable/ic_github" app:icon="@drawable/ic_github"

Loading…
Cancel
Save