Update ListView in Fragment after AlertDialog dismiss - java

I have a Fragment containing ListView. I'm adding some values to the database with a dialog and I want to update this ListView after dialog is dismissed. Also, when I change the tab, the ListView is not updated but when the application is turned on and off, the ListView is updated.
Fragment and Dialog classes are as follows:
Fragment:
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
View rootView = inflater.inflate(R.layout.fragment_teams, container, false);
listViewTeams = rootView.findViewById(R.id.listView_teams);
TeamDatabase teamDatabase = new TeamDatabase(getContext());
teamDatabase.open();
arrayListTeam = teamDatabase.getAllTeams();
teamDatabase.close();
int resID = R.layout.team_list_item;
teamListArrayAdapter = new TeamListArrayAdapter(getContext(), resID, arrayListTeam);
listViewTeams.setAdapter(teamListArrayAdapter);
return rootView;
}
Dialog onClick Method:
#Override
public void onClick(View view) {
int id = view.getId();
switch (id){
case R.id.button_alertDialogAddTeam_cancel:
this.dismiss();
break;
case R.id.button_alertDialogAddTeam_ok:
Team team = new Team();
team.setName(editTextTeamName.getText().toString());
team.setCode(editTextTeamCode.getText().toString());
TeamDatabase teamDatabase = new TeamDatabase(getContext());
teamDatabase.open();
if(teamDatabase.addNewTeam(team)) {
Toast.makeText(getContext(), team.getCode() + " - " +
team.getName() + " was added successfully", Toast.LENGTH_SHORT).show();
}
this.dismiss();
break;
}
}
TeamDatabase class:
public static final String TABLE_NAME = "team";
private static final String KEY_ID = "id";
private static final String KEY_NAME = "name";
private static final String KEY_CODE = "code";
private static final String KEY_EMBLEM = "emblem";
private Context context;
public static final String CREATE_TABLE = "CREATE TABLE "+
TABLE_NAME + " ("+
KEY_ID + " INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT UNIQUE, "+
KEY_NAME + " TEXT NOT NULL, "+
KEY_CODE + " TEXT NOT NULL, " +
KEY_EMBLEM + " TEXT);";
public TeamDatabase(Context context) {
super(context);
this.context = context;
}
public boolean addNewTeam(Team team){
ContentValues contentValues = new ContentValues();
contentValues.put(KEY_NAME, team.getName());
contentValues.put(KEY_CODE, team.getCode());
return db.insert(TABLE_NAME, null, contentValues) > 0;
}
public ArrayList<Team> getAllTeams()
{
ArrayList<Team> teams = new ArrayList<Team>();
Cursor cursor = db.query(TABLE_NAME, new String[]{KEY_ID,
KEY_NAME,
KEY_CODE}, null, null, null, null, null);
while(cursor.moveToNext()) {
Team team = new Team();
team.setId(cursor.getInt(cursor.getColumnIndex(KEY_ID)));
team.setName(cursor.getString(cursor.getColumnIndex(KEY_NAME)));
team.setCode(cursor.getString(cursor.getColumnIndex(KEY_CODE)));
teams.add(team);
}
return teams;
}
DatabaseHelper class:
private static final String DATABASE_NAME = "fixtureCreator.db";
private static final int DATABASE_VERSION = 1;
public SQLiteDatabase db;
public DatabaseHelper(Context context){
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
#Override
public void onCreate(SQLiteDatabase sqLiteDatabase) {
sqLiteDatabase.execSQL(TeamDatabase.CREATE_TABLE);
}
#Override
public void onUpgrade(SQLiteDatabase sqLiteDatabase, int oldVersion, int newVersinon) {
Log.w("TaskDBAdapter", "Upgrading from version " +
oldVersion + " to " + newVersinon + ", which will destroy all old data");
sqLiteDatabase.execSQL("DROP TABLE IF EXISTS " + TeamDatabase.TABLE_NAME);
onCreate(sqLiteDatabase);
}
public DatabaseHelper open() throws SQLException {
try{
db = this.getWritableDatabase();
}catch (SQLException e){
db = this.getReadableDatabase();
}
return this;
}
public void close(){
db.close();
}

On clicking the item in your first Activity, start your second Activity with startActivityForResult()
And then in Second Activity, after dismissing the dialog,in onClick of that button call,
intent.putExtra("new data", "item text");
setResult(RESULT_OK, intent);
finish();
Now you come back to your first Activity and here you have to implement onActivityResult() callback.
You can extract data from that intent's extras and set that respective item in your array and call notifyDataSetChanged().
This is ideally how you should be doing it.

The problem can be solved using fetching the data after saving it each time you click on the Dialog and then call notifyDataSetChanged() on your adapter. However, there is more elegant way of achieving this kind of behaviour, which will solve both of your problems using content observer.
In case of having a content observer in your database table you need to declare a URI first which references your table.
public static final Uri DB_TABLE_TEAM_URI = Uri
.parse("sqlite://" + Constants.ApplicationPackage + "/" + DB_TABLE_TEAM);
// DB_TABLE_TEAM refers to the database table that you have for storing teams.
Now in your addNewTeam function you need to do the following.
public boolean addNewTeam(Team team) {
// .. Save the team in database
// Notify the observer about the change in the content
context.getContentResolver().notifyChange(DBConstants.DB_TABLE_TEAM_URI, null);
}
You need to call notifyChange() function whenever you add or update an entry in your team table.
Now in your Activity or Fragment you need to register your observer on your cursor having the team data fetched from your team table.
cursor = teamDatabase.getAllTeamsInCursor();
this.registerContentObserver(cursor, DBConstants.DB_TABLE_TEAM_URI);
Now populate your ListView using the cursor by passing it to your adapter of ListView. The list will be updated automatically once a new data has been inserted in your team table.
Update
Modify the addNewTeam function in your TeamDatabase class as follows.
public static final Uri DB_TABLE_TEAM_URI = Uri
.parse("sqlite://" + Constants.ApplicationPackage + "/" + DB_TABLE_TEAM);
public boolean addNewTeam(Team team){
ContentValues contentValues = new ContentValues();
contentValues.put(KEY_NAME, team.getName());
contentValues.put(KEY_CODE, team.getCode());
boolean success = db.insert(TABLE_NAME, null, contentValues) > 0;
context.getContentResolver().notifyChange(DBConstants.DB_TABLE_TEAM_URI, null);
return success;
}
To implement the functionalities with LoaderCallbacks you first need to implement the interface of LoaderCallbacks in your Fragment. So the declaration of your Fragment will look like.
public class TeamsFragment extends Fragment implements LoaderManager.LoaderCallbacks<Cursor> {
// .... Code
}
Now you need to override the functions that comes along with the interface of LoaderCallbacks.
#Override
public Loader<Cursor> onCreateLoader(int id, Bundle args) {
return new SQLiteCursorLoader(getActivity()) {
#Override
public Cursor loadInBackground() {
// Initialize your database
TeamDatabase teamDatabase = new TeamDatabase(getActivity());
Cursor cursor = teamDatabase.getAllTeams();
if (cursor != null) {
// Register the content observer here
this.registerContentObserver(cursor, DBConstants.DB_TABLE_TEAM_URI);
}
return cursor;
}
};
}
#Override
public void onLoadFinished(Loader<Cursor> loader, Cursor data) {
// Set the cursor in your adapter. Handle null values in your setCursor function in your adapter. The cursor might return null when the table is empty.
teamAdapter.setCursor(cursor);
teamAdapter.notifyDataSetChanged();
}
#Override
public void onLoaderReset(Loader<Cursor> loader) {
}
Now in your onCreateView function in the Fragment, you need to initiate the loader to fetch data from the table.
getLoaderManager().initLoader(0, null, this).forceLoad();
And destroy the loader and un-register the receiver in the onDestroyView function.
#Override
public void onDestroyView() {
getLoaderManager().destroyLoader(0);
super.onDestroyView();
}
I was missing the SQLiteCursorLoader class to be added here.
package com.wooz.observer.databases;
import android.content.ContentResolver;
import android.content.Context;
import android.database.ContentObserver;
import android.database.Cursor;
import android.net.Uri;
import android.os.Handler;
import android.support.v4.content.AsyncTaskLoader;
import android.support.v4.content.Loader;
import java.io.FileDescriptor;
import java.io.PrintWriter;
import java.util.Arrays;
public abstract class SQLiteCursorLoader extends AsyncTaskLoader<Cursor> {
private final ForceLoadContentObserver mObserver;
private Uri mUri;
private String[] mProjection;
private String mSelection;
private String[] mSelectionArgs;
private String mSortOrder;
private Cursor mCursor;
/* Runs on a worker thread */
#Override
public abstract Cursor loadInBackground();
/**
* Registers an observer to get notifications from the content provider
* when the cursor needs to be refreshed.
*/
public void registerContentObserver(Cursor cursor, Uri observerUri) {
cursor.registerContentObserver(mObserver);
cursor.setNotificationUri(getContext().getContentResolver(), observerUri);
}
/* Runs on the UI thread */
#Override
public void deliverResult(Cursor cursor) {
try {
if (isReset()) {
// An async query came in while the loader is stopped
if (cursor != null) {
cursor.close();
}
return;
}
Cursor oldCursor = mCursor;
mCursor = cursor;
if (isStarted()) {
super.deliverResult(cursor);
}
if (oldCursor != null && oldCursor != cursor && !oldCursor.isClosed()) {
oldCursor.close();
}
} catch (Exception e) {
e.printStackTrace();
}
}
/**
* Creates an empty unspecified CursorLoader. You must follow this with
* calls to {#link #setUri(Uri)}, {#link #setSelection(String)}, etc
* to specify the query to perform.
*/
public SQLiteCursorLoader(Context context) {
super(context);
mObserver = new ForceLoadContentObserver();
}
/**
* Creates a fully-specified CursorLoader. See
* {#link ContentResolver#query(Uri, String[], String, String[], String)
* ContentResolver.query()} for documentation on the meaning of the
* parameters. These will be passed as-is to that call.
*/
public SQLiteCursorLoader(Context context, Uri uri, String[] projection, String selection,
String[] selectionArgs, String sortOrder) {
super(context);
mObserver = new ForceLoadContentObserver();
mUri = uri;
mProjection = projection;
mSelection = selection;
mSelectionArgs = selectionArgs;
mSortOrder = sortOrder;
}
/**
* Starts an asynchronous load of the contacts list data. When the result is ready the callbacks
* will be called on the UI thread. If a previous load has been completed and is still valid
* the result may be passed to the callbacks immediately.
* <p>
* Must be called from the UI thread
*/
#Override
protected void onStartLoading() {
if (mCursor != null) {
deliverResult(mCursor);
}
if (takeContentChanged() || mCursor == null) {
forceLoad();
}
}
/**
* Must be called from the UI thread
*/
#Override
protected void onStopLoading() {
// Attempt to cancel the current load task if possible.
cancelLoad();
}
#Override
public void onCanceled(Cursor cursor) {
if (cursor != null && !cursor.isClosed()) {
cursor.close();
}
}
#Override
protected void onReset() {
super.onReset();
// Ensure the loader is stopped
onStopLoading();
if (mCursor != null && !mCursor.isClosed()) {
mCursor.close();
}
mCursor = null;
}
public Uri getUri() {
return mUri;
}
public void setUri(Uri uri) {
mUri = uri;
}
public String[] getProjection() {
return mProjection;
}
public void setProjection(String[] projection) {
mProjection = projection;
}
public String getSelection() {
return mSelection;
}
public void setSelection(String selection) {
mSelection = selection;
}
public String[] getSelectionArgs() {
return mSelectionArgs;
}
public void setSelectionArgs(String[] selectionArgs) {
mSelectionArgs = selectionArgs;
}
public String getSortOrder() {
return mSortOrder;
}
public void setSortOrder(String sortOrder) {
mSortOrder = sortOrder;
}
#Override
public void dump(String prefix, FileDescriptor fd, PrintWriter writer, String[] args) {
super.dump(prefix, fd, writer, args);
writer.print(prefix);
writer.print("mUri=");
writer.println(mUri);
writer.print(prefix);
writer.print("mProjection=");
writer.println(Arrays.toString(mProjection));
writer.print(prefix);
writer.print("mSelection=");
writer.println(mSelection);
writer.print(prefix);
writer.print("mSelectionArgs=");
writer.println(Arrays.toString(mSelectionArgs));
writer.print(prefix);
writer.print("mSortOrder=");
writer.println(mSortOrder);
writer.print(prefix);
writer.print("mCursor=");
writer.println(mCursor);
//writer.print(prefix); writer.print("mContentChanged="); writer.println(mContentChanged);
}
private class CursorLoaderContentObserver extends ContentObserver {
public CursorLoaderContentObserver() {
super(new Handler());
}
#Override
public boolean deliverSelfNotifications() {
return true;
}
#Override
public void onChange(boolean selfChange) {
onContentChanged();
}
}
}

You should call notifyDataSetChanged just before dismissing the dialoge
teamListArrayAdapter.notifyDataSetChanged();
You should change you code something like this below
#Override
public void onClick(View view) {
int id = view.getId();
switch (id){
case R.id.button_alertDialogAddTeam_cancel:
this.dismiss();
break;
case R.id.button_alertDialogAddTeam_ok:
Team team = new Team();
team.setName(editTextTeamName.getText().toString());
team.setCode(editTextTeamCode.getText().toString());
TeamDatabase teamDatabase = new TeamDatabase(getContext());
teamDatabase.open();
if(teamDatabase.addNewTeam(team)) {
Toast.makeText(getContext(), team.getCode() + " - " +
team.getName() + " was added successfully", Toast.LENGTH_SHORT).show();
}
arrayListTeam = teamDatabase.getAllTeams();
teamListArrayAdapter.notifyDataSetChanged();
this.dismiss();
break;
}
}

Add this code in onCreateView:
teamListArrayAdapter.notifyDataSetChanged();

Related

Remove more than one element from CursorAdapter/List View

I'm making a project in Android/Java. I have an activity with a listview that displays values from a database and a remove button. For the moment, each row of this list view consists of a checktextview. This last one displays the name of an element of the database. I want to select different elements (with the check text view) and then if I press the remove button, all the selected elements have to be removed from the list and from database. In the following I put the essential parts of my classes. I already done most of the work.
This is my activity:
public class ShoppingListActivity extends AppCompatActivity {
// Variables for the management of the database
private DBManagerShoppingList dbShoppingList;
private Cursor crs;
// List view for the shopping list elements
private ListView shoppingListListView;
private ShoppingListViewAdapter shoppingListViewAdapter;
// Generic variables
private String selectedShoppingList;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_shopping_list);
// Find of the useful widgets
shoppingListListView = findViewById(R.id.listViewSelShoppingList);
shoppingListsSpinner = findViewById(R.id.spinnerShoppingLists);
selectedShoppingList = "List_1";
populateListView();
}
// Populate list view from database
public void populateListView() {
// Database management
dbShoppingList = new DBManagerShoppingList(this, selectedShoppingList);
crs = dbShoppingList.query();
new Handler().post(new Runnable() {
#Override
public void run() {
shoppingListViewAdapter = new ShoppingListViewAdapter(ShoppingListActivity.this, crs, 0);
shoppingListListView.setAdapter(shoppingListViewAdapter);
}
});
}
// Remove selected elements
public void removeSelectedElements(View btnRemove) {
// TODO
}
}
This is my custom adapter:
public class ShoppingListViewAdapter extends CursorAdapter {
private LayoutInflater layoutInflater;
private List<Integer> elementsPosArrayList = new ArrayList<>();
private HashMap<String, Integer> elementsMap = new HashMap<>();
public ShoppingListViewAdapter(Context context, Cursor c, int flags) {
super(context, c, flags);
layoutInflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
}
#Override
public View newView(Context context, Cursor cursor, ViewGroup viewGroup) {
return layoutInflater.inflate(R.layout.list_view_row, viewGroup, false);
}
#Override
public void bindView(View view, Context context, Cursor cursor) {
// CheckBox management
final CheckBox checkBoxElementName = view.findViewById(R.id.checkBoxElementName);
String elementName = cursor.getString(cursor.getColumnIndex(DBFieldsShoppingList.FIELD_ELEMENT_NAME));
checkBoxElementName.setText(elementName);
elementsMap.put(elementName, cursor.getPosition());
checkBoxElementName.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
#Override
public void onCheckedChanged(CompoundButton compoundButton, boolean isChecked) {
if (isChecked) {
elementsPosArrayList.add(elementsMap.get(checkBoxElementName.getText().toString()));
} else {
elementsPosArrayList.remove(elementsMap.get(checkBoxElementName.getText().toString()));
}
}
});
}
public long getElementId(Cursor crs, int position) {
crs.moveToPosition(position);
return crs.getLong(crs.getColumnIndex(DBFieldsShoppingList.FIELD_ID));
}
public List<Integer> getElementsPosArrayList() {
return elementsPosArrayList;
}
}
Classes for the database management are the following:
DBHelper:
public class DBHelperShoppingList extends SQLiteOpenHelper {
private String DBName;
public DBHelperShoppingList(#Nullable Context context, int dbVersion, String dbName) {
super(context, dbName, null, dbVersion);
this.DBName = dbName;
}
#Override
public void onCreate(SQLiteDatabase shoppingListDB) {
String q = "CREATE TABLE " + DBFieldsShoppingList.FIELD_TABLE_NAME +
" ( _id INTEGER PRIMARY KEY AUTOINCREMENT," +
DBFieldsShoppingList.FIELD_ELEMENT_NAME + " TEXT," +
DBFieldsShoppingList.FIELD_ELEMENT_TYPE + " TEXT," +
DBFieldsShoppingList.FIELD_ELEMENT_QUANT + " TEXT)";
shoppingListDB.execSQL(q);
}
#Override
public void onUpgrade(SQLiteDatabase shoppingListDB, int oldVersion, int newVersion) {}
}
Class for the fields of the database:
public class DBFieldsShoppingList {
public static final String FIELD_ID = "_Id";
public static final String FIELD_TABLE_NAME = "Shopping_List";
public static final String FIELD_ELEMENT_NAME = "Element_Name";
public static final String FIELD_ELEMENT_TYPE = "Element_Type";
public static final String FIELD_ELEMENT_QUANT = "Element_Quant";
}
Class database manager:
public class DBManagerShoppingList {
private DBHelperShoppingList dbHelperShoppingList;
public DBManagerShoppingList(Context ctx, String shoppingListName) {
dbHelperShoppingList = new DBHelperShoppingList(ctx, 1, shoppingListName);
}
public void dbSave(String elementName, String elementType, String elementQuantity) {
SQLiteDatabase db = dbHelperShoppingList.getWritableDatabase();
ContentValues cv = new ContentValues();
cv.put(DBFieldsShoppingList.FIELD_ELEMENT_NAME, elementName);
cv.put(DBFieldsShoppingList.FIELD_ELEMENT_TYPE, elementType);
cv.put(DBFieldsShoppingList.FIELD_ELEMENT_QUANT, elementQuantity);
try {
db.insert(DBFieldsShoppingList.FIELD_TABLE_NAME, null, cv);
} catch (SQLiteException ignored) {}
}
public boolean deleteElement(long id) {
SQLiteDatabase db = dbHelperShoppingList.getWritableDatabase();
try {
return db.delete(DBFieldsShoppingList.FIELD_TABLE_NAME, DBFieldsShoppingList.FIELD_ID + "=?", new String[]{Long.toString(id)})>0;
} catch(SQLiteException exc) {
return false;
}
}
public static void deleteDB(Context ctx, String DBName) {
ctx.deleteDatabase(DBName);
}
public Cursor query() {
Cursor crs;
try {
SQLiteDatabase db = dbHelperShoppingList.getReadableDatabase();
crs = db.query(DBFieldsShoppingList.FIELD_TABLE_NAME, null, null, null, null, null, null, null);
} catch (SQLiteException exc) {
return null;
}
return crs;
}
}
I tought, in bindView method of the adapter class, to save a map between element name and its position. Then, to create a list of the element names of the checked elements. In this way, I can know the positions of the checked elements, from the map. Now, I have to get indexes of the checked elements, in order to remove them from database, with delete method of the database manager class.
How can I solve this problem? If my structure is not correct, say me how to change.
Thank you very much in advance.
Marco
Hy to everybody,
I found the solution. In database manager class, I changed the delete method in the following way:
public boolean deleteElement(String elementName) {
SQLiteDatabase db = dbHelperShoppingList.getWritableDatabase();
try {
return db.delete(DBFieldsShoppingList.FIELD_TABLE_NAME, DBFieldsShoppingList.FIELD_ELEMENT_NAME + "=?", new String[]{(elementName)})>0;
} catch(SQLiteException exc) {
return false;
}
}
This allows, to search by name in database.
In adapter class, I removed the map, and I wrote an arraylist of string, where I put name of the checked elements:
#Override
public void bindView(View view, Context context, Cursor cursor) {
// CheckBox management
final CheckBox checkBoxElementName = view.findViewById(R.id.checkBoxElementName);
String elementName = cursor.getString(cursor.getColumnIndex(DBFieldsShoppingList.FIELD_ELEMENT_NAME));
checkBoxElementName.setText(elementName);
checkBoxElementName.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
#Override
public void onCheckedChanged(CompoundButton compoundButton, boolean isChecked) {
if (isChecked) {
elementNamesArrayList.add(checkBoxElementName.getText().toString());
} else {
elementNamesArrayList.remove(checkBoxElementName.getText().toString());
}
}
});
}
Finally, in the activity class, the remove method is the following:
public void removeSelectedElements(View btnRemove) {
List<String> elementNamesArrayList = shoppingListViewAdapter.getElementNamesArrayList();
for (String item: elementNamesArrayList) {
dbShoppingList.deleteElement(item);
}
populateListView();
}
In this way I solved my problem.
Marco

