Implement Contact Pick feature in and Android App
To allow the user to pick a contact from the phone's contacts list, we can use contact intent. You will get all information of the contact e.g. Name, Phone Number(s), Address, Thumbnail, Email, etc. You can use get the specific information according to your requirement. To pick a contact we need to READ_CONTACTS permission.
Add permission in AndroidMenifest:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.wongngaur.blogspot.pickcontact">
<!--Read contact permission-->
<uses-permission android:name="android.permission.READ_CONTACTS"/>
<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@style/Theme.PickContact">
<activity android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
</manifest>
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:padding="10dp"
tools:context=".MainActivity">
<!--ImageView: Show contact thumbnail-->
<ImageView
android:id="@+id/thumbnailIv"
android:layout_width="120dp"
android:layout_height="120dp"
android:src="@drawable/ic_person"
android:layout_centerHorizontal="true"/>
<!--TextView: Show contact info e.g. name, phone(s) etc-->
<TextView
android:id="@+id/contactTv"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="@id/thumbnailIv"/>
<!--FloatingActionButton: Click to begin contact pick-->
<com.google.android.material.floatingactionbutton.FloatingActionButton
android:id="@+id/addFab"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_margin="10dp"
android:src="@drawable/ic_person_add"
android:layout_alignParentEnd="true"
android:layout_alignParentBottom="true"/>
</RelativeLayout>
MainActivity.kt
package com.wongngaur.blogspot.contactpick
import android.content.Intent
import android.content.pm.PackageManager
import android.database.Cursor
import android.net.Uri
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.provider.ContactsContract
import android.widget.Toast
import androidx.core.app.ActivityCompat
import androidx.core.content.ContextCompat
import com.wongngaur.blogspot.contactpick.databinding.ActivityMainBinding
import java.util.jar.Manifest
class MainActivity : AppCompatActivity() {
//view binding
lateinit var binding: ActivityMainBinding
//contact permission code
private val CONTACT_PERMISSION_CODE = 1;
//contact pick code
private val CONTACT_PICK_CODE = 2
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
binding = ActivityMainBinding.inflate(layoutInflater)
setContentView(binding.root)
//handle click, to pick contact
binding.addFab.setOnClickListener {
//check permission allowed or not
if (checkContactPermission()){
//allowed
pickContact()
}
else{
//not allowed, request
requestContactPermission()
}
}
}
private fun checkContactPermission(): Boolean{
//check if permission was granted/allowed or not, returns true if granted/allowed, false if not
return ContextCompat.checkSelfPermission(
this,
android.Manifest.permission.READ_CONTACTS
) == PackageManager.PERMISSION_GRANTED
}
private fun requestContactPermission(){
//request the READ_CONTACTS permission
val permission = arrayOf(android.Manifest.permission.READ_CONTACTS)
ActivityCompat.requestPermissions(this, permission, CONTACT_PERMISSION_CODE)
}
private fun pickContact(){
//intent ti pick contact
val intent = Intent(Intent.ACTION_PICK, ContactsContract.Contacts.CONTENT_URI)
startActivityForResult(intent, CONTACT_PICK_CODE)
}
override fun onRequestPermissionsResult(
requestCode: Int,
permissions: Array<out String>,
grantResults: IntArray
) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults)
//handle permission request results || calls when user from Permission request dialog presses Allow or Deny
if (requestCode == CONTACT_PERMISSION_CODE){
if (grantResults.isNotEmpty() && grantResults[0] == PackageManager.PERMISSION_GRANTED){
//permission granted, can pick contact
pickContact()
}
else{
//permission denied, cann't pick contact, just show message
Toast.makeText(this, "Permission denied...", Toast.LENGTH_SHORT).show()
}
}
}
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
//handle intent results || calls when user from Intent (Contact Pick) picks or cancels pick contact
if (resultCode == RESULT_OK){
//calls when user click a contact from contacts (intent) list
if (requestCode == CONTACT_PICK_CODE){
binding.contactTv.text = ""
val cursor1: Cursor
val cursor2: Cursor?
//get data from intent
val uri = data!!.data
cursor1 = contentResolver.query(uri!!, null, null, null, null)!!
if (cursor1.moveToFirst()){
//get contact details
val contactId = cursor1.getString(cursor1.getColumnIndex(ContactsContract.Contacts._ID))
val contactName = cursor1.getString(cursor1.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME))
val contactThumbnail = cursor1.getString(cursor1.getColumnIndex(ContactsContract.Contacts.PHOTO_THUMBNAIL_URI))
val idResults = cursor1.getString(cursor1.getColumnIndex(ContactsContract.Contacts.HAS_PHONE_NUMBER))
val idResultHold = idResults.toInt()
//set details: contact id, contact name, image
binding.contactTv.append("ID: $contactId")
binding.contactTv.append("\nName: $contactName")
//set image, first check if uri/thumbnail is not null
if (contactThumbnail != null){
binding.thumbnailIv.setImageURI(Uri.parse(contactThumbnail))
}
else{
binding.thumbnailIv.setImageResource(R.drawable.ic_person)
}
//check if contact has a phone number or not
if (idResultHold == 1){
cursor2 = contentResolver.query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI,
null,
ContactsContract.CommonDataKinds.Phone.CONTACT_ID +" = "+contactId,
null,
null
)
//a contact may have multiple phone numbers
while (cursor2!!.moveToNext()){
//get phone number
val contactNumber = cursor2.getString(cursor2.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER))
//set phone number
binding.contactTv.append("\nPhone: $contactNumber")
}
cursor2.close()
}
cursor1.close()
}
}
}
else{
//cancelled picking contact
Toast.makeText(this, "Cancelled", Toast.LENGTH_SHORT).show()
}
}
}
That's it, tun project and check, here are some screenshots...