alexgmp6
alexgmp6

Reputation: 23

How can I request permissions in Jetpack Compose?

I'm doing an application with Jetpack Compose and Kotlin. It is an app to locate an android device. I need to implement run time permissions to follow the jetpack filosofy. I have a menu page where there is a switch that when is activate saves the location of the device but just activate the switch it is necessary to request permissions "fine_location", "coarse_location" and "back_groundlocation". This is my menu.kt code:

LazyColumn {
        item {

            Row {
                Box(
                    modifier =
                    Modifier.fillMaxWidth(0.8f)
                )
                {
                    Text(
                        color = Color.Black,
                        text = stringResource(R.string.location_gps),
                        fontSize = 30.sp,
                        modifier = Modifier.padding(20.dp)
                    )

                }
                Box(
                    modifier =
                    Modifier.fillMaxSize(),
                    contentAlignment = Alignment.CenterEnd
                ) {
                    Switch(
                        checked = checkedStateGps.value,
                        onCheckedChange = { checkedStateGps.value = it },
                        modifier = Modifier
                            .padding(20.dp),
                        colors= SwitchDefaults.colors(
                            //color of switches
                            checkedThumbColor = Color(0xFF00CC99),
                            checkedTrackColor = Color(0xFF7BB661),
                            uncheckedThumbColor = Color(0xFF83010B),
                            uncheckedTrackColor = Color(0xFFBB4C4C)
                        )

                    )
                }
            }

I'd want to know how can I implement accompanist permissions for this.

Upvotes: 1

Views: 6457

Answers (2)

Bolt UIX
Bolt UIX

Reputation: 7032

Request camera permission sample:

implementation "com.google.accompanist:accompanist-permissions:0.20.0"

The permission APIs are currently experimental and they could change at any time. All of the APIs are marked with the @ExperimentalPermissionsApi annotation.

import android.os.Bundle
import androidx.activity.ComponentActivity
import androidx.activity.compose.setContent
import androidx.compose.foundation.layout.*
import androidx.compose.material.Button
import androidx.compose.material.MaterialTheme
import androidx.compose.material.Surface
import androidx.compose.material.Text
import androidx.compose.runtime.Composable
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.saveable.rememberSaveable
import androidx.compose.ui.Modifier
import androidx.compose.ui.unit.dp
import com.google.accompanist.permissions.ExperimentalPermissionsApi
import com.google.accompanist.permissions.PermissionRequired
import com.google.accompanist.permissions.rememberPermissionState
import pe.edu.upc.permissionscompose.ui.theme.PermissionsComposeTheme
import androidx.compose.runtime.getValue
import androidx.compose.runtime.setValue
import androidx.compose.ui.platform.LocalContext

class MainActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            PermissionsComposeTheme {
                // A surface container using the 'background' color from the theme
                Surface(color = MaterialTheme.colors.background) {
                    FeatureThatRequiresCameraPermission()
                }
            }
        }
    }
}


@OptIn(ExperimentalPermissionsApi::class)
@Composable
fun FeatureThatRequiresCameraPermission() {
    var doNotShowRationale by rememberSaveable {
        mutableStateOf(false)
    }

    val cameraPermissionState =
        rememberPermissionState(permission = android.Manifest.permission.CAMERA)

    val context = LocalContext.current

    PermissionRequired(
        permissionState = cameraPermissionState,
        permissionNotGrantedContent = {
            if (doNotShowRationale) {
                Text("Feature not available")
            } else {
                PermissionNotGrantedUI(
                    onYesClick = {
                        cameraPermissionState.launchPermissionRequest()
                    }, onCancelClick = {
                        doNotShowRationale = true
                    })
            }
        },
        permissionNotAvailableContent = {
            PermissionNotAvailableContent(
                onOpenSettingsClick = { context.openSettings() })
        },
        content = {
            Text("Camera Permission Granted")
        }
    )


}

@Composable
fun PermissionNotAvailableContent(onOpenSettingsClick: () -> Unit) {

    Column {
        Text("Camera permission denied.")
        Spacer(modifier = Modifier.height(8.dp))
        Button(onClick = { onOpenSettingsClick() }) {
            Text("Open settings")
        }
    }
}


@Composable
fun PermissionNotGrantedUI(onYesClick: () -> Unit, onCancelClick: () -> Unit) {
    Column {
        Text("Camera is important for this app. Please grant ther permission.")
        Spacer(modifier = Modifier.height(8.dp))
        Row {
            Button(onClick = {
                onYesClick()
            }) {
                Text("Yes")
            }
            Spacer(modifier = Modifier.width(8.dp))
            Button(onClick = {
                onCancelClick()
            }) {
                Text("Cancel")
            }
        }
    }

}

enter image description here

Upvotes: 0

Stefano Sansone
Stefano Sansone

Reputation: 2709

In Compose you can use Google's Accompanist library to request permission at runtime, just with PermissionRequired.
This is an example with camera permission but you can request any permissions you have in your manifest file as android.Manifest.permission.*

var doNotShowRationale by rememberSaveable { mutableStateOf(false) }
val cameraPermissionState = rememberPermissionState(android.Manifest.permission.CAMERA)
PermissionRequired(
    permissionState = cameraPermissionState,
    permissionNotGrantedContent = {
        if (doNotShowRationale) {
            Text("Feature not available")
        } else {
            Column {
                Text("The camera is important for this app. Please grant the permission.")
                Spacer(modifier = Modifier.height(8.dp))
                Row {
                    Button(onClick = { cameraPermissionState.launchPermissionRequest() }) {
                        Text("Ok!")
                    }
                    Spacer(Modifier.width(8.dp))
                    Button(onClick = { doNotShowRationale = true }) {
                        Text("Nope")
                    }
                }
            }
        }
    },
    permissionNotAvailableContent = {
        Column {
            Text(
                "Camera permission denied. See this FAQ with information about why we " +
                    "need this permission. Please, grant us access on the Settings screen."
            )
            Spacer(modifier = Modifier.height(8.dp))
            Button(onClick = navigateToSettingsScreen) {
                Text("Open Settings")
            }
        }
    }
) {
    Text("Camera permission Granted")
}

Upvotes: 1

Related Questions