skip to Main Content

Caused by: java.lang.IllegalStateException: Couldn’t read row 0, col -1 from CursorWindow. Make sure the Cursor is initialized correctly before accessing data from it.
I changed android:allowBackup="true" into "False" In android manifest.

public class ListViewActivity extends Activity {
    SQLiteHelper SQLITEHELPER;
    SQLiteDatabase SQLITEDATABASE;
    Cursor cursor;
    SQLiteListAdapter ListAdapter;

    ArrayList<String> CODE_ArrayList = new ArrayList<String>();
    ArrayList<String> ITEM_ArrayList = new ArrayList<String>();
    ArrayList<String> QUANTITY_ArrayList = new ArrayList<String>();
    ArrayList<String> TAX_ArrayList = new ArrayList<String>();
    ArrayList<String> UNITPRICE_ArrayList = new ArrayList<String>();
    ArrayList<String> TOTALPRICE_ArrayList = new ArrayList<String>();
    ArrayList<String> SELLER_ArrayList = new ArrayList<String>();
    ListView LISTVIEW;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_list_view);    
        LISTVIEW = (ListView)findViewById(R.id.listView1);
        SQLITEHELPER = new SQLiteHelper(this);
    }

    @Override
    protected void onResume() {    
        ShowSQLiteDBdata();
        super.onResume();
    }

    private void ShowSQLiteDBdata() {    
        SQLITEDATABASE = SQLITEHELPER.getWritableDatabase();
        cursor = SQLITEDATABASE.rawQuery("SELECT * FROM demoTableb", null);
        CODE_ArrayList.clear();
        ITEM_ArrayList.clear();
        QUANTITY_ArrayList.clear();
        TAX_ArrayList.clear();
        UNITPRICE_ArrayList.clear();
        TOTALPRICE_ArrayList.clear();
        SELLER_ArrayList.clear();

        if (cursor.moveToFirst()) {
            do {
                CODE_ArrayList.add(cursor.getString(cursor.getColumnIndex(SQLiteHelper.Codes)));
                ITEM_ArrayList.add(cursor.getString(cursor.getColumnIndex(SQLiteHelper.Item)));
                QUANTITY_ArrayList.add(cursor.getString(cursor.getColumnIndex(SQLiteHelper.Quantity)));
                TAX_ArrayList.add(cursor.getString(cursor.getColumnIndex(SQLiteHelper.Tax)));
                UNITPRICE_ArrayList.add(cursor.getString(cursor.getColumnIndex(SQLiteHelper.Unitprice)));
                TOTALPRICE_ArrayList.add(cursor.getString(cursor.getColumnIndex(SQLiteHelper.Totalprice)));
                SELLER_ArrayList.add(cursor.getString(cursor.getColumnIndex(SQLiteHelper.Seller)));    
            } while (cursor.moveToNext());
        }

        ListAdapter = new SQLiteListAdapter(ListViewActivity.this, 
                CODE_ArrayList,
                ITEM_ArrayList,
                QUANTITY_ArrayList,
                TAX_ArrayList,
                UNITPRICE_ArrayList,
                TOTALPRICE_ArrayList,
                SELLER_ArrayList
                );   
        LISTVIEW.setAdapter(ListAdapter);    
        cursor.close();
    }
}
  • error is shown in line ShowSQLiteDBdata();,and SQLITEDATABASE = SQLITEHELPER.getWritableDatabase();

This is EditDataActivity

public class EditDataActivity extends Activity {
    Button next, previous, update, delete;    
    EditText item,quantity,tax,unitprice,totalprice,seller;
    SQLiteDatabase SQLITEDATABASE, SQLITEDATABASE2;
    String GetSQliteQuery, UpdateRecordQuery, DeleteQuery ;
    Cursor cursor, cursorCheckDataIsEmptyOrNot ;
    TextView purchase;
    Boolean CheckEditTextEmpty;
    String Item,Quantity,Tax,Unitprice,Totalprice,Seller;
    int ItemCode ;
    String ConvertCode ;
    SQLiteHelper SQLITEHELPER;

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

