在安卓中使用XML布局创建自定义视图

8
我有一个包含许多不同行布局的ListAdapter。为了使代码更清晰,我想将行的布局从适配器的getView()中外包到View类中。是否可以将XML布局填充到自定义视图中?我只找到LayoutInflater,但它返回一个View,这并没有帮助。我想要像Activity的setLayout()那样的东西。这可能吗?
谢谢!

无法理解您的意思。您能以更好的方式解释吗? - Dinesh Sharma
如果您查看Matthew Willis的回答,您可能会理解我的问题。 - dbrettschneider
2个回答

28

您可以创建自定义行视图,并在其构造函数中填充您的xml:

public MyRow extends LinearLayout {
    public MyRow(Context context) {
        super(context);
        LayoutInflater.from(context).inflate(R.layout.my_row, this, true);
          ... other initialization ...
    }
}

然后在my_row.xml中使用merge

<?xml version="1.0" encoding="utf-8"?>
<merge xmlns:android="http://schemas.android.com/apk/res/android">
  ... your row layout ...
</merge>

merge元素会将其子元素添加为您自定义视图的子元素。有关更多信息,请查看合并布局


我尝试了这个,但是出现了错误“merge can be used only with a valid view group root and attachtoroot=true”。为什么?我使用的是完全相同的调用方式,我使用一个根为merge的xml文件,没有任何属性。 - Frederic Blase
1
那个链接现在是404错误页面。我找到的最接近的是http://developer.android.com/training/improving-layouts/reusing-layouts.html,但我还建议阅读http://android-developers.blogspot.ca/2009/03/android-layout-tricks-3-optimize-by.html - Chani

0

我总是使用一个带有viewholder的自定义适配器,例如:

public class CalendarAdapter extends BaseAdapter {
protected static CalViewHolder holder;
private LayoutInflater mInflater;
public HashMap<Integer,String[]> appointments = new HashMap<Integer,String[]>();

public CalendarAdapter(Context context,HashMap<Integer,String[]> set_appointments) {
    // Cache the LayoutInf
     mInflater = LayoutInflater.from(context);
     appointments = set_appointments;
}
@Override
public int getCount() {
    // TODO Auto-generated method stub
    return appointments == null ? 0:appointments.size();
}
@Override
public Object getItem(int arg0) {
    // TODO Auto-generated method stub
    return null;
}
@Override
public long getItemId(int arg0) {
    // TODO Auto-generated method stub
    return 0;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
     if (convertView == null) {
         convertView = mInflater.inflate(R.xml.appointment, null);
         holder = new CalViewHolder();
         holder.app_lay = (LinearLayout) convertView.findViewById(R.id.appointment_layout);
         holder.app_head = (TextView) convertView.findViewById(R.id.appointment_head);
         holder.app_body = (TextView) convertView.findViewById(R.id.appointment_body);
         convertView.setTag(holder);
     }else{
        holder = (CalViewHolder) convertView.getTag();
     }
     holder.app_head.setText(appointments.get(position)[0]);
     holder.app_body.setText(appointments.get(position)[1]);
     return convertView;
}

static class CalViewHolder {
    LinearLayout app_lay;
    TextView app_head;
    TextView app_body; 
}

}


我也使用这种方法,但是我的行有很多不同的布局,所以有一个非常大的“if else”。 - dbrettschneider
有许多不同的布局,性能会变慢。我意识到一个类似的Listview最多可以有六个不同的持有者,这是可以接受的,但请记住,如果您添加或删除控件,则必须重新加载每个单独的项。也许ListView并不是您真正需要的,考虑将视图简单地添加到LinearLayout中。 - 2red13

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接