The following error is shown whenever user is requested permission to access contacts and presses “Yes”.
2021-08-28 13:41:19.242 24199-24199/com.example.criminalintent E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.example.criminalintent, PID: 24199
java.lang.RuntimeException: Failure delivering result ResultInfo{who=@android:requestPermissions:, request=131074, result=-1, data=Intent { act=android.content.pm.action.REQUEST_PERMISSIONS (has extras) }} to activity {com.example.criminalintent/com.example.criminalintent.CrimePagerActivity}: java.lang.IllegalArgumentException: the bind value at index 1 is null
**com.example.criminalintent.CrimeFragment.getSuspectPhoneNumber(CrimeFragment.java:302)**
** at com.example.criminalintent.CrimeFragment.updateSuspectNumber(CrimeFragment.java:322)**
** at com.example.criminalintent.CrimeFragment.onRequestPermissionsResult(CrimeFragment.java:337)**
The code for my Crime Fragment.java is as follows. I believe the error points to the arguments in the query to get the phone number. Any help would be appreciated. Thanks!
public class CrimeFragment extends Fragment {
private static final String ARG_CRIME_ID="crime_id";
private static final String DIALOG_DATE="DialogDate";
private static final String[] CONTACTS_PERMISSIONS=new String[]{
Manifest.permission.READ_CONTACTS,
};
private static final int REQUEST_DATE=0;
private static final int REQUEST_CONTACT= 1;
private static final int REQUEST_CONTACTS_PERMISSIONS=2;
private Crime mCrime;
private EditText mTitleField;
private Button mDateButton;
private CheckBox mSolvedCheckBox;
private Button mSuspectButton;
private Button mReportButton;
private Button mCallSuspect;
private String mSuspectId;
public static CrimeFragment newInstance(UUID crimeId){
Bundle args = new Bundle();
args.putSerializable(ARG_CRIME_ID, crimeId);
CrimeFragment fragment=new CrimeFragment();
fragment.setArguments(args);
return fragment;
}
@Override
public void onCreate(Bundle savedInstanceState){
super.onCreate(savedInstanceState);
UUID crimeId=(UUID) getArguments().getSerializable(ARG_CRIME_ID);
mCrime= CrimeLab.get(getActivity()).getCrime(crimeId);
setHasOptionsMenu(true);
}
@Override
public void onPause(){
super.onPause();
CrimeLab.get(getActivity()).updateCrime(mCrime);
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState){
View v=inflater.inflate(R.layout.fragment_crime, container, false);
mTitleField = (EditText)v.findViewById(R.id.crime_title);
mTitleField.setText(mCrime.getTitle());
mTitleField.addTextChangedListener(new TextWatcher() {
@Override
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
}
@Override
public void onTextChanged(CharSequence s, int start, int before, int count) {
mCrime.setTitle(s.toString());
}
@Override
public void afterTextChanged(Editable s) {
}
});
mDateButton = (Button) v.findViewById(R.id.crime_date);
updateDate();
mDateButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
FragmentManager manager=getFragmentManager();
DatePickerFragment dialog= DatePickerFragment.newInstance(mCrime.getDate());
dialog.setTargetFragment(CrimeFragment.this, REQUEST_DATE);
dialog.show(manager,DIALOG_DATE);
}
});
mSolvedCheckBox=(CheckBox)v.findViewById(R.id.crime_solved);
mSolvedCheckBox.setChecked(mCrime.isSolved());
mSolvedCheckBox.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener(){
@Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked){
mCrime.setSolved(isChecked);
}
});
mReportButton=(Button)v.findViewById(R.id.crime_report);
mReportButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent i= ShareCompat.IntentBuilder.from(getActivity()).setType("text/plain")
.setChooserTitle(getString(R.string.send_report))
.setText(getCrimeReport())
.setSubject(getString(R.string.Crime_report_subject))
.createChooserIntent();
startActivity(i);
}
});
final Intent pickContact= new Intent(Intent.ACTION_PICK, ContactsContract.Contacts.CONTENT_URI);
mSuspectButton = (Button)v.findViewById(R.id.crime_suspect);
mSuspectButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
startActivityForResult(pickContact, REQUEST_CONTACT);
}
});
final Intent callContact=new Intent(Intent.ACTION_DIAL);
mCallSuspect=(Button)v.findViewById(R.id.call_suspect);
mCallSuspect.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
String hpnum= mCrime.getPhoneNumber();
Uri number= Uri.parse("tel"+hpnum );
callContact.setData(number);
startActivity(callContact);
}
});
if (mCrime.getSuspect() != null){
mSuspectButton.setText(mCrime.getSuspect());
}
/*PackageManager packageManager = getActivity().getPackageManager();
if (packageManager.resolveActivity(pickContact, PackageManager.MATCH_DEFAULT_ONLY)==null){
mSuspectButton.setEnabled(false);
}*/
return v;
}
@Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater){
super.onCreateOptionsMenu(menu, inflater);
inflater.inflate(R.menu.fragment_crime, menu);
}
@Override
public boolean onOptionsItemSelected(MenuItem item){
switch (item.getItemId()){
case R.id.delete_crime:
CrimeLab.get(getActivity()).deleteCrime(mCrime.getId());
getActivity().finish();
}
return true;
}
@Override
public void onActivityResult(int requestCode, int resultCode, Intent data){
if (resultCode != Activity.RESULT_OK){
return;
}
if (requestCode==REQUEST_DATE){
Date date=(Date) data.getSerializableExtra(DatePickerFragment.EXTRA_DATE);
mCrime.setDate(date);
updateDate();
} else if (requestCode == REQUEST_CONTACT && data != null){
String suspectName=getCrimeSuspect(data);
mCrime.setSuspect(suspectName);
mSuspectButton.setText(suspectName);
if (hasContactsPermission()){
updateSuspectNumber(); }
else{
requestPermissions(CONTACTS_PERMISSIONS,REQUEST_CONTACTS_PERMISSIONS);
}
}
}
private void updateDate() {
mDateButton.setText(mCrime.getDate().toString());}
private String getCrimeReport(){
String solvedString = null;
if (mCrime.isSolved()){
solvedString=getString(R.string.crime_report_solved);
}else{
solvedString=getString(R.string.crime_report_unsolved);
}
String dateFormat="EEE, MMM dd";
String dateString= DateFormat.format(dateFormat,mCrime.getDate()).toString();
String suspect=mCrime.getSuspect();
if (suspect==null){
suspect=getString(R.string.crime_report_no_suspect);
}else{
suspect=getString(R.string.crime_report_suspect,suspect);
}
String report = getString (R.string.crime_report, mCrime.getTitle(),dateString,solvedString,suspect);
return report;
}
private String getCrimeSuspect(Intent data){
Uri contactUri = data.getData();
String[] queryFields= new String[] {
ContactsContract.Contacts.DISPLAY_NAME,
ContactsContract.Contacts._ID
};
Cursor c=getActivity().getContentResolver().
query(contactUri,queryFields,null,null,null);
try {
if (c.getCount() == 0) {
return null;
}
c.moveToFirst();
String suspect = c.getString(0);
mSuspectId =c.getString(1);
return suspect;
}finally {
c.close(); }
}
private String getSuspectPhoneNumber(String contactId){
String suspectPhoneNumber=null;
Uri phoneContactUri= ContactsContract.CommonDataKinds.Phone.CONTENT_URI;
//returns columns
String[] queryFields= new String[] {
ContactsContract.Data.CONTACT_ID,
ContactsContract.CommonDataKinds.Phone.NUMBER,
ContactsContract.CommonDataKinds.Phone.TYPE
};
//Selection criteria (where clause)
String mSelectionClause= ContactsContract.Data.CONTACT_ID + "=?";
//Selection criteria (where args)
String mSelectionArgs[] ={ contactId };
//Does query and returns cursor object
Cursor c= getActivity().getContentResolver().
query(phoneContactUri,queryFields,mSelectionClause,mSelectionArgs,null);
try {
if (c.getCount() == 0) {
return null;
}
c.moveToNext();
int phoneType=c.getInt(c.getColumnIndex(ContactsContract.CommonDataKinds.Phone.TYPE));
if (phoneType==ContactsContract.CommonDataKinds.Phone.TYPE_MOBILE) {
suspectPhoneNumber=c.getString(c.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
}
}finally {
c.close(); }
return suspectPhoneNumber;
}
private void updateSuspectNumber () {
String suspectPhoneNumber = getSuspectPhoneNumber(mSuspectId);
mCrime.setPhoneNumber(suspectPhoneNumber);
}
private boolean hasContactsPermission() {
int result = ContextCompat
.checkSelfPermission(getActivity(), CONTACTS_PERMISSIONS[0]);
return result == PackageManager.PERMISSION_GRANTED;
}
@Override
public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
switch (requestCode) {
case REQUEST_CONTACTS_PERMISSIONS:
if (hasContactsPermission()) {
updateSuspectNumber();
}
/*default:
super.onRequestPermissionsResult(requestCode, permissions, grantResults);*/
}
}