简体   繁体   中英

Android application crashes when I click save button or search

I am new to Android. I am running SQLite Filter ListView. I added an EditText , priceEditTxt , in the dialog box and another column "Price " in the database. When I search or click the save button, the application stops. I don't know how to solve it.

The Display() function has two EditText and one save button. When I click the save button, the application, unfortunately, stops working.

The getPlanet() function is used to show a search list when I click on the searchview. I don't have much understanding about it.

MainActivity.java:

private void displayDialog()
{
    Dialog d=new Dialog(this);
    d.setTitle("SQLite Database");
    d.setContentView(R.layout.dialog_layout);

    nameEditText= (EditText) d.findViewById(R.id.nameEditTxt);

        **////////////////////Price edit text which I add/////////////**
    priceEditText= (EditText) d.findViewById(R.id.priceEditTxt);
    saveBtn= (Button) d.findViewById(R.id.saveBtn);
    retrieveBtn= (Button) d.findViewById(R.id.retrieveBtn);

    saveBtn.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            save(nameEditText.getText().toString(),priceEditText.getText().toString());
        }
    });
    retrieveBtn.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
             getPlanets(null);
        }
    });

    d.show();
}
** //save button took one argument "name" only, i add "price" later//**
private void save(String name,String price)
{
    DBAdapter db=new DBAdapter(this);
    db.openDB();
    if(db.add(name,price))
    {
        nameEditText.setText("");
        priceEditText.setText("");
    }else {
        Toast.makeText(this,"Unable To Save",Toast.LENGTH_SHORT).show();
    }

    db.closeDB();

    this.getPlanets(null);
}

private void getPlanets(String searchTerm)
{
    planets.clear();

    DBAdapter db=new DBAdapter(this);
    db.openDB();
    Planet p=null;
    Cursor c=db.retrieve(searchTerm);
    while (c.moveToNext())
    {
        int id=c.getInt(0);
        String name=c.getString(1);

        p=new Planet();
        p.setId(id);
        p.setName(name);

        planets.add(p);
    }

    db.closeDB();

    lv.setAdapter(adapter);

}

DBAdapter.java contains the add and retrieve functions, which I call from MainActivity .

DBAdapter.java:

public class DBAdapter {

    Context c;
    SQLiteDatabase db;
    DBHelper helper;

    public DBAdapter(Context c) {
        this.c = c;
        helper=new DBHelper(c);
    }

    //OPEN DB
    public void openDB()
    {
        try
        {
           db=helper.getWritableDatabase();
        }catch (SQLException e)
        {
            e.printStackTrace();
        }
    }

    //CLOSE
    public void closeDB()
    {
        try
        {
            helper.close();
        }catch (SQLException e)
        {
            e.printStackTrace();
        }
    }

    //INSERT DATA
    public boolean add(String name,String price)
    {
        try
        {
            ContentValues cv=new ContentValues();
            cv.put(Constants.NAME, name);
            cv.put(Constants.PRICE, price);
            //Log.d(Constants.PRICE,"here we gooooooooooooooooooooooooooooooooooooooooooooooooooo");

            db.insert(Constants.TB_NAME, Constants.ROW_ID, cv);

            return true;

        }catch (SQLException e)
        {
            e.printStackTrace();
        }
        return false;
    }

    //RETRIEVE DATA AND FILTER
    public Cursor retrieve(String searchTerm)
    {
        String[] columns={Constants.ROW_ID,Constants.NAME};
        Cursor c=null;

        if(searchTerm != null && searchTerm.length()>0)
        {
            String sql="SELECT * FROM "+Constants.TB_NAME+" WHERE "+Constants.NAME+" LIKE '%"+searchTerm+"%'";
            c=db.rawQuery(sql,null);
            return c;

        }

        c=db.query(Constants.TB_NAME,columns,null,null,null,null,null);
        return c;
    }
}

Constants.java contains the creatable and droptable query. I don't know if create table query is right or not.

Constants.java:

public class Constants {
    //COLUMNS
    static final String ROW_ID="id";
    static final String NAME="name";
    static final String PRICE="price";

    //DB
    static final String DB_NAME="ii_DB";
    static final String TB_NAME="ii_TB";
    static final int DB_VERSION=2;

    //CREATE TB
    static final String CREATE_TB="CREATE TABLE ii_TB(id INTEGER PRIMARY KEY AUTOINCREMENT,"
            + "name TEXT NOT NULL,price TEXT NOT NULL);";

    //DROP TB
    static final String DROP_TB="DROP TABLE IF EXISTS "+TB_NAME;
}

You are creating different instances of DBAdapter for each operation and opening a new connection to the database on these operations. Also, you are closing these connections each time you are done with the operation.

Trying to get a new connection to your database is expensive, as stated here: Persisting database connection . The database is probably not open or not ready when you do a new operation to your database.

Knowing these simple things, we probably would assume that dbAdapter.openDB() may throw an exception when the database is not yet ready. Thus, leaving the variable db still be equal to null. I assume that your error is NullPointerException and because of this, you cant do operations to your database.


TL;DR
Create a single instance of DBAdapter. Call openDB once. And call closeDB on destroy.


More or Other Sources
Kevin Galligan's Answer for Best Practices

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