Skip to content

Commit

Permalink
Fixes #120
Browse files Browse the repository at this point in the history
  • Loading branch information
samolego committed Jan 27, 2025
1 parent 63cd724 commit 2eecbe1
Showing 1 changed file with 63 additions and 51 deletions.
114 changes: 63 additions & 51 deletions app/src/main/java/org/samo_lego/canta/MainActivity.kt
Original file line number Diff line number Diff line change
Expand Up @@ -30,43 +30,48 @@ const val packageName = "org.samo_lego.canta"
class MainActivity : ComponentActivity() {

override fun onCreate(savedInstanceState: Bundle?) {
enableEdgeToEdge()
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
enableEdgeToEdge()
}
super.onCreate(savedInstanceState)

setContent {
CantaTheme {
Surface(
modifier = Modifier.fillMaxSize(),
color = MaterialTheme.colorScheme.background
modifier = Modifier.fillMaxSize(),
color = MaterialTheme.colorScheme.background
) {
CantaApp(
launchShizuku = {
// Open shizuku app
val launchIntent =
packageManager.getLaunchIntentForPackage(SHIZUKU_PACKAGE_NAME)
startActivity(launchIntent)
},
uninstallApp = { uninstallApp(it) },
reinstallApp = { reinstallApp(it) },
launchShizuku = {
// Open shizuku app
val launchIntent =
packageManager.getLaunchIntentForPackage(
SHIZUKU_PACKAGE_NAME
)
startActivity(launchIntent)
},
uninstallApp = { uninstallApp(it) },
reinstallApp = { reinstallApp(it) },
)
}
}
}
}

/**
* Uninstalls app using Shizuku.
* See <a href="https://cs.android.com/android/platform/superproject/main/+/main:frameworks/base/services/core/java/com/android/server/pm/PackageManagerShellCommand.java;drc=bcb2b436bde55ee40050400783a9c083e77ce2fe;l=2144">PackageManagerShellCommand.java</a>
* Uninstalls app using Shizuku. See <a
* href="https://cs.android.com/android/platform/superproject/main/+/main:frameworks/base/services/core/java/com/android/server/pm/PackageManagerShellCommand.java;drc=bcb2b436bde55ee40050400783a9c083e77ce2fe;l=2144">PackageManagerShellCommand.java</a>
* @param packageName package name of the app to uninstall
*/
private fun uninstallApp(packageName: String): Boolean {
val broadcastIntent = Intent("org.samo_lego.canta.UNINSTALL_RESULT_ACTION")
val intent = PendingIntent.getBroadcast(
applicationContext,
0,
broadcastIntent,
PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE
)
val intent =
PendingIntent.getBroadcast(
applicationContext,
0,
broadcastIntent,
PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE
)

val packageInstaller = getPackageInstaller()
val packageInfo = packageManager.getInfoForPackage(packageName)
Expand All @@ -79,23 +84,26 @@ class MainActivity : ComponentActivity() {
// 0x00000002 = PackageManager.DELETE_ALL_USERS
val flags = if (isSystem) 0x00000004 else 0x00000002

return try {
return try {
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.P) {
PackageInstaller::class.java.getDeclaredMethod(
"uninstall",
String::class.java,
Int::class.javaPrimitiveType,
PendingIntent::class.java
).invoke(packageInstaller, packageName, flags, intent)
//packageInstaller.uninstall(packageName, flags, intent.intentSender)
PackageInstaller::class
.java
.getDeclaredMethod(
"uninstall",
String::class.java,
Int::class.javaPrimitiveType,
PendingIntent::class.java
)
.invoke(packageInstaller, packageName, flags, intent)
// packageInstaller.uninstall(packageName, flags, intent.intentSender)
} else {
HiddenApiBypass.invoke(
PackageInstaller::class.java,
packageInstaller,
"uninstall",
packageName,
flags,
intent.intentSender
PackageInstaller::class.java,
packageInstaller,
"uninstall",
packageName,
flags,
intent.intentSender
)
}
true
Expand All @@ -108,19 +116,20 @@ class MainActivity : ComponentActivity() {
}

/**
* Reinstalls app using Shizuku.
* See <a href="https://cs.android.com/android/platform/superproject/main/+/main:frameworks/base/services/core/java/com/android/server/pm/PackageManagerShellCommand.java;drc=bcb2b436bde55ee40050400783a9c083e77ce2fe;l=1408>PackageManagerShellCommand.java</a>
* Reinstalls app using Shizuku. See <a
* href="https://cs.android.com/android/platform/superproject/main/+/main:frameworks/base/services/core/java/com/android/server/pm/PackageManagerShellCommand.java;drc=bcb2b436bde55ee40050400783a9c083e77ce2fe;l=1408>PackageManagerShellCommand.java</a>
* @param packageName package name of the app to reinstall (must preinstalled on the phone)
*/
private fun reinstallApp(packageName: String): Boolean {
val installReason = PackageManager.INSTALL_REASON_UNKNOWN
val broadcastIntent = Intent("org.samo_lego.canta.INSTALL_RESULT_ACTION")
val intent = PendingIntent.getBroadcast(
applicationContext,
0,
broadcastIntent,
PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE
)
val intent =
PendingIntent.getBroadcast(
applicationContext,
0,
broadcastIntent,
PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE
)

LogUtils.i(APP_NAME, "Reinstalling '$packageName'")

Expand All @@ -129,15 +138,15 @@ class MainActivity : ComponentActivity() {

return try {
HiddenApiBypass.invoke(
IPackageInstaller::class.java,
ShizukuPackageInstallerUtils.getPrivilegedPackageInstaller(),
"installExistingPackage",
packageName,
installFlags,
installReason,
intent.intentSender,
0,
null
IPackageInstaller::class.java,
ShizukuPackageInstallerUtils.getPrivilegedPackageInstaller(),
"installExistingPackage",
packageName,
installFlags,
installReason,
intent.intentSender,
0,
null
)
true
} catch (e: Exception) {
Expand All @@ -156,7 +165,10 @@ class MainActivity : ComponentActivity() {
// The reason for use "com.android.shell" as installer package under adb is that
// getMySessions will check installer package's owner
return ShizukuPackageInstallerUtils.createPackageInstaller(
iPackageInstaller, "com.android.shell", userId, this
iPackageInstaller,
"com.android.shell",
userId,
this
)
}
}

0 comments on commit 2eecbe1

Please sign in to comment.