简体   繁体   中英

ListView updates the entry only when the application is restarted again

In this application, I have a listview and a sqlitedatabase . There is a floating action button which on clicking displays a dialog box containing two edittext one for name and another for number. The problem is that the after clicking on the add option of the dialog box the entry is not shown on the listview . But when the activity is destroyed and onCreate is called again on the activity , the entry is shown.

I tried using adapter.notifyDataSetChanged() but it doesn't work. The code is shown below :

Code

public class DetailsActivity extends AppCompatActivity {

private DatabaseManager manager;
private ListView listView;
private SimpleCursorAdapter adapter;

final String[] from=new String[] {UserDatabase.NAME,UserDatabase.NUMBER};

final int[] to=new int[] {R.id.nameDisplay,R.id.phoneDisplay};


@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_details);

    manager = new DatabaseManager(getApplicationContext());
    manager.open();
    Cursor cursor=manager.fetch();

    listView = (ListView) findViewById(R.id.listViewId);
    listView.setEmptyView(findViewById(R.id.empty));

    adapter = new SimpleCursorAdapter(getApplicationContext(),
            R.layout.row_item, cursor, from, to, 0);
    adapter.notifyDataSetChanged();

    listView.setAdapter(adapter);

    FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab);
    fab.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            final AlertDialog.Builder dialogBuilder = new AlertDialog.Builder(DetailsActivity.this);
            LayoutInflater inflater = DetailsActivity.this.getLayoutInflater();
            final View dialogView = inflater.inflate(R.layout.custom_dialog, null);
            dialogBuilder.setView(dialogView);
            final EditText name = (EditText) dialogView.findViewById(R.id.dialogEditNmID);
            final EditText phone = (EditText) dialogView.findViewById(R.id.dialogEditPhID);

            dialogBuilder.setTitle("Add Details");
            dialogBuilder.setPositiveButton("Add", new DialogInterface.OnClickListener() {
                @Override
                public void onClick(DialogInterface dialog, int which) {
                    if (!TextUtils.isEmpty(name.getText().toString()) &&
                            !TextUtils.isEmpty(phone.getText().toString())) {
                        /*adapter.notifyDataSetChanged();
                        manager.insert(name.getText().toString(), phone.getText().toString());
                        Toast.makeText(getApplicationContext(),
                                "Added " + name.getText().toString(), Toast.LENGTH_SHORT).show();*/
                        insertData(name.getText().toString(),phone.getText().toString());
                    } else {
                        Toast.makeText(getApplicationContext(),
                                "Empty field(s)", Toast.LENGTH_SHORT).show();
                    }

                }
            });

            dialogBuilder.setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
                @Override
                public void onClick(DialogInterface dialog, int which) {
                    dialog.dismiss();
                }
            });

            AlertDialog b = dialogBuilder.create();
            b.show();
            //  listView.setAdapter(adapter);
            //adapter.notifyDataSetChanged();
        }
    });
}

public void insertData(String fname,String phnumber){
    manager.insert(fname,phnumber);
    listView.setAdapter(adapter);
    adapter.notifyDataSetChanged();
}
}

Some of the statements are commented because I tried to get the desired result but couldn't get it.

There's a couple things here you have to change. Taking a look at this code:

dialogBuilder.setPositiveButton("Add", new DialogInterface.OnClickListener() {
    @Override
    public void onClick(DialogInterface dialog, int which) {
        if (!TextUtils.isEmpty(name.getText().toString()) && !TextUtils.isEmpty(phone.getText().toString())) {
            adapter.notifyDataSetChanged();
            manager.insert(name.getText().toString(), phone.getText().toString());
            Toast.makeText(getApplicationContext(), "Added " + name.getText().toString(), Toast.LENGTH_SHORT).show();
        } else {
            Toast.makeText(getApplicationContext(), "Empty field(s)", Toast.LENGTH_SHORT).show();
        }
    }
});
  1. When you click the "Add" button, right away you call adapter.notifyDataSetChanged(); . In your case, you are only supposed to call that after you have added items to listView , but you haven't added anything yet.
  2. You insert into your database using manager.insert(name.getText().toString(), phone.getText().toString()); , but you don't update listView with your newly added data. You need to insert that data to the database, and then also add that data to listView .

