recycler view data not showing after run time permission check - android

I can't seem to figure out how do I display data after run time allow permission button is pressed.The data is in a recycler view
The permission dialog works correctly because this gives me correct result on log cat but I cannot seem to get data on mobile device
Here is the code:
private val requestMultiplePermissions =registerForActivityResult(ActivityResultContracts.RequestMultiplePermissions()) { permissions ->
if (permissions[READ_EXTERNAL_STORAGE] == true && permissions[WRITE_EXTERNAL_STORAGE] == true) {
getMusicList()
} else {
checkPermissions()
Log.d(TAG, "Permission not granted")
}
}
private fun checkPermissions(){
if (context?.let {
ContextCompat.checkSelfPermission(
it,
READ_EXTERNAL_STORAGE
)
} != PackageManager.PERMISSION_GRANTED) {
requestMultiplePermissions.launch(
arrayOf(READ_EXTERNAL_STORAGE, WRITE_EXTERNAL_STORAGE))
}
else {
requestMultiplePermissions
}
}
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?,savedInstanceState: Bundle?): View {
checkPermissions()
}

private fun checkPermissions() {
if (context?.let {
ContextCompat.checkSelfPermission(
it,
READ_EXTERNAL_STORAGE
)
} != PackageManager.PERMISSION_GRANTED) {
requestMultiplePermissions.launch(
arrayOf(READ_EXTERNAL_STORAGE, WRITE_EXTERNAL_STORAGE))
} else {
//requestMultiplePermissions
getMusicList()
}
}
Do not need to request permission again when it is granted

Related

Location Permission Prompt is not showing up