        next = (Button)findViewById(R.id.button1);
        previous = (Button)findViewById(R.id.button2);
        update = (Button)findViewById(R.id.button3);
        delete = (Button)findViewById(R.id.button4);
        item = (EditText)findViewById(R.id.editText2);
        quantity = (EditText)findViewById(R.id.editText3);
        tax = (EditText)findViewById(R.id.editText4);
        unitprice = (EditText)findViewById(R.id.editText5);
        totalprice = (EditText)findViewById(R.id.editText6);
        seller = (EditText)findViewById(R.id.editText7);
        purchase = (TextView)findViewById(R.id.textview1);
        GetSQliteQuery = "SELECT * FROM demoTableb" ;

        SQLITEDATABASE = openOrCreateDatabase("DemoDataBaseb", Context.MODE_PRIVATE, null);
        cursor = SQLITEDATABASE.rawQuery(GetSQliteQuery, null);
        cursor.moveToFirst();
        GetSQLiteDatabaseRecords();
        next.setOnClickListener(new View.OnClickListener() {

            @Override
            public void onClick(View v) {
                // TODO Auto-generated method stub
                if (!cursor.isLast()){
                    cursor.moveToNext();
                }
                GetSQLiteDatabaseRecords();
            }
        });
        previous.setOnClickListener(new View.OnClickListener() {

            @Override
            public void onClick(View v) {
                // TODO Auto-generated method stub
                if (!cursor.isFirst()){
                    cursor.moveToPrevious();
                }
                GetSQLiteDatabaseRecords();
            }
        });
        update.setOnClickListener(new View.OnClickListener() {

            @Override
            public void onClick(View v) {
                // TODO Auto-generated method stub
                Item = item.getText().toString();
                Quantity = quantity.getText().toString();
                Tax = tax.getText().toString();
                Unitprice = unitprice.getText().toString();
                Totalprice = totalprice.getText().toString();
                Seller = seller.getText().toString();
                ConvertCode = purchase.getText().toString();
                ItemCode = Integer.parseInt(ConvertCode);
                UpdateRecordQuery = "UPDATE demoTableb SET  Item ='" + Item + "', Quantity ='" + Quantity + "' ,Tax = '"+Tax+"',Unitprice = '"+Unitprice+"',Totalprice = '"+Totalprice+"',Seller ='"+Seller+"' WHERE Code=" + ItemCode + ";";
                CheckEditTextIsEmptyOrNot(Item,Quantity,Tax,Unitprice,Totalprice,Seller ); 
                if (CheckEditTextEmpty == false) {
                    SQLITEDATABASE.execSQL(UpdateRecordQuery);
                    cursor = SQLITEDATABASE.rawQuery(GetSQliteQuery, null);
                    cursor.moveToPosition(ItemCode);
                    Toast.makeText(EditDataActivity.this,"Data Updated Successfully", Toast.LENGTH_LONG).show();
                }else {
                    Toast.makeText(EditDataActivity.this,"Please Fill All the Fields", Toast.LENGTH_LONG).show();
                }
            }
        });

        delete.setOnClickListener(new View.OnClickListener() {

            @Override
            public void onClick(View v) {
                // TODO Auto-generated method stub
                ConvertCode = purchase.getText().toString();
                ItemCode = Integer.parseInt(ConvertCode);
                DeleteQuery = "DELETE FROM demoTableb WHERE Code=" + ItemCode + ";";
                SQLITEDATABASE.execSQL(DeleteQuery);
                Toast.makeText(EditDataActivity.this, "Record Deleted Successfully", Toast.LENGTH_LONG).show();
                cursor = SQLITEDATABASE.rawQuery(GetSQliteQuery, null);
            }
        });
    }

    public void GetSQLiteDatabaseRecords(){
        purchase.setText(cursor.getString(0).toString());
        item.setText(cursor.getString(1).toString());
        quantity.setText(cursor.getString(2).toString());
        tax.setText(cursor.getString(3).toString());
        unitprice.setText(cursor.getString(4).toString());
        totalprice.setText(cursor.getString(5).toString());
        seller.setText(cursor.getString(6).toString());
    }

    public void CheckEditTextIsEmptyOrNot (String Item, String Quantity, String Tax, String Unitprice, String Totalprice,String Seller){
        if( TextUtils.isEmpty(Item) || TextUtils.isEmpty(Quantity)|| TextUtils.isEmpty(Tax)|| TextUtils.isEmpty(Unitprice)|| TextUtils.isEmpty(Totalprice) || TextUtils.isEmpty(Seller)){

            CheckEditTextEmpty = true ;
        }
        else {
            CheckEditTextEmpty = false ;
        }
    }
}

