Revert "Added an option to switch between internal and external storage"

This reverts commit 98c4b88961.
This commit is contained in:
X1nto 2021-04-18 15:31:54 +04:00
parent f82dc4eecf
commit a570aae1a1
18 changed files with 44 additions and 210 deletions

View File

@ -24,6 +24,6 @@ object MicrogDownloader {
fun startMicrogInstall(context: Context) { fun startMicrogInstall(context: Context) {
installing.postValue(true) installing.postValue(true)
postReset() postReset()
install(context.getFilePathInStorage("$folderName/$fileName"), context) install("$folderName/$fileName".managerFilepath, context)
} }
} }

View File

@ -68,6 +68,6 @@ object MusicDownloader {
if (variant == "root") if (variant == "root")
installMusicRoot(context) installMusicRoot(context)
else else
install(context.getFilePathInStorage("music/nonroot/nonroot.apk"), context) install("music/nonroot/nonroot.apk".managerFilepath, context)
} }
} }

View File

@ -41,7 +41,7 @@ object VancedDownloader {
prefs = context.installPrefs prefs = context.installPrefs
variant = defPrefs.managerVariant variant = defPrefs.managerVariant
folderName = "vanced/$variant" folderName = "vanced/$variant"
downloadPath = context.getFilePathInStorage(folderName!!) downloadPath = context.getExternalFilesDir(folderName)?.path
File(downloadPath.toString()).deleteRecursively() File(downloadPath.toString()).deleteRecursively()
prefs.lang?.let { prefs.lang?.let {
lang = it.split(", ").toMutableList() lang = it.split(", ").toMutableList()

View File

@ -102,7 +102,7 @@ class MainActivity : AppCompatActivity() {
setFinalTheme() setFinalTheme()
super.onResume() super.onResume()
Crowdin.registerDataLoadingObserver(loadingObserver) Crowdin.registerDataLoadingObserver(loadingObserver)
if (defPrefs.managerStorage == externalPath && !canAccessStorage(this)) { if (!canAccessStorage(this)) {
DialogContainer.storageDialog(this) DialogContainer.storageDialog(this)
} }
} }

View File

@ -42,7 +42,7 @@ object DialogContainer {
setMessage(R.string.storage_access_required_summary) setMessage(R.string.storage_access_required_summary)
setPositiveButton(R.string.auth_dialog_ok) { dialog, _ -> setPositiveButton(R.string.auth_dialog_ok) { dialog, _ ->
dialog.cancel() dialog.cancel()
requestStoragePerms(activity, null) requestStoragePerms(activity)
} }
setCancelable(false) setCancelable(false)
create() create()

View File

@ -1,67 +0,0 @@
package com.vanced.manager.ui.dialogs
import android.os.Bundle
import android.view.LayoutInflater
import android.view.ViewGroup
import androidx.activity.result.contract.ActivityResultContracts
import androidx.preference.PreferenceManager.getDefaultSharedPreferences
import com.google.android.material.radiobutton.MaterialRadioButton
import com.vanced.manager.core.ui.base.BindingBottomSheetDialogFragment
import com.vanced.manager.databinding.DialogManagerStorageBinding
import com.vanced.manager.utils.*
class ManagerStorageDialog : BindingBottomSheetDialogFragment<DialogManagerStorageBinding>() {
private val permissionLauncher = registerForActivityResult(ActivityResultContracts.RequestMultiplePermissions()) { results ->
if (results.all { it.value == true }) {
prefs.managerStorage = externalPath
} else {
prefs.managerStorage = internalPath
}
dismiss()
}
companion object {
fun newInstance(): ManagerStorageDialog = ManagerStorageDialog().apply {
arguments = Bundle()
}
}
private val prefs by lazy { getDefaultSharedPreferences(requireActivity()) }
override fun binding(
inflater: LayoutInflater,
container: ViewGroup?,
savedInstanceState: Bundle?
) = DialogManagerStorageBinding.inflate(inflater, container, false)
override fun otherSetups() {
bindData()
}
private fun bindData() {
with(binding) {
val storage = prefs.managerStorage
root.findViewWithTag<MaterialRadioButton>(storage).isChecked = true
storageSave.setOnClickListener {
val newPref = storageRadiogroup.checkedButtonTag
if (storage != newPref) {
if (newPref == externalPath) {
if (!canAccessStorage(requireActivity())) {
return@setOnClickListener requestStoragePerms(requireActivity(), permissionLauncher)
}
prefs.managerStorage = externalPath
} else {
prefs.managerStorage = internalPath
}
dismiss()
requireActivity().recreate()
} else {
dismiss()
}
}
}
}
}

View File

@ -10,7 +10,7 @@ import com.vanced.manager.core.ui.base.BindingFragment
import com.vanced.manager.databinding.FragmentLogBinding import com.vanced.manager.databinding.FragmentLogBinding
import com.vanced.manager.utils.AppUtils import com.vanced.manager.utils.AppUtils
import com.vanced.manager.utils.AppUtils.logs import com.vanced.manager.utils.AppUtils.logs
import com.vanced.manager.utils.getFilePathInStorage import com.vanced.manager.utils.managerFilepath
import com.vanced.manager.utils.performStorageAction import com.vanced.manager.utils.performStorageAction
import java.io.File import java.io.File
import java.io.FileWriter import java.io.FileWriter
@ -42,7 +42,7 @@ class LogFragment : BindingFragment<FragmentLogBinding>() {
val second = calendar.get(Calendar.SECOND) val second = calendar.get(Calendar.SECOND)
try { try {
performStorageAction(requireActivity()) { performStorageAction(requireActivity()) {
val logPath = File(requireActivity().getFilePathInStorage("logs")).apply { val logPath = File("logs".managerFilepath).apply {
if (!exists()) { if (!exists()) {
mkdirs() mkdirs()
} }

View File

@ -19,7 +19,10 @@ import com.vanced.manager.core.ui.base.BindingFragment
import com.vanced.manager.core.ui.ext.showDialog import com.vanced.manager.core.ui.ext.showDialog
import com.vanced.manager.databinding.FragmentSettingsBinding import com.vanced.manager.databinding.FragmentSettingsBinding
import com.vanced.manager.ui.dialogs.* import com.vanced.manager.ui.dialogs.*
import com.vanced.manager.utils.* import com.vanced.manager.utils.accentColor
import com.vanced.manager.utils.defAccentColor
import com.vanced.manager.utils.getLanguageFormat
import com.vanced.manager.utils.toHex
import java.io.File import java.io.File
class SettingsFragment : BindingFragment<FragmentSettingsBinding>() { class SettingsFragment : BindingFragment<FragmentSettingsBinding>() {
@ -57,7 +60,6 @@ class SettingsFragment : BindingFragment<FragmentSettingsBinding>() {
bindManagerTheme() bindManagerTheme()
bindManagerAccentColor() bindManagerAccentColor()
bindManagerLanguage() bindManagerLanguage()
bindManagerStorage()
selectApps.setOnClickListener { showDialog(SelectAppsDialog()) } selectApps.setOnClickListener { showDialog(SelectAppsDialog()) }
} }
} }
@ -84,21 +86,6 @@ class SettingsFragment : BindingFragment<FragmentSettingsBinding>() {
} }
} }
private fun FragmentSettingsBinding.bindManagerStorage() {
managerStorage.apply {
setSummary(
getString(
if (prefs.managerStorage == externalPath) {
R.string.storage_external
} else {
R.string.storage_internal
}
)
)
setOnClickListener { showDialog(ManagerStorageDialog()) }
}
}
private fun FragmentSettingsBinding.bindServiceDTimer() { private fun FragmentSettingsBinding.bindServiceDTimer() {
servicedTimer.apply { servicedTimer.apply {
if (variant == "root") this.isVisible = true if (variant == "root") this.isVisible = true
@ -109,13 +96,10 @@ class SettingsFragment : BindingFragment<FragmentSettingsBinding>() {
private fun FragmentSettingsBinding.bindClearFiles() { private fun FragmentSettingsBinding.bindClearFiles() {
clearFiles.setOnClickListener { clearFiles.setOnClickListener {
with(requireActivity()) { with(requireActivity()) {
performStorageAction(this) { managerPath -> listOf("vanced/nonroot", "vanced/root", "music/nonroot", "music/root", "microg").forEach { dir ->
if (File(managerPath).deleteRecursively()) { File(getExternalFilesDir(dir)?.path.toString()).deleteRecursively()
Toast.makeText(this, getString(R.string.cleared_files), Toast.LENGTH_SHORT).show()
} else {
Toast.makeText(this, getString(R.string.clear_files_failed), Toast.LENGTH_SHORT).show()
}
} }
Toast.makeText(this, getString(R.string.cleared_files), Toast.LENGTH_SHORT).show()
} }
} }
} }

View File

@ -110,7 +110,7 @@ class HomeViewModel(private val activity: FragmentActivity): ViewModel() {
activity.getString(R.string.vanced) -> { activity.getString(R.string.vanced) -> {
when (variant) { when (variant) {
"nonroot" -> { "nonroot" -> {
if (vancedInstallFilesExist(activity)) { if (vancedInstallFilesExist()) {
InstallationFilesDetectedDialog.newInstance(app).show(activity) InstallationFilesDetectedDialog.newInstance(app).show(activity)
} else { } else {
VancedPreferencesDialog().show(activity) VancedPreferencesDialog().show(activity)
@ -124,7 +124,7 @@ class HomeViewModel(private val activity: FragmentActivity): ViewModel() {
activity.getString(R.string.music) -> { activity.getString(R.string.music) -> {
when (variant) { when (variant) {
"nonroot" -> { "nonroot" -> {
if (musicApkExists(activity)) { if (musicApkExists()) {
InstallationFilesDetectedDialog.newInstance(app).show(activity) InstallationFilesDetectedDialog.newInstance(app).show(activity)
} else { } else {
MusicPreferencesDialog().show(activity) MusicPreferencesDialog().show(activity)
@ -136,7 +136,7 @@ class HomeViewModel(private val activity: FragmentActivity): ViewModel() {
} }
} }
activity.getString(R.string.microg) -> { activity.getString(R.string.microg) -> {
if (apkExist("microg.apk", activity)) { if (apkExist("microg.apk")) {
InstallationFilesDetectedDialog.newInstance(app).show(activity) InstallationFilesDetectedDialog.newInstance(app).show(activity)
} else { } else {
AppDownloadDialog.newInstance(app).show(activity) AppDownloadDialog.newInstance(app).show(activity)

View File

@ -49,7 +49,7 @@ object DownloadHelper : CoroutineScope by CoroutineScope(Dispatchers.IO) {
override fun onResponse(call: Call<ResponseBody>, response: Response<ResponseBody>) { override fun onResponse(call: Call<ResponseBody>, response: Response<ResponseBody>) {
if (response.isSuccessful) { if (response.isSuccessful) {
launch { launch {
if (response.body()?.let { writeFile(it, fileFolder, fileName, context) } == true) { if (response.body()?.let { writeFile(it, fileFolder, fileName) } == true) {
onDownloadComplete() onDownloadComplete()
} else { } else {
onError(response.errorBody().toString()) onError(response.errorBody().toString())
@ -78,12 +78,12 @@ object DownloadHelper : CoroutineScope by CoroutineScope(Dispatchers.IO) {
}) })
} }
fun writeFile(body: ResponseBody, folderName: String, fileName: String, context: Context): Boolean = fun writeFile(body: ResponseBody, folderName: String, fileName: String): Boolean =
try { try {
val totalBytes = body.contentLength() val totalBytes = body.contentLength()
val fileReader = ByteArray(8096) val fileReader = ByteArray(8096)
var downloadedBytes: Long = 0 var downloadedBytes: Long = 0
val dir = File(context.getFilePathInStorage(folderName)).apply { val dir = File(managerPath, folderName).apply {
if (!exists()) { if (!exists()) {
mkdirs() mkdirs()
} }
@ -114,7 +114,7 @@ object DownloadHelper : CoroutineScope by CoroutineScope(Dispatchers.IO) {
"manager.apk", "manager.apk",
context, context,
onDownloadComplete = { onDownloadComplete = {
val apk = File(context.getFilePathInStorage("manager/manager.apk")) val apk = File("manager/manager.apk".managerFilepath)
val uri = val uri =
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N)
FileProvider.getUriForFile(context, "${context.packageName}.provider", apk) FileProvider.getUriForFile(context, "${context.packageName}.provider", apk)

View File

@ -19,6 +19,8 @@ import java.util.*
val RadioGroup.checkedButtonTag: String? get() = findViewById<MaterialRadioButton>(checkedRadioButtonId)?.tag?.toString() val RadioGroup.checkedButtonTag: String? get() = findViewById<MaterialRadioButton>(checkedRadioButtonId)?.tag?.toString()
val String.managerFilepath get() = "$managerPath/$this"
fun DialogFragment.show(activity: FragmentActivity) { fun DialogFragment.show(activity: FragmentActivity) {
try { try {
show(activity.supportFragmentManager, "") show(activity.supportFragmentManager, "")

View File

@ -100,16 +100,16 @@ object PackageHelper {
} }
} }
fun apkExist(apk: String, context: Context): Boolean { fun apkExist(apk: String): Boolean {
val apkPath = File(context.getFilePathInStorage("${apk.removeSuffix(".apk")}/$apk")) val apkPath = File("${apk.removeSuffix(".apk")}/$apk".managerFilepath)
if (apkPath.exists()) if (apkPath.exists())
return true return true
return false return false
} }
fun musicApkExists(context: Context): Boolean { fun musicApkExists(): Boolean {
val apkPath = File(context.getFilePathInStorage("music/nonroot/nonroot.apk")) val apkPath = File("music/nonroot/nonroot.apk".managerFilepath)
if (apkPath.exists()) { if (apkPath.exists()) {
return true return true
} }
@ -117,8 +117,8 @@ object PackageHelper {
return false return false
} }
fun vancedInstallFilesExist(context: Context): Boolean { fun vancedInstallFilesExist(): Boolean {
val apksPath = File(context.getFilePathInStorage("vanced/nonroot")) val apksPath = File("vanced/nonroot".managerFilepath)
val splitFiles = mutableListOf<String>() val splitFiles = mutableListOf<String>()
if (apksPath.exists()) { if (apksPath.exists()) {
val files = apksPath.listFiles() val files = apksPath.listFiles()
@ -212,7 +212,7 @@ object PackageHelper {
private fun installRootApp(context: Context, app: String, appVerCode: Int?, pkg: String, modApkBool: (fileName: String) -> Boolean) = CoroutineScope(Dispatchers.IO).launch { private fun installRootApp(context: Context, app: String, appVerCode: Int?, pkg: String, modApkBool: (fileName: String) -> Boolean) = CoroutineScope(Dispatchers.IO).launch {
Shell.getShell { Shell.getShell {
val apkFilesPath = context.getFilePathInStorage("$app/root") val apkFilesPath = "$app/root".managerFilepath
val files = File(apkFilesPath).listFiles()?.toList() val files = File(apkFilesPath).listFiles()?.toList()
if (files != null) { if (files != null) {
val modApk: File? = files.lastOrNull { modApkBool(it.name) } val modApk: File? = files.lastOrNull { modApkBool(it.name) }
@ -268,7 +268,7 @@ object PackageHelper {
appName: String appName: String
) { ) {
val packageInstaller = context.packageManager.packageInstaller val packageInstaller = context.packageManager.packageInstaller
val folder = File(context.getFilePathInStorage("$appName/nonroot")) val folder = File("$appName/nonroot".managerFilepath)
var session: PackageInstaller.Session? = null var session: PackageInstaller.Session? = null
val sessionId: Int val sessionId: Int
val sessionParams = PackageInstaller.SessionParams(PackageInstaller.SessionParams.MODE_FULL_INSTALL) val sessionParams = PackageInstaller.SessionParams(PackageInstaller.SessionParams.MODE_FULL_INSTALL)

View File

@ -19,10 +19,6 @@ var SharedPreferences.managerVariant
get() = getString("vanced_variant", "nonroot") get() = getString("vanced_variant", "nonroot")
set(value) = edit { putString("vanced_variant", value) } set(value) = edit { putString("vanced_variant", value) }
var SharedPreferences.managerStorage
get() = getString("manager_storage", internalPath)
set(value) = edit { putString("manager_storage", value) }
var SharedPreferences.managerLang var SharedPreferences.managerLang
get() = getString("manager_lang", "System Default") get() = getString("manager_lang", "System Default")
set(value) = edit { putString("manager_lang", value) } set(value) = edit { putString("manager_lang", value) }

View File

@ -1,63 +1,40 @@
package com.vanced.manager.utils package com.vanced.manager.utils
import android.Manifest import android.Manifest
import android.content.Context
import android.content.Intent import android.content.Intent
import android.content.pm.PackageManager import android.content.pm.PackageManager
import android.os.Build import android.os.Build
import android.os.Environment import android.os.Environment
import android.provider.Settings import android.provider.Settings
import androidx.activity.result.ActivityResultLauncher
import androidx.fragment.app.FragmentActivity import androidx.fragment.app.FragmentActivity
import com.vanced.manager.ui.MainActivity
import com.vanced.manager.ui.dialogs.DialogContainer.storageDialog import com.vanced.manager.ui.dialogs.DialogContainer.storageDialog
const val storage = "/storage/emulated/0" @Suppress("DEPRECATION")
val managerPath get() = "${Environment.getExternalStorageDirectory().path}/Vanced Manager"
const val internalPath = "$storage/Android/data/com.vanced.manager/files"
const val externalPath = "$storage/Vanced Manager"
val Context.managerPath: String
get() {
var path = defPrefs.managerStorage ?: internalPath
if (path == externalPath && !canAccessStorage(this)) {
path = internalPath
}
return path
}
fun Context.getFilePathInStorage(child: String): String = "$managerPath/$child"
inline fun performStorageAction(activity: FragmentActivity, action: (managerPath: String) -> Unit) {
val managerPath = activity.managerPath
if (managerPath == internalPath) {
return action(managerPath)
}
inline fun performStorageAction(activity: FragmentActivity, action: () -> Unit) {
if (canAccessStorage(activity)) { if (canAccessStorage(activity)) {
action(managerPath) action()
} else { } else {
storageDialog(activity) storageDialog(activity)
} }
} }
fun canAccessStorage(context: Context): Boolean = when { fun canAccessStorage(activity: FragmentActivity): Boolean = when {
Build.VERSION.SDK_INT >= Build.VERSION_CODES.R -> Environment.isExternalStorageManager() Build.VERSION.SDK_INT >= Build.VERSION_CODES.R -> Environment.isExternalStorageManager()
Build.VERSION.SDK_INT >= Build.VERSION_CODES.M -> { Build.VERSION.SDK_INT >= Build.VERSION_CODES.M -> {
listOf( listOf(
Manifest.permission.READ_EXTERNAL_STORAGE, Manifest.permission.READ_EXTERNAL_STORAGE,
Manifest.permission.WRITE_EXTERNAL_STORAGE Manifest.permission.WRITE_EXTERNAL_STORAGE
).all { ).all {
context.checkSelfPermission(it) == PackageManager.PERMISSION_GRANTED activity.checkSelfPermission(it) == PackageManager.PERMISSION_GRANTED
} }
} }
else -> true else -> true
} }
fun requestStoragePerms(activity: FragmentActivity, permissionLauncher: ActivityResultLauncher<Array<String>>?) { fun requestStoragePerms(activity: FragmentActivity) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
activity.startActivity( activity.startActivity(
Intent( Intent(
@ -65,11 +42,12 @@ fun requestStoragePerms(activity: FragmentActivity, permissionLauncher: Activity
) )
) )
} else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
permissionLauncher?.launch( activity.requestPermissions(
arrayOf( arrayOf(
Manifest.permission.WRITE_EXTERNAL_STORAGE, Manifest.permission.READ_EXTERNAL_STORAGE,
Manifest.permission.READ_EXTERNAL_STORAGE Manifest.permission.WRITE_EXTERNAL_STORAGE
) ),
MainActivity.REQUEST_CODE
) )
} }
} }

View File

@ -1,46 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<com.google.android.material.card.MaterialCardView xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
style="@style/BottomDialogCard">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<TextView
android:text="@string/storage"
style="@style/BottomDialogCardTitle" />
<androidx.core.widget.NestedScrollView
android:layout_width="match_parent"
android:layout_height="wrap_content">
<RadioGroup
android:id="@+id/storage_radiogroup"
android:layout_width="match_parent"
android:layout_height="wrap_content"
tools:ignore="HardcodedText">
<com.vanced.manager.ui.core.ThemedMaterialRadioButton
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:tag="@string/internal_storage_path"
android:text="@string/storage_internal"
android:textSize="18sp" />
<com.vanced.manager.ui.core.ThemedMaterialRadioButton
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:tag="@string/external_storage_path"
android:text="@string/storage_external"
android:textSize="18sp" />
</RadioGroup>
</androidx.core.widget.NestedScrollView>
<com.vanced.manager.ui.core.ThemedMaterialButton
android:id="@+id/storage_save"
android:text="@string/save"
style="@style/BottomDialogButtonStyle" />
</LinearLayout>
</com.google.android.material.card.MaterialCardView>

View File

@ -49,12 +49,6 @@
android:layout_height="wrap_content" android:layout_height="wrap_content"
app:preference_title="@string/variant" /> app:preference_title="@string/variant" />
<com.vanced.manager.ui.core.EmptyPreference
android:id="@+id/manager_storage"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:preference_title="@string/storage" />
<com.vanced.manager.ui.core.EmptyPreference <com.vanced.manager.ui.core.EmptyPreference
android:id="@+id/serviced_timer" android:id="@+id/serviced_timer"
android:layout_width="match_parent" android:layout_width="match_parent"

View File

@ -16,7 +16,4 @@
<!-- prefs --> <!-- prefs -->
<string name="use_custom_tabs" translatable="false">use_custom_tabs</string> <string name="use_custom_tabs" translatable="false">use_custom_tabs</string>
<string name="internal_storage_path" translatable="false">/storage/emulated/0/Android/data/com.vanced.manager/files</string>
<string name="external_storage_path" translatable="false">/storage/emulated/0/Vanced Manager</string>
</resources> </resources>

View File

@ -50,7 +50,6 @@
<string name="category_appearance">Appearance</string> <string name="category_appearance">Appearance</string>
<string name="category_behaviour">Behavior</string> <string name="category_behaviour">Behavior</string>
<string name="clear_files">Clear downloaded files</string> <string name="clear_files">Clear downloaded files</string>
<string name="clear_files_failed">Failed to clear files</string>
<string name="cleared_files">Successfully cleared files</string> <string name="cleared_files">Successfully cleared files</string>
<string name="firebase_summary">This lets us collect information about app performance and crash logs</string> <string name="firebase_summary">This lets us collect information about app performance and crash logs</string>
<string name="firebase_title">Firebase Analytics</string> <string name="firebase_title">Firebase Analytics</string>
@ -96,11 +95,8 @@
<string name="please_be_patient">Please do NOT exit the app during this process!</string> <string name="please_be_patient">Please do NOT exit the app during this process!</string>
<string name="redownload">Redownload</string> <string name="redownload">Redownload</string>
<string name="security_context">Make sure that you downloaded the app from vancedapp.com, the Vanced Discord server, or the Vanced GitHub</string> <string name="security_context">Make sure that you downloaded the app from vancedapp.com, the Vanced Discord server, or the Vanced GitHub</string>
<string name="storage">Storage</string>
<string name="storage_access_required">Storage access required</string> <string name="storage_access_required">Storage access required</string>
<string name="storage_access_required_summary">In order for Vanced Manager to work, you must grant the storage permission</string> <string name="storage_access_required_summary">In order for Vanced Manager to work, you must grant the storage permission</string>
<string name="storage_external">Internal Storage</string>
<string name="storage_internal">App-Specific Storage</string>
<string name="version">Version</string> <string name="version">Version</string>
<string name="welcome">Welcome</string> <string name="welcome">Welcome</string>