-3

I'll start saying I just hope this isn't something so stupid I couldn't notice it, but after hours of researches I haven't found my answer. In my SMSActivity I have created a Button cmdApriRubrica which opens the Contacts default app and then when a Contact is selected returns its data to my activity, theorically (I've looked this up at Android Developer Basic Trainings). The Contacts app opens fine, but the problem is I never get the result. My code is the following:

((Button)findViewById(R.id.cmdApriRubrica)).setOnClickListener( new Button.OnClickListener() {

        @Override
        public void onClick(View v) {

            Intent pickContactIntent = new Intent(Intent.ACTION_PICK, Uri.parse("content://contacts"));
            pickContactIntent.setType(ContactsContract.CommonDataKinds.Phone.CONTENT_TYPE); // Show user only contacts w/ phone numbers
            startActivityForResult(pickContactIntent, 200);
        }

        @Override
        protected void onActivityResult(int requestCode, int resultCode, Intent data) {

            //super.onActivityResult(int requestCode, int resultCode, Intent data); CAN'T CALL THIS

            // Check which request it is that we're responding to

            if (requestCode == 200 && resultCode == RESULT_OK) {

                // Make sure the request was successful
                    // Get the URI that points to the selected contact

                    Uri contactUri = data.getData();

                    // We only need the NUMBER column, because there will be only one row in the result

                    String[] projection = {ContactsContract.CommonDataKinds.Phone.NUMBER};

                    // Perform the query on the contact to get the NUMBER column
                    // We don't need a selection or sort order (there's only one result for the given URI)
                    // CAUTION: The query() method should be called from a separate thread to avoid blocking
                    // your app's UI thread. (For simplicity of the sample, this code doesn't do that.)
                    // Consider using CursorLoader to perform the query.

                    Cursor cursor = getContentResolver()
                            .query(contactUri, projection, null, null, null);
                    cursor.moveToFirst();


                    // Retrieve the phone number from the NUMBER column

                    int column = cursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER);
                    String nome = cursor.getString(cursor.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME));
                    String numero = cursor.getString(column);

                    Log.i("Dati contatto: ","Nome = "+nome+", numero = "+numero);


                    // Do something with the phone number...

                    txtDati.setText(new StringBuilder().append(nome).append("\t------------\t").append(numero).toString()); //Android Studio suggested me doing this...
                }
            }
    });

I think the main problem is that I'm in the onClick() event: I've looked out for this answer, this answer, this bug, this answer, this site and some other less voted answers. Many suggested to call super.onActivityResult but it doesn't find the method, so I can't call it. Also, Android Studio tells me that the onActivityResult I wrote there doesn't override its superclass's method. Why does this happen? I haven't found any answer about this. Is there a way to avoid writing this inside the onClick method, if this is the problem, or am I doing something wrong I couldn't find a solution about? Thank you for your time.


EDIT: I have modified the code as I've been suggested; my code is now the following:
    TextView txtDati = null; //This is initialized just below the class declaration to have it visible
    public static final int PICK_CONTACT_REQ_CODE = 200;
        ...
        findViewById(R.id.cmdApriRubrica).setOnClickListener(new View.OnClickListener() {

            @Override
            public void onClick(View v) {

                Intent pickContactIntent = new Intent(Intent.ACTION_PICK, Uri.parse("content://contacts"));
                pickContactIntent.setType(ContactsContract.CommonDataKinds.Phone.CONTENT_TYPE); // Show user only contacts w/ phone numbers
                startActivityForResult(pickContactIntent, PICK_CONTACT_REQ_CODE);
            }
        });

        ...
//At the same level of the onCreate() method, as I've been told!
    @Override
    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        // Check which request it is that we're responding to

        if (requestCode == 200 && resultCode == RESULT_OK && txtDati != null) {

            // Make sure the request was successful
            // Get the URI that points to the selected contact

            Uri contactUri = data.getData();

            // We only need the NUMBER column, because there will be only one row in the result

            String[] projection = {ContactsContract.CommonDataKinds.Phone.NUMBER};

            // Perform the query on the contact to get the NUMBER column
            // We don't need a selection or sort order (there's only one result for the given URI)
            // CAUTION: The query() method should be called from a separate thread to avoid blocking
            // your app's UI thread. (For simplicity of the sample, this code doesn't do that.)
            // Consider using CursorLoader to perform the query.

            Cursor cursor = getContentResolver()
                    .query(contactUri, projection, null, null, null);
            cursor.moveToFirst();


            // Retrieve the phone number from the NUMBER column

            int column = cursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER);
            String nome = cursor.getString(cursor.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME));
            String numero = cursor.getString(column);

            Log.i("Dati contatto: ","Nome = "+nome+", numero = "+numero);


            // Do something with the phone number...

            txtDati.setText(new StringBuilder().append(nome).append("\t------------\t").append(numero).toString()); //Android Studio suggested me doing this...
        }

        else
            Log.i("Problem ActivityResult","Something wrong in onActivityResult method!");
    }

I now get this exception but I can't understand how the Cursor.query works very well:


java.lang.RuntimeException: Failure delivering result ResultInfo{who=null, request=200, result=-1, data=Intent { dat=content://com.android.contacts/data/3045 flg=0x1 }} to activity {com.fun.is.activity.gguiduzzi.orariobello/com.fun.is.activity.gguiduzzi.orariobello.SMSActivity}: java.lang.IllegalStateException: Couldn't read row 0, col -1 from CursorWindow. Make sure the Cursor is initialized correctly before accessing data from it.
Can someone please tell me where's the problem? I've been looking so hard for it. Thank you!
Community
  • 1
  • 1
ServantGrunt
  • 35
  • 11

1 Answers1

1

You have two problems here in my opinion. You are using the method OnClickListener from Button. You should use View.

((Button)findViewById(R.id.cmdApriRubrica)).setOnClickListener( new Button.OnClickListener() { WRONG

((Button)findViewById(R.id.cmdApriRubrica)).setOnClickListener( new View.OnClickListener() { OK

The second problem you have is that you are overriding the onActivityResult inside de button listener and not the activity that's why you can't use super.onActivityResult.

You should put this code (onActivityResult) at the same level of onCreate, onDestroy, etc.

qmateub
  • 512
  • 4
  • 9
  • So I should override it outside, thank you! Can you explain me please what changes from using Button.OnClickListener to View? – ServantGrunt May 13 '15 at 11:36
  • @njzk2 Maybe wrong was not the correct word here, my fault, i should use "possible change" or something like that. He was looking for a solution to his problem and i answered what i think he could change to resolve it. In the API (http://developer.android.com/reference/android/widget/Button.html) and in most of the projects i've been part of, use Button.OnClickListener that's why i suggested it. – qmateub May 14 '15 at 06:33