Написал
ответ на
свой вопрос на StackOverflow, используя
ответ, который немного отредактировал и разобрал, от
2jan222.
Нужно создать composable и использовать его, когда необходима функция, для которой нужно получить разрешение. В него — передать массив разрешений
permissions
, код запроса
requestCode
(любое число) и две или больше лямбды:
onGranted
— будет использоваться, когда разшенеие будет дано —,
onDenied
— в обратном случае.
@Composable
fun PermissionsRequest(
permissions: Array<out String>,
requestCode: Int,
onGranted: @Composable () -> Unit,
onDenied: @Composable () -> Unit,
onDeniedPermanently: (@Composable () -> Unit)? = null,
rational: (@Composable () -> Unit)? = null,
awaitResult: (@Composable () -> Unit)? = null,
) {
val permissionHandler = AmbientPermissionHandler.current
val (permissionResult, setPermissionResult) = remember(permissions) {
mutableStateOf<PermissionResult?>(null)
}
LaunchedEffect(Unit) {
setPermissionResult(permissionHandler.requestPermissions(requestCode, permissions))
}
when (permissionResult) {
is PermissionResult.PermissionGranted -> onGranted()
is PermissionResult.PermissionDenied -> onDenied()
is PermissionResult.PermissionDeniedPermanently -> onDeniedPermanently?.invoke()
is PermissionResult.ShowRational -> rational?.invoke()
null -> awaitResult?.invoke()
}
}
Ещё нужно имплементировать ambient. Как я понял, он передаётся детям composables. Здесь —
AmbientPermissionHandler
будет передан в
PermissionsRequest
из
Providers
.
val AmbientPermissionHandler = ambientOf<PermissionHandler>()
PermissionHandler
. Он будет передан в
PermissionRequest
в виде
AmbientPermissionHandler
, используя
Providers
.
class PermissionHandler(private val context: AppCompatActivity) {
suspend fun requestPermissions(
requestCode: Int,
permissions: Array<out String>
): PermissionResult {
return PermissionManager.requestPermissions(context, requestCode, *permissions)
}
}
Затем испоьзуется примерно так:
class MainActivity : AppCompatActivity() {
private val permissionHandler = PermissionHandler(this)
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContent {
Providers(
AmbientPermissionHandler provides permissionHandler
) {
PermissionsRequest(
permissions = arrayOf(Manifest.permission.READ_SMS),
requestCode = PERMISSION_REQUEST_CODE,
onGranted = { /* Here goes the composables when the permission is granted */ },
onDenied = { /* Is used when the permission is denied */ }
)
}
}
}
}
Создать
PermissionHandler
в активити
MainActivity
, а потом передаётся внутри
setContent
, используя
Providers
.
Для
PermissionManager
и
LaunchedEffect
нужны зависимости:
implementation 'com.sagar:coroutinespermission:2.0.3'
implementation 'androidx.compose.runtime:runtime:1.0.0-alpha11'