and this is the mainactivity

public class SecondActivity extends Activity {
    EditText code,item,quantity,tax,unitprice,totalprice,seller ;
    Button Submit, EditData, DisplayData;
    SQLiteDatabase SQLITEDATABASE;
    String Codes,Item,Quantity,Tax,Unitprice,Totalprice,Seller ;
    Boolean CheckEditTextEmpty ;
    String SQLiteQuery ;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.purchase);
        code = (EditText)findViewById(R.id.edtcd);
        item = (EditText)findViewById(R.id.edtitm);
        quantity= (EditText)findViewById(R.id.edtqty);
        tax = (EditText) findViewById(R.id.edttax);
        unitprice = (EditText) findViewById(R.id.edtprc);
        totalprice = (EditText) findViewById(R.id.edttp);
        seller = (EditText) findViewById(R.id.edtslr);
        Submit = (Button)findViewById(R.id.sbt);
        EditData = (Button)findViewById(R.id.edt);
        DisplayData = (Button)findViewById(R.id.dply);
        Submit.setOnClickListener(new View.OnClickListener() {

            @Override
            public void onClick(View v) {
                // TODO Auto-generated method stub
                DBCreate();
                SubmitData2SQLiteDB();
            }
        });

        EditData.setOnClickListener(new View.OnClickListener() {

            @Override
            public void onClick(View v) {
                // TODO Auto-generated method stub
                Intent i=new Intent(getApplicationContext(),EditDataActivity.class);
                startActivity(i);
            }
        });
        DisplayData.setOnClickListener(new View.OnClickListener() {

            @Override
            public void onClick(View v) {
                // TODO Auto-generated method stub
                Intent i=new Intent(SecondActivity.this,ListViewActivity.class);
                startActivity(i);
            }
        });
    }

    public void DBCreate(){
        SQLITEDATABASE = openOrCreateDatabase("DemoDataBaseb", Context.MODE_PRIVATE, null);
        SQLITEDATABASE.execSQL("CREATE TABLE IF NOT EXISTS demoTableb(Code INTEGER PRIMARY KEY , item INTEGER,quantity  INTEGER, tax INTEGER,Unitprice INTEGER,Totalprice INTEGER,Seller VARCHAR);");
    }

    public void SubmitData2SQLiteDB(){
        Codes = code.getText().toString();
        Item = item.getText().toString();
        Quantity = quantity.getText().toString();
        Tax = tax.getText().toString();
        Unitprice = unitprice.getText().toString();
        Totalprice = totalprice.getText().toString();
        Seller = seller.getText().toString();
        CheckEditTextIsEmptyOrNot( Codes,Item,Quantity,Tax,Unitprice,Totalprice,Seller);
        if(CheckEditTextEmpty == true)
        {
            SQLiteQuery = "INSERT INTO demoTableb (code,item,quantity,tax,unitprice,totalprice,seller) VALUES('"+Codes+"', '"+Item+"','"+Quantity+"','"+Tax+"','"+Unitprice+"','"+Totalprice+"', '"+Seller+"');";
            SQLITEDATABASE.execSQL(SQLiteQuery);
            Toast.makeText(SecondActivity.this,"Data Submit Successfully", Toast.LENGTH_LONG).show();
            ClearEditTextAfterDoneTask();
        }
        else {
            Toast.makeText(SecondActivity.this,"Please Fill All the Fields", Toast.LENGTH_LONG).show();
        }
    }

    public void CheckEditTextIsEmptyOrNot(String code, String item, String quantity, String tax, String Name, String PhoneNumber, String subject){

        if(TextUtils.isEmpty(Codes)  || TextUtils.isEmpty(Item) || TextUtils.isEmpty(Quantity) || TextUtils.isEmpty(Tax) || TextUtils.isEmpty(Unitprice) || TextUtils.isEmpty(Totalprice) || TextUtils.isEmpty(Seller)){
            CheckEditTextEmpty = false ;
        }
        else {
            CheckEditTextEmpty = true ;
        }
    }

    public void ClearEditTextAfterDoneTask(){

        code.getText().clear();
        item.getText().clear();
        quantity.getText().clear();
        tax.getText().clear();
        unitprice.getText().clear();
        totalprice.getText().clear();
        seller.getText().clear();
    }
}
public class SQLiteHelper extends SQLiteOpenHelper {
    static String DATABASE_NAME="DemoDataBaseb";
    public static final String Codes="code";
    public static final String TABLE_NAME="demoTableb";
    public static final String Item="itm";
    public static final String Quantity="qty";
    public static final String Tax="tax";
    public static final String Unitprice="prc";
    public static final String Totalprice="tp";
    public static final String Seller="slr";
    public SQLiteHelper(Context context) {
        super(context, DATABASE_NAME, null, 1); 
    }