`I want to show a permission prompt to get location permission from user.
But my prompt is not showing up in the app.
I have tried many codes from different sites but nothing worked.
Here is my code....
`private fun requestpermission(){
islocationpermissiongranted = ContextCompat.checkSelfPermission(
this, Manifest.permission.ACCESS_FINE_LOCATION
) == PackageManager.PERMISSION_GRANTED
backgroundlocationpermission = ContextCompat.checkSelfPermission(
this, Manifest.permission.ACCESS_BACKGROUND_LOCATION
) == PackageManager.PERMISSION_GRANTED
val permissionRequest : MutableList<String> = ArrayList()
if(!islocationpermissiongranted){
permissionRequest.add(Manifest.permission.ACCESS_FINE_LOCATION)
}
if(!backgroundlocationpermission){
permissionRequest.add(Manifest.permission.ACCESS_BACKGROUND_LOCATION)
}
if(permissionRequest.isNotEmpty()){
permissionLauncher.launch(permissionRequest.toTypedArray())
}
}
override fun onCreate(savedInstanceState: Bundle?) {
WindowCompat.setDecorFitsSystemWindows(window, true)
super.onCreate(savedInstanceState)
permissionLauncher = registerForActivityResult(ActivityResultContracts.RequestMultiplePermissions()){
permissions ->
islocationpermissiongranted = permissions[Manifest.permission.ACCESS_FINE_LOCATION] ?: islocationpermissiongranted
backgroundlocationpermission = permissions[Manifest.permission.ACCESS_BACKGROUND_LOCATION] ?: backgroundlocationpermission
}
requestpermission()
}`
First of all you need to register permission of location in the manifest and if you already added that permission then here is another code and it's work perfectly fine
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
title = "Location"
if (ContextCompat.checkSelfPermission(this#MainActivity,
android.Manifest.permission.ACCESS_FINE_LOCATION) !==
PackageManager.PERMISSION_GRANTED) {
if (ActivityCompat.shouldShowRequestPermissionRationale(this#MainActivity,
android.Manifest.permission.ACCESS_FINE_LOCATION)) {
ActivityCompat.requestPermissions(this#MainActivity,
arrayOf(android.Manifest.permission.ACCESS_FINE_LOCATION), 1)
} else {
ActivityCompat.requestPermissions(this#MainActivity,
arrayOf(android.Manifest.permission.ACCESS_FINE_LOCATION), 1)
}
}
}
override fun onRequestPermissionsResult(requestCode: Int, permissions: Array<String>,
grantResults: IntArray) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults)
when (requestCode) {
1 -> {
if (grantResults.isNotEmpty() && grantResults[0] ==
PackageManager.PERMISSION_GRANTED) {
if ((ContextCompat.checkSelfPermission(this#MainActivity,
android.Manifest.permission.ACCESS_FINE_LOCATION) ===
PackageManager.PERMISSION_GRANTED)) {
Toast.makeText(this, "Permission Granted", Toast.LENGTH_SHORT).show()
}
} else {
Toast.makeText(this, "Permission Denied", Toast.LENGTH_SHORT).show()
}
return
}
}
}
This is a permission of location in manifest file.
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools">
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
<application
android:allowBackup="true"
android:dataExtractionRules="#xml/data_extraction_rules"

how to get permission result in kotlin

I am trying to use a camera on my android. the user will be prompt for the permission of the camera. previously I used startActivityForResult and onRequestPermissionRequest for them. recently I found out that they are deprecated, so I'm trying out with registerForActivity. I managed to change to startActivity but I'm stuck at the permission request. I am wondering do I have to create another permissionlauncher or can I do the permission inside my resultlauncher.
companion object{
private const val CAMERA_PERMISSION_CODE = 1
private const val CAMERA_REQUEST_CODE = 2
}
val checkpermission = Manifest.permission.CAMERA
var resultLauncher = registerForActivityResult(ActivityResultContracts.StartActivityForResult()){ result ->
if (result.resultCode == Activity.RESULT_OK) {
val data: Intent? = result.data
val DP: Bitmap = data!!.extras!!.get("data") as Bitmap
val image = findViewById<ImageView>(R.id.imageButtonVerifyPhoto)
image.setImageBitmap(DP)
}
}
val permissionLauncher = registerForActivityResult(ActivityResultContracts.RequestPermission()){
isGranted ->
if(isGranted){
val intent = Intent(MediaStore.ACTION_IMAGE_CAPTURE)
resultLauncher.launch((intent))
Toast.makeText(this,"Permission is tested", Toast.LENGTH_SHORT).show()
}else{
Toast.makeText(this,"Permission is denied",Toast.LENGTH_SHORT).show()
}
}
var cameraButton = findViewById<Button>(R.id.buttonRetakePhoto) // can change later
cameraButton.setOnClickListener {
if(ContextCompat.checkSelfPermission(
this,
checkpermission
) == PackageManager.PERMISSION_GRANTED
){
val intent = Intent(MediaStore.ACTION_IMAGE_CAPTURE)
resultLauncher.launch(intent)
}else{
permissionLauncher.launch(checkpermission)
}
}
}
below is my previous code for the onRequestPermission
override fun onRequestPermissionsResult(
requestCode: Int,
permissions: Array<out String>,
grantResults: IntArray
) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults)
if(requestCode == CAMERA_REQUEST_CODE){
if(grantResults.isNotEmpty()&& grantResults[0] == PackageManager.PERMISSION_GRANTED){
val intent = Intent(MediaStore.ACTION_IMAGE_CAPTURE)
startActivityForResult(intent, CAMERA_REQUEST_CODE)
}else{
Toast.makeText(this,"Permission is denied",Toast.LENGTH_SHORT).show()
}
}
}
Requesting runtime permissions is just a little more simplified
private val requestPermission =
registerForActivityResult(ActivityResultContracts.RequestPermission()) { isGranted ->
// do something
}
Now we can call this to get any type of permission you want
cameraButton.setOnClickListener {
if (ContextCompat.checkSelfPermission(
this,
Manifest.permission.CAMERA
) != PackageManager.PERMISSION_GRANTED
) {
// Pass any permission you want while launching
requestPermission.launch(Manifest.permission.CAMERA)
}
}
Make sure to add in build.gradle
implementation 'androidx.fragment:fragment-ktx:1.2.0' // or later
implementation 'androidx.activity:activity-ktx:1.3.0' // or later
If you want to understand how all this works check here
Latest soluton in 2022: (no more request code)
Create Helper Extension Functions (for use in Fragment):
fun Fragment.requestPermissions(request: ActivityResultLauncher<Array<String>>, permissions: Array<String>) = request.launch(permissions)
fun Fragment.isAllPermissionsGranted(permissions: Array<String>) = permissions.all {
ContextCompat.checkSelfPermission(requireContext(), it) == PackageManager.PERMISSION_GRANTED
}
Request Permissions in Fragment:
class FirstFragment : Fragment() {
companion object {
private val PERMISSIONS = arrayOf(Manifest.permission.ACCESS_FINE_LOCATION, Manifest.permission.ACCESS_BACKGROUND_LOCATION)
}
private lateinit var binding: FragmentFirstBinding
private lateinit var permissionsRequest: ActivityResultLauncher<Array<String>>
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View {
binding = DataBindingUtil.inflate(inflater, R.layout.fragment_first, container, false)
permissionsRequest = getPermissionsRequest()
binding.grantButton.setOnClickListener {
requestPermissions(permissionsRequest, PERMISSIONS) //extension function
}
return binding.root
}
private fun getPermissionsRequest() = registerForActivityResult(ActivityResultContracts.RequestMultiplePermissions()) {
if (isAllPermissionsGranted(PERMISSIONS)) { //extension function
//do your stuff
} else {
//do your stuff
}
}
}
You could try Aaper, it allows to request for permissions using annotations like so:
Fist, add the permission to your manifest:
<uses-permission android:name="android.permission.CAMERA" />
Then, annotate a method that needs to use the camera:
#EnsurePermissions(permissions = [Manifest.permission.CAMERA])
fun takePhoto() {
Toast.makeText(this, "Camera permission granted", Toast.LENGTH_SHORT).show()
}
That's it, when you call the takePhoto method, it'll check for the camera permission, and if it's not available it will launch a permission request dialog. If the user approves it, then it will proceed to run takePhotos body.
Disclaimer, I'm the creator of Aaper

onRequestPermissionsResult() is not being called

I am trying to make a phone call from the dialog fragment which is inside another fragment. However, my onRequestPermissionsResult() is not being called, whenever I choose allow or deny, it doesn't react. Here is my code:
private val PHONE_REQUEST_CODE = 100;
private lateinit var phonePermission: Array<String>
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
btnOk.setOnClickListener(this)
btnCancel.setOnClickListener(this)
dialog?.window?.setBackgroundDrawable(ColorDrawable(Color.TRANSPARENT))
phonePermission = arrayOf(android.Manifest.permission.CALL_PHONE)
}
override fun onClick(v: View?) {
when (v?.id) {
R.id.btnOk -> {
dismiss()
makePhoneCall()
}
R.id.btnCancel -> {
dismiss()
}
}
}
override fun onRequestPermissionsResult(requestCode: Int, permissions: Array<out String>, grantResults: IntArray) {
if (requestCode == PHONE_REQUEST_CODE) {
if (grantResults.isNotEmpty() && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
val intent = Intent(Intent.ACTION_CALL, Uri.parse("tel:" + "111 111 111"))
startActivity(intent)
}
}
}
private fun makePhoneCall(){
if (ContextCompat.checkSelfPermission(
requireContext(),
android.Manifest.permission.CALL_PHONE
) != PackageManager.PERMISSION_GRANTED
) {
requestPermissions(
phonePermission,
PHONE_REQUEST_CODE
)
} else {
val intent = Intent(Intent.ACTION_CALL, Uri.parse("tel:" + "111 111 111"))
startActivity(intent)
}
}
}
I have tried several solutions offered in stackoverflow for similar problems, such as replacing ActivityCompat.requestPermissions() with just requestPermissions(). But still it didn't work.
Thanks in advance
Fragment's "onRequestPermissionsResult" will be called if your hosting activity passed the onRequestPermissionsResult call to base activity.
On fragment parent activity's onRequestPermissionsResult make sure to call super.onRequestPermissionsResult

Kotlin - Internet and location permissions problem

Ι am writing an android application that uses both location and internet connection permissions and I am running it on my tablet. As you can see, I have included both in the manifest file. The problem is that when OnConnected() function is called the below if in the MainActivity.kt evaluates to true and I can't proceed further in the function. So can you give me some hint to provide some more code if it is not relevant
AndroidManifest.xml :
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
MainActivity.kt
override fun onConnected(p0: Bundle?) {
if(ActivityCompat.checkSelfPermission(this,Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(this,Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED)
{
return;
}
//some code
}
You have to understand the logic behind permissions in Android. Just adding the permissions in the manifest, doesn't mean that the user has authorized the application to do what those permissions enable.
If your if condition evaluates to true, since those permissions are not granted, you have to ask the user for those permissions.
Android has a some good documentation on how to this.
I highly suggest you go over that.
From Android 6.0 onwards needs to request permission the best way is to do a permissionManager Class to Handle that and then check in your Activity if the user has accepted the permissions:
class PermissionManager private constructor() {
fun checkPermission(
activity: Activity,
permissionRequests: Array<String>?,
requestCode: Int
): Boolean {
permissionRequests?.let {
it.firstOrNull {
ContextCompat.checkSelfPermission(
activity,
it
) != PackageManager.PERMISSION_GRANTED
}?.apply {
ActivityCompat.requestPermissions(
activity,
permissionRequests,
requestCode
)
return false
}
}
return true
}
companion object {
val instance by lazy { PermissionManager() }
const val CAMERA_PERMISSION = 1
}
}
Then in your activity check the permission Result:
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_ar)
//If the user has the permission accepted the next times
if (PermissionManager.instance.checkPermission(
this, arrayOf(
Manifest.permission.CAMERA
), PermissionManager.CAMERA_PERMISSION
)
) {
initLogic()
}
}
override fun onRequestPermissionsResult(
requestCode: Int,
permissions: Array<out String>,
grantResults: IntArray
) {
when (requestCode) {
PermissionManager.CAMERA_PERMISSION -> {
if (grantResults.isNotEmpty() && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
initLogic()
} else {
return
}
}
}
}
}

App not asking for permission upon installing

Why is this not working? I've modified the Manifest too.
It is not asking for permission as I've coded. It's behaving as if I'm not even requesting for any permission.
I've made a splash screen and I want it to ask for permission before it goes to the MainActivity.
Splash screen should last for 1sec.
class SplashActivity : AppCompatActivity() {
var permissionsString = arrayOf(
Manifest.permission.READ_EXTERNAL_STORAGE,
Manifest.permission.MODIFY_AUDIO_SETTINGS,
Manifest.permission.READ_PHONE_STATE,
Manifest.permission.PROCESS_OUTGOING_CALLS,
Manifest.permission.RECORD_AUDIO)
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_splash)
if (hasPermissions(this#SplashActivity,*permissionsString)){
ActivityCompat.requestPermissions(this#SplashActivity,permissionsString,131)
}else{
Handler().postDelayed({
val startAct = Intent(this#SplashActivity,MainActivity::class.java)
startActivity(startAct)
this.finish()},1000)
}
}
override fun onRequestPermissionsResult(requestCode: Int, permissions: Array<out String>, grantResults: IntArray) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults)
when(requestCode){
131 ->{
if (grantResults.isNotEmpty()
&& grantResults[0]==PackageManager.PERMISSION_GRANTED
&& grantResults[1]==PackageManager.PERMISSION_GRANTED
&& grantResults[2]==PackageManager.PERMISSION_GRANTED
&& grantResults[3]==PackageManager.PERMISSION_GRANTED
&& grantResults[4]==PackageManager.PERMISSION_GRANTED){
Handler().postDelayed({
val startAct = Intent(this#SplashActivity,MainActivity::class.java)
startActivity(startAct)
this.finish()},1000)
}else{
Toast.makeText(this#SplashActivity,"Grant it Please",Toast.LENGTH_SHORT).show()
this.finish()
}
return
}
else->{
Toast.makeText(this#SplashActivity,"Something wrong",Toast.LENGTH_SHORT).show()
this.finish()
return
}
}
}
fun hasPermissions(context: Context,vararg permissions: String): Boolean{
var hasAllPermissions = true
for (permission in permissions){
val res = context.checkCallingOrSelfPermission(permission)
if (res!=PackageManager.PERMISSION_GRANTED){
hasAllPermissions = false
}
}
return hasAllPermissions
}
}
Thats because your if condition is wrong. It should on include NOT operator to ask for permission as below:
if (!hasPermissions(this#SplashActivity,*permissionsString)) {
//Ask for permission
}
Ask for permission if you don't have the permission. In your case, you are checking if you have permission, then ask for permission which is wrong.
Check your
targetSdkVersion
in project gradle file.
It should be >= 23 to call run-time permission, otherwise will take permission automatically.

Categories

Resources