如何正确安装APK文件,以便启动器在主屏幕上创建一个新的应用程序图标?

时间:2018-06-15 09:56:18

标签: android apk android-launcher packageinstaller

背景

我有一个空闲时间应用程序(here),其中一个主要功能是安装APK文件。

问题

安装应用的用户希望启动器上会显示新的应用图标。

这可以从Play商店发生,但由于某种原因发射器会忽略其他类型的安装。

Play商店安装应用的方式与第三方应用的方式不同。

我想知道如何正确操作,就像在Play商店一样,这样安装APK文件也会创建一个应用程序图标。

我尝试了什么

我发现安装APK的唯一方法就是这样:

@Nullable
public static Intent prepareAppInstallationIntent(Context context, File file, final boolean requestResult) {
    Intent intent = null;
    try {
        intent = new Intent(Intent.ACTION_INSTALL_PACKAGE)//
                .setDataAndType(
                        VERSION.SDK_INT >= VERSION_CODES.N ?
                                android.support.v4.content.FileProvider.getUriForFile(context, context.getPackageName() + ".provider", file)
                                : Uri.fromFile(file),
                        "application/vnd.android.package-archive")
                .putExtra(Intent.EXTRA_NOT_UNKNOWN_SOURCE, true)
                .putExtra(Intent.EXTRA_RETURN_RESULT, requestResult)
                .addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
        if (VERSION.SDK_INT < VERSION_CODES.JELLY_BEAN)
            intent.putExtra(Intent.EXTRA_ALLOW_REPLACE, true);
    } catch (Throwable e) {
    }
    return intent;
}

清单

<provider
  android:name="androidx.core.content.FileProvider" android:authorities="${applicationId}.provider" android:exported="false" android:grantUriPermissions="true">
  <meta-data
    android:name="android.support.FILE_PROVIDER_PATHS" android:resource="@xml/provider_paths"/>
</provider>

XML / provider_paths.xml

<?xml version="1.0" encoding="utf-8"?>
<paths>
  <!--<external-path name="external_files" path="."/>-->
  <external-path
    name="files_root" path="Android/data/${applicationId}"/>
  <external-path
    name="external_storage_root" path="."/>
</paths>

但这不会在启动器上创建应用程序图标。

在问题跟踪器(here)上写下这个,我得到了一些我应该做的线索。我被告知:

  

如果通过新应用程序安装了应用程序,则会将图标添加到主屏幕   PackageInstaller API(并提供正确的安装原因)。   为命令安装应用程序不支持此功能。

问题

  1. 是否有第三方应用的API可以正确安装应用,在启动器上有一个新图标?如果是这样,究竟是怎么回事?

  2. 即使使用root,还有办法吗?并通过PC使用adb命令?

1 个答案:

答案 0 :(得分:0)

以下是使用 Intent 的方法(需要知道应用程序的包名称):

fun prepareAppInstallationIntent(context: Context, file: File, requestResult: Boolean, packageName: String? = null): Intent? {
    var intent: Intent? = null
    try {
        intent = Intent(Intent.ACTION_INSTALL_PACKAGE) //
            .setDataAndType(
                if (VERSION.SDK_INT >= VERSION_CODES.N)
                    androidx.core.content.FileProvider.getUriForFile(
                        context,
                        context.packageName,
                        file
                    )
                else
                    Uri.fromFile(file),
                "application/vnd.android.package-archive"
            )
            .putExtra(Intent.EXTRA_NOT_UNKNOWN_SOURCE, true)
            .putExtra(Intent.EXTRA_RETURN_RESULT, requestResult)
            .addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION)
        if (packageName != null && VERSION.SDK_INT >= VERSION_CODES.N) {
            intent.putExtra(Intent.EXTRA_PACKAGE_NAME, packageName)
        }
        intent.putExtra(Intent.EXTRA_ALLOW_REPLACE, true)
    } catch (e: Throwable) {
    }
    return intent
}