sqlite.SQLiteException: no such column. I checked on commas and spaces [duplicate]

This question already has answers here:
When does SQLiteOpenHelper onCreate() / onUpgrade() run?
(15 answers)
Closed 7 years ago.
I cannot find the problem in my (Android) Java code.
The problem (according the logcat) is that there is no such column as reminder_date.
This is the error:
09-19 21:27:24.440 23689-23689/com.example.sanne.reminderovapplication E/AndroidRuntime﹕ FATAL EXCEPTION: main
Process: com.example.sanne.reminderovapplication, PID: 23689
java.lang.RuntimeException: Unable to start activity ComponentInfo{com.example.sanne.reminderovapplication/com.example.sanne.reminderovapplication.MainActivity}: android.database.sqlite.SQLiteException: no such column: reminder_date (code 1): , while compiling: SELECT reminder_id AS _id , reminder_title , reminder_description , reminder_date FROM reminder
I checked for the commas and spaces.
I hope there is a solution for this problem.
This is my code of the MySQLiteHelper:
public class MySQLiteHelper extends SQLiteOpenHelper{
// Database info
private static final String DATABASE_NAME = "reminderOVApp.db";
private static final int DATABASE_VERSION = 8;
// Assignments
public static final String TABLE_REMINDER = "reminder";
public static final String COLUMN_REMINDER_ID = "reminder_id";
public static final String COLUMN_REMINDER_TITLE = "reminder_title";
public static final String COLUMN_REMINDER_DESCRIPTION = "reminder_description";
public static final String COLUMN_REMINDER_DATE = "reminder_date";
// Creating the table
private static final String DATABASE_CREATE_REMINDERS =
"CREATE TABLE " + TABLE_REMINDER +
"(" +
COLUMN_REMINDER_ID + " integer primary key autoincrement , " +
COLUMN_REMINDER_TITLE + " text not null , " +
COLUMN_REMINDER_DESCRIPTION + " text not null , " +
COLUMN_REMINDER_DATE + " text not null " +
");";
// Mandatory constructor which passes the context, database name and database version and passes it to the parent
public MySQLiteHelper(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
#Override
public void onCreate(SQLiteDatabase database)
{
// Execute the sql to create the table assignments
database.execSQL(DATABASE_CREATE_REMINDERS);
}
#Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion)
{
// When the database gets upgraded you should handle the update to make sure there is no data loss.
// This is the default code you put in the upgrade method, to delete the table and call the oncreate again.
if(oldVersion == 8)
{
db.execSQL("DROP TABLE IF EXISTS " + TABLE_REMINDER);
onCreate(db);
}
}
And this is the code of the DataSource Class:
public class DataSource {
private SQLiteDatabase database;
private MySQLiteHelper dbHelper;
private String[] assignmentAllColumns = {MySQLiteHelper.COLUMN_REMINDER_ID, MySQLiteHelper.COLUMN_REMINDER_TITLE, MySQLiteHelper.COLUMN_REMINDER_DESCRIPTION, MySQLiteHelper.COLUMN_REMINDER_DATE};
public DataSource(Context context) {
dbHelper = new MySQLiteHelper(context);
database = dbHelper.getWritableDatabase();
dbHelper.close();
}
// Opens the database to use it
public void open() throws SQLException {
database = dbHelper.getWritableDatabase();
}
// Closes the database when you no longer need it
public void close() {
dbHelper.close();
}
//Add a reminder to the database
public long createReminder(String reminder_title, String reminder_description, String reminder_date) {
// If the database is not open yet, open it
if (!database.isOpen()) {
open();
}
ContentValues values = new ContentValues();
values.put(MySQLiteHelper.COLUMN_REMINDER_TITLE, reminder_title);
values.put(MySQLiteHelper.COLUMN_REMINDER_DESCRIPTION, reminder_description);
values.put(MySQLiteHelper.COLUMN_REMINDER_DATE, reminder_date);
// values.put(MySQLiteHelper.COLUMN_REMINDER_TIME, reminder_time);
long insertId = database.insert(MySQLiteHelper.TABLE_REMINDER, null, values);
// If the database is open, close it
if (database.isOpen()) {
close();
}
return insertId;
}
//Change data of the specific reminder
public void updateReminder(Reminder reminder) {
if (!database.isOpen()) {
open();
}
ContentValues args = new ContentValues();
args.put(MySQLiteHelper.COLUMN_REMINDER_TITLE, reminder.getTitle());
args.put(MySQLiteHelper.COLUMN_REMINDER_DESCRIPTION, reminder.getDescription());
args.put(MySQLiteHelper.COLUMN_REMINDER_DATE, reminder.getDate());
database.update(MySQLiteHelper.TABLE_REMINDER, args, MySQLiteHelper.COLUMN_REMINDER_ID + "=?", new String[] { Long.toString(reminder.getId()) });
if (database.isOpen()) {
close();
}
}
//Delete a reminder from the database
public void deleteReminder(long id) {
if (!database.isOpen()) {
open();
}
database.delete(MySQLiteHelper.TABLE_REMINDER, MySQLiteHelper.COLUMN_REMINDER_ID + " =?", new String[]{Long.toString(id)});
if (database.isOpen()) {
close();
}
}
//Delete all reminders
public void deleteReminders() {
if (!database.isOpen()) {
open();
}
database.delete(MySQLiteHelper.TABLE_REMINDER, null, null);
if (database.isOpen()) {
close();
}
}
//This way you can get the id and the reminder from the cursor.
private Reminder cursorToReminder(Cursor cursor) {
try {
Reminder reminder = new Reminder();
reminder.setId(cursor.getLong(cursor.getColumnIndexOrThrow(MySQLiteHelper.COLUMN_REMINDER_ID)));
reminder.setTitle(cursor.getString(cursor.getColumnIndexOrThrow(MySQLiteHelper.COLUMN_REMINDER_TITLE)));
reminder.setDescription(cursor.getString(cursor.getColumnIndexOrThrow(MySQLiteHelper.COLUMN_REMINDER_DESCRIPTION)));
reminder.setDate(cursor.getString(cursor.getColumnIndexOrThrow(MySQLiteHelper.COLUMN_REMINDER_DATE)));
return reminder;
}catch(CursorIndexOutOfBoundsException exception) {
exception.printStackTrace();
return null;
}
}
//Get all the reminders to populate the listView --> ArrayList
public List<Reminder> getAllReminders() {
if (!database.isOpen()) {
open();
}
List<Reminder> reminders = new ArrayList<Reminder>();
Cursor cursor = database.query(MySQLiteHelper.TABLE_REMINDER, assignmentAllColumns, null, null, null, null, null);
cursor.moveToFirst();
while (!cursor.isAfterLast()) {
Reminder assignment = cursorToReminder(cursor);
reminders.add(assignment);
cursor.moveToNext();
}
// make sure to close the cursor
cursor.close();
if (database.isOpen()) {
close();
}
return reminders;
}
//A SimpleCursorAdapter requires a Cursor to get the data from the database instead of an ArrayList.
public Cursor getAllAssignmentsCursor()
{
if (!database.isOpen()) {
open();
}
Cursor cursor = database.rawQuery(
"SELECT " +
MySQLiteHelper.COLUMN_REMINDER_ID + " AS _id , " +
MySQLiteHelper.COLUMN_REMINDER_TITLE + " , " +
MySQLiteHelper.COLUMN_REMINDER_DESCRIPTION + " , " +
MySQLiteHelper.COLUMN_REMINDER_DATE +
" FROM " + MySQLiteHelper.TABLE_REMINDER, null);
if (cursor != null) {
cursor.moveToFirst();
}
if (database.isOpen()) {
close();
}
return cursor;
}
//Get one reminder
public Reminder getReminder(long columnId) {
if (!database.isOpen()) {
open();
}
Cursor cursor = database.query(MySQLiteHelper.TABLE_REMINDER, assignmentAllColumns, MySQLiteHelper.COLUMN_REMINDER_ID + "=?", new String[] { Long.toString(columnId)}, null, null, null);
cursor.moveToFirst();
Reminder assignment = cursorToReminder(cursor);
cursor.close();
if (database.isOpen()) {
close();
}
return assignment;
}}
And my MainActivity Class:
public class AddActivity extends AppCompatActivity {
private DataSource datasource;
private EditText addReminderEditText;
private EditText descriptionEditText;
private EditText dateEditText;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_add);
datasource = new DataSource(this);
addReminderEditText = (EditText) findViewById(R.id.add_reminder_editText);
descriptionEditText = (EditText) findViewById(R.id.description_reminder_editText);
dateEditText = (EditText) findViewById(R.id.date_reminder_editText);
}
#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_add, 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.add_assignment_menu_save) {
//Sending the data back to MainActivity
long reminderId = datasource.createReminder(addReminderEditText.getText().toString(), descriptionEditText.getText().toString(), dateEditText.getText().toString());
Intent resultIntent = new Intent();
resultIntent.putExtra(MainActivity.EXTRA_REMINDER_ID, reminderId);
setResult(Activity.RESULT_OK, resultIntent);
finish();
return true;
}
return super.onOptionsItemSelected(item);
}}
Well, it seems like reminder_date has been added after the first code execution.
Simply uninstall and reinstall your app.