    @Override
    public void onCreate(SQLiteDatabase database) {

        String CREATE_TABLE="CREATE TABLE IF NOT EXISTS "+TABLE_NAME+" ("+Codes+" INTEGER PRIMARY KEY, "+Item+" VARCHAR, "+Quantity+" INTEGER, "+Tax+" INTEGER,"+Unitprice+" INTEGER,"+Totalprice+" INTEGER,"+Seller+" VARCHAR )";
        database.execSQL(CREATE_TABLE);
    }

    @Override
    public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
        db.execSQL("DROP TABLE IF EXISTS "+TABLE_NAME);
        onCreate(db);
    }   
}

Additional error

public class MainActivity extends AppCompatActivity {

SuggestedSQLiteHelper dbHelper;
Cursor cursor;
SimpleCursorAdapter sca;
ListView listview1;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    dbHelper = new SuggestedSQLiteHelper(this);
    listview1 = this.findViewById(R.id.listView1);
    if (dbHelper.isTableEmpty(SuggestedSQLiteHelper.TABLE_NAME)) {
        dbHelper.insertDemoTablebRow("Item1",1,5,100,100,"Fred");
    }
    setOrRefreshListView();
}

private void setOrRefreshListView() {
    cursor = dbHelper.getAllFromDemoTableb();
    if (sca == null) {
        // setup the adapter
        // NOTE CURSOR ADAPTERS MUST HAVE _ID column which MUST be type INTEGER and UNIQUE
        // see use of BaseColumns._ID in table create
        sca = new SimpleCursorAdapter(this,R.layout.demotableb_layout,cursor,
                // The columns FROM which the data is to be retrieved
                new String[]{
                        SuggestedSQLiteHelper.ITEM_COLUMN,
                        SuggestedSQLiteHelper.QUANTITY_COLUMN,
                        SuggestedSQLiteHelper.TAX_COLUMN,
                        SuggestedSQLiteHelper.UNITPRICE_COLUMN,
                        SuggestedSQLiteHelper.TOTALPRICE_COLUMN,
                        SuggestedSQLiteHelper.SELLER_COLUMN
                },
                // The id of the view's to display the data as per the layout (2nd parm)
                new int[]{
                        R.id.item,
                        R.id.quantity,
                        R.id.tax,
                        R.id.unitprice,
                        R.id.totalprice,
                        R.id.seller
                },0 // 0 is fine
        );
        listview1.setAdapter(sca); // Tie the adapter to the ListView
        // Can add the Listeners here e.g.
        listview1.setOnItemClickListener(new AdapterView.OnItemClickListener() {
            @Override
            public void onItemClick(AdapterView<?> adapterView, View view, int i, long l) {
                // DO SOMETHING HERE NOTING
                // long l passed (4th parm) is the _id of the clicked item
                // hence l can be passed/used as it uniquely identifies the row
                // e.g.
                Cursor csr = dbHelper.getDemotablebById(l);
                DatabaseUtils.dumpCursor(csr);
                csr.close();
            }
        });
    } else {
        sca.swapCursor(cursor);
    }
}

@Override
protected void onResume() {
    super.onResume();
    setOrRefreshListView(); //<<<<<<<<<< will refresh the listview in case data has changed
}

@Override
protected void onDestroy() {
    cursor.close(); //<<<<<<<<< should always close the cursor when done with it
    super.onDestroy();
}

}

error

Caused by: java.lang.NullPointerException: Attempt to invoke virtual method ‘void android.widget.ListView.setAdapter(android.widget.ListAdapter)’ on a null object reference
at com.allmycode.stac.MainActivity.setOrRefreshListView(MainActivity.java:69)
at com.allmycode.stac.MainActivity.onCreate(MainActivity.java:40)

2

