在充气后,findViewById在自定义视图中返回null

Fab*_*ian 5 android nullpointerexception android-custom-view android-layout layout-inflater

我有一个自定义RelativeLayout,我在其中膨胀一个xml res文件.这工作得很好,如果我在一个XML文件中使用自定义布局,并将其设置为内容查看,但如果我尝试将其与添加的代码new LocationItem(this)addChild()findViewById方法始终返回null自定义的构造函数RelativeLayout.

这是代码:

public class LocationItem extends RelativeLayout {

private String parcelType;
private int countIntoBox, countFromBox;

private RelativeLayout deliveryContainer, pickupContainer;

private TextView countPickup, countDelivery;

public LocationItem(Context context) {
    this(context, null);
}

public LocationItem(Context context, AttributeSet attrs) {
    this(context, attrs, 0);
}

public LocationItem(Context context, AttributeSet attrs, int defStyle) {
    super(context, attrs, defStyle);
    inflate(getContext(), R.layout.list_item_location, this);
    deliveryContainer = (RelativeLayout) findViewById(R.id.rl_location_delivery_container);
    pickupContainer = (RelativeLayout) findViewById(R.id.rl_location_pickup_container);
    countPickup = (TextView) findViewById(R.id.tv_location_pickup_count);
    countDelivery = (TextView) findViewById(R.id.tv_location_delivery_count);

    countPickup.setOnClickListener(getShowNumberPickerListener());
    countDelivery.setOnClickListener(getShowNumberPickerListener());
}

private OnClickListener getShowNumberPickerListener() {
    return new OnClickListener() {
        @Override
        public void onClick(View view) {
            showNumberPickerDialog(view);
        }
    };
} ...
}
Run Code Online (Sandbox Code Playgroud)

在活动中添加自定义视图

mRootLayoutLocations.addView(new LocationItem(this));
Run Code Online (Sandbox Code Playgroud)

视图正确膨胀,因为我可以看到它,但是当我尝试访问自定义视图中的视图时,应用程序崩溃并出现NullPointerException.

Boj*_*man 1

您需要使用适当的构造函数,而不是重载它们。

public class LocationItem extends RelativeLayout {

    private String parcelType;
    private int countIntoBox, countFromBox;

    private RelativeLayout deliveryContainer, pickupContainer;

    private TextView countPickup, countDelivery;

    public LocationItem(Context context) {
        super(context);
        init(context, null, 0);
    }

    public LocationItem(Context context, AttributeSet attrs) {
        super(context, attrs);
        init(context, attrs, 0);
    }

    public LocationItem(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);
        init(context, attrs, defStyle);
    }

    private void init(Context context, AttributeSet attrs, int defStyle) {
        inflate(getContext(), R.layout.list_item_location, this);
        deliveryContainer = (RelativeLayout) findViewById(R.id.rl_location_delivery_container);
        pickupContainer = (RelativeLayout) findViewById(R.id.rl_location_pickup_container);
        countPickup = (TextView) findViewById(R.id.tv_location_pickup_count);
        countDelivery = (TextView) findViewById(R.id.tv_location_delivery_count);

        countPickup.setOnClickListener(getShowNumberPickerListener());
        countDelivery.setOnClickListener(getShowNumberPickerListener());
    }

    private OnClickListener getShowNumberPickerListener() {
        return new OnClickListener() {
            @Override
            public void onClick(View view) {
                showNumberPickerDialog(view);
            }
        };
    }

    ...
}
Run Code Online (Sandbox Code Playgroud)

  • 好吧,我将视图膨胀为 View(holder) View v = inflate(getContext(), R.layout.list_item_location, this); 然后通过 v.findViewById 访问视图。现在它正在发挥作用。也许视图没有那么快地附加到根视图? (2认同)