I want to make a phone call using the number displayed on the view in the recycler view.
override fun onBindViewHolder(holder: MyViewholder, position: Int) {
val currentItem = userlist[position]
holder.txtFirstName.text = currentItem.firstName
holder.txtLastName.text = currentItem.lastName
holder.txtAge.text = currentItem.phonenumber.toString()
num = currentItem.phonenumber.toString()
holder.call.setOnClickListener {
val number: String = currentItem.phonenumber.toString()
if (ContextCompat.checkSelfPermission(
context,
android.Manifest.permission.CALL_PHONE
) != PERMISSION_GRANTED
) {
ActivityCompat.requestPermissions(
context as Activity,
arrayOf(android.Manifest.permission.CALL_PHONE),
REQUEST_CALL
)
} else {
val dial = "tel:$number"
val intent = Intent(Intent.ACTION_CALL, Uri.parse(dial))
context.startActivity(intent)
}
}
}
I am not able to override OnResquestPermissionResult() inside the adapter.
override fun onRequestPermissionsResult(
requestCode: Int,
permissions: Array<out String>,
grantResults: IntArray
) {
if (requestCode == REQUEST_CALL) {
if (grantResults.size > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
val number: String = num
if (ContextCompat.checkSelfPermission(
context,
android.Manifest.permission.CALL_PHONE
) != PERMISSION_GRANTED
) {
ActivityCompat.requestPermissions(
context as Activity, arrayOf(android.Manifest.permission.CALL_PHONE),
REQUEST_CALL
)
} else {
onRequestPermissionsResult(requestCode,permissions,grantResults)
val dial = "tel:$number"
val intent = Intent(Intent.ACTION_CALL, Uri.parse(dial))
context.startActivity(intent)
}
} else {
Toast.makeText(context, "Permission Denied", Toast.LENGTH_SHORT).show()
}
}
}
if I try to override OnResquestPermissionResult() inside the activity I am not able to pass the current phone number from the view.
I removed this whole code:
override fun onRequestPermissionsResult(
requestCode: Int,
permissions: Array<out String>,
grantResults: IntArray
) {
if (requestCode == REQUEST_CALL) {
if (grantResults.size > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
val number: String = num
if (ContextCompat.checkSelfPermission(
context,
android.Manifest.permission.CALL_PHONE
) != PERMISSION_GRANTED
) {
ActivityCompat.requestPermissions(
context as Activity, arrayOf(android.Manifest.permission.CALL_PHONE),
REQUEST_CALL
)
} else {
onRequestPermissionsResult(requestCode,permissions,grantResults)
val dial = "tel:$number"
val intent = Intent(Intent.ACTION_CALL, Uri.parse(dial))
context.startActivity(intent)
}
} else {
Toast.makeText(context, "Permission Denied", Toast.LENGTH_SHORT).show()
}
}
}
and everything is working fine.
Dont do that, return your click call back into your activity or fragment, then do your request permission like this
Request permission in android
or this, new way of get permission
Request permission in android with activity result api
Related
I would like to create a custom ActivityResultContract to request both coarse and fine location that has a custom response.
class LocationPermission : ActivityResultContract<Void?, LocationPermissionResult>() {
override fun createIntent(context: Context, input: Array<String>): Intent {
val requestPermissions = arrayOf(
Manifest.permission.ACCESS_FINE_LOCATION,
Manifest.permission.ACCESS_COARSE_LOCATION
)
return Intent(ActivityResultContracts.RequestMultiplePermissions.ACTION_REQUEST_PERMISSIONS)
.putExtra(ActivityResultContracts.RequestMultiplePermissions.EXTRA_PERMISSIONS, requestPermissions)
}
...
}
Calling that from an activity:
private val reportLocationIntent = registerForActivityResult(LocationPermission()) { result ->
}
...
reportLocationIntent.launch()
However when doing so createIntent is never called. What am I doing wrong?
Your code in question has compilation errors, however this approach seems to work. I don't really know what the "custom response" should be from the question directly, so I've created a class called class LocationPermissionResult(val granted: Boolean) based on your question. It is mostly compiled from RequestMultiplePermissions from ActivityResultContracts.
Tested on API 30 and API 33 emulator, the permission dialog opens and the returned result is correct as well. (Make sure the permissions are added to AndroidManifest.xml)
Here is the source code:
class LocationPermission : ActivityResultContract<Void?, LocationPermissionResult>() {
private val permissions = arrayOf(
Manifest.permission.ACCESS_FINE_LOCATION,
Manifest.permission.ACCESS_COARSE_LOCATION
)
override fun createIntent(context: Context, input: Void?): Intent {
return Intent(ActivityResultContracts.RequestMultiplePermissions.ACTION_REQUEST_PERMISSIONS).putExtra(
ActivityResultContracts.RequestMultiplePermissions.EXTRA_PERMISSIONS, permissions)
}
override fun getSynchronousResult(context: Context,
input: Void?): SynchronousResult<LocationPermissionResult>? {
val allGranted = permissions.all { permission ->
ContextCompat.checkSelfPermission(
context,
permission
) == PackageManager.PERMISSION_GRANTED
}
return if (allGranted) {
SynchronousResult(LocationPermissionResult(true))
} else null
}
override fun parseResult(resultCode: Int, intent: Intent?): LocationPermissionResult {
if (resultCode != Activity.RESULT_OK) return LocationPermissionResult(false)
if (intent == null) return LocationPermissionResult(false)
val grantResults = intent.getIntArrayExtra(
ActivityResultContracts.RequestMultiplePermissions.EXTRA_PERMISSION_GRANT_RESULTS)
return LocationPermissionResult(grantResults?.all { it == PackageManager.PERMISSION_GRANTED } == true)
}
}
class LocationPermissionResult(val granted: Boolean)
this is my solution to request both coarse and fine location, i hope this will do the job
object Permission {
private const val REQUEST_CODE_PERMISSION: Int = 1
#SuppressLint("ObsoleteSdkInt")
fun isGrantedLocationPermission(context: Context): Boolean {
return if (Build.VERSION.SDK_INT < Build.VERSION_CODES.M) {
true
} else {
context.checkSelfPermission(Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED ||
context.checkSelfPermission(Manifest.permission.ACCESS_COARSE_LOCATION) == PackageManager.PERMISSION_GRANTED
}
}
fun grantLocationPermission(context: Context) {
val permissions = arrayOf(
Manifest.permission.ACCESS_FINE_LOCATION,
Manifest.permission.ACCESS_COARSE_LOCATION
)
(context as MainActivity).requestPermissions(permissions, REQUEST_CODE_PERMISSION)
}
}
Use it from MainActivity:
override fun onCreate(savedInstanceState: Bundle?) {
...
val button = findViewById<Button>(R.id.btnGetLocation)
button.setOnClickListener {
getLocation()
}
}
private fun getLocation() {
//check if permission isnt granted:
if (!Permission.isGrantedLocationPermission(this))
Permission.grantLocationPermission(this)
else {
...
}
}
//Check if user give permission or not:
override fun onRequestPermissionsResult(
requestCode: Int,
permissions: Array<out String>,
grantResults: IntArray
) {
if (grantResults.isNotEmpty() && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
//permission granted
} else {
//permission denied
}
super.onRequestPermissionsResult(requestCode, permissions, grantResults)
}
WhoDoctor was helped me on the Previous code
Now, the android application crashed when during running on my phone
and This is the error log
First problem is after I scanned the QRcode with camera it cannot show at the QRcode's result into the tvResult
Second problem is after I selected a QRcode image from the storage, then tap confirmed, it crash
Here below I think are the issue
Type mismatch: inferred type is Uri? but Uri was expected
galleryLauncher = registerForActivityResult(ActivityResultContracts.StartActivityForResult(), object :ActivityResultCallback<ActivityResult>{
override fun onActivityResult(result: ActivityResult?) {
val data=result?.data
inputImage = InputImage.fromFilePath(requireContext(), data?.data)
processQr()
}
})
Redundant SAM-constructor
binding.btnScanBarcode.setOnClickListener{
val options=arrayOf("camera","gallery")
val builder=AlertDialog.Builder(requireContext())
builder.setTitle("Pick a option")
builder.setItems(options, DialogInterface.OnClickListener { dialog, which ->
if(which==0){
val cameraIntent=Intent(MediaStore.ACTION_IMAGE_CAPTURE)
cameraLauncher.launch(cameraIntent)
}else{
val storageIntent=Intent()
storageIntent.setType("image/*")
storageIntent.setAction(Intent.ACTION_GET_CONTENT)
galleryLauncher.launch(storageIntent)
}
})
builder.show()
}
'onRequestPermissionsResult(Int, Array<(out) String!>, IntArray): Unit' is deprecated. Deprecated in Java
override fun onRequestPermissionsResult(requestCode: Int, permissions: Array<out String>, grantResults: IntArray) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults)
if(requestCode==CAMERA_PERMISSION_CODE){
if(grantResults.isNotEmpty() && grantResults[0] == PackageManager.PERMISSION_GRANTED){
checkPermission(
Manifest.permission.READ_EXTERNAL_STORAGE,
READ_STORAGE_PERMISSION_CODE)
}else{
Toast.makeText(requireContext(), "Camera Permission Denied", Toast.LENGTH_SHORT).show()
}
}else if(requestCode==READ_STORAGE_PERMISSION_CODE){
if((grantResults.isNotEmpty() && grantResults[0] == PackageManager.PERMISSION_GRANTED)){
checkPermission(
Manifest.permission.WRITE_EXTERNAL_STORAGE,
WRITE_STORAGE_PERMISSION_CODE)
}else{
Toast.makeText(requireContext(), "Storage Permission Denied", Toast.LENGTH_SHORT).show()
}
}else if(requestCode==WRITE_STORAGE_PERMISSION_CODE) {
if (!(grantResults.isNotEmpty() && grantResults[0] == PackageManager.PERMISSION_GRANTED)) {
Toast.makeText(requireContext(), "Storage Permission Denied", Toast.LENGTH_SHORT).show()
}
}
}
onRequestPermissionsResult() method is deprecated in androidx.fragment.app.Fragment.
So you use registerForActivityResult() method instead onRequestPermissionsResult().
Following is kotlin code. .
val permReqLuncher = registerForActivityResult(ActivityResultContracts.RequestPermission()){
if (it) {
// Good pass
} else {
// Failed pass
}
}
How to get a permission request in new ActivityResult API (1.3.0-alpha05)?
private ActivityResultLauncher<String> mPermissionResult = registerForActivityResult(
new ActivityResultContracts.RequestPermission(),
new ActivityResultCallback<Boolean>() {
#Override
public void onActivityResult(Boolean result) {
if(result) {
Log.e(TAG, "onActivityResult: PERMISSION GRANTED");
} else {
Log.e(TAG, "onActivityResult: PERMISSION DENIED");
}
}
});
// Launch the permission window -- this is in onCreateView()
floatingActionButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
mPermissionResult.launch(Manifest.permission.ACCESS_BACKGROUND_LOCATION);
}
});
You can request multiple permissions.
val requestMultiplePermissions = registerForActivityResult(ActivityResultContracts.RequestMultiplePermissions()) { permissions ->
permissions.entries.forEach {
Log.e("DEBUG", "${it.key} = ${it.value}")
}
}
requestMultiplePermissions.launch(
arrayOf(
Manifest.permission.READ_CONTACTS,
Manifest.permission.ACCESS_FINE_LOCATION
)
)
i need to upload image to php server but i need the image to be at max quality before it would capture and upload a bitmap but i need the image to be clear so i tried this code but cant seem to get it to work.
so basically i need to upload the image stored on this line
cameraIntent.putExtra(MediaStore.EXTRA_OUTPUT, image_uri)
class capture : AppCompatActivity() {
private val PERMISSION_CODE = 1000;
private val IMAGE_CAPTURE_CODE = 1001
var image_uri: Uri? = null
var bitmap: Bitmap? = null
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_capture)
//button click
btn_take_photo.setOnClickListener {
//if system os is Marshmallow or Above, we need to request runtime permission
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M){
if (checkSelfPermission(Manifest.permission.CAMERA)
== PackageManager.PERMISSION_DENIED ||
checkSelfPermission(Manifest.permission.WRITE_EXTERNAL_STORAGE)
== PackageManager.PERMISSION_DENIED){
//permission was not enabled
val permission = arrayOf(Manifest.permission.CAMERA, Manifest.permission.WRITE_EXTERNAL_STORAGE)
//show popup to request permission
requestPermissions(permission, PERMISSION_CODE)
}
else{
//permission already granted
openCamera()
}
}
else{
//system os is < marshmallow
openCamera()
}
}
}
private fun openCamera() {
val values = ContentValues()
values.put(MediaStore.Images.Media.TITLE, "New Picture")
values.put(MediaStore.Images.Media.DESCRIPTION, "From the Camera")
image_uri = contentResolver.insert(MediaStore.Images.Media.EXTERNAL_CONTENT_URI, values)
//camera intent
val cameraIntent = Intent(MediaStore.ACTION_IMAGE_CAPTURE)
cameraIntent.putExtra(MediaStore.EXTRA_OUTPUT, image_uri)
startActivityForResult(cameraIntent, IMAGE_CAPTURE_CODE)
}
override fun onRequestPermissionsResult(requestCode: Int, permissions: Array<out String>, grantResults: IntArray) {
//called when user presses ALLOW or DENY from Permission Request Popup
when(requestCode){
PERMISSION_CODE -> {
if (grantResults.size > 0 && grantResults[0] ==
PackageManager.PERMISSION_GRANTED){
//permission from popup was granted
openCamera()
}
else{
//permission from popup was denied
Toast.makeText(this, "Permission denied", Toast.LENGTH_SHORT).show()
}
}
}
}
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
//called when image was captured from camera intent
if (resultCode == Activity.RESULT_OK){
val takenImage: Bitmap = BitmapFactory.decodeFile(image_uri.toString())
//set image captured to image view
imgv_capture_image_preview.setImageURI(image_uri)
val url = connection.server_url + "body_pictures.php"
val rq: RequestQueue = Volley.newRequestQueue(this)
val sr = object : StringRequest(Method.POST, url, Response.Listener { response ->
val check: String = response
val checknew = check.replace("\\s".toRegex(), "")
if (checknew == "success") {
Toast.makeText(
this,
"Image uploaded Successful",
Toast.LENGTH_LONG
).show()
} else {
Toast.makeText(
this,
"ERROR image upload failed, " + checknew,
Toast.LENGTH_LONG
).show()
}
}, Response.ErrorListener { error ->
Toast.makeText(
this,
"Server TIME OUT",
Toast.LENGTH_LONG
).show()
}) {
override fun getParams(): MutableMap<String, String> {
val map = HashMap<String, String>()
val images = takenImage?.let { getStringImage(it) }
if (images != null) {
map.put("image_data", images)
}
return map
}
}
rq.add(sr)
}
}
fun getStringImage(bitmap: Bitmap): String? {
val baos = ByteArrayOutputStream()
bitmap.compress(Bitmap.CompressFormat.JPEG, 100, baos)
val b = baos.toByteArray()
return Base64.encodeToString(b, Base64.DEFAULT)
}
I am trying to select an image in an activity but as soon as I click to select, I get to the Device Folder but it has no picture in it. Please see my code below:
class AddPainting : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_add_painting)
}
fun select(view: View) {
if(checkSelfPermission(Manifest.permission.READ_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {
requestPermissions(arrayOf(Manifest.permission.READ_EXTERNAL_STORAGE), 2);
} else {
val intent = Intent(Intent.ACTION_PICK, MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
startActivityForResult(intent, 1);
}
}
override fun onRequestPermissionsResult(
requestCode: Int,
permissions: Array<out String>,
grantResults: IntArray
) {
if(requestCode == 2) {
if(grantResults.size > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
// val intent = Intent(Intent.ACTION_PICK, MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
val intent = Intent(Intent.ACTION_PICK);
intent.type = "image/*";
startActivityForResult(intent, 1);
}
}
super.onRequestPermissionsResult(requestCode, permissions, grantResults)
}
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
if(requestCode == 1 && requestCode == Activity.RESULT_OK && data != null) {
val image = data.data;
try{
val selectedImage = MediaStore.Images.Media.getBitmap(this.contentResolver, image);
imageView.setImageURI(data?.data);
}catch (e: Exception) {
e.printStackTrace();
}
}
super.onActivityResult(requestCode, resultCode, data)
}
fun save(view: View) {
}
}
This is what I see when it transfers me to pick a picture
Use your selectedImage bitmap to set in ImageView
imageView.setImageURI(data?.data);
to
imageView.setImageURI(selectedImage);
So here I tried implementing the above functionality but only managed to fetch image files only through the gallery,fileExplorer and google photos, but I'm not able to find out a way to do the same for a third party library like the camscanner or officeLens
private val IMAGE_PICK_CODE = 1000;
private val PERMISSION_CODE = 1001;
fab.setOnClickListener { view ->
if (VERSION.SDK_INT >= VERSION_CODES.M){
if (checkSelfPermission(Manifest.permission.READ_EXTERNAL_STORAGE) ==
PackageManager.PERMISSION_DENIED){
val permissions = arrayOf(Manifest.permission.READ_EXTERNAL_STORAGE);
requestPermissions(permissions, PERMISSION_CODE);
}
else{
pickImageFromGallery();
}
}
else{
pickImageFromGallery();
}
}
}
private fun pickImageFromGallery() {
val intent = Intent(Intent.ACTION_PICK)
intent.type = "image/*"
startActivityForResult(intent, IMAGE_PICK_CODE)
}
//
override fun onRequestPermissionsResult(requestCode: Int, permissions: Array<out String>, grantResults: IntArray) {
when(requestCode){
PERMISSION_CODE -> {
if (grantResults.size >0 && grantResults[0] ==
PackageManager.PERMISSION_GRANTED){
//permission from popup granted
pickImageFromGallery()
}
else{
//permission from popup denied
Toast.makeText(this, "Permission denied", Toast.LENGTH_SHORT).show()
}
}
}
}
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
if (resultCode == Activity.RESULT_OK && requestCode == IMAGE_PICK_CODE){
imageView.setImageURI(data?.data)
}
}
manifest file
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.CAMERA"/>