0

I am trying to update ListView after another activity finish()'es with result. Initialization (works correctly):

@Override
protected void onCreate(Bundle savedInstanceState) {

    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    databaseHelper = new DatabaseHelper(this);

    objects = databaseHelper.selectObjects();

    objectsListView = (ListView) findViewById(R.id.LIST_VIEW_OBJECTS);

    objectArrayAdapter = new ArrayAdapter<Object>(this, android.R.layout.simple_list_item_1, objects);

    objectsListView.setAdapter(objectArrayAdapter);
}

Problem occurs only when Im trying update ListView:

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

    if(requestCode == SECOND_ACTIVITY_REQUEST) {

        if (resultCode == RESULT_OK) {

            objects = databaseHelper.selectObjects();

            objectArrayAdapter.notifyDataSetChanged();
        }

        if (resultCode == RESULT_CANCELED) {

            Toast.makeText(getApplicationContext(), getResources().getString(R.string.TOAST_ERROR_RESULT_CANCELED), Toast.LENGTH_LONG).show();
        }
    }
}

But this code works just fine:

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

    if(requestCode == SECOND_ACTIVITY_REQUEST) {

        if (resultCode == RESULT_OK) {

            objects.add(newObject);

            objectArrayAdapter.notifyDataSetChanged();
        }

        if (resultCode == RESULT_CANCELED) {

            Toast.makeText(getApplicationContext(), getResources().getString(R.string.TOAST_ERROR_RESULT_CANCELED), Toast.LENGTH_LONG).show();
        }
    }
}

This code also works fine:

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

    if(requestCode == SECOND_ACTIVITY_REQUEST) {

        if (resultCode == RESULT_OK) {

            objects = databaseHelper.selectObjects();

            objectArrayAdapter = new ArrayAdapter<Object>(this, android.R.layout.simple_list_item_1, objects);

            objectsListView.setAdapter(objectArrayAdapter);
        }

        if (resultCode == RESULT_CANCELED) {

            Toast.makeText(getApplicationContext(), getResources().getString(R.string.TOAST_ERROR_RESULT_CANCELED), Toast.LENGTH_LONG).show();
        }
    }
}

My question is: why first method doesn't work as expected? Second and third seems to be a work round isn't it?

Jacob Jones
  • 501
  • 2
  • 6
  • 22

1 Answers1

0

In your first example, you are giving the information to questionnaires variable, which I don't see being related to your listview. onNotifyDataSetChanged() has the same data as before from what I can tell.

The second one works because you are directly changing the objects variable which is connected to your adapter.

EDIT: "For an ArrayAdapter, notifyDataSetChanged only works if you use the add(), insert(), remove(), and clear() on the Adapter." notifyDataSetChanged example

Community
  • 1
  • 1
Lukos
  • 712
  • 4
  • 5
  • I am really sorry! I was trying to simplify my code for this question. `questionnaires` = `objects`. `ArrayList`'s in both examples are the same (now updated). Sorry again... – Jacob Jones Nov 04 '14 at 21:10
  • Oh okay, I'm not sure but I think obectsListView itself needs to be manipulated before calling onNotifyDataSetChanged. ex: objectsListView.clear,.add etc. – Lukos Nov 04 '14 at 21:51
  • Hmmm... I really don't think so, because I have done similar functionality successfully before. The difference was that I added data to array like this: `objects.add(newObject);`. Here `objectsListView` is not manipulated too, isn't it? – Jacob Jones Nov 05 '14 at 05:31
  • I think the adapter is still holding a reference to the old values. This should clear things up. http://stackoverflow.com/questions/3669325/notifydatasetchanged-example – Lukos Nov 05 '14 at 14:29
  • But if I say `objectArrayAdapter.notifyDataSetChanged();` shouldn't this method refresh all list with new data set? – Jacob Jones Nov 05 '14 at 15:18
  • The adapter references 'objects' the first time you created it. I believe the adapter now no longer looks at objects. It is like saying: x = 10; y = x; x = 11; y will still be 10, if that makes sense. I could also be wrong, I'm not an expert on adapters. The reason the second method works is because you force the adapter to reacquire the reference every time. – Lukos Nov 05 '14 at 15:42