从片段安装 apk

Install apk from fragment

我正在尝试从我的片段安装一个应用程序。我希望显示未知来源许可消息,然后进行安装过程。问题是在我第一次安装时,应用程序似乎崩溃了。 当然,下次(安装另一个 apk 时)这个问题就会消失。我做了以下步骤:

在我的视图模型中:

    fun installApp(uri: Uri) {
        viewModelScope.launch(context = exceptionHandler + DEFAULT) {
            val promptInstall = Intent(Intent.ACTION_VIEW, uri)
            promptInstall.putExtra(Intent.EXTRA_NOT_UNKNOWN_SOURCE, true)
            promptInstall.setDataAndType(uri, "application/vnd.android" + ".package-archive")
            promptInstall.flags = Intent.FLAG_ACTIVITY_CLEAR_TASK or Intent.FLAG_ACTIVITY_NEW_TASK
            promptInstall.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION)
            startActivityMutableLiveData.postValue(promptInstall.toOneTimeEvent())
        }
    }

然后在我的片段中:

viewModel.startActivityLiveData.observe(viewLifecycleOwner, Observer { oneTimeEvent ->
                (oneTimeEvent.getValue() as Intent).startActivityFromIntent(requireActivity())})

最后这是我的扩展功能:

fun Intent.startActivityFromIntent(context: Context) = (context as Activity).startActivity(this)

嗯,看来我上面说的过程在Android10及以上有问题(崩溃了!)。这是我找到的解决方案:

private fun Uri.installApp(context: Context) {
 if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
        if (!context.packageManager.canRequestPackageInstalls()) {
            startForResult.launch(Intent(ACTION_MANAGE_UNKNOWN_APP_SOURCES))
              Intent(Settings.ACTION_MANAGE_UNKNOWN_APP_SOURCES).setData(
        } else {
            viewModel.installApp(this)
        }
    } else {
        viewModel.installApp(this)
    }

我们必须按照以下步骤做:

    private val startForResult =
    registerForActivityResult(ActivityResultContracts.StartActivityForResult()) { result ->
        when (result.resultCode) {
            RESULT_OK -> {
                // your logic...
            }
            RESULT_CANCELED -> {
                //do something
            }
            else -> {
            }
        }
    }