I spend much time on SQLite and I have a problem in deleting an item if it exist!
I'm working in Bookmark App that save links from webview into listview using SQLite, my problem is can't check if the item is exist > don't create a link.
this is my BookmarksDatabase used for sqlite:
public class BookmarksDatabase extends SQLiteOpenHelper {
private static final String DATABASE_NAME = "bookmarks.db";
private static final String TABLE_NAME = "bookmarks_data";
private static final String COL1 = "ID";
private static final String COL2 = "ITEM1";
private static final String COL3 = "ITEM2";
public BookmarksDatabase(Context context) {
super(context, DATABASE_NAME, null, 1);
}
#Override
public void onCreate(SQLiteDatabase db) {
String createTable = "CREATE TABLE " + TABLE_NAME + " (ID INTEGER PRIMARY KEY AUTOINCREMENT, " + " ITEM1 TEXT, " + " ITEM2 TEXT)";
db.execSQL(createTable);
}
#Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
db.execSQL("DROP TABLE IF EXISTS " + TABLE_NAME);
onCreate(db);
}
public boolean addData(String item1, String item2) {
SQLiteDatabase db = this.getWritableDatabase();
ContentValues contentValues = new ContentValues();
contentValues.put(COL2, item1);
contentValues.put(COL3, item2);
long result = db.insert(TABLE_NAME, null, contentValues);
// if date as inserted incorrectly it will return -1
return result != -1;
}
public Cursor getListContents() {
SQLiteDatabase db = this.getWritableDatabase();
return db.rawQuery("SELECT * FROM " + TABLE_NAME, null);
}
public ArrayList<Bookmarks> getAllData() {
ArrayList<Bookmarks> arrayList = new ArrayList<>();
SQLiteDatabase db = this.getWritableDatabase();
Cursor data = db.rawQuery("SELECT * FROM " + TABLE_NAME, null);
while (data.moveToNext()) {
int id = data.getInt(0);
String title = data.getString(1);
String link = data.getString(2);
Bookmarks bookmarks = new Bookmarks(id, title, link);
arrayList.add(bookmarks);
}
return arrayList;
}
public int deleteSpecificContents(int id) {
SQLiteDatabase db = this.getWritableDatabase();
return db.delete(TABLE_NAME, COL1 + "=?", new String[]{Integer.toString(id)});
}
}
this is my code used in MainActivity to fetch items on listview
/*---------------- Bookmark Tab, sqlite databases integrated ---------------*/
private void showBookmarksScreen() {
// initialize a dialog in the main activity
final Dialog bookmarksScreen = new Dialog(this);
bookmarksScreen.requestWindowFeature(Window.FEATURE_NO_TITLE);
bookmarksScreen.setContentView(R.layout.activity_bookmark);
bookmarksScreen.setCancelable(true);
final ListView listView = bookmarksScreen.findViewById(R.id.bookmark_list);
RelativeLayout bookmarkEmpty = bookmarksScreen.findViewById(R.id.bookmark_empty);
// create an array and call bookmark
// database to retrive data then
// fetch it into list view
arrayList = new ArrayList<>();
arrayList = bookmarkDB.getAllData();
// get all data from sqlite database
Cursor data = bookmarkDB.getListContents();
// check if no bookmarks
// then show view that inform
// user that there is no bookmarks
if(data.getCount() == 0 ) {
bookmarkEmpty.setVisibility(View.VISIBLE);
}
bookmarkListAdpater = new BookmarkListAdpater(this, arrayList);
listView.setAdapter(bookmarkListAdpater);
bookmarkListAdpater.notifyDataSetChanged();
// load link on item click
listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
TextView link = view.findViewById(R.id.list_link);
String convertedLink = link.getText().toString();
webView.loadUrl(convertedLink);
bookmarksScreen.dismiss();
}
});
// ask user to delete bookmark on item long click
listView.setOnItemLongClickListener(new AdapterView.OnItemLongClickListener() {
#Override
public boolean onItemLongClick(AdapterView<?> parent, View view, final int position, long id) {
// initialize a dialog in the main activity
final Dialog deleteDialog = new Dialog(MainActivity.this);
deleteDialog.requestWindowFeature(Window.FEATURE_NO_TITLE);
deleteDialog.setContentView(R.layout.activity_confirm);
// confirm message or dialog can't be
// canceled so we set it to false
deleteDialog.setCancelable(false);
TextView deleteMessage = deleteDialog.findViewById(R.id.confirm_text);
TextView deleteConfirm = deleteDialog.findViewById(R.id.confirm_allow);
TextView deleteCancel = deleteDialog.findViewById(R.id.confirm_deny);
deleteMessage.setText(getString(R.string.delete_bookmark));
// confirm button
deleteConfirm.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
Cursor data = bookmarkDB.getListContents();
int i = 0;
while(data.moveToNext()){
if(i == position){
break;
}
i++;
}
bookmarkDB.deleteSpecificContents(data.getInt(0));
deleteDialog.dismiss();
bookmarksScreen.dismiss();
customToast(getString(R.string.bookmark_deleted), 0);
}
});
// confirm cancel
deleteCancel.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
deleteDialog.dismiss();
}
});
deleteDialog.getWindow().setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT));
deleteDialog.show();
return true;
}
});
bookmarksScreen.getWindow().setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT));
bookmarksScreen.getWindow().setLayout(WindowManager.LayoutParams.MATCH_PARENT, WindowManager.LayoutParams.MATCH_PARENT);
bookmarksScreen.show();
}
My Model
public class Bookmarks {
int id;
String title, link;
public Bookmarks(int id, String title, String link) {
this.id = id;
this.title = title;
this.link = link;
}
public Bookmarks() {}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getLink() {
return link;
}
public void setLink(String link) {
this.link = link;
}
}
any ideas? thanks.
Try using below to delete item from DB
bookmarkDB.deleteSpecificContents(arrayList.get(position).getId(0));
If you want to check item exists or not before adding then add below code in your BookmarksDatabase
public boolean isExists(String link) {
SQLiteDatabase db = this.getWritableDatabase();
Cursor cursor = db.rawQuery("SELECT * FROM " + TABLE_NAME + " WHERE " + COL3 + "='" + link + "'", null);
return cursor.getCount() > 0;
}
And then check
if(bookmarkDB.isExists(link))
//Already Exist
else
//Not Exist, add now
With the same logic you're using:
SQLiteDatabase db = new DatabaseManager(context).getWritableDatabase();
String query = "SELECT * FROM " + TABLE_NAME + " WHERE " + ID_KEY + " = ?";
Cursor cursor = db.rawQuery(query, new String[]{Integer.toString(id)});
if(cursor.moveToFirst()){
db.delete(TABLE_NAME, ID_KEY + " = ?", new String[]{Integer.toString(id)});
}
cursor.close();
db.close();
Another possibility is changing the method return type to boolean and verifying the return count from the delete command:
public boolean deleteSpecificContents(int id) {
SQLiteDatabase db = this.getWritableDatabase();
return db.delete(TABLE_NAME, COL1 + "=?", new String[]{Integer.toString(id)}) > 0;
}
Related
I am new to Android Studio and I am trying to create an Inventory App that allows users to create their own inventory items. I am using SQlite database to do this. I've created my DBHelper class and Item class that stores results.
However, I am unsure how to continue this in my DisplayInventory class (MainActivity) I've written in some FIXME comments to help show where I am talking about.
DisplayInventory class
// TESTING SQLite CODE HERE
public void insertItem(int position) {
//FIXME: This is where I need to ADD items to the database
// inventoryDB.addItem();
mInventoryItemList.add(position, new InventoryItem(R.drawable.ic_delete, "Tap to Edit", "Items: ", (android.widget.Button) Button, (android.widget.Button) Button));
mAdapter.notifyItemInserted(position);
}
public void removeItem(int position) {
// FIXME: This is where I DELETE items from database
// inventoryDB.deleteItem(); <== This method needs to be written in InventoryDBHelper class
mInventoryItemList.remove(position);
mAdapter.notifyItemRemoved(position);
}
public void createExampleList() {
mInventoryItemList = new ArrayList<>();
// get all items from the database
Item[] items = inventoryDB.getAllItems();
// loop through all items to build the array list
for (int i = 0; i < items.length; ++i){
// FIXME: this is where I need to build my ArrayList based on the contents of the DB
// for new users this will be empty. However, as they add items then the database
// will be populated and this will return data the next time.
}
}
//TESTING CODE ENDS HERE
InventoryDBHelper
public class InventoryDBHelper extends SQLiteOpenHelper {
private Context context;
private static final String DATABASE_NAME = "InventoryList.db";
private static final int DATABASE_VERSION = 1;
private static final String TABLE_NAME = "my_inventory";
private static final String COLUMN_ID = "_id";
private static final String COLUMN_TITLE = "item_name";
private static final String COLUMN_OWNER = "item_owner";
private static final String COLUMN_ITEMNUMBER = "number_items";
public InventoryDBHelper(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
this.context = context;
}
#Override
public void onCreate(SQLiteDatabase sqLiteDatabase) {
String query = "CREATE TABLE " + TABLE_NAME +
" (" + COLUMN_ID + " INTEGER PRIMARY KEY AUTOINCREMENT," +
COLUMN_TITLE + " TEXT, " +
COLUMN_OWNER + " TEXT, " +
COLUMN_ITEMNUMBER + " INTEGER);";
sqLiteDatabase.execSQL(query);
}
#Override
public void onUpgrade(SQLiteDatabase sqLiteDatabase, int i, int i1) {
sqLiteDatabase.execSQL("DROP TABLE IF EXISTS " + TABLE_NAME);
onCreate(sqLiteDatabase);
}
void addItem(String title, String owner, int numItem) {
SQLiteDatabase db = this.getWritableDatabase();
ContentValues cv = new ContentValues();
cv.put(COLUMN_TITLE, title);
cv.put(COLUMN_OWNER, owner);
cv.put(COLUMN_ITEMNUMBER, numItem);
long result = db.insert(TABLE_NAME, null, cv);
if(result == -1) {
Toast.makeText(context, "FAILED", Toast.LENGTH_SHORT).show();
}
else {
Toast.makeText(context, "Added Successful", Toast.LENGTH_SHORT).show();
}
}
public Item[] getAllItems(){
// list of items to return
Item[] returnItems;
// initialize a readable database connection
SQLiteDatabase db = this.getReadableDatabase();
String query = "SELECT " +
COLUMN_ID + "," +
COLUMN_TITLE + "," +
COLUMN_OWNER + "," +
COLUMN_ITEMNUMBER +
" FROM " + TABLE_NAME + ";";
Cursor cursor = db.rawQuery(query, null);
returnItems = unpackRecordData(cursor);
cursor.close();
return returnItems;
}
private Item[] unpackRecordData(Cursor cursor){
Item[] items = new Item[cursor.getCount()];
int i = 0;
while (cursor.moveToNext()){
Item item = new Item(
// Item.id
cursor.getInt(
cursor.getColumnIndexOrThrow(COLUMN_ID)
),
// Item.title
cursor.getString(
cursor.getColumnIndexOrThrow(COLUMN_TITLE)
),
// Item.owner
cursor.getString(
cursor.getColumnIndexOrThrow(COLUMN_OWNER)
),
// Item.itemNumber
cursor.getInt(
cursor.getColumnIndexOrThrow(COLUMN_ITEMNUMBER)
)
);
// add Item to the list of items
items[i] = item;
}
return items;
}
}
Item Class
public class Item {
// Item Database columns to properties
private int id;
private String title;
private String owner;
private int itemNumber;
// class constructor
public Item(int id, String title, String owner, int itemNumber){
this.id = id;
this.title = title;
this.owner = owner;
this.itemNumber = itemNumber;
}
// getters and setters
public void setId(int id){
this.id = id;
}
public int getId(){
return this.id;
}
public void setTitle(String title){
this.title = title;
}
public String getTitle(){
return this.title;
}
public void setOwner(String owner){
this.owner = owner;
}
public String getOwner(){
return this.owner;
}
public void setItemNumber(int itemNumber){
this.itemNumber = itemNumber;
}
public int getItemNumber(){
return this.itemNumber;
}
}
Here's an example that shows all three types of actions being undertake. It's based upon your code and has some comments to explain suggested changes, additions (commented out) and removal of code.
First InventoryDBHelper
public class InventoryDBHelper extends SQLiteOpenHelper {
private Context context;
private static final String DATABASE_NAME = "InventoryList.db";
private static final int DATABASE_VERSION = 1;
private SQLiteDatabase db; //<<<<<<<< ADDED
/*
CHANGED to public (can be useful)
*/
public static final String TABLE_NAME = "my_inventory";
public static final String COLUMN_ID = "_id";
public static final String COLUMN_TITLE = "item_name";
public static final String COLUMN_OWNER = "item_owner";
public static final String COLUMN_ITEMNUMBER = "number_items";
private static volatile InventoryDBHelper instance;
private InventoryDBHelper(Context context) { //<<<<<<<<<< CHANGED TO PRIVATE
super(context, DATABASE_NAME, null, DATABASE_VERSION);
db = this.getWritableDatabase(); // Instantiates db variable that has full scope
this.context = context;
}
/*
ADDED so a singleton is used
*/
public static InventoryDBHelper getInstance(Context context) {
if (instance == null) {
instance = new InventoryDBHelper(context);
}
return instance;
}
#Override
public void onCreate(SQLiteDatabase sqLiteDatabase) {
String query = "CREATE TABLE " + TABLE_NAME +
" (" + COLUMN_ID + " INTEGER PRIMARY KEY," + //" INTEGER PRIMARY KEY AUTOINCREMENT," <<<<<<<<<< NO NEED FOR AUTOINCREMENT (has overheads)
COLUMN_TITLE + " TEXT, " +
COLUMN_OWNER + " TEXT, " +
COLUMN_ITEMNUMBER + " INTEGER);";
sqLiteDatabase.execSQL(query);
}
#Override
public void onUpgrade(SQLiteDatabase sqLiteDatabase, int i, int i1) {
sqLiteDatabase.execSQL("DROP TABLE IF EXISTS " + TABLE_NAME);
onCreate(sqLiteDatabase);
}
long addItem(String title, String owner, int numItem) { //<<<<<<<<<< CHANGED so result can be returned
// SQLiteDatabase db = this.getWritableDatabase(); //<<<<<<<<<< NOT NEEDED with db as class variable
ContentValues cv = new ContentValues();
cv.put(COLUMN_TITLE, title);
cv.put(COLUMN_OWNER, owner);
cv.put(COLUMN_ITEMNUMBER, numItem);
long result = db.insert(TABLE_NAME, null, cv);
if(result == -1) {
Toast.makeText(context, "FAILED", Toast.LENGTH_SHORT).show();
}
else {
Toast.makeText(context, "Added Successful", Toast.LENGTH_SHORT).show();
}
return result; //<<<<<<<< ADDED might as well return the result
}
/*
ADDED so you can add from a passed item
*/
long addItem(Item item) {
return addItem(item.getTitle(),item.getOwner(),item.getItemNumber());
}
public Item[] getAllItems(){
// list of items to return
Item[] returnItems;
// initialize a readable database connection
//SQLiteDatabase db = this.getReadableDatabase(); //<<<<<<<<<< NOT NEEDED HERE
// PS getReadable gets a writeable database in most situations
/* NOT NEEDED HERE
String query = "SELECT " +
COLUMN_ID + "," +
COLUMN_TITLE + "," +
COLUMN_OWNER + "," +
COLUMN_ITEMNUMBER +
" FROM " + TABLE_NAME + ";";
*/
// ADDED use the convienence query method equivalent to SELECT * FROM my_inventory (SQL is built for you)
Cursor cursor = db.query(TABLE_NAME,null,null,null,null,null,null);
//Cursor cursor = db.rawQuery(query, null);
returnItems = unpackRecordData(cursor);
cursor.close();
return returnItems;
}
/*
ADDED to remove an item from
*/
long removeItem(long itemId) {
return db.delete(TABLE_NAME,COLUMN_ID+"=?",new String[]{String.valueOf(itemId)});
}
/*
ADDED to allow removal of an Item via Item object
*/
long removeItem(Item item) {
return removeItem(item.getId());
}
private Item[] unpackRecordData(Cursor cursor){
Item[] items = new Item[cursor.getCount()];
int i = 0;
while (cursor.moveToNext()){
Item item = new Item(
// Item.id
cursor.getInt(
cursor.getColumnIndexOrThrow(COLUMN_ID)
),
// Item.title
cursor.getString(
cursor.getColumnIndexOrThrow(COLUMN_TITLE)
),
// Item.owner
cursor.getString(
cursor.getColumnIndexOrThrow(COLUMN_OWNER)
),
// Item.itemNumber
cursor.getInt(
cursor.getColumnIndexOrThrow(COLUMN_ITEMNUMBER)
)
);
// add Item to the list of items
items[i++] = item; //ERROR FIXED was i so i was always 0 not 0 1 2 etc
}
return items;
}
}
see AUTOINCREMENT for further reason why not to use AUTOINCREMENT
Item has not been changed (although I would suggest using long instead of int for id)
SQLite rowid (your id columns is an alias of rowid) can be 64-bit signed integer (too large for int).
The examples of Adding, Extracting and Removal of Items from the Database is as per :-
public class MainActivity extends AppCompatActivity {
InventoryDBHelper inventoryDBHelper; //<<<<<<<<< Want to use the Database in this activity
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
inventoryDBHelper = InventoryDBHelper.getInstance(this); // Gets an instance of the Database
//EXAMPLE Examples of Adding Items
inventoryDBHelper.addItem("MyItem","Fred",1);
inventoryDBHelper.addItem(new Item(-1000 /* irrelevant when adding*/,"Another Item","Mary",2));
//EXAMPLE Get a list of all Items
Item[] items = inventoryDBHelper.getAllItems();
//EXAMPLE Remove all Items
for(Item i: items) {
Log.d("INVENTRYINFO","Attempting to remove Item " + i.getTitle());
if (inventoryDBHelper.removeItem(i) > 0) {
Toast.makeText(this,"Item " + i.getTitle() + " deleted",Toast.LENGTH_LONG).show();
} else {
Toast.makeText(this,"Item " + i.getTitle() + " NOT DELETED",Toast.LENGTH_LONG).show();
}
// could use inventoryDBHelper.removeItem(i.getId()); //instead
}
}
}
You just need to adapt this for your needs.
The above is a working example (designed to be run once) it Adds 2 Items, Extracts them as an array of Items and then uses that list to Remove them all.
With a breakpoint at the for each loop that removes the items the following can be seen :-
i.e. the 2 Items have been added and extracted
After the proceeding (after the items have all been removed) then the Log contains :-
D/INVENTRYINFO: Attempting to remove Item MyItem
D/INVENTRYINFO: Attempting to remove Item Another Item
I know there has been a lot of these questions, but unfortunately none of these helps me with my problem.
With a button click i want to add some new content to my database,
or the existing columns should be overwritten. Adding the content to my database works fine. But if i want to overwrite the existing content, my code just adds a new row to the database.
This is my Code:
Main Activity: Add Content With Button To BD
btnAdd = (Button) findViewById(R.id.btnAdd);
btnAdd .setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
ListView shopList= (ListView) findViewById(R.id.lvShopList);
for(int i = 0; i < dataSource.size();i++){
tvname = (TextView) shoppingList.getChildAt(i).findViewById(R.id.tvName);
tvamount= (TextView) shoppingList.getChildAt(i).findViewById(R.id.tvAmount);
String nameTV = tvname.getText().toString();
String amaountTV = tvamount.getText().toString();
ingredient.setName(nameTV);
ingredient.setAmpunt(amaountTV );
myDB.getInstance(MainActivity.this).increaseIngredient(ingredient);
}
}
});
This Is My DB Class
public Ingredient increaseIngredient(final Ingredient ingredient){
SQLiteDatabase db = this.getWritableDatabase();
ContentValues values = new ContentValues();
values.put(COL_NAME, ingredient.getName());
values.put(COL_AMOUNT, ingredient.getAmount());
long newID = db.insert(TABLE_NAME, null, values);
db.close();
return getiIngredient(newID);
//Also tried this code, but with this, nothing will be shown:
// db.update(TABLE_NAME, values, KEY_ID + " = ?", new String[]{String.valueOf(ingredient.getId())});
// db.close();
// return getiIngredient(ingredient.getId());
}
public Ingredient getIngredient(final long id){
SQLiteDatabase db = this.getWritableDatabase();
Cursor c = db.query
(TABLE_NAME, new String[]{KEY_ID, COL_NAME, COL_AMOUNT},
KEY_ID + " = ?",
new String[]{String.valueOf(id)},
null, null, null);
Ingredient ingredient = null;
if(c != null && c.getCount() > 0) {
c.moveToFirst();
ingredient = new Ingredient(c.getString(c.getColumnIndex(COL_NAME)));
ingredient.setId(c.getLong(c.getColumnIndex(KEY_ID)));
ingredient.setAmount(c.getString(c.getColumnIndex(COL_AMOUNT)));
}
db.close();
return ingredient;
}
This Is My Model Class
public class Ingredient implements Serializable {
private long id;
private String name;
private String amount;
public Zutaten() {
this(null, null);
}
public Zutaten(String name) {
this(name, null);
}
public Zutaten(String name, String amount) {
this.name = name;
this.amount= amount;
}
public long getId() {
return id;
}
public void setId(long id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getAmount() {
return amount;
}
public void setAmount(String amount) {
this.amount= amount;
}
}
EDIT: This is my activity where i want to show the DB Content:
public class StorageDB extends AppCompatActivity {
myDB dbIngredients;
ListView lvDB;
TextView name, amount;
ArrayList<Ingredients> dataSource;
DbStorageAdapter adapter;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_ingredient_storage);
lvDB= (ListView) findViewById(R.id.lvDB);
dataSource = dbIngredients.getInstance(this).getAllIngredient();
this.adapter = new DbStorageAdapter (dataSource, this);
lvDB.setAdapter(adapter);
name = (TextView)findViewById(R.id.tvName);
amount= (TextView)findViewById(R.id.tvAmount);
showDBcontent();
}
private void showDBcontent(){
myDB db = new myDB (this);
ArrayList<Ingredients> iList = db.getAllIngredient();
adapter = new DbStorageAdapter (zList, this);
lvDB.setAdapter(adapter);
}
}
So if i use update, the listview in my storage activity is empty, and if i use insert all the rows from the database will be shown.
With the first click i add 8 rows to the database. If i use db.insert and click on the button i have 16 rows in my database, and all 16 rows will be shown in the storage activity.
SECOND EDIT:
In fact I just want that my code checks after button click if the table exists. If it exists i want that it will update my table rows. If the table does not exist I want that it insert my content which is send by button click.
I tried this, but it does not work:
public Ingredient increaseIngredient (final Ingredient ingredient ){
SQLiteDatabase db = this.getWritableDatabase();
Cursor c = db.rawQuery
("SELECT * FROM " + TABLE_NAME + " WHERE " + COL_NAME + " = ?",
null);
ContentValues values = new ContentValues();
values.put(COL_NAME, ingredient .getName());
values.put(COL_AMOUNT, ingredient .getAmount());
if(c !=null && c.getCount() > 0){
db.update(TABLE_NAME, values, KEY_ID + " = ?", new String[]{String.valueOf(zutaten.getId())});
db.close();
return getZutat(zutaten.getId());
} else {
long newID = db.insert(TABLE_NAME, null, values);
db.close();
return getZutat(newID);
}
This:
db.update(TABLE_NAME, values, KEY_ID + " = ?", new String[]{String.valueOf(ingredient.getId())});
would update the row with id = ingredient.getId() if this id exists in the table.
When you call:
myDB.getInstance(MainActivity.this).increaseIngredient(ingredient);
the ingredient object does not contain the id that you want to update.
If you do something like this:
ingredient.setId(10);
prior to calling increaseIngredient() then if there exists a row with id = 10, then this row will be updated.
Edit from comments:
I mean something like this:
public Ingredient increaseIngredient (Ingredient ingredient) {
SQLiteDatabase db = this.getWritableDatabase();
ContentValues values = new ContentValues();
values.put(COL_NAME, ingredient.getName());
values.put(COL_AMOUNT, ingredient.getAmount());
if (ingredient.getId() == null) {
long newID = db.insert(TABLE_NAME, null, values);
db.close();
return ???;
} else {
db.update(TABLE_NAME, values, KEY_ID + " = ?", new String[]{String.valueOf(ingredient.getId())});
db.close();
return ???;
}
}
The question marks mean I don't know what you need to return.
I am developing an app for listing details in database. The listing is not working. but it is showing in log as fine. Why my recyclerview listling is not working. when i am using bean1 = new Bean(cn.getName(), cn.getNumber(), cn.getSpeeddial()) it shows error.
My codes are shown below.
SpeedDialViewActivity.java
public class SpeedDialViewActivity extends AppCompatActivity {
private List<Bean> beanList = new ArrayList<>();
private RecyclerView recyclerView;
private ViewAdapter mAdapter;
Context context;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_speed_dial_view);
recyclerView = (RecyclerView) findViewById(R.id.recycler_view);
mAdapter = new ViewAdapter(beanList);
RecyclerView.LayoutManager mLayoutManager = new LinearLayoutManager(getApplicationContext());
recyclerView.setLayoutManager(mLayoutManager);
recyclerView.setItemAnimator(new DefaultItemAnimator());
recyclerView.setAdapter(mAdapter);
prepareData();
}
private void prepareData() {
DatabaseHandler handler = new DatabaseHandler(getApplicationContext());
Log.d("Reading: ", "Reading all contacts..");
List<Bean> beanList = handler.getAllContacts();
//Cursor cursor = (Cursor) handler.getAllContacts();
//Bean bean1;
for (Bean cn : beanList) {
String log = "Id: " + cn.getId() + " ,Name: " + cn.getName() + " ,Phone: " + cn.getNumber();
// Writing Contacts to log
Log.d("Name: ", log);
// bean1 = new Bean(cn.getName(), cn.getNumber(), cn.getSpeeddial()); // Error occurring
// beanList.add(bean1);
}
}
}
DatabaseHandler.java
public class DatabaseHandler extends SQLiteOpenHelper {
private static final int DATABASE_VERSION = 1;
private static final String DATABASE_NAME = "speeddial";
private static final String TABLE_CONTACTS = "contacts";
private static final String KEY_ID = "id";
private static final String KEY_NAME = "name";
private static final String KEY_PH_NO = "phone_number";
private static final String KEY_SPEED_DIAL = "speed_dial_number";
public DatabaseHandler(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
#Override
public void onCreate(SQLiteDatabase db) {
String CREATE_CONTACTS_TABLE = "CREATE TABLE " + TABLE_CONTACTS + "("
+ KEY_ID + " INTEGER PRIMARY KEY," + KEY_NAME + " TEXT,"
+ KEY_PH_NO + " TEXT" + KEY_SPEED_DIAL + " TEXT" + ")";
db.execSQL(CREATE_CONTACTS_TABLE);
}
#Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
// Drop older table if existed
db.execSQL("DROP TABLE IF EXISTS " + TABLE_CONTACTS);
// Create tables again
onCreate(db);
}
void addContact(Bean bean) {
SQLiteDatabase db = this.getWritableDatabase();
ContentValues values = new ContentValues();
values.put(KEY_NAME, bean.getName()); // Contact Name
values.put(KEY_PH_NO, bean.getNumber()); // Contact Phone
values.put(KEY_PH_NO, bean.getSpeeddial()); // Contact Phone
// Inserting Row
db.insert(TABLE_CONTACTS, null, values);
db.close(); // Closing database connection
}
Bean getBean(int id) {
SQLiteDatabase db = this.getReadableDatabase();
Cursor cursor = db.query(TABLE_CONTACTS, new String[] { KEY_ID,
KEY_NAME, KEY_PH_NO }, KEY_ID + "=?",
new String[] { String.valueOf(id) }, null, null, null, null);
if (cursor != null)
cursor.moveToFirst();
Bean bean = new Bean(Integer.parseInt(cursor.getString(0)),cursor.getString(1), cursor.getString(2), cursor.getString(3));
// return contact
return bean;
}
public List<Bean> getAllContacts() {
List<Bean> contactList = new ArrayList<Bean>();
// Select All Query
String selectQuery = "SELECT * FROM " + TABLE_CONTACTS;
SQLiteDatabase db = this.getWritableDatabase();
Cursor cursor = db.rawQuery(selectQuery, null);
// looping through all rows and adding to list
if (cursor.moveToFirst()) {
do {
Bean contact = new Bean();
contact.setId(Integer.parseInt(cursor.getString(0)));
contact.setName(cursor.getString(1));
contact.setNumber(cursor.getString(2));
// Adding contact to list
contactList.add(contact);
} while (cursor.moveToNext());
}
// return contact list
return contactList;
}
}
ViewAdapter.java
public class ViewAdapter extends RecyclerView.Adapter<ViewAdapter.MyViewHolder> {
private List<Bean> beanList;
public class MyViewHolder extends RecyclerView.ViewHolder {
public TextView name, number, speeddial_number;
public MyViewHolder(View view) {
super(view);
name = (TextView) view.findViewById(R.id.name);
number = (TextView) view.findViewById(R.id.number);
speeddial_number = (TextView) view.findViewById(R.id.speeddialNumber);
}
}
public ViewAdapter(List<Bean> beanList){
this.beanList = beanList;
}
#Override
public ViewAdapter.MyViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
View itemView = LayoutInflater.from(parent.getContext()).inflate(R.layout.speeddial_list_row, parent, false);
return new MyViewHolder(itemView);
}
#Override
public void onBindViewHolder(ViewAdapter.MyViewHolder holder, int position) {
Bean bean = beanList.get(position);
holder.name.setText(bean.getName());
holder.number.setText(bean.getNumber());
holder.speeddial_number.setText(bean.getSpeeddial());
}
#Override
public int getItemCount() {
return beanList.size();
}
}
Bean.java
public class Bean{
private int id;
private String name;
private String number;
private String speeddial;
public Bean(int id, String name, String number, String speeddial) {
this.id=id;
this.name=name;
this.number=number;
this.speeddial=speeddial;
}
public Bean(String name, String number, String speeddial) {
this.name=name;
this.number=number;
this.speeddial=speeddial;
}
public Bean() {
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getNumber() {
return number;
}
public void setNumber(String number) {
this.number = number;
}
public String getSpeeddial() {
return speeddial;
}
public void setSpeeddial(String speeddial) {
this.speeddial = speeddial;
}
}
The error is java.lang.RuntimeException: Unable to start activity ComponentInfo{com.app.appname/com.app.appname}: java.util.ConcurrentModificationException
Please help me
You are not adding the contacts you are fetching in the list and not doing notify data set changed. Change your onPrepare() method as follows
private void prepareData() {
DatabaseHandler handler = new DatabaseHandler(getApplicationContext());
Log.d("Reading: ", "Reading all contacts..");
List<Bean> beanList = handler.getAllContacts();
this.beanList.addAll(beanList);
mAdapter.notifyDatasetChanged();
}
pass the same list in prepareData(beanList) and add items in this list. And change your method to something likeprepareData(List<Bean> beanList>).after successfully adding, simply call mAdapter.notifyDataSetChanged() method so your adapter could know that some items have been added into the list.
You have not mention android:name in application tag in manifest file.
So you simple use context object or use SpeedDialViewActivity.this
DatabaseHandler handler = new DatabaseHandler(mContext);
or
DatabaseHandler handler = new DatabaseHandler(SpeedDialViewActivity.this);
private void prepareData() {
DatabaseHandler handler = new DatabaseHandler(SpeedDialViewActivity.this);
Log.d("Reading: ", "Reading all contacts..");
List<Bean> beanList = handler.getAllContacts();
//Cursor cursor = (Cursor) handler.getAllContacts();
//Bean bean1;
for (Bean cn : beanList) {
String log = "Id: " + cn.getId() + " ,Name: " + cn.getName() + " ,Phone: " + cn.getNumber();
// Writing Contacts to log
Log.d("Name: ", log);
// bean1 = new Bean(cn.getName(), cn.getNumber(), cn.getSpeeddial()); // Error occurring
// beanList.add(bean1);
}
}
i need to add my EditText details to My TextView using ActionBar and AlertDialog.
here some images to make clearView of my app,my detials are enterd in EditText
now by clicking ActionBar will popup an AlertDialog with NegativeButton and PositiveButton;now by clicking PositiveButton,i want the detial to be Stored in DataBase and TextView
but when i clicked PositiveButton Nothing Happens here!
i show my code ,that i tried below
public class MainActivity extends AppCompatActivity {
EditText firstName;
EditText lastName;
EditText mobile;
EditText password;
EditText email;
TextView textView;
List<AccountsModel>list=new ArrayList<AccountsModel>();
DatabaseHelper databaseHelper;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
databaseHelper =new DatabaseHelper(this);
firstName=(EditText)findViewById(R.id.edt_firstname);
lastName=(EditText)findViewById(R.id.edt_lastname);
mobile=(EditText)findViewById(R.id.edt_mobile);
password=(EditText)findViewById(R.id.edt_password);
email=(EditText)findViewById(R.id.edt_email);
textView=(TextView)findViewById(R.id.lst_view);
AccountsModel accountsModel=new AccountsModel();
accountsModel.firstName="Rahul";
accountsModel.lastName="uday";
accountsModel.mobile="9941677745";
accountsModel.passWord="1234";
accountsModel.emailId="rahul.uday";
databaseHelper.addAccountDetials(accountsModel);
list =databaseHelper.getAllAccountList();
print(list);
}
private void print(List<AccountsModel>list)
{
String value ="";
for (AccountsModel accountsModel : list)
{
value = value+"firstName: "+accountsModel.firstName+", lastName: "+accountsModel.lastName+", mobile: "+accountsModel.mobile+", passWord: "+accountsModel.passWord+", emailId: "+accountsModel.emailId+"\n";
}
textView.setText(value);
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.menu_main, menu);
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action bar item clicks here. The action bar will
// automatically handle clicks on the Home/Up button, so long
// as you specify a parent activity in AndroidManifest.xml.
int id = item.getItemId();
//noinspection SimplifiableIfStatement
if (id == R.id.action_add) {
AlertDialog.Builder builder = new AlertDialog.Builder(MainActivity.this);
builder.setTitle("ADD DATA TO LIST");
builder.setPositiveButton("OK", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
textView.setText(" ");
AccountsModel accountsModel = new AccountsModel();
accountsModel.firstName = firstName.getText().toString();
accountsModel.lastName = lastName.getText().toString();
accountsModel.mobile = mobile.getText().toString();
accountsModel.passWord = password.getText().toString();
accountsModel.emailId = email.getText().toString();
databaseHelper.addAccountDetials(accountsModel);
list = databaseHelper.getAllAccountList();
}
}).setNeutralButton("CANCEL", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
}
});
AlertDialog alertDialog = builder.create();
alertDialog.show();
return true;
}
return super.onOptionsItemSelected(item);
}}
DatabaseHelper.java
public class DatabaseHelper extends SQLiteOpenHelper {
public static String dataBaseName = "Login.db";
private static final int dataBaseVersion = 1;
private static final String tableName = "Accounts";
private static String Key_Id = "id";
private static String Key_FirstName = "firstname";
private static String Key_LastName = "lastname";
private static String Key_Password = "password";
private static String Key_Mobile = "mobile";
private static String Key_Email = "email";
public static String tag = "tag";
private static final String createTableAccounts = "CREATE TABLE " + tableName + "( " + Key_Id + " INTEGER PRIMARY KEY AUTOINCREMENT, " + Key_FirstName + " TEXT, " + Key_LastName + " TEXT, " + Key_Password + " TEXT, " + Key_Mobile + " TEXT, " + Key_Email + " TEXT );";
public DatabaseHelper(Context context) {
super(context, dataBaseName, null, dataBaseVersion);
}
#Override
public void onCreate(SQLiteDatabase db) {
db.execSQL(createTableAccounts);
}
#Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
db.execSQL("DROP TABLE IF EXISTS" + createTableAccounts);
onCreate(db);
}
public long addAccountDetials(AccountsModel accounts) {
SQLiteDatabase db = this.getWritableDatabase();
ContentValues values = new ContentValues();
values.put(Key_FirstName, accounts.firstName);
values.put(Key_LastName, accounts.lastName);
values.put(Key_Password, accounts.passWord);
values.put(Key_Mobile, accounts.mobile);
values.put(Key_Email, accounts.emailId);
long insert = db.insert(tableName, null, values);
return insert;
}
public int updateEntry(AccountsModel accounts) {
SQLiteDatabase db = this.getWritableDatabase();
ContentValues values = new ContentValues();
values.put(Key_FirstName, accounts.firstName);
values.put(Key_LastName, accounts.lastName);
values.put(Key_Password, accounts.passWord);
values.put(Key_Mobile, accounts.mobile);
values.put(Key_Email, accounts.emailId);
return db.update(tableName, values, Key_Id + "=?", new String[]{String.valueOf(accounts.id)});
}
public void deleteEntry(long id) {
SQLiteDatabase db = this.getWritableDatabase();
db.delete(tableName, Key_Id + " = ?", new String[]{String.valueOf(id)});
}
public AccountsModel getAccounts(long id) {
SQLiteDatabase db = this.getReadableDatabase();
String selectQuery = "Select * FROM " + tableName + " WHERE " + Key_Id + " = " + id;
Log.d(tag, selectQuery);
Cursor c = db.rawQuery(selectQuery, null);
if (c != null)
c.moveToFirst();
AccountsModel accountsModel = new AccountsModel();
accountsModel.id = c.getString(c.getColumnIndex(Key_Id));
accountsModel.firstName = c.getString(c.getColumnIndex(Key_FirstName));
accountsModel.lastName = c.getString(c.getColumnIndex(Key_LastName));
accountsModel.mobile = c.getString(c.getColumnIndex(Key_Mobile));
accountsModel.passWord = c.getString(c.getColumnIndex(Key_Password));
accountsModel.emailId = c.getString(c.getColumnIndex(Key_Email));
return accountsModel;
}
public List<AccountsModel> getAllAccountList() {
List<AccountsModel> accountsModelArrayList = new ArrayList<AccountsModel>();
String selectQuery = "SELECT * FROM " + tableName;
Log.d(tag, selectQuery);
SQLiteDatabase db = this.getReadableDatabase();
Cursor cursor = db.rawQuery(selectQuery, null);
if (cursor.moveToFirst()) {
do {
AccountsModel accountsModel = new AccountsModel();
accountsModel.id = cursor.getString(cursor.getColumnIndex(Key_Id));
accountsModel.firstName = cursor.getString(cursor.getColumnIndex(Key_FirstName));
accountsModel.lastName = cursor.getString(cursor.getColumnIndex(Key_LastName));
accountsModel.mobile = cursor.getString(cursor.getColumnIndex(Key_Mobile));
accountsModel.passWord = cursor.getString(cursor.getColumnIndex(Key_Password));
accountsModel.emailId = cursor.getString(cursor.getColumnIndex(Key_Email));
accountsModelArrayList.add(accountsModel);
} while (cursor.moveToNext());
}
return accountsModelArrayList;
}}
AccountsModel.java
public class AccountsModel {
String id;
String firstName;
String lastName;
String mobile;
String passWord;
String emailId;
public AccountsModel(String firstName,String lastName,String mobile,String passWord,String emailId)
{
this.id=id;
this.firstName=firstName;
this.lastName=lastName;
this.mobile=mobile;
this.passWord=passWord;
this.emailId=emailId;
}
public AccountsModel()
{
}}
Nothing happened because this condition is false always :
if (dialog == findViewById(R.id.action_add))
Remove it and run your app again
When I add data into sqlite and open it for the first time, the data inside will be displayed. However, if I try opening it again nothing will show up even though there is data inside. May I know what is the problem?
Class that performs the activity:
public class Watchlist extends ListActivity {
private ArrayList<String> results = new ArrayList<String>();
private String tableName = DatabaseHandler.TABLE_ITEM;
private SQLiteDatabase newDB;
/** Called when the activity is first created. */
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
openAndQueryDatabase();
displayResultList();
}
private void displayResultList() {
TextView tView = new TextView(this);
tView.setText("This data is retrieved from sqlite");
getListView().addHeaderView(tView);
setListAdapter(new ArrayAdapter<String>(this,
android.R.layout.simple_list_item_1, results));
getListView().setTextFilterEnabled(true);
}
private void openAndQueryDatabase() {
try {
DatabaseHandler db = new DatabaseHandler(this.getApplicationContext());
newDB = db.getWritableDatabase();
Cursor c = newDB.rawQuery("SELECT * FROM " + tableName, null);
if (c != null ) {
if (c.moveToFirst()) {
do {
String pid = c.getString(c.getColumnIndex("id"));
String name = c.getString(c.getColumnIndex("name"));
String price = c.getString(c.getColumnIndex("price"));
String date = c.getString(c.getColumnIndex("created_at"));
Log.d("pid",pid);
results.add("Name: " + name + "\n Price: " + price + "\n Date posted: " + date);
}while (c.moveToNext());
}
}
} catch (SQLiteException se ) {
Log.e(getClass().getSimpleName(), "Could not create or Open the database");
} finally {
if (newDB != null)
newDB.execSQL("DELETE FROM " + tableName);
newDB.close();
}
}
}
Database handler:
public class DatabaseHandler extends SQLiteOpenHelper {
// All Static variables
// Database Version
private static final int DATABASE_VERSION = 2;
// Database Name
private static final String DATABASE_NAME = "itemManager";
// table name
public static final String TABLE_ITEM = "item";
// Item Table Columns names
private static final String KEY_ID = "id";
private static final String KEY_NAME = "name";
private static final String KEY_PRICE = "price";
private static final String KEY_CREATED_AT = "created_at";
public DatabaseHandler(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
// Creating Tables
#Override
public void onCreate(SQLiteDatabase db) {
String CREATE_ITEM_TABLE = "CREATE TABLE " + TABLE_ITEM + "("
+ KEY_ID + " INTEGER PRIMARY KEY autoincrement,"
+ KEY_NAME + " TEXT, "
+ KEY_PRICE + " TEXT,"
+ KEY_CREATED_AT + " TEXT" + ")";
db.execSQL(CREATE_ITEM_TABLE);
}
// Upgrading database
#Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
// Drop older table if existed
db.execSQL("DROP TABLE IF EXISTS " + TABLE_ITEM);
// Create tables again
onCreate(db);
}
/**
* Storing item details in database
* */
public void addItem(Items item) {
SQLiteDatabase db = this.getWritableDatabase();
ContentValues values = new ContentValues();
values.put(KEY_NAME, item.getName()); // item name
values.put(KEY_PRICE, item.getPrice()); // item price
values.put(KEY_CREATED_AT, item.getDate()); // Created At
// Inserting Row
db.insert(TABLE_ITEM, null, values);
db.close(); // Closing database connection
}
/**
* Getting item data from database
* */
public List<Items> getAllItems(){
List<Items> itemList = new ArrayList<Items>();
String selectQuery = "SELECT * FROM " + TABLE_ITEM;
SQLiteDatabase db = this.getWritableDatabase();
Cursor cursor = db.rawQuery(selectQuery, null);
// Move to first row
if (cursor.moveToFirst()) {
do {
Items item = new Items();
item.setID(Integer.parseInt(cursor.getString(0)));
item.setName(cursor.getString(1));
item.setPrice(cursor.getString(2));
item.setDate(cursor.getString(2));
// Adding item to list
itemList.add(item);
} while (cursor.moveToNext());
}
// return item list
return itemList;
}
/**
* return true if rows are there in table
* */
public int getRowCount() {
String countQuery = "SELECT * FROM " + TABLE_ITEM;
SQLiteDatabase db = this.getReadableDatabase();
Cursor cursor = db.rawQuery(countQuery, null);
int rowCount = cursor.getCount();
db.close();
cursor.close();
// return row count
return rowCount;
}
// Updating item
public int updateItem(Items item) {
SQLiteDatabase db = this.getWritableDatabase();
ContentValues values = new ContentValues();
values.put(KEY_NAME, item.getName());
values.put(KEY_PRICE, item.getPrice());
values.put(KEY_CREATED_AT, item.getDate());
// updating row
return db.update(TABLE_ITEM, values, KEY_ID + " = ?",
new String[] { String.valueOf(item.getID()) });
}
// Deleting item
public void deleteItem(Items item) {
SQLiteDatabase db = this.getWritableDatabase();
db.delete(TABLE_ITEM, KEY_ID + " = ?",
new String[] { String.valueOf(item.getID()) });
db.close();
}
}
Well, don't you delete all the records before closing the database?
} finally {
if (newDB != null)
newDB.execSQL("DELETE FROM " + tableName);
newDB.close();
}
That would explain that behaviour.