How do I send String data from sqlite to another activity

I have sqlite database I succeeded to get all data from it and I stored it in String data and then displayed it using another java class which just has Toast.
Now I am trying to send this data to another activity.
How to I achieve this?
NotesDbAdapter.java:
public class NotesDbAdapter {
public static final String KEY_TITLE = "title";
public static final String KEY_DATE = "date";
public static final String KEY_BODY = "body";
public static final String KEY_ROWID = "_id";
private static final String TAG = "NotesDbAdapter";
private DatabaseHelper mDbHelper;
private SQLiteDatabase mDb;
/**
* Database creation sql statement
*/
private static final String DATABASE_CREATE =
"create table notes (_id integer primary key autoincrement, "
+ "title text not null, body text not null, date text not null);";
private static final String DATABASE_NAME = "data";
private static final String DATABASE_TABLE = "notes";
private static final int DATABASE_VERSION = 2;
private final Context mCtx;
private static class DatabaseHelper extends SQLiteOpenHelper {
DatabaseHelper(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
#Override
public void onCreate(SQLiteDatabase db) {
db.execSQL(DATABASE_CREATE);
}
#Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
Log.w(TAG, "Upgrading database from version " + oldVersion + " to "
+ newVersion + ", which will destroy all old data");
db.execSQL("DROP TABLE IF EXISTS notes");
onCreate(db);
}
}
/**
* Constructor - takes the context to allow the database to be
* opened/created
*
* #param ctx the Context within which to work
*/
public NotesDbAdapter(Context ctx) {
this.mCtx = ctx;
}
/**
* Open the notes database. If it cannot be opened, try to create a new
* instance of the database. If it cannot be created, throw an exception to
* signal the failure
*
* #return this (self reference, allowing this to be chained in an
* initialization call)
* #throws SQLException if the database could be neither opened or created
*/
public NotesDbAdapter open() throws SQLException {
mDbHelper = new DatabaseHelper(mCtx);
mDb = mDbHelper.getWritableDatabase();
return this;
}
public void close() {
mDbHelper.close();
}
/**
* Create a new note using the title and body provided. If the note is
* successfully created return the new rowId for that note, otherwise return
* a -1 to indicate failure.
*
* #param title the title of the note
* #param body the body of the note
* #return rowId or -1 if failed
*/
public long createNote(String title, String body, String date) {
ContentValues initialValues = new ContentValues();
initialValues.put(KEY_TITLE, title);
initialValues.put(KEY_BODY, body);
initialValues.put(KEY_DATE, date);
return mDb.insert(DATABASE_TABLE, null, initialValues);
}
/**
* Delete the note with the given rowId
*
* #param rowId id of note to delete
* #return true if deleted, false otherwise
*/
public boolean deleteNote(long rowId) {
return mDb.delete(DATABASE_TABLE, KEY_ROWID + "=" + rowId, null) > 0;
}
/**
* Return a Cursor over the list of all notes in the database
*
* #return Cursor over all notes
*/
public Cursor fetchAllNotes() {
return mDb.query(DATABASE_TABLE, new String[] {KEY_ROWID, KEY_TITLE,
KEY_BODY,KEY_DATE}, null, null, null, null, null);
}
/**
* Return a Cursor positioned at the note that matches the given rowId
*
* #param rowId id of note to retrieve
* #return Cursor positioned to matching note, if found
* #throws SQLException if note could not be found/retrieved
*/
public Cursor fetchNote(long rowId) throws SQLException {
Cursor mCursor =
mDb.query(true, DATABASE_TABLE, new String[] {KEY_ROWID,
KEY_TITLE, KEY_BODY,KEY_DATE}, KEY_ROWID + "=" + rowId, null,
null, null, null, null);
if (mCursor != null) {
mCursor.moveToFirst();
}
return mCursor;
}
/**
* Update the note using the details provided. The note to be updated is
* specified using the rowId, and it is altered to use the title and body
* values passed in
*
* #param rowId id of note to update
* #param title value to set note title to
* #param body value to set note body to
* #return true if the note was successfully updated, false otherwise
*/
public boolean updateNote(long rowId, String title, String body,String date) {
ContentValues args = new ContentValues();
args.put(KEY_TITLE, title);
args.put(KEY_BODY, body);
//This lines is added for personal reason
args.put(KEY_DATE, date);
//One more parameter is added for data
return mDb.update(DATABASE_TABLE, args, KEY_ROWID + "=" + rowId, null) > 0;
}
public String getALLData(){
mDb = mDbHelper.getWritableDatabase();
String[] columns={KEY_ROWID ,KEY_TITLE,KEY_BODY};
Cursor cursor = mDb.query(DATABASE_TABLE, columns, null, null, null, null, null);
StringBuffer buffer=new StringBuffer();
while (cursor.moveToNext()){
int cid=cursor.getInt(0);
String title=cursor.getString(1);
String body=cursor.getString(2);
buffer.append(cid+" "+title+" "+body+"\n");
}
return buffer.toString();
}}
The NoteEdit activity where I store data:
public class NoteEdit extends Activity {
public static int numTitle = 1;
public static String curDate = "";
public static String curText = "";
private EditText mTitleText;
private EditText mBodyText;
private TextView mDateText;
private Long mRowId;
private Cursor note;
private NotesDbAdapter mDbHelper;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mDbHelper = new NotesDbAdapter(this);
mDbHelper.open();
setContentView(R.layout.note_edit);
// getActionBar().setDisplayHomeAsUpEnabled(true);
setTitle(R.string.app_name);
mTitleText = (EditText) findViewById(R.id.title);
mBodyText = (EditText) findViewById(R.id.body);
mDateText = (TextView) findViewById(R.id.notelist_date);
long msTime = System.currentTimeMillis();
Date curDateTime = new Date(msTime);
SimpleDateFormat formatter = new SimpleDateFormat("d'/'M'/'y");
curDate = formatter.format(curDateTime);
mDateText.setText(""+curDate);
mRowId = (savedInstanceState == null) ? null :
(Long) savedInstanceState.getSerializable(NotesDbAdapter.KEY_ROWID);
if (mRowId == null) {
Bundle extras = getIntent().getExtras();
mRowId = extras != null ? extras.getLong(NotesDbAdapter.KEY_ROWID)
: null;
}
populateFields();
}
public static class LineEditText extends EditText{
// we need this constructor for LayoutInflater
public LineEditText(Context context, AttributeSet attrs) {
super(context, attrs);
mRect = new Rect();
mPaint = new Paint();
mPaint.setStyle(Paint.Style.FILL_AND_STROKE);
mPaint.setColor(Color.BLUE);
}
private Rect mRect;
private Paint mPaint;
#Override
protected void onDraw(Canvas canvas) {
int height = getHeight();
int line_height = getLineHeight();
int count = height / line_height;
if (getLineCount() > count)
count = getLineCount();
Rect r = mRect;
Paint paint = mPaint;
int baseline = getLineBounds(0, r);
for (int i = 0; i < count; i++) {
canvas.drawLine(r.left, baseline + 1, r.right, baseline + 1, paint);
baseline += getLineHeight();
super.onDraw(canvas);
}
}
}
#Override
protected void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
saveState();
outState.putSerializable(NotesDbAdapter.KEY_ROWID, mRowId);
}
#Override
protected void onPause() {
super.onPause();
saveState();
}
#Override
protected void onResume() {
super.onResume();
populateFields();
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.noteedit_menu, menu);
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case R.id.menu_about:
/* Here is the introduce about myself */
AlertDialog.Builder dialog = new AlertDialog.Builder(NoteEdit.this);
dialog.setTitle("About");
dialog.setMessage("This project "
);
dialog.setPositiveButton("OK", new DialogInterface.OnClickListener() {
#Override
public void onClick(DialogInterface dialog, int which) {
dialog.cancel();
}
});
dialog.show();
return true;
case R.id.menu_delete:
if(note != null){
note.close();
note = null;
}
if(mRowId != null){
mDbHelper.deleteNote(mRowId);
}
finish();
return true;
//speech button
case R.id.menu_speech:
//saveState();
//finish();
return true;
case R.id.menu_save:
saveState();
finish();
return true;
/* case android.R.id.home:
finish(); */
default:
return super.onOptionsItemSelected(item);
}
}
private void saveState() {
String title = mTitleText.getText().toString();
String body = mBodyText.getText().toString();
if(mRowId == null){
long id = mDbHelper.createNote(title, body, curDate);
if(id > 0){
mRowId = id;
}else{
Log.e("saveState","failed to create note");
}
}else{
if(!mDbHelper.updateNote(mRowId, title, body, curDate)){
Log.e("saveState","failed to update note");
}
}
}
private void populateFields() {
if (mRowId != null) {
note = mDbHelper.fetchNote(mRowId);
startManagingCursor(note);
mTitleText.setText(note.getString(
note.getColumnIndexOrThrow(NotesDbAdapter.KEY_TITLE)));
mBodyText.setText(note.getString(
note.getColumnIndexOrThrow(NotesDbAdapter.KEY_BODY)));
curText = note.getString(
note.getColumnIndexOrThrow(NotesDbAdapter.KEY_BODY));
}
}
public void viewDetails(View view){
String data= mDbHelper.getALLData();
Message.message(this,data);
}
}
Assuming you correctly received data from the database, you can send them to another activity of your app with various ways. The most simple of them being extras. Click the link and navigate to the paragraph that it titled "Extras" to see how you can use them.
You can pass your values like
Intent intent=new Intent(getApplicationContext(), SecondActivity.class);
intent.putExtra("key1", "your value1 here");
intent.putExtra("key2", "your value2 here");
startActivity(intent);
And recive your value like
String your_value1=getIntent().getStringExtra("key1");
String your_value2=getIntent().getStringExtra("key2");
you can pass String,integer,float,...
You can even pass a complete object too.

