Clean up app list settings
This commit is contained in:
parent
60dac3ce54
commit
205090bdce
|
|
@ -5,18 +5,14 @@ import android.app.Activity;
|
||||||
import android.app.Application;
|
import android.app.Application;
|
||||||
import android.content.Intent;
|
import android.content.Intent;
|
||||||
import android.content.SharedPreferences;
|
import android.content.SharedPreferences;
|
||||||
import android.content.pm.PackageManager;
|
|
||||||
import android.os.Bundle;
|
import android.os.Bundle;
|
||||||
import android.os.Handler;
|
import android.os.Handler;
|
||||||
import android.os.Looper;
|
import android.os.Looper;
|
||||||
import android.util.Log;
|
|
||||||
|
|
||||||
import androidx.annotation.NonNull;
|
import androidx.annotation.NonNull;
|
||||||
import androidx.preference.PreferenceManager;
|
import androidx.preference.PreferenceManager;
|
||||||
|
|
||||||
import org.meowcat.edxposed.manager.adapters.AppHelper;
|
|
||||||
import org.meowcat.edxposed.manager.ui.activity.CrashReportActivity;
|
import org.meowcat.edxposed.manager.ui.activity.CrashReportActivity;
|
||||||
import org.meowcat.edxposed.manager.ui.fragment.CompileDialogFragment;
|
|
||||||
import org.meowcat.edxposed.manager.util.CompileUtil;
|
import org.meowcat.edxposed.manager.util.CompileUtil;
|
||||||
import org.meowcat.edxposed.manager.util.ModuleUtil;
|
import org.meowcat.edxposed.manager.util.ModuleUtil;
|
||||||
import org.meowcat.edxposed.manager.util.NotificationUtil;
|
import org.meowcat.edxposed.manager.util.NotificationUtil;
|
||||||
|
|
@ -25,11 +21,6 @@ import org.meowcat.edxposed.manager.util.RebootUtil;
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.PrintWriter;
|
import java.io.PrintWriter;
|
||||||
import java.io.StringWriter;
|
import java.io.StringWriter;
|
||||||
import java.text.DateFormat;
|
|
||||||
import java.text.SimpleDateFormat;
|
|
||||||
import java.util.Collection;
|
|
||||||
import java.util.Date;
|
|
||||||
import java.util.Objects;
|
|
||||||
|
|
||||||
import rikka.shizuku.Shizuku;
|
import rikka.shizuku.Shizuku;
|
||||||
import rikka.sui.Sui;
|
import rikka.sui.Sui;
|
||||||
|
|
@ -143,22 +134,9 @@ public class App extends Application implements Application.ActivityLifecycleCal
|
||||||
|
|
||||||
createDirectories();
|
createDirectories();
|
||||||
NotificationUtil.init();
|
NotificationUtil.init();
|
||||||
|
ModuleUtil.getInstance();
|
||||||
registerActivityLifecycleCallbacks(this);
|
|
||||||
|
|
||||||
@SuppressLint("SimpleDateFormat") DateFormat dateFormat = new SimpleDateFormat("dd/MM/yyyy");
|
|
||||||
Date date = new Date();
|
|
||||||
|
|
||||||
Shizuku.addRequestPermissionResultListener(REQUEST_PERMISSION_RESULT_LISTENER);
|
Shizuku.addRequestPermissionResultListener(REQUEST_PERMISSION_RESULT_LISTENER);
|
||||||
|
|
||||||
if (!Objects.requireNonNull(pref.getString("date", "")).equals(dateFormat.format(date))) {
|
|
||||||
pref.edit().putString("date", dateFormat.format(date)).apply();
|
|
||||||
|
|
||||||
try {
|
|
||||||
Log.i(TAG, String.format("EdXposedManager - %s - %s", BuildConfig.VERSION_CODE, getPackageManager().getPackageInfo(getPackageName(), 0).versionName));
|
|
||||||
} catch (PackageManager.NameNotFoundException ignored) {
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressLint({"PrivateApi", "NewApi"})
|
@SuppressLint({"PrivateApi", "NewApi"})
|
||||||
|
|
@ -172,19 +150,6 @@ public class App extends Application implements Application.ActivityLifecycleCal
|
||||||
if (isUiLoaded) {
|
if (isUiLoaded) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
//RepoLoader.getInstance().triggerFirstLoadIfNecessary();
|
|
||||||
isUiLoaded = true;
|
|
||||||
|
|
||||||
if (pref.getBoolean("hook_modules", true)) {
|
|
||||||
Collection<ModuleUtil.InstalledModule> installedModules = ModuleUtil.getInstance().getModules().values();
|
|
||||||
for (ModuleUtil.InstalledModule info : installedModules) {
|
|
||||||
if (!AppHelper.forceWhiteList.contains(info.packageName)) {
|
|
||||||
AppHelper.forceWhiteList.add(info.packageName);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Log.d(TAG, "ApplicationList: Force add modules to list");
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,6 @@
|
||||||
package org.meowcat.edxposed.manager.adapters;
|
package org.meowcat.edxposed.manager.adapters;
|
||||||
|
|
||||||
import android.annotation.SuppressLint;
|
import android.annotation.SuppressLint;
|
||||||
import android.content.Context;
|
|
||||||
import android.content.SharedPreferences;
|
import android.content.SharedPreferences;
|
||||||
import android.content.pm.ApplicationInfo;
|
import android.content.pm.ApplicationInfo;
|
||||||
import android.content.pm.PackageInfo;
|
import android.content.pm.PackageInfo;
|
||||||
|
|
@ -32,6 +31,7 @@ import com.bumptech.glide.request.transition.Transition;
|
||||||
|
|
||||||
import org.meowcat.edxposed.manager.App;
|
import org.meowcat.edxposed.manager.App;
|
||||||
import org.meowcat.edxposed.manager.R;
|
import org.meowcat.edxposed.manager.R;
|
||||||
|
import org.meowcat.edxposed.manager.ui.activity.AppListActivity;
|
||||||
import org.meowcat.edxposed.manager.util.GlideApp;
|
import org.meowcat.edxposed.manager.util.GlideApp;
|
||||||
|
|
||||||
import java.text.DateFormat;
|
import java.text.DateFormat;
|
||||||
|
|
@ -45,9 +45,8 @@ import java.util.Locale;
|
||||||
|
|
||||||
public class AppAdapter extends RecyclerView.Adapter<AppAdapter.ViewHolder> implements Filterable {
|
public class AppAdapter extends RecyclerView.Adapter<AppAdapter.ViewHolder> implements Filterable {
|
||||||
|
|
||||||
protected Context context;
|
protected AppListActivity activity;
|
||||||
private final ApplicationInfo.DisplayNameComparator displayNameComparator;
|
private final ApplicationInfo.DisplayNameComparator displayNameComparator;
|
||||||
private Callback callback;
|
|
||||||
protected List<ApplicationInfo> fullList, showList;
|
protected List<ApplicationInfo> fullList, showList;
|
||||||
private final DateFormat dateformat = new SimpleDateFormat("yyyy-MM-dd", Locale.getDefault());
|
private final DateFormat dateformat = new SimpleDateFormat("yyyy-MM-dd", Locale.getDefault());
|
||||||
private List<String> checkedList;
|
private List<String> checkedList;
|
||||||
|
|
@ -56,26 +55,22 @@ public class AppAdapter extends RecyclerView.Adapter<AppAdapter.ViewHolder> impl
|
||||||
private Comparator<ApplicationInfo> cmp;
|
private Comparator<ApplicationInfo> cmp;
|
||||||
private final SharedPreferences preferences;
|
private final SharedPreferences preferences;
|
||||||
|
|
||||||
AppAdapter(Context context) {
|
AppAdapter(AppListActivity activity) {
|
||||||
this.context = context;
|
this.activity = activity;
|
||||||
preferences = App.getPreferences();
|
preferences = App.getPreferences();
|
||||||
fullList = showList = Collections.emptyList();
|
fullList = showList = Collections.emptyList();
|
||||||
checkedList = Collections.emptyList();
|
checkedList = Collections.emptyList();
|
||||||
filter = new ApplicationFilter();
|
filter = new ApplicationFilter();
|
||||||
pm = context.getPackageManager();
|
pm = activity.getPackageManager();
|
||||||
displayNameComparator = new ApplicationInfo.DisplayNameComparator(pm);
|
displayNameComparator = new ApplicationInfo.DisplayNameComparator(pm);
|
||||||
cmp = displayNameComparator;
|
cmp = displayNameComparator;
|
||||||
refresh();
|
refresh();
|
||||||
}
|
}
|
||||||
|
|
||||||
public void setCallback(Callback callback) {
|
|
||||||
this.callback = callback;
|
|
||||||
}
|
|
||||||
|
|
||||||
@NonNull
|
@NonNull
|
||||||
@Override
|
@Override
|
||||||
public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
|
public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
|
||||||
View v = LayoutInflater.from(context).inflate(R.layout.item_module, parent, false);
|
View v = LayoutInflater.from(activity).inflate(R.layout.item_module, parent, false);
|
||||||
return new ViewHolder(v);
|
return new ViewHolder(v);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -84,15 +79,15 @@ public class AppAdapter extends RecyclerView.Adapter<AppAdapter.ViewHolder> impl
|
||||||
List<ApplicationInfo> rmList = new ArrayList<>();
|
List<ApplicationInfo> rmList = new ArrayList<>();
|
||||||
for (ApplicationInfo info : fullList) {
|
for (ApplicationInfo info : fullList) {
|
||||||
if (this instanceof ScopeAdapter) {
|
if (this instanceof ScopeAdapter) {
|
||||||
if (AppHelper.isWhiteListMode()) {
|
boolean white = AppHelper.isWhiteListMode();
|
||||||
List<String> whiteList = AppHelper.getWhiteList();
|
List<String> list = AppHelper.getAppList(white);
|
||||||
if (!whiteList.contains(info.packageName)) {
|
if (white) {
|
||||||
|
if (!list.contains(info.packageName)) {
|
||||||
rmList.add(info);
|
rmList.add(info);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
List<String> blackList = AppHelper.getBlackList();
|
if (list.contains(info.packageName)) {
|
||||||
if (blackList.contains(info.packageName)) {
|
|
||||||
rmList.add(info);
|
rmList.add(info);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
@ -117,8 +112,8 @@ public class AppAdapter extends RecyclerView.Adapter<AppAdapter.ViewHolder> impl
|
||||||
checkedList = generateCheckedList();
|
checkedList = generateCheckedList();
|
||||||
sortApps();
|
sortApps();
|
||||||
showList = fullList;
|
showList = fullList;
|
||||||
if (callback != null) {
|
if (activity != null) {
|
||||||
callback.onDataReady();
|
activity.onDataReady();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -312,9 +307,7 @@ public class AppAdapter extends RecyclerView.Adapter<AppAdapter.ViewHolder> impl
|
||||||
holder.mSwitch.setOnCheckedChangeListener((v, isChecked) ->
|
holder.mSwitch.setOnCheckedChangeListener((v, isChecked) ->
|
||||||
onCheckedChange(v, isChecked, info));
|
onCheckedChange(v, isChecked, info));
|
||||||
holder.itemView.setOnClickListener(v -> {
|
holder.itemView.setOnClickListener(v -> {
|
||||||
if (callback != null) {
|
AppHelper.showMenu(activity, activity.getSupportFragmentManager(), v, info);
|
||||||
callback.onItemClick(v, info);
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -346,12 +339,6 @@ public class AppAdapter extends RecyclerView.Adapter<AppAdapter.ViewHolder> impl
|
||||||
// override this to implements your functions
|
// override this to implements your functions
|
||||||
}
|
}
|
||||||
|
|
||||||
public interface Callback {
|
|
||||||
void onDataReady();
|
|
||||||
|
|
||||||
void onItemClick(View v, ApplicationInfo info);
|
|
||||||
}
|
|
||||||
|
|
||||||
static class ViewHolder extends RecyclerView.ViewHolder {
|
static class ViewHolder extends RecyclerView.ViewHolder {
|
||||||
|
|
||||||
ImageView appIcon;
|
ImageView appIcon;
|
||||||
|
|
@ -372,7 +359,7 @@ public class AppAdapter extends RecyclerView.Adapter<AppAdapter.ViewHolder> impl
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class ApplicationFilter extends Filter {
|
private class ApplicationFilter extends Filter {
|
||||||
|
|
||||||
private boolean lowercaseContains(String s, CharSequence filter) {
|
private boolean lowercaseContains(String s, CharSequence filter) {
|
||||||
return !TextUtils.isEmpty(s) && s.toLowerCase().contains(filter);
|
return !TextUtils.isEmpty(s) && s.toLowerCase().contains(filter);
|
||||||
|
|
|
||||||
|
|
@ -10,8 +10,6 @@ import android.view.View;
|
||||||
import android.widget.Toast;
|
import android.widget.Toast;
|
||||||
|
|
||||||
import androidx.annotation.NonNull;
|
import androidx.annotation.NonNull;
|
||||||
import androidx.appcompat.view.menu.MenuBuilder;
|
|
||||||
import androidx.appcompat.view.menu.MenuPopupHelper;
|
|
||||||
import androidx.appcompat.widget.PopupMenu;
|
import androidx.appcompat.widget.PopupMenu;
|
||||||
import androidx.fragment.app.FragmentManager;
|
import androidx.fragment.app.FragmentManager;
|
||||||
|
|
||||||
|
|
@ -20,14 +18,11 @@ import org.meowcat.edxposed.manager.Constants;
|
||||||
import org.meowcat.edxposed.manager.R;
|
import org.meowcat.edxposed.manager.R;
|
||||||
import org.meowcat.edxposed.manager.util.CompileUtil;
|
import org.meowcat.edxposed.manager.util.CompileUtil;
|
||||||
|
|
||||||
import java.io.BufferedReader;
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileNotFoundException;
|
|
||||||
import java.io.FileOutputStream;
|
|
||||||
import java.io.FileReader;
|
|
||||||
import java.io.FileWriter;
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.PrintWriter;
|
import java.nio.file.Files;
|
||||||
|
import java.nio.file.Path;
|
||||||
|
import java.nio.file.Paths;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
@ -47,7 +42,7 @@ public class AppHelper {
|
||||||
|
|
||||||
private static final HashMap<String, List<String>> scopeList = new HashMap<>();
|
private static final HashMap<String, List<String>> scopeList = new HashMap<>();
|
||||||
|
|
||||||
static void makeSurePath() {
|
public static void makeSurePath() {
|
||||||
App.mkdir(WHITE_LIST_PATH);
|
App.mkdir(WHITE_LIST_PATH);
|
||||||
App.mkdir(BLACK_LIST_PATH);
|
App.mkdir(BLACK_LIST_PATH);
|
||||||
}
|
}
|
||||||
|
|
@ -56,143 +51,61 @@ public class AppHelper {
|
||||||
return new File(BASE_PATH + WHITE_LIST_MODE).exists();
|
return new File(BASE_PATH + WHITE_LIST_MODE).exists();
|
||||||
}
|
}
|
||||||
|
|
||||||
private static boolean addWhiteList(String packageName) {
|
|
||||||
return whiteListFileName(packageName, true);
|
public static List<String> getAppList() {
|
||||||
|
return getAppList(isWhiteListMode());
|
||||||
}
|
}
|
||||||
|
|
||||||
private static boolean addBlackList(String packageName) {
|
public static List<String> getAppList(boolean white) {
|
||||||
if (forceWhiteList.contains(packageName)) {
|
Path dir = Paths.get(BASE_PATH + (white ? WHITE_LIST_PATH : BLACK_LIST_PATH));
|
||||||
removeBlackList(packageName);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
return blackListFileName(packageName, true);
|
|
||||||
}
|
|
||||||
|
|
||||||
private static boolean removeWhiteList(String packageName) {
|
|
||||||
if (forceWhiteList.contains(packageName)) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
return whiteListFileName(packageName, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
private static boolean removeBlackList(String packageName) {
|
|
||||||
return blackListFileName(packageName, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
static List<String> getBlackList() {
|
|
||||||
File file = new File(BASE_PATH + BLACK_LIST_PATH);
|
|
||||||
File[] files = file.listFiles();
|
|
||||||
if (files == null) {
|
|
||||||
return new ArrayList<>();
|
|
||||||
}
|
|
||||||
List<String> s = new ArrayList<>();
|
List<String> s = new ArrayList<>();
|
||||||
for (File file1 : files) {
|
try {
|
||||||
if (!file1.isDirectory()) {
|
Files.list(dir).forEach(path -> {
|
||||||
s.add(file1.getName());
|
if (!Files.isDirectory(path)) {
|
||||||
}
|
String packageName = path.getFileName().toString();
|
||||||
}
|
if (forceWhiteList.contains(packageName)) {
|
||||||
for (String pn : forceWhiteList) {
|
createAppListFile(packageName, white, white);
|
||||||
if (s.contains(pn)) {
|
} else {
|
||||||
s.remove(pn);
|
s.add(packageName);
|
||||||
removeBlackList(pn);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return s;
|
|
||||||
}
|
|
||||||
|
|
||||||
static List<String> getWhiteList() {
|
|
||||||
File file = new File(BASE_PATH + WHITE_LIST_PATH);
|
|
||||||
File[] files = file.listFiles();
|
|
||||||
if (files == null) {
|
|
||||||
return forceWhiteList;
|
|
||||||
}
|
|
||||||
List<String> result = new ArrayList<>();
|
|
||||||
for (File file1 : files) {
|
|
||||||
result.add(file1.getName());
|
|
||||||
}
|
|
||||||
for (String pn : forceWhiteList) {
|
|
||||||
if (!result.contains(pn)) {
|
|
||||||
result.add(pn);
|
|
||||||
addWhiteList(pn);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressLint("WorldReadableFiles")
|
|
||||||
private static Boolean whiteListFileName(String packageName, boolean isAdd) {
|
|
||||||
boolean returns = true;
|
|
||||||
File file = new File(BASE_PATH + WHITE_LIST_PATH + packageName);
|
|
||||||
if (isAdd) {
|
|
||||||
if (!file.exists()) {
|
|
||||||
FileOutputStream fos = null;
|
|
||||||
try {
|
|
||||||
fos = new FileOutputStream(file.getPath());
|
|
||||||
} catch (FileNotFoundException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
} finally {
|
|
||||||
if (fos != null) {
|
|
||||||
try {
|
|
||||||
fos.close();
|
|
||||||
} catch (IOException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
try {
|
|
||||||
returns = file.createNewFile();
|
|
||||||
} catch (IOException e1) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
});
|
||||||
} else {
|
return s;
|
||||||
if (file.exists()) {
|
} catch (IOException e) {
|
||||||
returns = file.delete();
|
return s;
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return returns;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressLint("WorldReadableFiles")
|
private static boolean createAppListFile(String packageName, boolean white, boolean add) {
|
||||||
private static Boolean blackListFileName(String packageName, boolean isAdd) {
|
Path path = Paths.get(BASE_PATH + (white ? WHITE_LIST_PATH : BLACK_LIST_PATH) + packageName);
|
||||||
boolean returns = true;
|
try {
|
||||||
File file = new File(BASE_PATH + BLACK_LIST_PATH + packageName);
|
if (Files.exists(path)) {
|
||||||
if (isAdd) {
|
if (!add) {
|
||||||
if (!file.exists()) {
|
Files.delete(path);
|
||||||
FileOutputStream fos = null;
|
|
||||||
try {
|
|
||||||
fos = new FileOutputStream(file.getPath());
|
|
||||||
} catch (FileNotFoundException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
} finally {
|
|
||||||
if (fos != null) {
|
|
||||||
try {
|
|
||||||
fos.close();
|
|
||||||
} catch (IOException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
try {
|
|
||||||
returns = file.createNewFile();
|
|
||||||
} catch (IOException e1) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
} else if (add) {
|
||||||
|
Files.createFile(path);
|
||||||
}
|
}
|
||||||
} else {
|
return true;
|
||||||
if (file.exists()) {
|
} catch (IOException e) {
|
||||||
returns = file.delete();
|
e.printStackTrace();
|
||||||
}
|
return false;
|
||||||
}
|
}
|
||||||
return returns;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static boolean addPackageName(boolean isWhiteListMode, String packageName) {
|
static boolean setPackageAppList(String packageName, boolean add) {
|
||||||
return isWhiteListMode ? addWhiteList(packageName) : addBlackList(packageName);
|
return setPackageAppList(packageName, isWhiteListMode(), add);
|
||||||
}
|
}
|
||||||
|
|
||||||
static boolean removePackageName(boolean isWhiteListMode, String packageName) {
|
static boolean setPackageAppList(String packageName, boolean white, boolean add) {
|
||||||
return isWhiteListMode ? removeWhiteList(packageName) : removeBlackList(packageName);
|
if (add && !white && forceWhiteList.contains(packageName)) {
|
||||||
|
createAppListFile(packageName, false, false);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (!add && white && forceWhiteList.contains(packageName)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return createAppListFile(packageName, white, add);
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressLint("RestrictedApi")
|
@SuppressLint("RestrictedApi")
|
||||||
|
|
@ -240,19 +153,14 @@ public class AppHelper {
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
});
|
});
|
||||||
MenuPopupHelper menuHelper = new MenuPopupHelper(context, (MenuBuilder) appMenu.getMenu(), anchor);
|
appMenu.show();
|
||||||
menuHelper.setForceShowIcon(true);
|
|
||||||
menuHelper.show();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static List<String> getEnabledModuleList() {
|
public static List<String> getEnabledModuleList() {
|
||||||
File file = new File(Constants.getEnabledModulesListFile());
|
Path path = Paths.get(Constants.getEnabledModulesListFile());
|
||||||
List<String> s = new ArrayList<>();
|
List<String> s = new ArrayList<>();
|
||||||
try {
|
try {
|
||||||
BufferedReader bufferedReader = new BufferedReader(new FileReader(file));
|
s = Files.readAllLines(path);
|
||||||
for (String line; (line = bufferedReader.readLine()) != null; ) {
|
|
||||||
s.add(line);
|
|
||||||
}
|
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
|
|
@ -263,13 +171,10 @@ public class AppHelper {
|
||||||
if (scopeList.containsKey(modulePackageName)) {
|
if (scopeList.containsKey(modulePackageName)) {
|
||||||
return scopeList.get(modulePackageName);
|
return scopeList.get(modulePackageName);
|
||||||
}
|
}
|
||||||
File file = new File(BASE_PATH + String.format(SCOPE_LIST_PATH, modulePackageName));
|
Path path = Paths.get(BASE_PATH + String.format(SCOPE_LIST_PATH, modulePackageName));
|
||||||
List<String> s = new ArrayList<>();
|
List<String> s = new ArrayList<>();
|
||||||
try {
|
try {
|
||||||
BufferedReader bufferedReader = new BufferedReader(new FileReader(file));
|
s = Files.readAllLines(path);
|
||||||
for (String line; (line = bufferedReader.readLine()) != null; ) {
|
|
||||||
s.add(line);
|
|
||||||
}
|
|
||||||
scopeList.put(modulePackageName, s);
|
scopeList.put(modulePackageName, s);
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
|
|
@ -279,17 +184,19 @@ public class AppHelper {
|
||||||
|
|
||||||
@SuppressLint("WorldReadableFiles")
|
@SuppressLint("WorldReadableFiles")
|
||||||
static boolean saveScopeList(String modulePackageName, List<String> list) {
|
static boolean saveScopeList(String modulePackageName, List<String> list) {
|
||||||
File file = new File(BASE_PATH + String.format(SCOPE_LIST_PATH, modulePackageName));
|
Path path = Paths.get(BASE_PATH + String.format(SCOPE_LIST_PATH, modulePackageName));
|
||||||
if (list.size() == 0) {
|
if (list.size() == 0) {
|
||||||
scopeList.put(modulePackageName, list);
|
scopeList.put(modulePackageName, list);
|
||||||
return file.delete();
|
try {
|
||||||
|
Files.delete(path);
|
||||||
|
return true;
|
||||||
|
} catch (IOException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
PrintWriter pr = new PrintWriter(new FileWriter(file));
|
Files.write(path, list);
|
||||||
for (String line : list) {
|
|
||||||
pr.println(line);
|
|
||||||
}
|
|
||||||
pr.close();
|
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
return false;
|
return false;
|
||||||
|
|
|
||||||
|
|
@ -1,13 +1,14 @@
|
||||||
package org.meowcat.edxposed.manager.adapters;
|
package org.meowcat.edxposed.manager.adapters;
|
||||||
|
|
||||||
import android.content.Context;
|
|
||||||
import android.content.pm.ApplicationInfo;
|
import android.content.pm.ApplicationInfo;
|
||||||
import android.widget.CompoundButton;
|
import android.widget.CompoundButton;
|
||||||
|
|
||||||
|
import com.google.android.material.snackbar.Snackbar;
|
||||||
|
|
||||||
import org.meowcat.edxposed.manager.App;
|
import org.meowcat.edxposed.manager.App;
|
||||||
import org.meowcat.edxposed.manager.R;
|
import org.meowcat.edxposed.manager.R;
|
||||||
|
import org.meowcat.edxposed.manager.ui.activity.AppListActivity;
|
||||||
import org.meowcat.edxposed.manager.util.ModuleUtil;
|
import org.meowcat.edxposed.manager.util.ModuleUtil;
|
||||||
import org.meowcat.edxposed.manager.util.ToastUtil;
|
|
||||||
|
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
@ -15,36 +16,22 @@ import java.util.List;
|
||||||
|
|
||||||
public class BlackListAdapter extends AppAdapter {
|
public class BlackListAdapter extends AppAdapter {
|
||||||
|
|
||||||
private final boolean isWhiteListMode;
|
|
||||||
private List<String> checkedList;
|
private List<String> checkedList;
|
||||||
|
|
||||||
public BlackListAdapter(Context context, boolean isWhiteListMode) {
|
public BlackListAdapter(AppListActivity activity) {
|
||||||
super(context);
|
super(activity);
|
||||||
this.isWhiteListMode = isWhiteListMode;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<String> generateCheckedList() {
|
public List<String> generateCheckedList() {
|
||||||
if (App.getPreferences().getBoolean("hook_modules", true)) {
|
|
||||||
Collection<ModuleUtil.InstalledModule> installedModules = ModuleUtil.getInstance().getModules().values();
|
|
||||||
for (ModuleUtil.InstalledModule info : installedModules) {
|
|
||||||
AppHelper.forceWhiteList.add(info.packageName);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
AppHelper.makeSurePath();
|
AppHelper.makeSurePath();
|
||||||
if (isWhiteListMode) {
|
checkedList = AppHelper.getAppList(AppHelper.isWhiteListMode());
|
||||||
checkedList = AppHelper.getWhiteList();
|
|
||||||
} else {
|
|
||||||
checkedList = AppHelper.getBlackList();
|
|
||||||
}
|
|
||||||
return checkedList;
|
return checkedList;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void onCheckedChange(CompoundButton view, boolean isChecked, ApplicationInfo info) {
|
protected void onCheckedChange(CompoundButton view, boolean isChecked, ApplicationInfo info) {
|
||||||
boolean success = isChecked ?
|
boolean success = AppHelper.setPackageAppList(info.packageName, isChecked);
|
||||||
AppHelper.addPackageName(isWhiteListMode, info.packageName) :
|
|
||||||
AppHelper.removePackageName(isWhiteListMode, info.packageName);
|
|
||||||
if (success) {
|
if (success) {
|
||||||
if (isChecked) {
|
if (isChecked) {
|
||||||
checkedList.add(info.packageName);
|
checkedList.add(info.packageName);
|
||||||
|
|
@ -52,7 +39,7 @@ public class BlackListAdapter extends AppAdapter {
|
||||||
checkedList.remove(info.packageName);
|
checkedList.remove(info.packageName);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
ToastUtil.showShortToast(context, R.string.add_package_failed);
|
activity.makeSnackBar(R.string.add_package_failed, Snackbar.LENGTH_SHORT);
|
||||||
view.setChecked(!isChecked);
|
view.setChecked(!isChecked);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,13 +1,13 @@
|
||||||
package org.meowcat.edxposed.manager.adapters;
|
package org.meowcat.edxposed.manager.adapters;
|
||||||
|
|
||||||
import android.app.Activity;
|
|
||||||
import android.content.Context;
|
|
||||||
import android.content.pm.ApplicationInfo;
|
import android.content.pm.ApplicationInfo;
|
||||||
import android.widget.CompoundButton;
|
import android.widget.CompoundButton;
|
||||||
|
|
||||||
|
import com.google.android.material.snackbar.Snackbar;
|
||||||
|
|
||||||
import org.meowcat.edxposed.manager.R;
|
import org.meowcat.edxposed.manager.R;
|
||||||
|
import org.meowcat.edxposed.manager.ui.activity.AppListActivity;
|
||||||
import org.meowcat.edxposed.manager.ui.widget.MasterSwitch;
|
import org.meowcat.edxposed.manager.ui.widget.MasterSwitch;
|
||||||
import org.meowcat.edxposed.manager.util.ToastUtil;
|
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
@ -19,11 +19,10 @@ public class ScopeAdapter extends AppAdapter {
|
||||||
private List<String> checkedList;
|
private List<String> checkedList;
|
||||||
private final MasterSwitch masterSwitch;
|
private final MasterSwitch masterSwitch;
|
||||||
|
|
||||||
public ScopeAdapter(Context context, String modulePackageName, MasterSwitch masterSwitch) {
|
public ScopeAdapter(AppListActivity activity, String modulePackageName, MasterSwitch masterSwitch) {
|
||||||
super(context);
|
super(activity);
|
||||||
this.modulePackageName = modulePackageName;
|
this.modulePackageName = modulePackageName;
|
||||||
this.masterSwitch = masterSwitch;
|
this.masterSwitch = masterSwitch;
|
||||||
masterSwitch.setTitle(context.getString(R.string.enable_scope));
|
|
||||||
masterSwitch.setOnCheckedChangedListener(new MasterSwitch.OnCheckedChangeListener() {
|
masterSwitch.setOnCheckedChangedListener(new MasterSwitch.OnCheckedChangeListener() {
|
||||||
@Override
|
@Override
|
||||||
public void onCheckedChanged(boolean checked) {
|
public void onCheckedChanged(boolean checked) {
|
||||||
|
|
@ -45,7 +44,7 @@ public class ScopeAdapter extends AppAdapter {
|
||||||
scopeList.retainAll(list);
|
scopeList.retainAll(list);
|
||||||
checkedList = scopeList;
|
checkedList = scopeList;
|
||||||
enabled = checkedList.size() != 0;
|
enabled = checkedList.size() != 0;
|
||||||
((Activity) context).runOnUiThread(() -> masterSwitch.setChecked(enabled));
|
activity.runOnUiThread(() -> masterSwitch.setChecked(enabled));
|
||||||
return checkedList;
|
return checkedList;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -57,7 +56,7 @@ public class ScopeAdapter extends AppAdapter {
|
||||||
checkedList.remove(info.packageName);
|
checkedList.remove(info.packageName);
|
||||||
}
|
}
|
||||||
if (!AppHelper.saveScopeList(modulePackageName, checkedList)) {
|
if (!AppHelper.saveScopeList(modulePackageName, checkedList)) {
|
||||||
ToastUtil.showShortToast(context, R.string.add_package_failed);
|
activity.makeSnackBar(R.string.add_package_failed, Snackbar.LENGTH_SHORT);
|
||||||
if (!isChecked) {
|
if (!isChecked) {
|
||||||
checkedList.add(info.packageName);
|
checkedList.add(info.packageName);
|
||||||
} else {
|
} else {
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,5 @@
|
||||||
package org.meowcat.edxposed.manager.ui.activity;
|
package org.meowcat.edxposed.manager.ui.activity;
|
||||||
|
|
||||||
import android.content.pm.ApplicationInfo;
|
|
||||||
import android.os.Bundle;
|
import android.os.Bundle;
|
||||||
import android.os.Handler;
|
import android.os.Handler;
|
||||||
import android.os.Looper;
|
import android.os.Looper;
|
||||||
|
|
@ -8,13 +7,17 @@ import android.text.TextUtils;
|
||||||
import android.view.Menu;
|
import android.view.Menu;
|
||||||
import android.view.MenuItem;
|
import android.view.MenuItem;
|
||||||
import android.view.View;
|
import android.view.View;
|
||||||
|
import android.widget.Toast;
|
||||||
|
|
||||||
import androidx.annotation.NonNull;
|
import androidx.annotation.NonNull;
|
||||||
import androidx.annotation.Nullable;
|
import androidx.annotation.Nullable;
|
||||||
|
import androidx.annotation.StringRes;
|
||||||
import androidx.appcompat.app.ActionBar;
|
import androidx.appcompat.app.ActionBar;
|
||||||
import androidx.appcompat.widget.SearchView;
|
import androidx.appcompat.widget.SearchView;
|
||||||
import androidx.recyclerview.widget.DividerItemDecoration;
|
import androidx.recyclerview.widget.DividerItemDecoration;
|
||||||
|
|
||||||
|
import com.google.android.material.snackbar.Snackbar;
|
||||||
|
|
||||||
import org.meowcat.edxposed.manager.R;
|
import org.meowcat.edxposed.manager.R;
|
||||||
import org.meowcat.edxposed.manager.adapters.AppAdapter;
|
import org.meowcat.edxposed.manager.adapters.AppAdapter;
|
||||||
import org.meowcat.edxposed.manager.adapters.AppHelper;
|
import org.meowcat.edxposed.manager.adapters.AppHelper;
|
||||||
|
|
@ -25,7 +28,7 @@ import org.meowcat.edxposed.manager.util.LinearLayoutManagerFix;
|
||||||
|
|
||||||
import me.zhanghai.android.fastscroll.FastScrollerBuilder;
|
import me.zhanghai.android.fastscroll.FastScrollerBuilder;
|
||||||
|
|
||||||
public class AppListActivity extends BaseActivity implements AppAdapter.Callback {
|
public class AppListActivity extends BaseActivity {
|
||||||
private SearchView searchView;
|
private SearchView searchView;
|
||||||
private AppAdapter appAdapter;
|
private AppAdapter appAdapter;
|
||||||
|
|
||||||
|
|
@ -55,10 +58,9 @@ public class AppListActivity extends BaseActivity implements AppAdapter.Callback
|
||||||
bar.setSubtitle(moduleName);
|
bar.setSubtitle(moduleName);
|
||||||
appAdapter = new ScopeAdapter(this, modulePackageName, binding.masterSwitch);
|
appAdapter = new ScopeAdapter(this, modulePackageName, binding.masterSwitch);
|
||||||
} else {
|
} else {
|
||||||
final boolean isWhiteListMode = AppHelper.isWhiteListMode();
|
bar.setTitle(AppHelper.isWhiteListMode() ? R.string.title_white_list : R.string.title_black_list);
|
||||||
bar.setTitle(isWhiteListMode ? R.string.title_white_list : R.string.title_black_list);
|
|
||||||
binding.masterSwitch.setVisibility(View.GONE);
|
binding.masterSwitch.setVisibility(View.GONE);
|
||||||
appAdapter = new BlackListAdapter(this, isWhiteListMode);
|
appAdapter = new BlackListAdapter(this);
|
||||||
}
|
}
|
||||||
appAdapter.setHasStableIds(true);
|
appAdapter.setHasStableIds(true);
|
||||||
binding.recyclerView.setAdapter(appAdapter);
|
binding.recyclerView.setAdapter(appAdapter);
|
||||||
|
|
@ -72,7 +74,6 @@ public class AppListActivity extends BaseActivity implements AppAdapter.Callback
|
||||||
fastScrollerBuilder.useMd2Style();
|
fastScrollerBuilder.useMd2Style();
|
||||||
}
|
}
|
||||||
fastScrollerBuilder.build();
|
fastScrollerBuilder.build();
|
||||||
appAdapter.setCallback(this);
|
|
||||||
handler.postDelayed(runnable, 300);
|
handler.postDelayed(runnable, 300);
|
||||||
binding.swipeRefreshLayout.setOnRefreshListener(appAdapter::refresh);
|
binding.swipeRefreshLayout.setOnRefreshListener(appAdapter::refresh);
|
||||||
|
|
||||||
|
|
@ -107,7 +108,6 @@ public class AppListActivity extends BaseActivity implements AppAdapter.Callback
|
||||||
return super.onCreateOptionsMenu(menu);
|
return super.onCreateOptionsMenu(menu);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onDataReady() {
|
public void onDataReady() {
|
||||||
handler.removeCallbacks(runnable);
|
handler.removeCallbacks(runnable);
|
||||||
binding.swipeRefreshLayout.setRefreshing(false);
|
binding.swipeRefreshLayout.setRefreshing(false);
|
||||||
|
|
@ -115,11 +115,6 @@ public class AppListActivity extends BaseActivity implements AppAdapter.Callback
|
||||||
runOnUiThread(() -> appAdapter.getFilter().filter(queryStr));
|
runOnUiThread(() -> appAdapter.getFilter().filter(queryStr));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onItemClick(View v, ApplicationInfo info) {
|
|
||||||
AppHelper.showMenu(this, getSupportFragmentManager(), v, info);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onBackPressed() {
|
public void onBackPressed() {
|
||||||
if (searchView.isIconified()) {
|
if (searchView.isIconified()) {
|
||||||
|
|
@ -128,4 +123,12 @@ public class AppListActivity extends BaseActivity implements AppAdapter.Callback
|
||||||
searchView.setIconified(true);
|
searchView.setIconified(true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void makeSnackBar(@StringRes int text, @Snackbar.Duration int duration) {
|
||||||
|
if (binding != null) {
|
||||||
|
Snackbar.make(binding.snackbar, text, duration).show();
|
||||||
|
} else {
|
||||||
|
Toast.makeText(this, text, duration == Snackbar.LENGTH_LONG ? Toast.LENGTH_LONG : Toast.LENGTH_SHORT).show();
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -12,8 +12,6 @@ import com.bumptech.glide.Glide;
|
||||||
|
|
||||||
import org.meowcat.edxposed.manager.Constants;
|
import org.meowcat.edxposed.manager.Constants;
|
||||||
import org.meowcat.edxposed.manager.R;
|
import org.meowcat.edxposed.manager.R;
|
||||||
import org.meowcat.edxposed.manager.adapters.AppHelper;
|
|
||||||
import org.meowcat.edxposed.manager.adapters.BlackListAdapter;
|
|
||||||
import org.meowcat.edxposed.manager.databinding.ActivityMainBinding;
|
import org.meowcat.edxposed.manager.databinding.ActivityMainBinding;
|
||||||
import org.meowcat.edxposed.manager.ui.fragment.StatusDialogBuilder;
|
import org.meowcat.edxposed.manager.ui.fragment.StatusDialogBuilder;
|
||||||
import org.meowcat.edxposed.manager.util.GlideHelper;
|
import org.meowcat.edxposed.manager.util.GlideHelper;
|
||||||
|
|
@ -95,7 +93,6 @@ public class MainActivity extends BaseActivity implements ModuleUtil.ModuleListe
|
||||||
binding.statusIcon.setImageResource(R.drawable.ic_error);
|
binding.statusIcon.setImageResource(R.drawable.ic_error);
|
||||||
}
|
}
|
||||||
binding.modulesSummary.setText(String.format(getString(R.string.ModulesDetail), ModuleUtil.getInstance().getEnabledModules().size()));
|
binding.modulesSummary.setText(String.format(getString(R.string.ModulesDetail), ModuleUtil.getInstance().getEnabledModules().size()));
|
||||||
new Thread(() -> new BlackListAdapter(getApplicationContext(), AppHelper.isWhiteListMode()).generateCheckedList());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
||||||
|
|
@ -19,11 +19,8 @@ import org.meowcat.edxposed.manager.R;
|
||||||
|
|
||||||
public class MasterSwitch extends FrameLayout implements View.OnClickListener, Checkable {
|
public class MasterSwitch extends FrameLayout implements View.OnClickListener, Checkable {
|
||||||
|
|
||||||
private TextView masterTitle;
|
|
||||||
private SwitchCompat switchCompat;
|
private SwitchCompat switchCompat;
|
||||||
|
|
||||||
private String title;
|
|
||||||
|
|
||||||
private OnCheckedChangeListener listener;
|
private OnCheckedChangeListener listener;
|
||||||
|
|
||||||
private boolean isChecked;
|
private boolean isChecked;
|
||||||
|
|
@ -57,17 +54,13 @@ public class MasterSwitch extends FrameLayout implements View.OnClickListener, C
|
||||||
drawable.addState(new int[]{}, new ColorDrawable(colorOff));
|
drawable.addState(new int[]{}, new ColorDrawable(colorOff));
|
||||||
setBackground(drawable);
|
setBackground(drawable);
|
||||||
|
|
||||||
masterTitle = findViewById(android.R.id.title);
|
TextView masterTitle = findViewById(android.R.id.title);
|
||||||
|
masterTitle.setText(R.string.enable_scope);
|
||||||
switchCompat = findViewById(R.id.switchWidget);
|
switchCompat = findViewById(R.id.switchWidget);
|
||||||
|
|
||||||
setOnClickListener(this);
|
setOnClickListener(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void setTitle(String title) {
|
|
||||||
this.title = title;
|
|
||||||
masterTitle.setText(title);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void updateViews() {
|
private void updateViews() {
|
||||||
if (switchCompat != null) {
|
if (switchCompat != null) {
|
||||||
setSelected(isChecked);
|
setSelected(isChecked);
|
||||||
|
|
|
||||||
|
|
@ -21,6 +21,7 @@ import org.meowcat.edxposed.manager.databinding.ActivityModulesBinding;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.PrintWriter;
|
import java.io.PrintWriter;
|
||||||
|
import java.util.Collection;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.Iterator;
|
import java.util.Iterator;
|
||||||
import java.util.LinkedList;
|
import java.util.LinkedList;
|
||||||
|
|
@ -76,6 +77,7 @@ public final class ModuleUtil {
|
||||||
}
|
}
|
||||||
|
|
||||||
Map<String, InstalledModule> modules = new HashMap<>();
|
Map<String, InstalledModule> modules = new HashMap<>();
|
||||||
|
AppHelper.forceWhiteList.clear();
|
||||||
|
|
||||||
for (PackageInfo pkg : pm.getInstalledPackages(PackageManager.GET_META_DATA)) {
|
for (PackageInfo pkg : pm.getInstalledPackages(PackageManager.GET_META_DATA)) {
|
||||||
ApplicationInfo app = pkg.applicationInfo;
|
ApplicationInfo app = pkg.applicationInfo;
|
||||||
|
|
@ -85,6 +87,7 @@ public final class ModuleUtil {
|
||||||
if (app.metaData != null && app.metaData.containsKey("xposedmodule")) {
|
if (app.metaData != null && app.metaData.containsKey("xposedmodule")) {
|
||||||
InstalledModule installed = new InstalledModule(pkg, false);
|
InstalledModule installed = new InstalledModule(pkg, false);
|
||||||
modules.put(pkg.packageName, installed);
|
modules.put(pkg.packageName, installed);
|
||||||
|
AppHelper.forceWhiteList.add(pkg.packageName);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,26 +0,0 @@
|
||||||
package org.meowcat.edxposed.manager.util.chrome;
|
|
||||||
|
|
||||||
import android.text.style.URLSpan;
|
|
||||||
import android.view.View;
|
|
||||||
|
|
||||||
import org.meowcat.edxposed.manager.ui.activity.BaseActivity;
|
|
||||||
import org.meowcat.edxposed.manager.util.NavUtil;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Created by Nikola D. on 12/23/2015.
|
|
||||||
*/
|
|
||||||
public class CustomTabsURLSpan extends URLSpan {
|
|
||||||
|
|
||||||
private final BaseActivity activity;
|
|
||||||
|
|
||||||
CustomTabsURLSpan(BaseActivity activity, String url) {
|
|
||||||
super(url);
|
|
||||||
this.activity = activity;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onClick(View widget) {
|
|
||||||
String url = getURL();
|
|
||||||
NavUtil.startURL(activity, url);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Loading…
Reference in New Issue