Answers


  1. The issue is that the getColumnIndex method, if passed a column name that does not exist in the cursor returns -1 as per :-

    Returns the zero-based index for the given column name, or -1 if the column doesn’t exist. If you expect the column to exist use getColumnIndexOrThrow(java.lang.String) instead, which will make the error more clear. https://developer.android.com/reference/android/database/Cursor#getColumnIndex(java.lang.String)

    As such one of the expected columns does not exist in the Cursor and as you are using SELECT * .... then the column does not exist in the table demoTableb.

    You need to make check that the table and extracted columns are compatible. That is either add the missing column to the table or remove the missing column from the columns being extracted from the cursor.

    NOTE I believe that the getColumnIndex has a bug in that it is (was) case sensitive (it certainly used to be) so the issue could be the case of the column names

    If you are unsure then you may find dumping the Cursor helpful. e.g. you could use:-

    cursor = SQLITEDATABASE.rawQuery("SELECT * FROM demoTableb", null);
    DatabaseUtils.dumpCursor(cursor); //<<<<<<<<<< Will dump the cursor to the log.
    

    Here’s an example of a dumped Cursor :-

    09-30 08:25:57.238 1933-1933/so52573525.so52573525 D/ADDRESULT: Added row
    09-30 08:25:57.238 1933-1933/so52573525.so52573525 I/System.out: >>>>> Dumping cursor android.database.sqlite.SQLiteCursor@456d67
        0 {
           SEM_ID=1
           Date=2018-09-01
           Department=Area 1
           Topic=Blah
           Speaker=Fred
           No_of_Students=10
           Guests=Tom
           Organisation=The org
        }
        1 {
           SEM_ID=2
           Date=2018-08-01
           Department=Area 2
           Topic=Another
           Speaker=Mary
           No_of_Students=100
           Guests=Sue, Tom and Anne
           Organisation=Acme
        }
        <<<<<
    
    • From the dump you can see that the columns in the Cursor are:-

      • SEM_ID
      • Date
      • Department
      • Topic
      • Speaker
      • No_of_Students
      • Guests
      • Organisation
    • You can also see that row’s 0 and 1 were extracted.


    ADDITIONAL re the comment :-

    i uninstalled and reinstalled it but listview doesn’t display.i uploaded th SQLiteHelper above could you pls correct it.

    I believe that uninstalling and reinstalling has allowed you to move on, that is it would appear that you changed the table to add a column and the col -1 was then fixed as the table was then changed so the column now exists.

    Certainly the essence of your code works. To show that it does work I put together a test App by using your SQLiteHelper class without any changes and then extracted the core code from your ListViewActivity and placed it into an activity (MainActivity) as per :-

    public class MainActivity extends AppCompatActivity {
    
        SQLiteHelper SQLITEHELPER;
        SQLiteDatabase SQLITEDATABASE;
        Cursor cursor;
        //SQLiteListAdapter ListAdapter;
    
        ArrayList<String> CODE_ArrayList = new ArrayList<String>();
        ArrayList<String> ITEM_ArrayList = new ArrayList<String>();
        ArrayList<String> QUANTITY_ArrayList = new ArrayList<String>();
        ArrayList<String> TAX_ArrayList = new ArrayList<String>();
        ArrayList<String> UNITPRICE_ArrayList = new ArrayList<String>();
        ArrayList<String> TOTALPRICE_ArrayList = new ArrayList<String>();
        ArrayList<String> SELLER_ArrayList = new ArrayList<String>();
        ListView LISTVIEW;
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
            SQLITEHELPER = new SQLiteHelper(this);
            SQLITEDATABASE = SQLITEHELPER.getWritableDatabase();
            /* ADDED to insert a row ino the table */
            ContentValues cv = new ContentValues();
            cv.put(SQLiteHelper.Item,"Item1");
            cv.put(SQLiteHelper.Quantity,"1");
            cv.put(SQLiteHelper.Seller,"Seller1");
            cv.put(SQLiteHelper.Tax,"X");
            cv.put(SQLiteHelper.Totalprice,"100");
            cv.put(SQLiteHelper.Unitprice,"100");
            SQLITEDATABASE.insert(SQLiteHelper.TABLE_NAME,null,cv);
            ShowSQLiteDBdata();
        }
    
        private void ShowSQLiteDBdata() {
            SQLITEDATABASE = SQLITEHELPER.getWritableDatabase();
    
            /*>>>>>>>>>> ADDED to display the schema (tables)*/
            cursor = SQLITEDATABASE.rawQuery("SELECT * FROM sqlite_master;",null);
            DatabaseUtils.dumpCursor(cursor);
            cursor = SQLITEDATABASE.rawQuery("SELECT * FROM demoTableb", null);
            /*>>>>>>>>>> ADDED to dump the cursor from your code */
            DatabaseUtils.dumpCursor(cursor);
    
            CODE_ArrayList.clear();
            ITEM_ArrayList.clear();
            QUANTITY_ArrayList.clear();
            TAX_ArrayList.clear();
            UNITPRICE_ArrayList.clear();
            TOTALPRICE_ArrayList.clear();
            SELLER_ArrayList.clear();
    
            if (cursor.moveToFirst()) {
                do {
                    CODE_ArrayList.add(cursor.getString(cursor.getColumnIndex(SQLiteHelper.Codes)));
                    ITEM_ArrayList.add(cursor.getString(cursor.getColumnIndex(SQLiteHelper.Item)));
                    QUANTITY_ArrayList.add(cursor.getString(cursor.getColumnIndex(SQLiteHelper.Quantity)));
                    TAX_ArrayList.add(cursor.getString(cursor.getColumnIndex(SQLiteHelper.Tax)));
                    UNITPRICE_ArrayList.add(cursor.getString(cursor.getColumnIndex(SQLiteHelper.Unitprice)));
                    TOTALPRICE_ArrayList.add(cursor.getString(cursor.getColumnIndex(SQLiteHelper.Totalprice)));
                    SELLER_ArrayList.add(cursor.getString(cursor.getColumnIndex(SQLiteHelper.Seller)));
                } while (cursor.moveToNext());
            }
    
            /*>>>>>>>>>> commented out as the SQLiteAdapter class is not available
            ListAdapter = new SQLiteListAdapter(ListViewActivity.this,
                    CODE_ArrayList,
                    ITEM_ArrayList,
                    QUANTITY_ArrayList,
                    TAX_ArrayList,
                    UNITPRICE_ArrayList,
                    TOTALPRICE_ArrayList,
                    SELLER_ArrayList
            );
            LISTVIEW.setAdapter(ListAdapter);
    
             */
            cursor.close();
        }
    }
    

    Result

    When the above was run, the App didn’t crash and the log included:-

    I/System.out: >>>>> Dumping cursor android.database.sqlite.SQLiteCursor@b9ccda0
    I/System.out: 0 {
    I/System.out:    type=table
    I/System.out:    name=android_metadata
    I/System.out:    tbl_name=android_metadata
    I/System.out:    rootpage=3
    I/System.out:    sql=CREATE TABLE android_metadata (locale TEXT)
    I/System.out: }
    I/System.out: 1 {
    I/System.out:    type=table
    I/System.out:    name=demoTableb
    I/System.out:    tbl_name=demoTableb
    I/System.out:    rootpage=4
    I/System.out:    sql=CREATE TABLE demoTableb (code INTEGER PRIMARY KEY, itm VARCHAR, qty INTEGER, tax INTEGER,prc INTEGER,tp INTEGER,slr VARCHAR )
    I/System.out: }
    I/System.out: <<<<<
    
    • The dump of the schema (i.e. the contents of sqlite_master)

    • This confirms the existence of the demoTableb table and the SQL used to create the table

      • android_metadata is a table generated via the SQLiteOpenHelper class and contains the locale

    Also included was the dump of the Cursor generated by your Query as per :-

    I/System.out: >>>>> Dumping cursor android.database.sqlite.SQLiteCursor@22a7d59
    I/System.out: 0 {
    I/System.out:    code=1
    I/System.out:    itm=Item1
    I/System.out:    qty=1
    I/System.out:    tax=X
    I/System.out:    prc=100
    I/System.out:    tp=100
    I/System.out:    slr=Seller1
    I/System.out: }
    I/System.out: <<<<<
    

    Using Database Inspector (now App Inspection) further confirms that all is as expected :-

    enter image description here

    Last placing a breaking point on the line cursor.close(); allows inspection of the populated arrays from the debug window as e.g. :-

    enter image description here

    • Note that the size of the arrays is 2 rather than 1 as the above was run a second time and a second row (the same data as the first BUT the code column was auto generated due to it being defined using INTEGER PRIMARY KEY in conjunction with no value being supplied)

    As such you original issue has been resolved, probably by uninstalling and re-installing the App as the table had probably been changed.


    Ongoing Issues

    If you are having ongoing issues (the ListView showing nothing) then that should be another question and if so it will very much depend upon the SQLiteListAdapter class.


    Login or Signup to reply.
  2. Additional

    Here’s a work example/demo with a ListView more along the lines of how I would do what you are doing.

    Instead of trying to convert a cursor into multiple arrays and then use a ListAdapter, instead it uses a CursorAdpater (SimpleCursorAdapater). Thes are designed to handle data in Cursors and are therefore simpler.

    HOWEVER, a Cursor adapter requires a column named _id, so the code column name has been changed accordingly (it could remain as is and an alias extracted as _id).

    Code that access the database e.g. the query to get the cursor has been moved to the Helper.

    The demo only inserts a single row, but does include an onItemClickListener that gets the clicked row from the database (you wouldn’t do this normally but it shows how simple passing a single value the id can be used in another activity).

    To start with a layout to allow all the relevant data (from the user perspective) so demotableb_layout :-

    <?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:orientation="horizontal"
        android:layout_width="match_parent"
        android:layout_height="wrap_content">
        <TextView
            android:id="@+id/item"
            android:layout_width="0dp"
            android:layout_weight="30"
            android:layout_height="match_parent">
        </TextView>
        <TextView
            android:id="@+id/quantity"
            android:layout_width="0dp"
            android:layout_weight="10"
            android:layout_height="match_parent">
        </TextView>
        <TextView
            android:id="@+id/tax"
            android:layout_width="0dp"
            android:layout_weight="10"
            android:layout_height="match_parent">
        </TextView>
        <TextView
            android:id="@+id/unitprice"
            android:layout_width="0dp"
            android:layout_weight="10"
            android:layout_height="match_parent">
        </TextView>
        <TextView
            android:id="@+id/totalprice"
            android:layout_width="0dp"
            android:layout_weight="10"
            android:layout_height="match_parent">
        </TextView>
        <TextView
            android:id="@+id/seller"
            android:layout_width="0dp"
            android:layout_weight="10"
            android:layout_height="match_parent">
        </TextView>
    </LinearLayout>
    
    • this could obviously be more complex and if you have such a layout then that could be used with a few changes to the code (view id’s in the adapter setup)

    The database helper SuggestedSQLiteHelper :-

    class SuggestedSQLiteHelper extends SQLiteOpenHelper {
        static String DATABASE_NAME="DemoDataBaseb";
        public static final String TABLE_NAME="demoTableb";
        /* column name constant names changed to upper case and more descriptive */
        public static final String CODES_COLUMN = BaseColumns._ID; //<<<<<<<<<< renamed for Cursor Adapter
        public static final String ITEM_COLUMN ="itm";
        public static final String QUANTITY_COLUMN ="qty";
        public static final String TAX_COLUMN="tax";
        public static final String UNITPRICE_COLUMN ="prc";
        public static final String TOTALPRICE_COLUMN ="tp";
        public static final String SELLER_COLUMN ="slr";
    
        private SQLiteDatabase db; //<<<<<<<<<< Added
    
        public SuggestedSQLiteHelper(Context context) {
            super(context, DATABASE_NAME, null, 1);
            db = this.getWritableDatabase(); //<<<<<<<<<< ADDED to instantiate db
        }
    
        @Override
        public void onCreate(SQLiteDatabase database) {
            String CREATE_TABLE="CREATE TABLE IF NOT EXISTS "+TABLE_NAME+" " +
                    "("+
                    CODES_COLUMN +" INTEGER PRIMARY KEY, "+
                    ITEM_COLUMN +" VARCHAR, "+
                    QUANTITY_COLUMN +" INTEGER, "+
                    TAX_COLUMN+" INTEGER,"+
                    UNITPRICE_COLUMN +" INTEGER,"+
                    TOTALPRICE_COLUMN +" INTEGER,"+
                    SELLER_COLUMN +" VARCHAR )";
            database.execSQL(CREATE_TABLE);
        }
    
        @Override
        public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
            db.execSQL("DROP TABLE IF EXISTS "+TABLE_NAME);
            onCreate(db);
        }
    
        public long insertDemoTablebRow(String item, int quantity, int tax, int unitPrice, int totalPrice, String seller) {
            ContentValues cv = new ContentValues();
            cv.put(ITEM_COLUMN,item);
            cv.put(QUANTITY_COLUMN,quantity);
            cv.put(TAX_COLUMN,tax);
            cv.put(UNITPRICE_COLUMN,unitPrice);
            cv.put(TOTALPRICE_COLUMN,totalPrice);
            cv.put(SELLER_COLUMN,seller);
            return db.insert(TABLE_NAME,null,cv);
        }
    
        public boolean isTableEmpty(String tableName) {
            return DatabaseUtils.queryNumEntries(db,TABLE_NAME) < 1;
        }
    
        public Cursor getAllFromDemoTableb() {
            return db.query(TABLE_NAME, null,null,null,null,null,null);
        }
    
        public Cursor getDemotablebById(long code) {
            return db.query(TABLE_NAME,null,CODES_COLUMN+"=?",new String[]{String.valueOf(code)},null,null,null);
        }
    }
    
    • Note that the convenience methods insert and query have been used, these write the underlying SQL for you. They also bind data thus protecting against SQL injection.

    • Please take note of the comments

    Last putting it all together in an activity (the equivalent of your ListViewActivity) is MainActivity :-

    public class MainActivity extends AppCompatActivity {
    
        SuggestedSQLiteHelper dbHelper;
        Cursor cursor;
        SimpleCursorAdapter sca;
        ListView listview1;
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
            dbHelper = new SuggestedSQLiteHelper(this);
            listview1 = this.findViewById(R.id.listview1);
            if (dbHelper.isTableEmpty(SuggestedSQLiteHelper.TABLE_NAME)) {
                dbHelper.insertDemoTablebRow("Item1",1,5,100,100,"Fred");
            }
            setOrRefreshListView();
        }
    
        private void setOrRefreshListView() {
            cursor = dbHelper.getAllFromDemoTableb();
            if (sca == null) {
                // setup the adapter
                // NOTE CURSOR ADAPTERS MUST HAVE _ID column which MUST be type INTEGER and UNIQUE
                // see use of BaseColumns._ID in table create
                sca = new SimpleCursorAdapter(this,R.layout.demotableb_list,cursor,
                        // The columns FROM which the data is to be retrieved
                        new String[]{
                                SuggestedSQLiteHelper.ITEM_COLUMN,
                                SuggestedSQLiteHelper.QUANTITY_COLUMN,
                                SuggestedSQLiteHelper.TAX_COLUMN,
                                SuggestedSQLiteHelper.UNITPRICE_COLUMN,
                                SuggestedSQLiteHelper.TOTALPRICE_COLUMN,
                                SuggestedSQLiteHelper.SELLER_COLUMN
                        },
                        // The id of the view's to display the data as per the layout (2nd parm)
                        new int[]{
                                R.id.item,
                                R.id.quantity,
                                R.id.tax,
                                R.id.unitprice,
                                R.id.totalprice,
                                R.id.seller
                        },0 // 0 is fine
                );
                listview1.setAdapter(sca); // Tie the adapter to the ListView
                // Can add the Listeners here e.g.
                listview1.setOnItemClickListener(new AdapterView.OnItemClickListener() {
                    @Override
                    public void onItemClick(AdapterView<?> adapterView, View view, int i, long l) {
                        // DO SOMETHING HERE NOTING
                        // long l passed (4th parm) is the _id of the clicked item
                        // hence l can be passed/used as it uniquely identifies the row
                        // e.g.
                        Cursor csr = dbHelper.getDemotablebById(l);
                        DatabaseUtils.dumpCursor(csr);
                        csr.close();
                    }
                });
            } else {
                sca.swapCursor(cursor);
            }
        }
    
        @Override
        protected void onResume() {
            super.onResume();
            setOrRefreshListView(); //<<<<<<<<<< will refresh the listview in case data has changed
        }
    
        @Override
        protected void onDestroy() {
            cursor.close(); //<<<<<<<<< should always close the cursor when done with it
            super.onDestroy();
        }
    }
    

    Result

    The demo when run :-

    enter image description here

    Clicking on an item (only the one in the above) and the log includes:-

    I/System.out: >>>>> Dumping cursor android.database.sqlite.SQLiteCursor@1e2064
    I/System.out: 0 {
    I/System.out:    _id=1
    I/System.out:    itm=Item1
    I/System.out:    qty=1
    I/System.out:    tax=5
    I/System.out:    prc=100
    I/System.out:    tp=100
    I/System.out:    slr=Fred
    I/System.out: }
    I/System.out: <<<<<
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search