diff --git a/app/src/main/java/com/topjohnwu/magisk/arch/UIActivity.kt b/app/src/main/java/com/topjohnwu/magisk/arch/UIActivity.kt index 147a57730..e37f50076 100644 --- a/app/src/main/java/com/topjohnwu/magisk/arch/UIActivity.kt +++ b/app/src/main/java/com/topjohnwu/magisk/arch/UIActivity.kt @@ -27,8 +27,7 @@ abstract class UIActivity : BaseActivity(), ViewModel open val snackbarAnchorView: View? get() = null init { - val theme = Config.darkTheme - AppCompatDelegate.setDefaultNightMode(theme) + AppCompatDelegate.setDefaultNightMode(Config.darkTheme) } override fun onCreate(savedInstanceState: Bundle?) { diff --git a/app/src/main/java/com/topjohnwu/magisk/core/base/BaseActivity.kt b/app/src/main/java/com/topjohnwu/magisk/core/base/BaseActivity.kt index aa07052be..0f727f982 100644 --- a/app/src/main/java/com/topjohnwu/magisk/core/base/BaseActivity.kt +++ b/app/src/main/java/com/topjohnwu/magisk/core/base/BaseActivity.kt @@ -2,6 +2,7 @@ package com.topjohnwu.magisk.core.base import android.Manifest.permission.REQUEST_INSTALL_PACKAGES import android.Manifest.permission.WRITE_EXTERNAL_STORAGE +import android.app.Activity import android.content.ActivityNotFoundException import android.content.Context import android.content.Intent @@ -54,6 +55,18 @@ abstract class BaseActivity : AppCompatActivity() { uninstallLatch.countDown() } + private val mReferrerField by lazy(LazyThreadSafetyMode.NONE) { + Activity::class.java.reflectField("mReferrer") + } + + val realCallingPackage: String? get() { + callingPackage?.let { return it } + if (Build.VERSION.SDK_INT >= 22) { + mReferrerField.get(this)?.let { return it as String } + } + return null + } + override fun attachBaseContext(base: Context) { super.attachBaseContext(base.wrap()) } diff --git a/app/src/main/java/com/topjohnwu/magisk/core/tasks/HideAPK.kt b/app/src/main/java/com/topjohnwu/magisk/core/tasks/HideAPK.kt index e51f32fd7..c8b874c1e 100644 --- a/app/src/main/java/com/topjohnwu/magisk/core/tasks/HideAPK.kt +++ b/app/src/main/java/com/topjohnwu/magisk/core/tasks/HideAPK.kt @@ -99,8 +99,7 @@ object HideAPK { val flag = Intent.FLAG_GRANT_READ_URI_PERMISSION activity.grantUriPermission(pkg, Provider.preferencesUri(self), flag) intent.putExtra(Const.Key.PREV_PKG, self) - intent.flags = 0 - activity.startActivityForResult(intent, Int.MAX_VALUE) + activity.startActivity(intent) activity.finish() } diff --git a/app/src/main/java/com/topjohnwu/magisk/events/dialog/DarkThemeDialog.kt b/app/src/main/java/com/topjohnwu/magisk/events/dialog/DarkThemeDialog.kt index 24fd1e356..12648ad4b 100644 --- a/app/src/main/java/com/topjohnwu/magisk/events/dialog/DarkThemeDialog.kt +++ b/app/src/main/java/com/topjohnwu/magisk/events/dialog/DarkThemeDialog.kt @@ -3,6 +3,7 @@ package com.topjohnwu.magisk.events.dialog import android.app.Activity import androidx.appcompat.app.AppCompatDelegate import com.topjohnwu.magisk.R +import com.topjohnwu.magisk.arch.UIActivity import com.topjohnwu.magisk.core.Config import com.topjohnwu.magisk.view.MagiskDialog @@ -33,6 +34,6 @@ class DarkThemeDialog : DialogEvent() { private fun selectTheme(mode: Int, activity: Activity) { Config.darkTheme = mode - activity.recreate() + (activity as UIActivity<*>).delegate.localNightMode = mode } } diff --git a/app/src/main/java/com/topjohnwu/magisk/ui/MainActivity.kt b/app/src/main/java/com/topjohnwu/magisk/ui/MainActivity.kt index 32d9baaa0..0c7e64024 100644 --- a/app/src/main/java/com/topjohnwu/magisk/ui/MainActivity.kt +++ b/app/src/main/java/com/topjohnwu/magisk/ui/MainActivity.kt @@ -13,7 +13,6 @@ import androidx.core.view.isVisible import androidx.navigation.NavDirections import com.topjohnwu.magisk.MainDirections import com.topjohnwu.magisk.R -import com.topjohnwu.magisk.arch.BaseMainActivity import com.topjohnwu.magisk.arch.BaseViewModel import com.topjohnwu.magisk.arch.viewModel import com.topjohnwu.magisk.core.Config @@ -31,7 +30,7 @@ import java.io.File class MainViewModel : BaseViewModel() -class MainActivity : BaseMainActivity() { +class MainActivity : SplashActivity() { override val layoutRes = R.layout.activity_main_md2 override val viewModel by viewModel() diff --git a/app/src/main/java/com/topjohnwu/magisk/arch/BaseMainActivity.kt b/app/src/main/java/com/topjohnwu/magisk/ui/SplashActivity.kt similarity index 78% rename from app/src/main/java/com/topjohnwu/magisk/arch/BaseMainActivity.kt rename to app/src/main/java/com/topjohnwu/magisk/ui/SplashActivity.kt index 58130f9d7..365ef3d8f 100644 --- a/app/src/main/java/com/topjohnwu/magisk/arch/BaseMainActivity.kt +++ b/app/src/main/java/com/topjohnwu/magisk/ui/SplashActivity.kt @@ -1,4 +1,4 @@ -package com.topjohnwu.magisk.arch +package com.topjohnwu.magisk.ui import android.Manifest.permission.REQUEST_INSTALL_PACKAGES import android.annotation.SuppressLint @@ -9,7 +9,7 @@ import androidx.databinding.ViewDataBinding import androidx.lifecycle.lifecycleScope import com.topjohnwu.magisk.BuildConfig.APPLICATION_ID import com.topjohnwu.magisk.R -import com.topjohnwu.magisk.StubApk +import com.topjohnwu.magisk.arch.NavigationActivity import com.topjohnwu.magisk.core.Config import com.topjohnwu.magisk.core.Const import com.topjohnwu.magisk.core.JobService @@ -25,16 +25,17 @@ import com.topjohnwu.magisk.view.Shortcuts import com.topjohnwu.superuser.Shell import kotlinx.coroutines.launch -abstract class BaseMainActivity : NavigationActivity() { +@SuppressLint("CustomSplashScreen") +abstract class SplashActivity : NavigationActivity() { companion object { - private var doPreload = true + private var skipSplash = false } override fun onCreate(savedInstanceState: Bundle?) { setTheme(Theme.selected.themeRes) - if (isRunningAsStub && doPreload) { + if (isRunningAsStub && !skipSplash) { // Manually apply splash theme for stub theme.applyStyle(R.style.StubSplashTheme, true) } @@ -43,28 +44,19 @@ abstract class BaseMainActivity : NavigationActivity< if (!isRunningAsStub) { val splashScreen = installSplashScreen() - splashScreen.setKeepOnScreenCondition { doPreload } + splashScreen.setKeepOnScreenCondition { !skipSplash } } - if (doPreload) { + if (skipSplash) { + showMainUI(savedInstanceState) + } else { Shell.getShell(Shell.EXECUTOR) { if (isRunningAsStub && !it.isRoot) { showInvalidStateMessage() return@getShell } - preLoad() - runOnUiThread { - doPreload = false - if (isRunningAsStub) { - // Re-launch main activity without splash theme - relaunch() - } else { - showMainUI(savedInstanceState) - } - } + preLoad(savedInstanceState) } - } else { - showMainUI(savedInstanceState) } } @@ -84,7 +76,7 @@ abstract class BaseMainActivity : NavigationActivity< showInvalidStateMessage() } else { lifecycleScope.launch { - HideAPK.restore(this@BaseMainActivity) + HideAPK.restore(this@SplashActivity) } } } @@ -95,10 +87,10 @@ abstract class BaseMainActivity : NavigationActivity< } } - private fun preLoad() { + private fun preLoad(savedState: Bundle?) { val prevPkg = intent.getStringExtra(Const.Key.PREV_PKG)?.let { // Make sure the calling package matches (prevent DoS) - if (it == callingPackage) + if (it == realCallingPackage) it else null @@ -106,9 +98,14 @@ abstract class BaseMainActivity : NavigationActivity< Config.load(prevPkg) handleRepackage(prevPkg) - if (prevPkg != null) { - StubApk.restartProcess(this) + if (prevPkg != null && !isRunningAsStub) { + runOnUiThread { + // Might have new configuration loaded, relaunch the activity + relaunch() + } + return } + Notifications.setup(this) JobService.schedule(this) Shortcuts.setupDynamic(this) @@ -118,6 +115,16 @@ abstract class BaseMainActivity : NavigationActivity< // Wait for root service RootUtils.Connection.await() + + runOnUiThread { + skipSplash = true + if (isRunningAsStub) { + // Re-launch main activity without splash theme + relaunch() + } else { + showMainUI(savedState) + } + } } private fun handleRepackage(pkg: String?) { diff --git a/app/src/main/java/com/topjohnwu/magisk/ui/theme/ThemeViewModel.kt b/app/src/main/java/com/topjohnwu/magisk/ui/theme/ThemeViewModel.kt index 1075dd9fb..f1722a8f3 100644 --- a/app/src/main/java/com/topjohnwu/magisk/ui/theme/ThemeViewModel.kt +++ b/app/src/main/java/com/topjohnwu/magisk/ui/theme/ThemeViewModel.kt @@ -1,6 +1,7 @@ package com.topjohnwu.magisk.ui.theme import com.topjohnwu.magisk.arch.BaseViewModel +import com.topjohnwu.magisk.core.Config import com.topjohnwu.magisk.events.RecreateEvent import com.topjohnwu.magisk.events.dialog.DarkThemeDialog import com.topjohnwu.magisk.view.TappableHeadlineItem @@ -10,15 +11,13 @@ class ThemeViewModel : BaseViewModel(), TappableHeadlineItem.Listener { val themeHeadline = TappableHeadlineItem.ThemeMode override fun onItemPressed(item: TappableHeadlineItem) = when (item) { - is TappableHeadlineItem.ThemeMode -> darkModePressed() - else -> Unit + is TappableHeadlineItem.ThemeMode -> DarkThemeDialog().publish() } fun saveTheme(theme: Theme) { - theme.select() - RecreateEvent().publish() + if (!theme.isSelected) { + Config.themeOrdinal = theme.ordinal + RecreateEvent().publish() + } } - - private fun darkModePressed() = DarkThemeDialog().publish() - }