Now this might be a difficult to understand problem.
What I actually wanted : To get a populated list of distinct callers from call log, let user select as manny he wants and then blacklist them by tapping on a button.
Thus I concluded that what I wanted is following
Concluded What I wanted : To have an activity with a header button and a list of items. From the list of items, user can select any number of the items(implemented this by using checkboxes, will show how I did it later) and then perform an action by selecting header button.
What I did : The activity layout:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" >
<LinearLayout android:id="#+id/add_btn_layout" android:layout_width="match_parent" android:layout_height="50dp" android:padding="2dp" >
<Button android:id="#+id/btn_blacklist_sender" android:layout_width="match_parent" android:layout_height="wrap_content" android:textSize="21dp" >
</Button>
</LinearLayout>
<ListView android:id="#+id/list_chose_to_blacklist" android:layout_width="wrap_content" android:layout_height="wrap_content" >
</ListView>
</LinearLayout>
The row layout :
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="horizontal" android:padding="2dp" >
<CheckBox android:id="#+id/isDelete" android:layout_width="wrap_content" android:layout_height="wrap_content" android:paddingLeft="43dp" android:paddingRight="3dp" />
</LinearLayout>
In the activity:
public class CallerChooseToBlacklistActivity extends Activity {
Button btnBlacklistCaller;
ListView listCallers;
HashSet<String> toBlacklistNumbers = new HashSet<String>();
String caller = "Sender";
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_chose_to_blacklist);
btnBlacklistCaller = (Button) findViewById(R.id.btn_blacklist_sender);
btnBlacklistCaller.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
BlacklistNumberHelper helper = new BlacklistNumberHelper(
getApplicationContext());
for (String number : toBlacklistNumbers) {
helper.insert(number, DbHelper.TABLE_CALL_BLACKLIST,
DbHelper.C_CALL_BLACKLIST_NO);
}
helper.close();
onResume();
}
});
btnBlacklistCaller.setText(getString(R.string.btn_blacklist_caller));
listCallers = (ListView) findViewById(R.id.list_chose_to_blacklist);
}
#Override
protected void onResume() {
super.onResume();
String[] projection = new String[] { CallLog.Calls._ID,
CallLog.Calls.NUMBER };
Cursor cursor = getContentResolver().query(CallLog.Calls.CONTENT_URI,
projection, null, null, null);
for (int idx = 0; idx < cursor.getColumnCount(); idx++) {
Log.d(MainActivity.TAG, idx + ":" + cursor.getColumnName(idx));
}
HashSet<String> distinctCallers = new HashSet<String>();
ArrayList<String> allreadyBlacklisted = (new BlacklistNumberHelper(
getApplicationContext())).getAllNumbers(
DbHelper.TABLE_CALL_BLACKLIST, DbHelper.C_CALL_BLACKLIST_NO);
if (cursor.moveToFirst()) {
for (int i = 0; i < cursor.getCount(); i++) {
try {
String address = cursor.getString(
cursor.getColumnIndexOrThrow("number")).toString();
boolean isPresent = false;
for (String no : allreadyBlacklisted)
if (no.equalsIgnoreCase(address)) {
isPresent = true;
break;
}
if (!isPresent)
distinctCallers.add(address);
cursor.moveToNext();
} catch (IllegalArgumentException e) {
}
}
}
ArrayList<HashMap<String, String>> fillMaps = new ArrayList<HashMap<String, String>>();
for (String address : distinctCallers) {
HashMap<String, String> map = new HashMap<String, String>();
map.put(caller, address);
fillMaps.add(map);
}
String[] from = { caller };
int[] to = { R.id.isDelete };
SimpleAdapter cursorAdapter = new SimpleAdapter(this, fillMaps,
R.layout.row_blacklist, from, to);
cursorAdapter.setViewBinder(VIEW_BINDER);
listCallers.setAdapter(cursorAdapter);
}
// custom binder to bind columns customally
final ViewBinder VIEW_BINDER = new ViewBinder() {
public boolean setViewValue(View view, Object arg1, String arg2) {
if (view.getId() == R.id.isDelete) {
CheckBox cb = (CheckBox) view;
cb.setText(arg2);
cb.setOnCheckedChangeListener(new OnCheckedChangeListener() {
public void onCheckedChanged(CompoundButton buttonView,
boolean isChecked) {
String text = buttonView.getText().toString();
if (isChecked)
toBlacklistNumbers.add(text);
else if (toBlacklistNumbers.contains(text))
toBlacklistNumbers.remove(text);
}
});
return true;
} else {
return false;
}
}
};
}
What the problem is : When I select an item and scroll down and come back by scrolling up the selected item check on the selected item gets changed. Although when I look at the hashset toBlacklistNumbers the number I originally selected is there only. That means when I tap on the header button it does blacklist it. To remove it from the hashset I have to select it first, then unselect it. But this is not what I want.
I dont want the item to get unselected when I scroll down the list. This is obviously not the problem with the android version as I have checked it on Android 2.2 and Android 4.1
Update : By selected item getting changed, I meant that the item I selected is not selected any more, instead any item above it or below it is selected. Also, When I scroll down, many items in the list below are also selected automatically
You aren't handling the recycling right, you aren't setting the status of the CheckBox based on the data in toBlacklistNumbers:
#Override
public boolean setViewValue(View view, Object arg1, String arg2) {
if (view.getId() == R.id.isDelete) {
CheckBox cb = (CheckBox) view;
cb.setText(arg2);
String data = (String) arg1;
if (toBlacklistNumbers.contains(data)) {
cb.setChecked(true);
} else {
cb.setChecked(false);
}
cb.setOnCheckedChangeListener(mListener);
return true;
} else {
return false;
}
}
where mListener is a single OnCheckedChangeListener so you don't create each time one when the user scrolls:
private OnCheckedChangeListener mListener = new OnCheckedChangeListener() {
#Override
public void onCheckedChanged(CompoundButton buttonView,
boolean isChecked) {
String text = buttonView.getText().toString();
if (isChecked)
toBlacklistNumbers.add(text);
else if (toBlacklistNumbers.contains(text))
toBlacklistNumbers.remove(text);
}
};
Also, don't call the onResume method yourself, that is a lifecycle method to be called only by the system.
Related
For my Android project, I have a listview which has a checkbox for every item. The data is loaded from an SQLite database by using a CursorAdapter class. However, whenever I scroll, the checkbox positions will get moved and get carried down to the next part of the listview. How can I fix this problem?
GIF of my CheckBox Problem
Here's my Cursor Adapter Class:
public class VocabCursorAdapter extends CursorAdapter {
private static final int DIFFICULT = 0;
private static final int FAMILIAR = 1;
private static final int EASY = 2;
private static final int PERFECT = 3;
public VocabCursorAdapter(Context context, Cursor c, int flags) {
super(context, c, 0);
}
#Override
public View newView(Context context, Cursor cursor, ViewGroup parent) {
return LayoutInflater.from(context).inflate(R.layout.item_vocab, parent, false);
}
#Override
public void bindView(View view, Context context, Cursor cursor) {
// Find fields to populate in inflated template
TextView tvVocabName = (TextView) view.findViewById(R.id.vocabName);
TextView tvVocabDefinition = (TextView) view.findViewById(R.id.vocabDefinition);
ImageView tvVocabLevel = (ImageView) view.findViewById(R.id.vocabLevel);
// Extract properties from cursor
String vocab = cursor.getString(cursor.getColumnIndexOrThrow(VocabDbContract.COLUMN_NAME_VOCAB));
String definition = cursor.getString(cursor.getColumnIndexOrThrow(VocabDbContract.COLUMN_NAME_DEFINITION));
int level = cursor.getInt(cursor.getColumnIndexOrThrow(VocabDbContract.COLUMN_NAME_LEVEL));
// Populate fields with extracted properties
tvVocabName.setText(vocab);
tvVocabDefinition.setText(definition);
if (level == DIFFICULT) {
tvVocabLevel.setImageResource(R.drawable.level_bars_difficult);
tvVocabLevel.setTag(DIFFICULT);
}
else if (level == FAMILIAR) {
tvVocabLevel.setImageResource(R.drawable.level_bars_familiar);
tvVocabLevel.setTag(FAMILIAR);
}
else if (level == EASY) {
tvVocabLevel.setImageResource(R.drawable.level_bars_easy);
tvVocabLevel.setTag(EASY);
}
else if (level == PERFECT) {
tvVocabLevel.setImageResource(R.drawable.level_bars_perfect);
tvVocabLevel.setTag(PERFECT);
}
}
And here's my list item xml, item_vocab.xml:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:longClickable="true">
<ImageView
android:layout_width="36sp"
android:layout_height="36sp"
android:id="#+id/vocabLevel"
android:layout_gravity="right"
android:src="#drawable/level_bars"
android:scaleType="fitXY"
android:contentDescription="#string/vocab_level"
android:layout_centerVertical="true"
android:layout_toLeftOf="#+id/editCheckbox"
android:layout_toStartOf="#+id/editCheckbox"/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textAppearance="?android:attr/textAppearanceLarge"
android:text="Large Text"
android:id="#+id/vocabName"
android:layout_alignParentTop="true"
android:layout_alignParentLeft="true"
android:layout_alignParentStart="true"
android:layout_toLeftOf="#+id/vocabLevel"
android:layout_toStartOf="#+id/vocabLevel"/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textAppearance="?android:attr/textAppearanceSmall"
android:text="Small Text"
android:id="#+id/vocabDefinition"
android:layout_alignParentLeft="true"
android:layout_alignParentStart="true"
android:layout_toLeftOf="#+id/vocabLevel"
android:layout_toStartOf="#+id/vocabLevel"
android:layout_below="#id/vocabName"/>
<CheckBox
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/editCheckbox"
android:layout_centerVertical="true"
android:layout_alignParentRight="true"
android:layout_alignParentEnd="true"/>
</RelativeLayout>
And here's my xml which contains a listview
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".controller.MyVocab"
android:paddingLeft="5dp">
<ListView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:id="#+id/mVocabList"
android:layout_alignParentTop="true"
android:layout_alignParentLeft="true"
android:layout_alignParentStart="true"/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="#string/empty_text_view"
android:id="#android:id/empty"
android:layout_alignParentTop="true"
android:layout_alignParentLeft="true"
android:layout_alignParentStart="true"/>
</RelativeLayout>
I have looked at a lot of different solutions on StackOverflow, but I wasn't able to successfully do it in my own app. For an example, this post has a similar problem, but its solution used getView and I had trouble understanding how to implement it with newView and bindView instead.
And some other solutions might be examples where a cursoradapter is not involved. Any help is much appreciated, thanks a lot!
Edit #1: After incorporating Phan's changes, the checkbox states get resets to false rather than keeping its states when I scroll the listview (See ).
Reason : ListView re-uses the views.
Solution :
class VocabCursorAdapter extends CursorAdapter {
List<Integer> selectedItemsPositions;//to store all selected items position
public VocabCursorAdapter(Context context, Cursor c,int flags) {
super(context, c,0);
selectedItemsPositions = new ArrayList<>();
}
#Override
public View newView(Context context, Cursor cursor, ViewGroup viewGroup) {
View view = LayoutInflater.from(context).inflate(R.layout.item_vocab, viewGroup, false);
CheckBox box = (CheckBox) view.findViewById(R.id.editCheckbox);
box.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
#Override
public void onCheckedChanged(CompoundButton compoundButton, boolean b) {
int position = (int) compoundButton.getTag();
if (b) {
//check whether its already selected or not
if (!selectedItemsPositions.contains(position))
selectedItemsPositions.add(position);
} else {
//remove position if unchecked checked item
selectedItemsPositions.remove((Object) position);
}
}
});
return view;
}
#Override
public void bindView(View view, Context context, Cursor cursor) {
//your other stuff
CheckBox box = (CheckBox) view.findViewById(R.id.editCheckbox);
box.setTag(cursor.getPosition());
if (selectedItemsPositions.contains(cursor.getPosition()))
box.setChecked(true);
else
box.setChecked(false);
}
}
Try this
public class VocabCursorAdapter extends CursorAdapter {
private ArrayList<Boolean> itemChecked = new ArrayList<Boolean>(); // array list for store state of each checkbox
public VocabCursorAdapter(Context context, Cursor c, int flags) {
for (int i = 0; i < c.getCount(); i++) { // c.getCount() return total number of your Cursor
itemChecked.add(i, false); // initializes all items value with false
}
}
#Override
public void bindView(View view, Context context, Cursor cursor) {
...
final int position = cursor.getPosition(); // get position by cursor
CheckBox checkBox = (CheckBox) view.findViewById(R.id.editCheckbox);
checkBox.setOnClickListener(new OnClickListener() {
public void onClick(View v) {
if (itemChecked.get(position) == true) { // if current checkbox is checked, when you click -> change it to false
itemChecked.set(position, false);
} else {
itemChecked.set(position, true);
}
}
});
checkBox.setChecked(itemChecked.get(position)); // set the checkbox state base on arraylist object state
Log.i("In VocabCursorAdapter","position: "+position+" - checkbox state: "+itemChecked.get(position));
}
}
public class ObservationselectattributeFragment extends Fragment {
DatabaseHandler mDBHandler;
ListView mListView;
SimpleCursorAdapter mSCA;
Cursor mCsr;
ArrayList<String> attributeItems = new ArrayList<>();
public ObservationselectattributeFragment() {
// Required empty public constructor
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// Inflate the layout for this fragment
View view1=inflater.inflate(R.layout.fragment_observationselectattribute, container, false);
//Bundle bundle2 = getArguments();
Bundle bundle1 = getArguments();
final int firsttext= bundle1.getInt("TotalCount");
final String selectedtreatment= bundle1.getString("SelectedTreatment");
Toast.makeText(getActivity(),"value \n"+firsttext+"\n"+"treatment \n"+selectedtreatment, Toast.LENGTH_SHORT).show();
// Toast.makeText(getActivity(),"SelectedTreatment \n"+selectedtreatment, Toast.LENGTH_SHORT).show();
mListView = (ListView)view1.findViewById(R.id.lv001);
mListView.setChoiceMode(ListView.CHOICE_MODE_MULTIPLE);
Button addattribute = (Button)view1.findViewById(R.id.addattribute);
addattribute.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
String items1="";
Integer tcount1=0;
for(String item1:attributeItems){
items1+="-"+item1+"\n";
tcount1++;
}
Toast.makeText(getActivity(),"you have selected \n"+items1,Toast.LENGTH_LONG).show();
Toast.makeText(getActivity(),"you have selected \n"+tcount1,Toast.LENGTH_LONG).show();
/*FragmentTransaction fr= getFragmentManager().beginTransaction();
fr.replace(R.id.main_container, new ShowObservationDataRecordingFragment()).addToBackStack("ObservationselectattributeFragment");
fr.commit();*/
Bundle bundle = new Bundle();
bundle.putInt("TotalCount2",firsttext);
bundle.putInt("TotalCount1", tcount1);
bundle.putString("SelectedTreatment", selectedtreatment);
Fragment showobservationdatarecordingfragment = new ShowObservationDataRecordingFragment();
showobservationdatarecordingfragment.setArguments(bundle);
FragmentManager fragmentManager = getFragmentManager();
fragmentManager.beginTransaction().replace(R.id.main_container, showobservationdatarecordingfragment).addToBackStack("ObservationselectattributeFragment").commit();
}
});
mDBHandler = new DatabaseHandler(this.getActivity());
mCsr = mDBHandler.getAllRecords();
// Prepare a list of the columns to get the data from, for the ListViewt
String[] columns_to_get_data_from = new String[]{
DatabaseHandler.KEY_IDS,
DatabaseHandler.KEY_NAMES,
DatabaseHandler.KEY_FNAME,
DatabaseHandler.KEY_MONAME,
DatabaseHandler.KEY_SNAME
};
// Prepare a list of the Views into which to place the data
int[] itemviews_to_place_data_in = new int[]{
R.id.euserid,
R.id.eusername,
R.id.efname,
R.id.emoname,
R.id.esname
};
// get and instance of SimpleCursorAdapter
mSCA = new SimpleCursorAdapter(getActivity(),
R.layout.listviewitem_record,
mCsr,
columns_to_get_data_from,
itemviews_to_place_data_in,
0);
// Save the ListView state (= includes scroll position) as a Parceble
Parcelable state = mListView.onSaveInstanceState();
// get and instance of SimpleCursorAdapter the listviewitem_record layout
mListView.setAdapter(mSCA);
// Restore previous state (including selected item index and scroll position)
mListView.onRestoreInstanceState(state);
mListView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
String attributeItem1 = ((TextView)view.findViewById(R.id.euserid)).getText().toString();
String attributeItem2 = ((TextView)view.findViewById(R.id.eusername)).getText().toString();
String attributeItem3 = ((TextView)view.findViewById(R.id.efname)).getText().toString();
String attributeItem4 = ((TextView)view.findViewById(R.id.emoname)).getText().toString();
String attributeItem5 = ((TextView)view.findViewById(R.id.esname)).getText().toString();
String attributeItem = attributeItem1 + attributeItem2 + attributeItem3 + attributeItem4 + attributeItem5;
// CheckedTextView box = (CheckedTextView) view.findViewById(R.id.record_checkbox);
// box.setChecked(true);
CheckedTextView checkedTextView = (CheckedTextView) view.findViewById(R.id.record_checkbox);
if(checkedTextView.isChecked()) {
checkedTextView.setChecked(false);
} else {
checkedTextView.setChecked(true);
}
if(attributeItems.contains(attributeItem)){
attributeItems.remove(attributeItem);//uncheck item
}
else
{
attributeItems.add(attributeItem);
}
Toast.makeText(getActivity(), "Item1 = " + attributeItem1 +"\n"+ "Item2 ="+attributeItem2 +"\n"+"Item3 ="+attributeItem3+"\n"+"Item4 ="+attributeItem4+"\n"+"Item5 ="+attributeItem5, Toast.LENGTH_SHORT).show();
}
});
((HomeActivity) getActivity())
.setActionBarTitle("Select Attribute");
return view1;
}
}
How do you add multiple adapters to a listview? After reading this question and following the tutorial, I still don't have what I want.
Scenario
Adding two types of text into an SQLite database table and retrieving them on another activity in the form of a card with a title on top, a separator, and the content underneath.
Visuals
Adding content to main list:
Card on main list:
My Code
I take it no one really needs to see the layout for the edittext part so I'll jump right to the main card row item layout:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="16dp"
android:background="#drawable/card_selecter_background">
<TextView
android:id="#+id/tvTitle"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Sample"
android:textSize="30sp"/>
<View
android:id="#+id/separator"
android:layout_marginTop="5dp"
android:layout_marginBottom="2dp"
android:layout_width="fill_parent"
android:layout_height="1dp"
android:background="#android:color/darker_gray"/>
<TextView
android:id="#+id/tvContent"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Sample"
android:textSize="22sp"/>
</LinearLayout>
This is where I add the edittext strings to the database:
db.execSQL("CREATE TABLE IF NOT EXISTS Lists (Title VARCHAR, Content VARCHAR);");
addListBtn.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
boolean cancel = false;
String listName = listNameET.getText().toString();
String content = contentET.getText().toString();
if (TextUtils.isEmpty(listName)) {
listNameET.setError("Please enter a list name.");
cancel = true;
} else if (listName.contains("'") || listName.contains("\"")) {
listNameET.setError("Please enter alphanumeric (abc123) characters only.");
cancel = true;
}
if (TextUtils.isEmpty(content)) {
contentET.setError("Field cannot be left blank.");
cancel = true;
} else if (content.contains("'") || content.contains("\"")) {
contentET.setError("Please enter alphanumeric (abc123) characters only.");
cancel = true;
}
if (cancel) {
//Nothing happens
} else {
db.execSQL("INSERT INTO Lists VALUES('" + listName + "', '" + content + "');");
db.close();
finish();
}
}
});
Here is where it is retrieved in the listview activity:
Cursor c = db.rawQuery("SELECT Title from Lists", null);
Cursor c2 = db.rawQuery("SELECT Content from Lists", null);
final ArrayList<String> titleList = new ArrayList<String>();
final ArrayList<String> contentList = new ArrayList<String>();
if (c.moveToFirst() && c2.moveToFirst()) {
do {
titleList.add(c.getString(c.getColumnIndex("Title")));
contentList.add(c2.getString(c2.getColumnIndex("Content")));
} while (c.moveToNext() && c2.moveToNext());
}
ArrayAdapter<String> titleAdapter = new ArrayAdapter<String>(MainActivity.this, R.layout.listname_row, R.id.tvTitle, titleList);
ArrayAdapter<String> contentAdapter = new ArrayAdapter<String>(MainActivity.this, R.layout.listname_row, R.id.tvContent, contentList);
ListView lv = (ListView) findViewById(R.id.listOfNames);
//Since Java works top to bottom, the contentAdapter is set even though
//this line is here.
lv.setAdapter(titleAdapter);
lv.setAdapter(contentAdapter);
db.close();
c.close();
I need to be able to attach the title and the content to the same listview.
Help is much appreciated!
You can create a custom Adapter like this:
class ExampleAdapter extends BaseAdapter{
List<String> mTitles;
List<String> mContents;
#Override
public int getCount() {
return mTitles.size();
}
#Override
public Object getItem(int position) {
return null;
}
#Override
public long getItemId(int position) {
return 0;
}
#Override
public View getView(int position, View convertView, ViewGroup parent) {
View v;
//inflate view if needed
...
TextView tv_title;
TextView tv_content;
String title = mTitles.get(position);
String content = mContents.get(position);
tv_title.setText(title);
tv_content.setText(content);
return v;
}
}
Now past 2 list of String to this Adapter and call setAdapter of ListView.
I've been having a lot of trouble with this problem. I have a listview that contains:
ImageView / contactName / TextView / CheckBox
The contactName in the listview is populated by reading the contacts on the phone from a SimpleCursorAdapter. All for elements show when the app runs, but the problem I'm having is connecting the checkboxes to their corresponding item in the list.
Through some research, I found that I must use a getView() to link the checkboxes with the items in the list, but through practice, I can't seem to get it to work right. Furthermore, none of the examples I've tried really explained how to apply getView(). The most full example I've been working from is from here:
http://androidcocktail.blogspot.com/2012/04/adding-checkboxes-to-custom-listview-in.html
The twist is that this reads and populates my listview with my contacts:
private void populateContactList() {
// Build adapter with contact entries
Cursor cursor = getContacts();
String[] fields = new String[] {
ContactsContract.Data.DISPLAY_NAME
};
SimpleCursorAdapter adapter = new SimpleCursorAdapter(this, R.layout.contact_entry, cursor,
fields, new int[] {R.id.contactEntryText});
lv.setAdapter(adapter);
} // END POPULATECONTACTLIST
private Cursor getContacts()
{
// Run query
Uri uri = ContactsContract.Contacts.CONTENT_URI;
String[] projection = new String[] {
ContactsContract.Contacts._ID,
ContactsContract.Contacts.DISPLAY_NAME
};
String selection = ContactsContract.Contacts.IN_VISIBLE_GROUP + " = '" +
(chkboxAllVisible ? "0" : "1") + "'";
String[] selectionArgs = null;
String sortOrder = ContactsContract.Contacts.DISPLAY_NAME + " COLLATE LOCALIZED ASC";
return managedQuery(uri, projection, selection, selectionArgs, sortOrder);
} // END GETCONTACTS
How do I link each checkbox to the a corresponding contact items in my listview?
Ok i have created a test project for you try to understand code if any problem you are having then ask I will try to help you...
HERE IS MY ONCREATE FUNCTION OF ACTIVITY.
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
ArrayList<String> elements = new ArrayList<String>();
for (int i = 0; i < 10; i++) {
elements.add("elements " + i);
}
CheckBox master_cb = new CheckBox(getApplicationContext());
master_cb.setText("Check All");
//HERE IS THE LIST VIEW WHICH I HAVE CREATED IN MY XML FILE.
ListView lv = (ListView) findViewById(R.id.listView1);
//HERE I AM CREATING CUSTOM ADAPTER OBJECT.
my_custom_adapter adapter = new my_custom_adapter(this, android.R.layout.simple_list_item_1, elements);
lv.addHeaderView(master_cb);
lv.setAdapter(adapter);
master_cb.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
#Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
Intent my_intent = new Intent("master_check_change");
my_intent.putExtra("check_value", isChecked);
sendBroadcast(my_intent);
}
});
}
HERE IS MY CUSTOM ADAPTER.
public class my_custom_adapter extends ArrayAdapter<String> {
private Context context = null;
ArrayList<String> elements = null;
private ArrayList<Boolean> itemChecked = null;
public my_custom_adapter(Context context, int type, ArrayList<String> elements)
{
super(context, type, elements);
this.elements = elements;
this.context = context;
itemChecked = new ArrayList<Boolean>();
BroadcastReceiver receiver = new BroadcastReceiver() {
#Override
public void onReceive(Context context, Intent intent) {
if (intent.getAction().equals("master_check_change")) {
boolean check_value = intent.getBooleanExtra("check_value", false);
set_checked(check_value);
notifyDataSetChanged();
}
}
};
context.registerReceiver(receiver, new IntentFilter("master_check_change"));
set_checked(false);
}
// AS EVERY TIME LISTVIEW INFLATE YOUR VIEWS WHEN YOU MOVE THEM SO YOU NEED TO SAVE ALL OF YOUR CHECKBOX STATES IN SOME ARRAYLIST OTHERWISE IT WILL SET ANY DEFAULT VALUE.
private void set_checked(boolean is_checked)
{
for (int i=0; i < elements.size(); i++) {
itemChecked.add(i, is_checked);
}
}
//THIS IS SIMPLY A CLASS VIEW WILL HOLD DIFFERENT VIEWS OF YOUR ROW.
static class ViewHolder
{
public TextView tv;
public CheckBox cb;
public ImageView iv;
}
#Override
public View getView (final int position, View convertView, ViewGroup parent)
{
View rowView = convertView;
ViewHolder holder = null;
if (rowView == null) {
LayoutInflater inflater = (LayoutInflater)context.getSystemService(
Context.LAYOUT_INFLATER_SERVICE);
// HERE I AM INFLATING LISTVIEW LAYOUT.
rowView = inflater.inflate(R.layout.inflated_layout, null, false);
holder = new ViewHolder();
holder.cb = (CheckBox) rowView.findViewById(R.id.checkBox1);
holder.tv = (TextView) rowView.findViewById(R.id.textView1);
holder.iv = (ImageView) rowView.findViewById(R.id.imageView1);
rowView.setTag(holder);
} else {
holder = (ViewHolder) rowView.getTag();
}
if (holder != null) {
holder.tv.setText(elements.get(position));
holder.cb.setOnCheckedChangeListener(new OnCheckedChangeListener() {
#Override
public void onCheckedChanged(CompoundButton buttonView,
boolean isChecked) {
itemChecked.set(position, isChecked);
}
});
if(position < itemChecked.size()) {
holder.cb.setChecked(itemChecked.get(position));
}
}
return rowView;
}
}
main.xml file is this:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/RelativeLayout1"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical" >
<ListView
android:id="#+id/listView1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentLeft="true"
android:layout_alignParentTop="true" >
</ListView>
</RelativeLayout>
inflated_layout code is :
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/RelativeLayout1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical" >
<CheckBox
android:id="#+id/checkBox1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_alignParentTop="true"
android:layout_marginRight="17dp" />
<TextView
android:id="#+id/textView1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerVertical="true"
android:layout_toLeftOf="#+id/checkBox1"
android:layout_toRightOf="#+id/imageView1"
android:singleLine="true"
android:text="Large Text"
android:textAppearance="?android:attr/textAppearanceLarge" />
<ImageView
android:id="#+id/imageView1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerVertical="true"
android:src="#drawable/ic_launcher" />
</RelativeLayout>
if you want to use string array instead of arraylist then replace
String[] elements = new String[10];
for (int i = 0; i < 10; i++) {
elements[i] = "elements " + i;
}
// IN YOUR CUSTOM ADAPTER CUNSTRUCTOR
public my_custom_adapter(Context context, int type, String[] elements)
and some more changes accordingly
SimpleCursorAdapter adapter = new SimpleCursorAdapter(this, R.layout.contact_entry, cursor,
fields, new int[] {R.id.contactEntryText});
See in this particular code you are only mapping text source (in field ) with actual textView (R.id.contactEntryText)... So similarly you need to add... another field and corresponding view to map for Checkbox.
or better make a CustomAdapter, you can find tutorials on that and override getView method,you get maximum flexibility.You can do whatever you want to do.
This might help: http://windrealm.org/tutorials/android/listview-with-checkboxes-without-listactivity.php
don,t go with custom list view you can use default listview having the facility of check boxes but only one with each list item read listview on android developer site for list view property. listview having checkbox you just need to set multiselection list view
Edit 1:
follow the link : click here
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setListAdapter(new ArrayAdapter<String>(this,
android.R.layout.simple_list_item_multiple_choice, GENRES));
final ListView listView = getListView();
listView.setItemsCanFocus(false);
listView.setChoiceMode(ListView.CHOICE_MODE_MULTIPLE);
}
After reading and try'n'error for days, I´m giving up and ask for help.
< edit >
I am using ActionBarSherlock.
< /edit >
What I want to achieve:
A ListView with a custom layout for each row, where the user can select multiple list items.
A selected list item should have a different background color. When there is at least one item selected, a contextual action bar (CAB) should be shown.
It should look more or less like the multiple selection of emails in the GMail app. The only difference is that in the gmail app the selection is done by clicking the checkbox of a row, whereas I don´t want to have a checkbox, but a row should be selected no matter, where the user clicks.
What I tried:
Following this tutorial, using a Checkable row layout with some logic to change the background color when the check state was toggled, I got everything working except that I could not register a click listener like OnItemClickListener on the ListView to show the CAB. Neither providing a click listener for each row View helped because this prevented to change the background color of the selected items.
I also tried adding a MultiChoiceModeListener to the ListView like that
listView.setChoiceMode(ListView.CHOICE_MODE_MULTIPLE_MODAL);
listView.setMultiChoiceModeListener(new MultiChoiceModeListener() { //.. });
With the same result, no background color change.
What I am looking for: A hint or a tutorial or sample code how to do this. If you need some code snippets to help, let me know.
See if the code helps you(it's basically a ListActivity with a custom adapter to hold the status of checked items(+ different background)):
public class CABSelection extends ListActivity {
private ArrayList<String> mItems = new ArrayList<String>();
private SelectionAdapter mAdapter;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
for (int i = 0; i < 24; i++) {
mItems.add("Name" + i);
}
// R.layout.adapters_cabselection_row is a LinearLayout(with green
// background(#99cc00)) that wraps an ImageView and a TextView
mAdapter = new SelectionAdapter(this,
R.layout.adapters_cabselection_row, R.id.the_text, mItems);
setListAdapter(mAdapter);
getListView().setChoiceMode(ListView.CHOICE_MODE_MULTIPLE_MODAL);
getListView().setMultiChoiceModeListener(new MultiChoiceModeListener() {
private int nr = 0;
#Override
public boolean onCreateActionMode(ActionMode mode, Menu menu) {
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.cabselection_menu, menu);
return true;
}
#Override
public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
return false;
}
#Override
public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
StringBuilder sb = new StringBuilder();
Set<Integer> positions = mAdapter.getCurrentCheckedPosition();
for (Integer pos : positions) {
sb.append(" " + pos + ",");
}
switch (item.getItemId()) {
case R.id.edit_entry:
Toast.makeText(CABSelection.this, "Edited entries: " + sb.toString(),
Toast.LENGTH_SHORT).show();
break;
case R.id.delete_entry:
Toast.makeText(CABSelection.this, "Deleted entries : " + sb.toString(),
Toast.LENGTH_SHORT).show();
break;
case R.id.finish_it:
nr = 0;
mAdapter.clearSelection();
Toast.makeText(CABSelection.this, "Finish the CAB!",
Toast.LENGTH_SHORT).show();
mode.finish();
}
return false;
}
#Override
public void onDestroyActionMode(ActionMode mode) {
nr = 0;
mAdapter.clearSelection();
}
#Override
public void onItemCheckedStateChanged(ActionMode mode,
int position, long id, boolean checked) {
if (checked) {
nr++;
mAdapter.setNewSelection(position, checked);
} else {
nr--;
mAdapter.removeSelection(position);
}
mode.setTitle(nr + " rows selected!");
}
});
}
#Override
protected void onListItemClick(ListView l, View v, int position, long id) {
l.setItemChecked(position, !mAdapter.isPositionChecked(position));
}
private class SelectionAdapter extends ArrayAdapter<String> {
private HashMap<Integer, Boolean> mSelection = new HashMap<Integer, Boolean>();
public SelectionAdapter(Context context, int resource,
int textViewResourceId, List<String> objects) {
super(context, resource, textViewResourceId, objects);
}
public void setNewSelection(int position, boolean value) {
mSelection.put(position, value);
notifyDataSetChanged();
}
public boolean isPositionChecked(int position) {
Boolean result = mSelection.get(position);
return result == null ? false : result;
}
public Set<Integer> getCurrentCheckedPosition() {
return mSelection.keySet();
}
public void removeSelection(int position) {
mSelection.remove(position);
notifyDataSetChanged();
}
public void clearSelection() {
mSelection = new HashMap<Integer, Boolean>();
notifyDataSetChanged();
}
#Override
public View getView(int position, View convertView, ViewGroup parent) {
View v = super.getView(position, convertView, parent);//let the adapter handle setting up the row views
v.setBackgroundColor(Color.parseColor("#99cc00")); //default color
if (mSelection.get(position) != null) {
v.setBackgroundColor(Color.RED);// this is a selected position so make it red
}
return v;
}
}
}
The R.layout.adapters_cabselection_row is a custom layout for the row(a very simple one) with a green background:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#99cc00" >
<ImageView
android:id="#+id/imageView1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="#drawable/ic_launcher" />
<TextView
android:id="#+id/the_text"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textColor="#ffffff"
android:textSize="17sp"
android:textStyle="bold" />
</LinearLayout>
R.menu.cabselection_menu is a menu file with 3 options(edit, delete, finish the CAB) which don't do anything except pop a Toast with a message regarding the rows selected:
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android" >
<item
android:id="#+id/edit_entry"
android:icon="#android:drawable/ic_menu_edit"
android:title="Edit!"/>
<item
android:id="#+id/delete_entry"
android:icon="#android:drawable/ic_menu_delete"
android:title="Delete!"/>
<item
android:id="#+id/finish_it"
android:icon="#android:drawable/ic_menu_crop"
android:title="Get me out!"/>
</menu>
I think the easiest way is to apply
android:background="android:attr/activatedBackgroundIndicator"
To which ever layout is the one you will be clicking.
This highlights the layout when selected using
listView.setChoiceMode(ListView.CHOICE_MODE_MULTIPLE_MODAL);
worked for me anyway
Using ActionBarSherlock the MultiChoiceModeListener used in Luksprog´s answer is not yet available if you want to support API level < 11.
A workaround is to use the onItemClickListener.
List setup:
listView = (ListView) timeline.findViewById(android.R.id.list);
listView.setChoiceMode(ListView.CHOICE_MODE_MULTIPLE);
listView.setItemsCanFocus(false);
listView.setAdapter(new ListAdapter(getActivity(), R.layout.cleaning_list_item, items));
Listener of ListFragment or ListActivity:
#Override
public void onListItemClick(ListView l, View v, int position, long id) {
SparseBooleanArray checked = listView.getCheckedItemPositions();
boolean hasCheckedElement = false;
for (int i = 0; i < checked.size() && !hasCheckedElement; i++) {
hasCheckedElement = checked.valueAt(i);
}
if (hasCheckedElement) {
if (mMode == null) {
mMode = ((SherlockFragmentActivity) getActivity()).startActionMode(new MyActionMode());
mMode.invalidate();
} else {
mMode.invalidate();
}
} else {
if (mMode != null) {
mMode.finish();
}
}
}
Where MyActionMode is an implementation of ActionMode.Callback:
private final class MyActionMode implements ActionMode.Callback { /* ... */ }
I have ONE annoying problem with SimpleCursorAdapter. My programm has list view and ListActivity. Each row has it's own layout:
<TableLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_height="wrap_content" android:layout_width="fill_parent"
android:orientation="horizontal" android:weightSum="1.0">
<TableRow>
<TextView android:id="#+id/task_time"
android:layout_width="wrap_content" android:layout_height="wrap_content"
android:textSize="24sp" android:text="Time">
</TextView>
<LinearLayout android:orientation="vertical"
android:layout_width="wrap_content"
android:layout_height="fill_parent">
<TextView android:id="#+id/task_name"
android:layout_width="wrap_content" android:layout_height="wrap_content"
android:textSize="20sp" android:text="Name">
</TextView>
<TextView android:id="#+id/task_categoty"
android:layout_width="wrap_content" android:layout_height="wrap_content"
android:text="Category" android:textSize="12sp">
</TextView>
</LinearLayout>
<TextView android:id="#+id/task_state"
android:layout_width="wrap_content" android:layout_height="wrap_content"
android:text="State" android:textSize="12sp">
</TextView>
<CheckBox android:id="#+id/task_enabled"
android:layout_width="wrap_content"
android:layout_height="wrap_content" android:focusable="false">
</CheckBox>
</TableRow>
Tasks are stored in SQLite database. I have DAO object (singleton) to access the database.
TaskDao:
public void updateEnabled(int id, boolean enabled){
SQLiteDatabase db = dbHelper.getWritableDatabase();
ContentValues cv = new ContentValues();
cv.put(ENABLED_COLUMN, enabled==true?1:0);
Log.i(TAG, "update to " + cv.get(ENABLED_COLUMN) );
try{
db.beginTransaction();
db.update(TASK_TABLE, cv, ID_COLUMN+"=?", new String[]{id+""});
db.setTransactionSuccessful();
} catch (SQLException e) {
Log.i(TAG, "edit task failed!");
} finally {
db.endTransaction();
if (db != null)
db.close();
}
}
and the Cursor method for ListActivity:
public Cursor getTasks(){
SQLiteDatabase db = dbHelper.getReadableDatabase();
return db.query(TASK_TABLE, COLUMNS, null, null, null, null, NAME_COLUMN);
}
I extended SimpleCursorAdapter (TaskDbAdapter) like this:
#Override
public View getView(int position, View convertView, ViewGroup parent) {
if(convertView==null){
convertView = inflater.inflate(R.layout.task_list_row, null);
}
Cursor c = getCursor();
c.moveToPosition(position);
Log.i(TAG, "getView " + position + " = " + c.getInt(enabledIdx));
enabled.setTag(c.getInt(c.getColumnIndex(BaseColumns._ID)));
enabled.setChecked(c.getInt(enabledIdx)>0?true:false);
enabled.setOnClickListener(this);
return convertView;
}
#Override
public void onClick(View v) {
CheckBox box = (CheckBox) v;
Integer id = (Integer)box.getTag();
TaskDao.getInstance(context).updateEnabled(id.intValue(), box.isChecked());
}
And at last I use all the above stuff in my main ListActivity
private void refreshList(){
c = TaskDao.getInstance(this).getTasks();
startManagingCursor(c);
adapter = new TaskDbAdapter(this, R.layout.task_list_row, c, new String[]{TaskDao.ENABLED_COLUMN}, new int[]{R.id.task_enabled});
setListAdapter(adapter);
}
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.task);
getListView().setItemsCanFocus(false);
getListView().setChoiceMode(ListView.CHOICE_MODE_MULTIPLE);
getListView().setVerticalScrollBarEnabled(true);
registerForContextMenu(getListView());
getListView().setOnCreateContextMenuListener(this);
refreshList();
}
#Override
protected void onResume() {
super.onResume();
refreshList();
}
#Override
protected void onPause() {
super.onPause();
}
Everything works fine. But CheckBoxes loose their states. For instance I check my first column and scroll the list down. In my trace before press I have:
getView 0 = 0
getView 2 = 0
getView 3 = 0
then
uptate to 1
and then (when I scroll up to the first element)
getView 0 = 0
getView 2 = 0
getView 3 = 0
I tried to make getCursor().requery(); in my TaskDbAdapter onClick method. But then I saw no items in the list! And exception because of cursor management(connection was closed by android). When I write startManagingCursor(c); in refreshList() method then check and uncheck methods don't work.
Please, Help!
I didn't read all your source so my suggestion may be totally wrong, but I will give a try.
Take a look at the documentation of BaseAdapter class.
public void notifyDataSetChanged ()
may do the work.
You also can register Observer for this...
public void registerDataSetObserver (DataSetObserver observer)
I struggled with this as well. I ended up storing all checked boxes in the db as either 0 or 1. Then I check their state from the database to determine if they are marked or not.
public class DetailCursorAdapter extends SimpleCursorAdapter {
private Cursor c;
private Context context;
public DetailCursorAdapter(Context context, int layout, Cursor c,
String[] from, int[] to) {
super(context, layout, c, from, to);
this.c = c;
this.context = context;
}
public View getView(int pos, View inView, ViewGroup parent) {
View v = inView;
if (v == null) {
LayoutInflater inflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
v = inflater.inflate(R.layout.check_list, null);
}
Log.i("pos = ..................", "pos = "+pos);
this.c.moveToPosition(pos);
//this.c.moveToPosition(this.c.getInt(this.c.getColumnIndex("_id")));
CheckBox cBox = (CheckBox) v.findViewById(R.id.bcheck);
cBox.setTag(this.c.getInt(this.c.getColumnIndex("_id")));
/*
* when reloading the list, check for chkd status, this is broken. Need to query db directly.
*/
EventDbAdapter mDbHelper = new EventDbAdapter(context);
mDbHelper.open();
int idTag = (Integer) cBox.getTag();
int checked = mDbHelper.selectChk(idTag);
mDbHelper.close();
Log.i("results from selectChk.....................", ""+checked);
if (checked == 1) {
cBox.setChecked(true);
} else {
cBox.setChecked(false);
}
/*
* Populate the list
*/
TextView txtdateTime = (TextView)v.findViewById(R.id.time);
txtdateTime.setText(this.c.getString(this.c.getColumnIndex("time")));
TextView txtdateEvent = (TextView)v.findViewById(R.id.event);
txtdateEvent.setText(this.c.getString(this.c.getColumnIndex("event")));
TextView txtdateLocation = (TextView)v.findViewById(R.id.location);
txtdateLocation.setText(this.c.getString(this.c.getColumnIndex("location")));
ImageView arrow = (ImageView) v.findViewById(R.id.arrowId);
arrow.setImageResource(R.drawable.rightarrow);
Log.i("if chk in db is = 1 then set checked.........",this.c.getString(this.c.getColumnIndex("checked")) +" " +this.c.getString(this.c.getColumnIndex("time")));
/*
* Controls action based on clicked list item (background)
*/
View lv = v.getRootView();
lv.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View lv) {
CheckBox cBox = (CheckBox) lv.findViewById(R.id.bcheck);
// id holds the rowid of each event. pass this to a new activity to query for description
// Call Event Detail
String id = cBox.getTag().toString();
Intent i = new Intent(context, EventDetail.class);
//i.putExtra("description", c.getString(c.getColumnIndex("description")));
i.putExtra("_id", id);
context.startActivity(i);
}
});
/*
* Begin - Controls action based on clicked Text only
txtdateEvent.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
CharSequence charseq = "Darth Vader is alive";
Toast.makeText(context, charseq, Toast.LENGTH_SHORT).show();
}
});
* End - Controls action based on clicked Text only
*/
/*
* Controls action based on clicked checkbox
*/
cBox.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
EventDbAdapter mDbHelper = new EventDbAdapter(context);
mDbHelper.open();
CheckBox cBox = (CheckBox) v.findViewById(R.id.bcheck);
if (cBox.isChecked()) {
//cBox.setChecked(false);
CharSequence charseq = "Added to My Schedule";
Toast.makeText(context, charseq, Toast.LENGTH_SHORT).show();
// Update the database for each checked item
mDbHelper.updateChecked(cBox.getTag().toString(), "1");
c.requery();
// Verify that the db was updated for debugging purposes
String event = c.getString(c.getColumnIndex("event"));
int id = (Integer) cBox.getTag();
Log.i("checked _id...........", "id= " + id + " " +c.getString(c.getColumnIndex("_id")));
Log.i("checked checked...........", ""+c.getString(c.getColumnIndex("checked")));
} else if (!cBox.isChecked()) {
//cBox.setChecked(true);
CharSequence charseq = "Removed from My Schedule";
Toast.makeText(context, charseq, Toast.LENGTH_SHORT).show();
// checkList.remove(cBox.getTag());
//checkList.add((Integer) cBox.getTag());
String event = c.getString(c.getColumnIndex("event"));
//int id = c.getInt(c.getColumnIndex("_id"));
int id = (Integer) cBox.getTag();
mDbHelper.updateChecked(cBox.getTag().toString(), "0");
c.requery();
//int sqlresult = mDbHelper.selectChk(id, event);
//Log.i("sqlresult checked value after update...........", ""+ sqlresult);
//Log.i("unchecked _id...........", ""+c.getString(c.getColumnIndex("_id")));
//Log.i("unchecked checked...........", ""+c.getString(c.getColumnIndex("checked")));
}
//mDbHelper.close();
}
});
return(v);
}
}