Total price using rawQuery in android [closed]

Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 8 years ago.
Improve this question
I've been trying to get the price value from the database and try to make a grand total. I used the rawQuery but always crashed.I think theres a problem in my rawQuery..i still cant get the total after many times i've tried..
this is the code:
DBAdapter
import android.content.ContentValues;
import android.content.Context;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import android.util.Log;
// ------------------------------------ DBAdapter.java ---------------------------------------------
// TO USE:
// Change the package (at top) to match your project.
// Search for "TODO", and make the appropriate changes.
public class DBAdapter {
/////////////////////////////////////////////////////////////////////
// Constants & Data
/////////////////////////////////////////////////////////////////////
// For logging:
private static final String TAG = "DBAdapter";
// DB Fields
public static final String KEY_ROWID = "_id";
public static final int COL_ROWID = 0;
/*
* CHANGE 1:
*/
// TODO: Setup your fields here:
public static final String KEY_NAME = "name";
public static final String KEY_QUANTITY = "studentnum";
public static final String KEY_PRICE = "favcolour";
// TODO: Setup your field numbers here (0 = KEY_ROWID, 1=...)
public static final int COL_NAME = 1;
public static final int COL_QUANTITY = 2;
public static final int COL_PRICE = 3;
public static final String[] ALL_KEYS = new String[] {KEY_ROWID, KEY_NAME, KEY_QUANTITY, KEY_PRICE};
// DB info: it's name, and the table we are using (just one).
public static final String DATABASE_NAME = "MyDb";
public static final String DATABASE_TABLE = "mainTable";
// Track DB version if a new version of your app changes the format.
public static final int DATABASE_VERSION = 2;
private static final String DATABASE_CREATE_SQL =
"create table " + DATABASE_TABLE
+ " (" + KEY_ROWID + " integer primary key autoincrement, "
/*
* CHANGE 2:
*/
// TODO: Place your fields here!
// + KEY_{...} + " {type} not null"
// - Key is the column name you created above.
// - {type} is one of: text, integer, real, blob
// (http://www.sqlite.org/datatype3.html)
// - "not null" means it is a required field (must be given a value).
// NOTE: All must be comma separated (end of line!) Last one must have NO comma!!
+ KEY_NAME + " text not null, "
+ KEY_QUANTITY + " integer not null, "
+ KEY_PRICE + " string not null"
// Rest of creation:
+ ");";
// Context of application who uses us.
private final Context context;
private DatabaseHelper myDBHelper;
private SQLiteDatabase db;
/////////////////////////////////////////////////////////////////////
// Public methods:
/////////////////////////////////////////////////////////////////////
public DBAdapter(Context ctx) {
this.context = ctx;
myDBHelper = new DatabaseHelper(context);
}
// Open the database connection.
public DBAdapter open() {
db = myDBHelper.getWritableDatabase();
return this;
}
// Close the database connection.
public void close() {
myDBHelper.close();
}
// Add a new set of values to the database.
public long insertRow(String name, String studentNum, String favColour) {
/*
* CHANGE 3:
*/
// TODO: Update data in the row with new fields.
// TODO: Also change the function's arguments to be what you need!
// Create row's data:
ContentValues initialValues = new ContentValues();
initialValues.put(KEY_NAME, name);
initialValues.put(KEY_QUANTITY, studentNum);
initialValues.put(KEY_PRICE, favColour);
// Insert it into the database.
return db.insert(DATABASE_TABLE, null, initialValues);
}
// Delete a row from the database, by rowId (primary key)
public boolean deleteRow(long rowId) {
String where = KEY_ROWID + "=" + rowId;
return db.delete(DATABASE_TABLE, where, null) != 0;
}
public Cursor getTotalPrice() {
Cursor c = db.rawQuery("SELECT SUM("+ KEY_PRICE +")from " + DATABASE_TABLE, null);
return c;
}
public void deleteAll() {
Cursor c = getAllRows();
long rowId = c.getColumnIndexOrThrow(KEY_ROWID);
if (c.moveToFirst()) {
do {
deleteRow(c.getLong((int) rowId));
} while (c.moveToNext());
}
c.close();
}
// Return all data in the database.
public Cursor getAllRows() {
String where = null;
Cursor c = db.query(true, DATABASE_TABLE, ALL_KEYS,
where, null, null, null, null, null);
if (c != null) {
c.moveToFirst();
}
return c;
}
// Get a specific row (by rowId)
public Cursor getRow(long rowId) {
String where = KEY_ROWID + "=" + rowId;
Cursor c = db.query(true, DATABASE_TABLE, ALL_KEYS,
where, null, null, null, null, null);
if (c != null) {
c.moveToFirst();
}
return c;
}
// Change an existing row to be equal to new data.
public boolean updateRow(long rowId, String name, int studentNum, String favColour) {
String where = KEY_ROWID + "=" + rowId;
/*
* CHANGE 4:
*/
// TODO: Update data in the row with new fields.
// TODO: Also change the function's arguments to be what you need!
// Create row's data:
ContentValues newValues = new ContentValues();
newValues.put(KEY_NAME, name);
newValues.put(KEY_QUANTITY, studentNum);
newValues.put(KEY_PRICE, favColour);
// Insert it into the database.
return db.update(DATABASE_TABLE, newValues, where, null) != 0;
}
/////////////////////////////////////////////////////////////////////
// Private Helper Classes:
/////////////////////////////////////////////////////////////////////
/**
* Private class which handles database creation and upgrading.
* Used to handle low-level database access.
*/
private static class DatabaseHelper extends SQLiteOpenHelper
{
DatabaseHelper(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
#Override
public void onCreate(SQLiteDatabase _db) {
_db.execSQL(DATABASE_CREATE_SQL);
}
#Override
public void onUpgrade(SQLiteDatabase _db, int oldVersion, int newVersion) {
Log.w(TAG, "Upgrading application's database from version " + oldVersion
+ " to " + newVersion + ", which will destroy all old data!");
// Destroy old database:
_db.execSQL("DROP TABLE IF EXISTS " + DATABASE_TABLE);
// Recreate new database:
onCreate(_db);
}
}
}
Listprice:
import android.app.AlertDialog;
import android.content.DialogInterface;
import android.content.Intent;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.support.v7.app.ActionBarActivity;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.widget.*;
/**
* Created by User on 6/2/2015.
*/
public class Listprice extends ActionBarActivity {
DBAdapter myDb;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.listprice);
openDB();
TextView textView = (TextView) findViewById(R.id.order90);
TextView textView1 = (TextView) findViewById(R.id.quan90);
TextView textView2 = (TextView) findViewById(R.id.price90);
TextView textView3 = (TextView) findViewById(R.id.totalprice);
Bundle extras = getIntent().getExtras();
if (extras != null) {
String newText = extras.getString("firstmessage");
String newText1 = extras.getString("secondmessage");
String newText2 = extras.getString("thirdmessage");
if (newText != null) {
textView.setText(newText);
}
if (newText1 != null) {
textView1.setText(newText1);
}
if (newText2 != null) {
textView2.setText(newText2);
}
}
String num1 = textView.getText().toString().trim();
int num2 = Integer.parseInt(textView1.getText().toString());
int num3 = Integer.parseInt(textView2.getText().toString());
int num4 = num2 * num3;
registerListClickCallBack();
myDb.insertRow(num1, "Quantity = " + num2, ""+num4);
populateListViewFromDB();
Cursor sum=myDb.getTotalPrice();
textView3.setText(""+sum);
}
private void populateListViewFromDB() {
Cursor cursor = myDb.getAllRows();
//Query for the record we just added.
//Use the ID:
startManagingCursor(cursor);
String[] fromFieldNames = new String[]
{DBAdapter.KEY_NAME, DBAdapter.KEY_QUANTITY, DBAdapter.KEY_PRICE};
int[] toViewIDs = new int[]
{R.id.item_name, R.id.quantities, R.id.pricest};
SimpleCursorAdapter myCursorAdapter =
new SimpleCursorAdapter(
this,
R.layout.item_layout,
cursor,
fromFieldNames,
toViewIDs
);
// Set the adapter for the list view
ListView myList = (ListView) findViewById(R.id.listViewFromDB);
myList.setAdapter(myCursorAdapter);
}
private void openDB(){
myDb = new DBAdapter(this);
myDb.open();
}
#Override
protected void onDestroy() {
super.onDestroy();
closeDB();
}
private void closeDB() {
myDb.close();
}
private void registerListClickCallBack() {
ListView myList = (ListView) findViewById(R.id.listViewFromDB);
myList.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View viewClicked,
int position, long idInDB) {
updateItemForId(idInDB);
}
});
}
private void updateItemForId(final long idInDB) {
final Cursor cursor = myDb.getRow(idInDB);
if (cursor.moveToFirst()) {
AlertDialog.Builder alertDialog = new AlertDialog.Builder(Listprice.this);
// Setting Dialog Title
alertDialog.setTitle("Confirm Delete...");
// Setting Dialog Message
alertDialog.setMessage("Are you sure you want delete this?");
// Setting Positive "Yes" Button
alertDialog.setPositiveButton("YES", new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog,int which) {
// Write your code here to invoke YES event
Toast.makeText(getApplicationContext(), "You clicked on YES", Toast.LENGTH_SHORT).show();
myDb.deleteRow(idInDB);
populateListViewFromDB();
}
});
// Setting Negative "NO" Button
alertDialog.setNegativeButton("NO", new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int which) {
// Write your code here to invoke NO event
Toast.makeText(getApplicationContext(), "You clicked on NO", Toast.LENGTH_SHORT).show();
dialog.cancel();
}
});
// Showing Alert Message
alertDialog.show();
}
cursor.close();
populateListViewFromDB();
}
public void clear(View view) {
myDb.deleteAll();
populateListViewFromDB();
}
#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_settings) {
return true;
}
return super.onOptionsItemSelected(item);
}
public void addFood(View view) {
Intent gotofood = new Intent(this, food.class);
startActivity(gotofood);
}
public void addDrinks(View view) {
Intent gotodrinks = new Intent(this, drink.class);
startActivity(gotodrinks);
}
public void gotomainmaenu(View view) {
Intent gotomain = new Intent(this, MainActivity.class);
startActivity(gotomain);
}
}
It sounds like you want the sum of each item's price multiplied by that item's quantity. If so, this should work:
public double getTotalPrice() {
String sql = "select sum(" + KEY_QUANTITY + " * " + KEY_PRICE + ") from "
+ DATABASE_TABLE;
Cursor cursor = db.rawQuery(sql, null);
if (cursor.moveToFirst()) {
return cursor.getDouble(0);
}
return 0;
}