Now you can call adapter.notifyDataSetChanged(); .

I would recommend that when you want to insert into your database, create a method which will insert the data, add the new data to the listView , and then tell the adapter to refresh.

Edit

Regarding your recent edit, there's still a few things that need to be taken care of.

  1. You should not have listView.setAdapter(adapter) in the method. You had it right the first time (in onCreate() but before the dialog builder).
  2. You call manager.insert(fname,phnumber); , but still do not add the newly inserted data to listView .

Here's pseudocode for what you should have in your method:

public void insertData(String fname,String phnumber){
    manager.insert(fname,phnumber);
    // Code to add the data you just inserted into the manager above to `listView`.
    adapter.notifyDataSetChanged();
}

Remember, adapter.notifyDataSetChanged(); only updates listView if there's changes to listView , and as of right now you haven't added/deleted/modified listView .

i have did some changes into the code please try it and let me know if it is helpful or not

public class DetailsActivity extends AppCompatActivity {

private DatabaseManager manager;
private ListView listView;
private SimpleCursorAdapter adapter;

final String[] from=new String[] {UserDatabase.NAME,UserDatabase.NUMBER};

final int[] to=new int[] {R.id.nameDisplay,R.id.phoneDisplay};

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_details);

    manager = new DatabaseManager(getApplicationContext());
    manager.open();


    listView = (ListView) findViewById(R.id.listViewId);
    listView.setEmptyView(findViewById(R.id.empty));
    adapter = new SimpleCursorAdapter(getApplicationContext(),R.layout.row_item, cursor, from, to, 0);
    //adapter.notifyDataSetChanged();

    FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab);
    fab.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            final AlertDialog.Builder dialogBuilder = new AlertDialog.Builder(DetailsActivity.this);
            LayoutInflater inflater = DetailsActivity.this.getLayoutInflater();
            final View dialogView = inflater.inflate(R.layout.custom_dialog, null);
            dialogBuilder.setView(dialogView);
            final EditText name = (EditText) dialogView.findViewById(R.id.dialogEditNmID);
            final EditText phone = (EditText) dialogView.findViewById(R.id.dialogEditPhID);

            dialogBuilder.setTitle("Add Details");
            dialogBuilder.setPositiveButton("Add", new DialogInterface.OnClickListener() {
                @Override
                public void onClick(DialogInterface dialog, int which) {
                    if (!TextUtils.isEmpty(name.getText().toString()) &&
                            !TextUtils.isEmpty(phone.getText().toString())) {
                        adapter.notifyDataSetChanged();
                        manager.insert(name.getText().toString(), phone.getText().toString());
                        Toast.makeText(getApplicationContext(),
                                "Added " + name.getText().toString(), Toast.LENGTH_SHORT).show();

                        Cursor cursor = manager.fetch();

                        listView.setAdapter(adapter);
                    } else {
                        Toast.makeText(getApplicationContext(),
                                "Empty field(s)", Toast.LENGTH_SHORT).show();
                    }

                }
            });

            dialogBuilder.setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
                @Override
                public void onClick(DialogInterface dialog, int which) {
                    dialog.dismiss();
                }
            });

            AlertDialog b = dialogBuilder.create();
            b.show();
            //  listView.setAdapter(adapter);
            //adapter.notifyDataSetChanged();
        }
    });
}}

After you insert the entries in your database, you should fetch the data again so that your list has the newest entry. So you can either modify your code to be able to add a data point to the list you are passing to the adapter or refetch the data from the database after insertions and before notifyDatasetChanged().

Try to use notifyDataSetChanged after insert operation. In all place where you call(try to call) notify manager data isn't change yet.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM