Я работаю с ListView, пытаюсь заставить оптимизацию convertView / referenceHolder работать должным образом, но это доставляет мне проблемы. (Это система, в которой вы храните указатели R.id.xxx в качестве тега для каждого представления, чтобы избежать необходимости вызывать findViewById). У меня есть ListView, заполненный простыми строками ImageView и небольшим текстом, но ImageView можно отформатировать как для портретных изображений (высокий и узкий), так и для альбомных изображений (короткий и широкий). Он корректирует это форматирование для каждой строки, которая не работает, как я надеялся.
Основная система состоит в том, что для начала она раздувает макет каждой строки и устанавливает параметры ImageView на основе данных, а также включает int, обозначающий ориентацию в теге, содержащем значения R.id.xxx. Затем, когда он начинает повторно использовать convertViews, он проверяет эту сохраненную ориентацию по отношению к ориентации новой строки. Теория заключается в том, что если ориентация одинакова, то ImageView уже должен быть настроен правильно. Если это не так, тогда он соответствующим образом устанавливает параметры для ImageView и обновляет тег.
Однако я обнаружил, что это как-то запуталось; иногда тег может быть не синхронизирован с ориентацией ImageView. Например, тег будет по-прежнему говорить портрет, но фактический ImageView будет по-прежнему в альбомной ориентации. Я не мог найти образец того, как или когда это произошло; это не соответствовало ориентации, положению в списке или скорости прокрутки. Я могу решить эту проблему, просто сняв проверку ориентации convertView и просто всегда устанавливая параметры ImageView, но, похоже, это не соответствует цели этой оптимизации.
Кто-нибудь может увидеть, что я сделал неправильно в приведенном ниже коде?
static LinearLayout.LayoutParams layoutParams;
(...)
public View getView(int position, View convertView, ViewGroup parent){
ReferenceHolder holder;
if (convertView == null){
convertView = inflater.inflate(R.layout.pick_image_row, null);
holder = new ReferenceHolder();
holder.getIdsAndSetTag(convertView, position);
if (data[position][ORIENTATION] == LANDSCAPE) {
// Layout defaults to portrait settings, so ImageView size needs adjusting.
// layoutParams is modified here, with specific values for width, height, margins etc
holder.image.setLayoutParams(layoutParams);
}
holder.orientation = data[position][ORIENTATION];
} else {
holder = (ReferenceHolder) convertView.getTag();
if (holder.orientation != data[position][ORIENTATION]){ //This is the key if statement for my question
switch (image[position][ORIENTATION]) {
case PORTRAIT:
// layoutParams is reset to the Portrait settings
holder.orientation = data[position][ORIENTATION];
break;
case LANDSCAPE:
// layoutParams is reset to the Landscape settings
holder.orientation = data[position][ORIENTATION];
break;
}
holder.image.setLayoutParams(layoutParams);
}
}
// and the row's image and text is set here, using holder.image.xxx
// and holder.text.xxx
return convertView;
}
static class ReferenceHolder {
ImageView image;
TextView text;
int orientation;
void getIdsAndSetTag(View v, int position){
image = (ImageView) v.findViewById(R.id.pickImageImage);
text = (TextView) v.findViewById(R.id.pickImageText);
orientation = data[position][ORIENTATION];
v.setTag(this);
}
}
Спасибо!