Android: customsearchadapter displays empty results

I'm trying to get my custom search box suggestions to display, but the results I receive are empty. I followed a few guides to implement this feature, namely:
For the contentprovidor: http://www.androidcompetencycenter.com/2009/01/basics-of-android-part-iv-android-content-providers/
To make it work in ABS: https://github.com/JakeWharton/ActionBarSherlock/pull/653/files
This resulted in this code:
Adding the search box:
#Override
public boolean onCreateOptionsMenu(Menu menu) {
getSupportMenuInflater().inflate(R.menu.building_search, menu);
SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
SearchView searchView = new SearchView(getSupportActionBar().getThemedContext());
searchView.setSearchableInfo(searchManager.getSearchableInfo(getComponentName()));
searchView.setSuggestionsAdapter(new BuildingSuggestionsAdapter(this, searchManager.getSearchableInfo(getComponentName()), searchView));
return super.onCreateOptionsMenu(menu);
}
Adding the buildings to my database:
for (Resto resto : restos) {
ContentValues values = new ContentValues();
values.put(TableBuildings.Buildings.NAME, resto.name);
values.put(TableBuildings.Buildings.DISTANCE, "3");
getContentResolver().insert(TableBuildings.Buildings.CONTENT_URI, values);
}
The BuildingSuggestionAdapter:
public class BuildingSuggestionsAdapter extends CursorAdapter {
private static final int QUERY_LIMIT = 50;
private LayoutInflater inflater;
private SearchView searchView;
private SearchableInfo searchable;
public BuildingSuggestionsAdapter(Context context, SearchableInfo info, SearchView searchView) {
super(context, null, CursorAdapter.FLAG_REGISTER_CONTENT_OBSERVER);
this.searchable = info;
this.searchView = searchView;
this.inflater = LayoutInflater.from(context);
}
#Override
public void bindView(View v, Context context, Cursor c) {
String name = c.getString(c.getColumnIndex(TableBuildings.Buildings.NAME));
TextView namet = (TextView) v.findViewById(R.id.resto_search_name);
namet.setText(name);
String man = c.getString(c.getColumnIndex(TableBuildings.Buildings.DISTANCE));
TextView manuf = (TextView) v.findViewById(R.id.resto_search_distance);
manuf.setText(man);
Toast.makeText(context, name + " " + man, Toast.LENGTH_LONG).show();
}
#Override
public View newView(Context arg0, Cursor arg1, ViewGroup arg2) {
return this.inflater.inflate(R.layout.resto_search_suggestion_view, null);
}
/**
* Use the search suggestions provider to obtain a live cursor. This will be called in a worker
* thread, so it's OK if the query is slow (e.g. round trip for suggestions). The results will
* be processed in the UI thread and changeCursor() will be called.
*/
#Override
public Cursor runQueryOnBackgroundThread(CharSequence constraint) {
String query = (constraint == null) ? "" : constraint.toString();
/**
* for in app search we show the progress spinner until the cursor is returned with the
* results.
*/
Cursor cursor = null;
if (searchView.getVisibility() != View.VISIBLE
|| searchView.getWindowVisibility() != View.VISIBLE) {
return null;
}
try {
cursor = getSuggestions(searchable, query, QUERY_LIMIT);
// trigger fill window so the spinner stays up until the results are copied over and
// closer to being ready
if (cursor != null) {
cursor.getCount();
return cursor;
}
} catch (RuntimeException e) {
}
// If cursor is null or an exception was thrown, stop the spinner and return null.
// changeCursor doesn't get called if cursor is null
return null;
}
public Cursor getSuggestions(SearchableInfo searchable, String query, int limit) {
if (searchable == null) {
return null;
}
String authority = searchable.getSuggestAuthority();
if (authority == null) {
return null;
}
Uri.Builder uriBuilder = new Uri.Builder()
.scheme(ContentResolver.SCHEME_CONTENT)
.authority(authority)
.query("")
.fragment("");
// if content path provided, insert it now
final String contentPath = searchable.getSuggestPath();
if (contentPath != null) {
uriBuilder.appendEncodedPath(contentPath);
}
// append standard suggestion query path
uriBuilder.appendPath(SearchManager.SUGGEST_URI_PATH_QUERY);
// get the query selection, may be null
String selection = searchable.getSuggestSelection();
// inject query, either as selection args or inline
String[] selArgs = null;
if (selection != null) { // use selection if provided
selArgs = new String[]{query};
} else { // no selection, use REST pattern
uriBuilder.appendPath(query);
}
if (limit > 0) {
uriBuilder.appendQueryParameter("limit", String.valueOf(limit));
}
Uri uri = uriBuilder.build();
// finally, make the query
return mContext.getContentResolver().query(uri, null, selection, selArgs, null);
}
}
The providor:
public class BuildingSuggestionProvider extends ContentProvider {
private SQLiteDatabase sqlDB;
private DatabaseHelper dbHelper;
private static final String DATABASE_NAME = "Buildings.db";
private static final int DATABASE_VERSION = 1;
private static final String TABLE_NAME = "Buildings";
private static class DatabaseHelper extends SQLiteOpenHelper {
DatabaseHelper(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
#Override
public void onCreate(SQLiteDatabase db) {
//create table to store user names
db.execSQL("Create table " + TABLE_NAME + "( _id INTEGER PRIMARY KEY AUTOINCREMENT, NAME TEXT, DISTANCE TEXT);");
}
#Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
db.execSQL("DROP TABLE IF EXISTS " + TABLE_NAME);
onCreate(db);
}
}
#Override
public int delete(Uri uri, String s, String[] as) {
return 0;
}
#Override
public String getType(Uri uri) {
return null;
}
#Override
public Uri insert(Uri uri, ContentValues contentvalues) {
// get database to insert records
sqlDB = dbHelper.getWritableDatabase();
// insert record in user table and get the row number of recently inserted record
long rowId = sqlDB.insert(TABLE_NAME, "", contentvalues);
if (rowId > 0) {
Uri rowUri = ContentUris.appendId(TableBuildings.Buildings.CONTENT_URI.buildUpon(), rowId).build();
getContext().getContentResolver().notifyChange(rowUri, null);
return rowUri;
}
throw new SQLException("Failed to insert row into " + uri);
}
#Override
public boolean onCreate() {
dbHelper = new DatabaseHelper(getContext());
return (dbHelper == null) ? false : true;
}
#Override
public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs, String sortOrder) {
SQLiteQueryBuilder qb = new SQLiteQueryBuilder();
SQLiteDatabase db = dbHelper.getReadableDatabase();
qb.setTables(TABLE_NAME);
Cursor c = qb.query(db, projection, selection, null, null, null, sortOrder);
c.setNotificationUri(getContext().getContentResolver(), uri);
return c;
}
#Override
public int update(Uri uri, ContentValues contentvalues, String s, String[] as) {
return 0;
}
}
The tablebuildings:
import android.net.Uri;
import android.provider.BaseColumns;
public class TableBuildings {
public static final String AUTHORITY = "be.ugent.zeus.hydra.ui.map.suggestions.BuildingSuggestionProvider";
// BaseColumn contains _id.
public static final class Buildings implements BaseColumns {
public static final Uri CONTENT_URI = Uri.parse("content://be.ugent.zeus.hydra.ui.map.suggestions.BuildingSuggestionProvider");
// Table column
public static final String NAME = "NAME";
public static final String DISTANCE = "DISTANCE";
}
}
And finally the XML used to define the search box, followed by the xml used for the providor in my application:
<?xml version="1.0" encoding="UTF-8"?>
<searchable xmlns:android="http://schemas.android.com/apk/res/android"
android:label="#string/resto_search_label"
android:hint="#string/resto_search_hint"
android:searchSuggestAuthority="be.ugent.zeus.hydra.ui.map.suggestions.BuildingSuggestionProvider" />
<provider
android:name=".ui.map.suggestions.BuildingSuggestionProvider"
android:authorities="be.ugent.zeus.hydra.ui.map.suggestions.BuildingSuggestionProvider" />
The results I got where the following:
No errors; it opens up the searchview and queries the contentprovider. The weird part is that the query methods in the Provider gets called, but it doesn't get called from the adapter, as in, when I put a breakpoint, my program doesn't stop.
Visually, my keyboard pops up and I see a list, but the list only contains empty items...
Does anyone have any idea?
Thanks in advance.
I know this is late, but I faced the same issue and have solved it with the use of the Constants provided by the SearchManager class as column names in my database.
See a tutorial on search on the Android developers site.
The SUGGEST_COLUMN_TEXT_1 is what you need specifically. This is the primary text the ContentProvider needs to show in the resulting ListView and what it will search through.

Categories

Resources