Вот пример, основанный на вашем коде, который обрабатывает нажатие кнопки для каждого элемента в списке.
Если вы щелкнете по переключателю, то с помощью тоста будет показан идентификатор элемента.
При этом используется пользовательский адаптер на основе (расширяет) класс CursorAdapter.
Сначала макет adapter.xml , используемый для элемента (должен иметь основную информацию и включать переключатель, идентификатор которого - the_switch): -
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView
android:id="@+id/id"
android:layout_width="0dp"
android:layout_weight="1"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/KEYCODE"
android:layout_width="0dp"
android:layout_weight="2"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/NAME"
android:layout_width="0dp"
android:layout_weight="6"
android:layout_height="wrap_content" />
<Switch
android:id="@+id/the_switch"
android:layout_width="0dp"
android:layout_weight="1"
android:layout_height="wrap_content"
android:focusable="false"
/>
</LinearLayout>
Активность Lights.java теперь: -
public class Lights extends AppCompatActivity {
ListView users_list, alt_users_list;
private DatabaseManager dbManager;
private MyCustomCursorAdapter adapter;
//private DatabaseManager dbHelper; //?????? a second not needed
Cursor cursor;
Context mContext;
//<<<<<<<<<< Not needed although could be passed
//final String[] from = new String[]{DatabaseManager._ID, DatabaseManager.TITLE, DatabaseManager.DESC};
//final int[] to = new int[]{R.id.id, R.id.KEYCODE, R.id.NAME};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mContext = this;
setContentView(R.layout.activity_lights);
startconnection(); //?????? dummied out
users_list = findViewById(R.id.users_list);
alt_users_list = findViewById(R.id.alt_users_list);
dbManager = new DatabaseManager(this);
dbManager.open();
manageListView(); //Handles the ListView
}
// Moved here handles list refresh if called (e.g. in onResume)
private void manageListView() {
cursor = dbManager.fetch();
//Setup the adapter if not already setup else swaps (refreshes) the cursor
if (adapter == null) {
adapter = new MyCustomCursorAdapter(this, cursor);
users_list.setAdapter(adapter);
users_list.setOnItemClickListener(new AdapterView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
Toast.makeText(mContext,"You clicked on the item with an ID of " + String.valueOf(id),Toast.LENGTH_SHORT).show();
}
});
} else {
adapter.swapCursor(cursor);
}
}
private void startconnection(){}
@Override
protected void onDestroy() {
super.onDestroy();
// Close the Cursors when done with them
cursor.close();
}
@Override
protected void onResume() {
super.onResume();
// Refresh the listviews when returning to the activity
manageListView();
}
}
- Комментарии пытаются объяснить изменения (в основном это очень похоже).
- Самым большим изменением является то, что настройка просмотра списка была перенесена в собственный метод, который также обрабатывает обновление просмотра списка (повторное отображение его после изменения базовых данных).
- Создание экземпляра адаптера также проще, чем для SimpleCursorAdapter (макет и столбец для просмотра обработки, закодированной в адаптере).
Адаптер myCustomAdapter.java - это: -
public class MyCustomCursorAdapter extends CursorAdapter {
public MyCustomCursorAdapter(Context context, Cursor c) {
super(context, c, 0);
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
View view = super.getView(position, convertView, parent);
if (position % 2 == 0) {
view.setBackgroundColor(0xFFAAAAFF);
} else {
view.setBackgroundColor(0xAAAAAAFF);
}
return view;
}
@Override
public View newView(Context context, Cursor cursor, ViewGroup parent) {
return LayoutInflater.from(context).inflate(R.layout.adapter,parent,false);
}
@Override
public void bindView(View view, Context context, Cursor cursor) {
((TextView)view.findViewById(R.id.id)).setText(cursor.getString(cursor.getColumnIndex(DatabaseManager._ID)));
((TextView)view.findViewById(R.id.KEYCODE)).setText(cursor.getString(cursor.getColumnIndex(DatabaseManager.TITLE)));
((TextView)view.findViewById(R.id.NAME)).setText(cursor.getString(cursor.getColumnIndex(DatabaseManager.DESC)));
Switch thisswitch = view.findViewById(R.id.the_switch);
thisswitch.setTag(cursor.getString(cursor.getColumnIndex(DatabaseManager._ID)));
thisswitch.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
@Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
Toast.makeText(buttonView.getContext(),
"You clicked the switch for ID " + (String) buttonView.getTag() +
" the status is now " + (new Boolean(isChecked)).toString(),
Toast.LENGTH_SHORT)
.show()
;
}
});
}
}
- bindView в основном использовался им: -
- привязывает значения из столбцов курсора к представлениям для каждого элемента
- и в этом случае устанавливает тег переключателя на id, а затем добавляет onCheckChangedListener для Button.
- Преимущество bindView в том, что ему передаются курсор и контекст.
- Можно также использовать getView, он имеет преимущество в том, что позиция элемента передается в списке.
- В этом случае он использовался для чередования цвета фона для каждого элемента.
Результат
Вот снимок экрана, показывающий тост (данные тестирования заметок были добавлены в базовую базу данных, так что это, очевидно, будет отличаться от вашей): -
![enter image description here](https://i.stack.imgur.com/8mw1a.png)
Дополнительно
Возможно, вам нужно обработать изменение проверки переключателя в операции владения.
Следующие изменения показывают основные средства, через интерфейс, для обработки события переключения в действии, а не в адаптере.
Первый интерфейс myOnCheckedChangedInterface.java
public interface myOnCheckedChangedInterface {
void myOnCheckedChangedHandler(String id, boolean check_status);
}
Второе изменение Lights.java путем добавления метода-обработчика myOnCheckedChangedHandler
@Override
public void myOnCheckedChangedHandler(String id, boolean check_status) {
Toast.makeText(
this,
"You changed the status for the row with an id of " + id +
" the status is now " + new Boolean(check_status).toString(),
Toast.LENGTH_SHORT).show();
}
- Игнорировать ошибку, что метод не переопределяет метод из своего суперкласса.
В-третьих, измените объявление Class для реализации интерфейса, добавив implements myOnCheckedChangedInterface
согласно: -
public class Lights extends AppCompatActivity implements myOnCheckedChangedInterface {
Наконец, измените MyCustomCursorAdapter, чтобы иметь возможность вызывать myOnCheckedChangedHandler
, например
public class MyCustomCursorAdapter extends CursorAdapter {
Lights calling_activity; //<<<<<<<<<<@@@@@@@@@@@ ADDED for interface
public MyCustomCursorAdapter(Context context, Cursor c) {
super(context, c, 0);
this.calling_activity = (Lights) context; //<<<<<<<<<<@@@@@@@@@@@ ADDED for interface
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
View view = super.getView(position, convertView, parent);
if (position % 2 == 0) {
view.setBackgroundColor(0xFFAAAAFF);
} else {
view.setBackgroundColor(0xAAAAAAFF);
}
return view;
}
@Override
public View newView(Context context, Cursor cursor, ViewGroup parent) {
return LayoutInflater.from(context).inflate(R.layout.adapter,parent,false);
}
@Override
public void bindView(View view, Context context, Cursor cursor) {
((TextView)view.findViewById(R.id.id)).setText(cursor.getString(cursor.getColumnIndex(DatabaseManager._ID)));
((TextView)view.findViewById(R.id.KEYCODE)).setText(cursor.getString(cursor.getColumnIndex(DatabaseManager.TITLE)));
((TextView)view.findViewById(R.id.NAME)).setText(cursor.getString(cursor.getColumnIndex(DatabaseManager.DESC)));
Switch thisswitch = view.findViewById(R.id.the_switch);
thisswitch.setTag(cursor.getString(cursor.getColumnIndex(DatabaseManager._ID)));
thisswitch.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
@Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
/**
Toast.makeText(buttonView.getContext(),
"You clicked the switch for ID " + (String) buttonView.getTag() +
" the status is now " + (new Boolean(isChecked)).toString(),
Toast.LENGTH_SHORT)
.show()
**/
calling_activity.myOnCheckedChangedHandler((String)buttonView.getTag(),isChecked); //<<<<<<<<<<@@@@@@@@@@@ ADDED for interface
}
});
}
}
- См. Комментарии с // <<<<<<<<<< @@@@@@@@@@@ ДОБАВЛЕНО для интерфейса для изменений </li>
- Оригинальный тост закомментирован, так как он больше не нужен
- Обратите внимание, что это не самый аккуратный способ, так как адаптер привязан к действию Lights, это просто простой пример.