Как вы можете скрыть элемент в ListView или по крайней мере установить его высоту на ноль?
Я попытался установить видимость представления в GONE, но он все еще сохраняет пространство элемента (высота).
Как вы можете скрыть элемент в ListView или по крайней мере установить его высоту на ноль?
Я попытался установить видимость представления в GONE, но он все еще сохраняет пространство элемента (высота).
Повторное рассмотрение старого вопроса, но у меня была эта проблема, когда я хотел скрыть элементы списка временно на основе критериев вне данных списка. То, что я закончил делать, это создать макет "нулевого элемента" в xml и вернуть его на основе моих критериев вместо преобразования в getView()...
вместо возврата convertView, я вернул свой null_item...
return inflater.inflate(R.layout.null_item, null);
null_item.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="wrap_content" >
</LinearLayout>
если вы хотите скрыть элемент следующим образом:
convertView.setLayoutParams(new AbsListView.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT,1));
convertView.setVisibility(View.GONE);
не может быть AbsListView.LayoutParams(-1,0);
если convertview повторно используется, вы должны добавить это ниже, чтобы установить высоту назад:
if(convertView.getVisibility() == View.GONE) {
convertView.setLayoutParams(new AbsListView.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, AbsListView.LayoutParams.WRAP_CONTENT));
convertView.setVisibility(View.VISIBLE);
}
Когда дело доходит до ListView, чтобы сделать его эффективным, мы используем шаблон ViewHolder. Способ использования шаблона ViewHolder и R.layout.row_null следующего xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="wrap_content" >
</LinearLayout>
следует использовать с getViewTypeCount() и getItemViewType (int position) следующим образом.
@Override
public int getViewTypeCount() {
return 2;
}
@Override
public int getItemViewType(int position) {
return (hideStatusCheck(position)) ? 1 : 0;
}
@Override
public View getView(int pos, View convertView, ViewGroup parent) {
View rowView = convertView;
if (hideStatusCheck(pos)) {
if (rowView == null || rowView.getTag() != null) {
LayoutInflater inflater = mActivity.getLayoutInflater();
rowView = inflater.inflate(R.layout.row_null, parent, false);
}
} else {
if (rowView == null) {
rowView = inflateNormalView(parent);
} else if (rowView.getTag() == null) {
rowView = inflateNormalView(parent);
} else {
ViewHolder holderToCheck = (ViewHolder) rowView.getTag();
Integer storedPos = (Integer) holderToCheck.getTag(POSITION);
if (storedPos == null || storedPos != pos)
rowView = inflateNormalView(parent);
}
ViewHolder holder = (ViewHolder) rowView.getTag();
holder.setTag(POSITION,pos);
/*
Populate data
*/
return rowView;
}
private View inflateNormalView(ViewGroup parent) {
View rowView;
LayoutInflater inflater = mActivity.getLayoutInflater();
rowView = inflater.inflate(R.layout.normal_item, parent, false);
ViewHolder viewHolder = new ViewHolder();
assert rowView != null;
/* Initiate normal findViewById thing*/
rowView.setTag(viewHolder);
return rowView;
}
Мы проверяем тип элемента item и, если он отвечает проверке hide, он возвращает 1, в противном случае 0. ListView знает, что будут два типа View из getViewTypeCount. Теперь getView вернет approriate View в зависимости от hideStatusCheck. Чтобы создать надежный ListView, мы хотим использовать шаблон ViewHolder. Нам не нужно использовать ViewHolder, когда он скрыт. Мы просто надуваем R.layout.row_null и возвращаем его. Мы будем использовать ViewHolder для R.layout.normal_item. Вот сложная часть, предполагающая, что проверка скрытия не является статичной. Первая проверка rowView==null
является стандартной. Вторая проверка rowView.getTag()==null
заключается в том, чтобы увидеть, вернется ли представление в нормальное состояние
от сокрытия. Третья проверка последнего предложения else
заключается в проверке того, является ли ViewHolder сохраненным в теге правильным ViewHolder. Если эти условия соблюдены, мы снова раздуваем представление. Да, это правда, что шаблон ViewHolder не используется повсюду, но он использует определенные расширения. Это лучше, чем ничего.
Я немного потрудился с перетаскиванием списка из здесь. Когда элемент выталкивается из списка, который должен быть перемещен вокруг занимаемого им пространства ячеек, он имеет высоту, установленную в 1px (см. Строку 238), поэтому она появляется "ушла". Я не мог найти способ справиться с этим лучше, так как установка высоты до 0 сбой, как и видимость GONE.
Тем не менее, если вы действительно хотите избавиться от строки менее временно, может быть хорошей идеей изменить поддержку Adapter
и вызвать notifyDataSetChanged()
на нем.
Я смотрю исходный код. И есть только один способ скрыть элемент без notifyDataSetChanged()
. Вы должны установить видимость GONE
для всех внутренних видов и удалить фоновое изображение и paddings для просмотра позиций.
Примечание. Строка с таким невидимым элементом будет выбрана.
P.S: Это очень полезно для ExpandableListView
, если вы хотите скрыть групповой просмотр сам.
добавить в объект ListView: андроид: dividerHeight = "0px" Android: делитель = "# FFFFFF"
Цвет разделителя не имеет значения только установка dividerHeight не работает
Это устраняет разделитель, хотя...
Я думаю, что у меня гораздо более легкое/безопасное решение: вам просто нужно "внедрить" ваш элемент в макет и изменить видимость этого родительского макета.
<?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="wrap_content"
android:orientation="horizontal" >
<!-- Embed ListView Item into a "parent" Layout -->
<LinearLayout
android:id="@+id/parentLayout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal" >
<!-- This is the normal content of your ListView Item -->
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Hello" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="World" />
</LinearLayout>
</LinearLayout>
Тогда в вашем коде просто выполните:
public View getView(int position, View view, ViewGroup parent) {
if (view == null) {
LayoutInflater li = mActivity.getLayoutInflater();
view = li.inflate(R.layout.my_listview_item, null);
}
LinearLayout parentLayout = (LinearLayout) view.findViewById(R.id.parentLayout);
if (shouldDisplayItem(position)) {
parentLayout.setVisibility(View.VISIBLE);
} else {
parentLayout.setVisibility(View.GONE);
}
return view;
}
Таким образом, вы всегда используете/повторно используете один и тот же элемент и просто скрываете/показываете его.