Я хотів би знати, чим відрізняються ці стани. Я не знайшов жодної веб-сторінки, яка б це пояснила.
Я хотів би знати, чим відрізняються ці стани. Я не знайшов жодної веб-сторінки, яка б це пояснила.
Відповіді:
Різниця між перевіреним та активованим насправді досить цікава. Навіть документація Google вибачається (акцент нижче додано):
... Наприклад, у поданні списку з увімкненим одним чи кількома виділеннями активізуються представлення даних у поточному наборі вибору. (Гм, так, нам дуже шкода термінології тут.) Активований стан передається дітям того виду, на який він встановлений.
Тож ось різниця:
ListView (після Honeycomb) викликає setChecked () OR setActivate () залежно від версії Android, як показано нижче (взято з вихідного коду Android):
if (mChoiceMode != CHOICE_MODE_NONE && mCheckStates != null) {
if (child instanceof Checkable) {
((Checkable) child).setChecked(mCheckStates.get(position));
} else if (getContext().getApplicationInfo().targetSdkVersion
>= android.os.Build.VERSION_CODES.HONEYCOMB) {
child.setActivated(mCheckStates.get(position));
}
}
Зверніть увагу на змінну mCheckStates. Він відстежує, які позиції у вашому списку перевіряються / активуються. До них можна отримати, наприклад, getCheckedItemPositions (). Зауважте також, що виклик ListView.setItemChecked () викликає вищезазначене. Іншими словами, це однаково можна назвати setItemActivate ().
До створення стільникових мереж нам довелося здійснити обхідні шляхи, щоб відобразити стан_контролю в нашому списку. Це тому, що ListView викликає setChecked () ТОЛЬКО на самому верхньому перегляді у макеті (а макети не реалізують перевірку) ... і він НЕ розповсюджується без сторонньої допомоги. Ці способи вирішення набули такої форми: Розширення кореневого макета для реалізації Checkable. У його конструкторі рекурсивно знайдіть усіх дітей, які реалізують Checkable. Коли викликається setChecked () тощо ..., передайте виклик цим переглядам. Якщо ці представлення реалізують чернетки списку станів (наприклад, CheckBox) з іншим малюнком для state_kljuно, то перевірений стан відображається в інтерфейсі користувача.
Щоб зробити гарний фон для елемента списку після Honeycomb, все, що вам потрібно зробити, - це список списку статей, який можна малювати для такого стану state_activate (і, звичайно, використовувати setItemChecked ()):
<item android:state_pressed="true"
android:drawable="@drawable/list_item_bg_pressed"/>
<item android:state_activated="true"
android:drawable="@drawable/list_item_bg_activated"/>
<item android:drawable="@drawable/list_item_bg_normal"/>
Щоб зробити гарне тло для елемента списку до HoneyComb, ви зробите щось подібне до вищевказаного для стану_контролю, і вам ТАКОЖ потрібно розширити перегляд у верхній частині, щоб реалізувати інтерфейс Checkable. Після цього вам потрібно повідомити Android, чи стан, який ви реалізуєте, істинне чи помилкове, ввімкнувши OnCreateDravableState () та викликаючи refreshDravableState (), коли стан змінюється.
<item android:state_pressed="true"
android:drawable="@drawable/list_item_bg_pressed"/>
<item android:state_checked="true"
android:drawable="@drawable/list_item_bg_checked"/>
<item android:drawable="@drawable/list_item_bg_normal"/>
... і код для реалізації Checkable у поєднанні з state_ перевіреним у RelativeLayout може бути:
public class RelativeLayoutCheckable extends RelativeLayout implements Checkable {
public RelativeLayoutCheckable(Context context, AttributeSet attrs) {
super(context, attrs);
}
public RelativeLayoutCheckable(Context context) {
super(context);
}
private boolean mChecked = false;
@Override
protected void onFinishInflate() {
super.onFinishInflate();
}
@Override
public boolean isChecked() {
return mChecked;
}
@Override
public void setChecked(boolean checked) {
mChecked = checked;
refreshDrawableState();
}
private static final int[] mCheckedStateSet = {
android.R.attr.state_checked,
};
@Override
protected int[] onCreateDrawableState(int extraSpace) {
final int[] drawableState = super.onCreateDrawableState(extraSpace + 1);
if (isChecked()) {
mergeDrawableStates(drawableState, mCheckedStateSet);
}
return drawableState;
}
@Override
public void toggle() {
setChecked(!mChecked);
}
}
Завдяки наступному:
http://sriramramani.wordpress.com/2012/11/17/custom-states/
Stackoverflow: як додати спеціальний стан кнопки
Stackoverflow: спеціальний вид, який можна перевірити, що відповідає Selector
http://www.charlesharley.com/2012/programming/custom-dravable-states-in-android/
http://developer.android.com/guide/topics/resources/dravable-resource.html#StateList
http://blog.marvinlabs.com/2010/10/29/custom-listview-ability-check-items/
Selection is a transient property, representing the view (hierarchy) the user is currently interacting with. Activation is a longer-term state that the user can move views in and out of. For example, in a list view with single or multiple selection enabled, the views in the current selection set are activated. (Um, yeah, we are deeply sorry about the terminology here.)
setItemChecked()
та використання селектора з властивістюandroid:state_activated="true"
Відповідно до док .
android: state_selected Boolean . " true
" якщо цей елемент повинен використовуватися, коли об'єктом є поточний вибір користувача під час навігації з керованим керуванням (наприклад, при навігації по списку з d-pad); " false
" якщо цей елемент слід використовувати, коли об'єкт не обраний. Вибраний стан використовується, коли фокус (android: state_focused) недостатній (наприклад, коли у переліку списку є фокус і елемент у ньому вибраний за допомогою d-pad).
Android: state_checked Boolean . " true
" якщо цей елемент слід використовувати під час перевірки об'єкта; " false
" якщо він повинен бути використаний, коли об'єкт не перевірено.
Android: state_activated Boolean . " true
" якщо цей елемент слід використовувати, коли об'єкт активовано як постійний вибір (наприклад, для "виділення" раніше вибраного елемента списку в постійному режимі навігації); " false
" якщо його слід використовувати, коли об'єкт не активований. Введено в рівень 11 API .
Я думаю, що документ досить зрозумілий, тож у чому проблема?
Ось інше рішення цієї проблеми: https://github.com/jiahaoliuliu/CustomizedListRow/blob/master/src/com/jiahaoliuliu/android/customizedlistview/MainActivity.java
Я переосмислив метод setOnItemClickListener і перевірив різницю випадків у коді. Але остаточно рішення Марвіна набагато краще.
listView.setOnItemClickListener(new OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> adapterView, View view, int position,
long id) {
CheckedTextView checkedTextView =
(CheckedTextView)view.findViewById(R.id.checkedTextView);
// Save the actual selected row data
boolean checked = checkedTextView.isChecked();
int choiceMode = listView.getChoiceMode();
switch (choiceMode) {
// Not choosing anything
case (ListView.CHOICE_MODE_NONE):
// Clear all selected data
clearSelection();
//printCheckedElements();
break;
// Single choice
case (ListView.CHOICE_MODE_SINGLE):
// Clear all the selected data
// Revert the actual row data
clearSelection();
toggle(checked, checkedTextView, position);
//printCheckedElements();
break;
// Multiple choice
case (ListView.CHOICE_MODE_MULTIPLE):
case (ListView.CHOICE_MODE_MULTIPLE_MODAL):
// Revert the actual selected row data
toggle(checked, checkedTextView, position);
//printCheckedElements();
break;
}
}
});