Android:View类中getTag()和setTag()的用途

时间:2014-08-27 15:31:23

标签: android android-view

public void setTag(final Object tag) {
                mTag = tag;
}
public Object getTag() {
            return mTag;
}

这是Android中View Class的两种方法。 以下是这两种方法的官方文档。

 /**
     * Returns this view's tag.
     *
     * @return the Object stored in this view as a tag
     *
     * @see #setTag(Object)
     * @see #getTag(int)


        */
 /**
     * Sets the tag associated with this view. A tag can be used to mark
     * a view in its hierarchy and does not have to be unique within the
     * hierarchy. Tags can also be used to store data within a view without
     * resorting to another data structure.
     *
     * @param tag an Object to tag the view with
     *
     * @see #getTag()
     * @see #setTag(int, Object)
     */

标记函数广泛用于baseadapter实现,但我无法理解其目的以及如何使用它们。能否请您解释一下这个好例子,以帮助我理解这些功能的作用

5 个答案:

答案 0 :(得分:10)

将其视为尽可能简单明了 - "标记"。

杂货店产品标签告诉您什么? 基本上很多东西,比如名称,价格,原产国,折扣等等。

想象一下,您正在使用ImageView制作一个在网格中显示此类产品的应用程序。 如何从ImageView轻松确定产品功能?标记它是可能的解决方案之一。

class Product {

    String mName;
    String mManufacturer;
    String mOriginCountry;

    double mPrice;
    int mDiscount;

    int mImageId; // A reference to a drawable item id
}

[...]

class My Activity {

    @Override
    protected void onCreate() {
        [...] // Some code

        // Grab the imageView reference and grab (or create) the tag for it
        ImageView someItemView = (ImageView) findViewById(R.id.some_product_view);
        Product someProductTag = new Product( ... some data ...);

        // Add the tag to the ImageView
        someItemView.addTag(someProductTag);
    }

    private void displayItemInfo(ImageView iv) {

        // Grab the tag and display the info.
        String productName = ((Product)iv.getTag()).mName();
        Toast.show(mContext, "This is " + productName, Toast.LONG).show(); 

    }

}

当然这是非常简化。理想情况下,你会有一个适配器,可以根据你提供的标签创建视图,或者自动创建你的标签。

我希望你明白这个想法

答案 1 :(得分:3)

一个很好的例子是View Holder模式。可以在ListViews上的this tutorial中找到实现。

  

View Holder模式允许避免适配器中的findViewById()方法。

     

ViewHolder类是适配器中的静态内部类,它保存对相关视图的引用。在你的布局中。此引用通过setTag()方法作为标记分配给行视图。

     

如果我们收到convertView对象,我们可以通过getTag()方法获取ViewHolder的实例,并通过ViewHolder引用将新属性分配给视图。

     

虽然这听起来很复杂,但使用findViewById()方法的速度要快15%。

示例

  

以下代码显示了性能优化的适配器实现,它重用现有视图并实现持有者模式。

import android.app.Activity;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.ImageView;
import android.widget.TextView;

public class MyPerformanceArrayAdapter extends ArrayAdapter<String> {
  private final Activity context;
  private final String[] names;

  static class ViewHolder {
    public TextView text;
    public ImageView image;
  }

  public MyPerformanceArrayAdapter(Activity context, String[] names) {
    super(context, R.layout.rowlayout, names);
    this.context = context;
    this.names = names;
  }

  @Override
  public View getView(int position, View convertView, ViewGroup parent) {
    View rowView = convertView;
    // reuse views
    if (rowView == null) {
      LayoutInflater inflater = context.getLayoutInflater();
      rowView = inflater.inflate(R.layout.rowlayout, null);
      // configure view holder
      ViewHolder viewHolder = new ViewHolder();
      viewHolder.text = (TextView) rowView.findViewById(R.id.TextView01);
      viewHolder.image = (ImageView) rowView
          .findViewById(R.id.ImageView01);
      rowView.setTag(viewHolder);
    }

    // fill data
    ViewHolder holder = (ViewHolder) rowView.getTag();
    String s = names[position];
    holder.text.setText(s);
    if (s.startsWith("Windows7") || s.startsWith("iPhone")
        || s.startsWith("Solaris")) {
      holder.image.setImageResource(R.drawable.no);
    } else {
      holder.image.setImageResource(R.drawable.ok);
    }

    return rowView;
  }
} 

答案 2 :(得分:1)

它们只是将Object附加到视图的一种方式 在BaseAdapter中,它用于存储视图ID,以避免每次系统请求视图时进行昂贵的findViewById操作。

答案 3 :(得分:1)

setTag(int, object)对于将自定义类存储到视图非常有用。这是我的实施:

 itemView.setTag(R.id.food_tag, food);

变量食物是自定义对象食物的一个实例。 setTag的关键应该始终是资源ID。

我可以在OnClickListener()

中以这种方式检索此自定义对象
Food selectedFood = (Food) view.getTag(R.id.food_tag);

答案 4 :(得分:0)

Tag字段是为任何视图类存储自己的状态信息的好方法。一种用途是将视图的位置存储在ListView中。有关示例,请参阅此answer