Jason Axelrod
Jason Axelrod

Reputation: 7805

Cant use OnClickListener in Custom Layout in Android?

So I made my own LinearLayout because I needed a horizontal number picker. I am using this custom layout twice in my activity:

enter image description here

XML:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="horizontal"
    android:layout_width="match_parent"
    android:layout_height="wrap_content">

    <Button
        android:id="@+id/button_minus"
        android:layout_width="50dp"
        android:layout_height="wrap_content"
        android:text="@string/lt"
        android:textSize="30sp"
        android:textStyle="bold" />

    <EditText
        android:id="@+id/number"
        android:layout_width="75dp"
        android:layout_height="match_parent"
        android:inputType="number"
        android:gravity="center"
        android:focusable="false"
        android:text="0" />

    <Button
        android:id="@+id/button_plus"
        android:layout_width="50dp"
        android:layout_height="wrap_content"
        android:text="@string/gt"
        android:textSize="30sp"
        android:textStyle="bold" />

</LinearLayout>

JAVA:

public class NumberPickerHorizontal extends LinearLayout
{
    private final EditText number;
    private final Button button_minus, button_plus;

    public NumberPickerHorizontal(Context context) {
        super(context);
        LayoutInflater.from(context).inflate(R.layout.numberpicker_horizontal, this, true);

        number = (EditText) findViewById(R.id.number);

        button_minus = (Button) findViewById(R.id.button_minus);
        button_minus.setOnClickListener(new View.OnClickListener() {
            public void onClick(View view) {
                int count = Integer.parseInt(number.getText().toString());
                number.setText(count--);
            }
        });

        button_plus = (Button) findViewById(R.id.button_plus);
        button_plus.setOnClickListener(new View.OnClickListener() {
            public void onClick(View view) {
                int count = Integer.parseInt(number.getText().toString());
                number.setText(count++);
            }
        });
    }
}

You'll notice I'm trying to activate the onClick methods for the plus and minus buttons... However, when I actually click the buttons, I get the following error:

android.content.res.Resources$NotFoundException: String resource ID #0x0

Not quite sure what I'm doing wrong.

Upvotes: 0

Views: 88

Answers (3)

madar
madar

Reputation: 106

You are trying to setText for 0, which should be an string resource(int). Also your new increased value is never used. Increase count before setting the text. Then use setText(String.valueOf(increased count value)).

Upvotes: 3

EpicPandaForce
EpicPandaForce

Reputation: 81568

You should do this:

<merge xmlns:android="http://schemas.android.com/apk/res/android">

    <Button
        android:id="@+id/button_minus"
        android:layout_width="50dp"
        android:layout_height="wrap_content"
        android:text="@string/lt"
        android:textSize="30sp"
        android:textStyle="bold" />

    <EditText
        android:id="@+id/number"
        android:layout_width="75dp"
        android:layout_height="match_parent"
        android:inputType="number"
        android:gravity="center"
        android:focusable="false"
        android:text="0" />

    <Button
        android:id="@+id/button_plus"
        android:layout_width="50dp"
        android:layout_height="wrap_content"
        android:text="@string/gt"
        android:textSize="30sp"
        android:textStyle="bold" />

</merge>

Java:

public class NumberPickerHorizontal extends LinearLayout
{
    private final EditText number;
    private final Button button_minus, button_plus;

    @Override
    public NumberPickerHorizontal(Context context) {
        super(context);
        init(context);
    }

    @Override
    public NumberPickerHorizontal(Context context, AttributeSet attributeSet) {
        super(context, attributeSet);
        init(context);
    }

    @TargetApi(11)
    @Override
    public NumberPickerHorizontal(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        init(context);
    }

    @TargetApi(21)
    @Override
    public NumberPickerHorizontal(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
        super(context, attrs, defStyleAttr, defStyleRes);
        init(context);
    }

    private void init(Context context) {
    //android:layout_width="match_parent"
    //android:layout_height="wrap_content"
    //set these where you instantiate the view, XML or code!

        this.setOrientation(LinearLayout.HORIZONTAL);
        LayoutInflater.from(context).inflate(R.layout.numberpicker_horizontal, this, true);

            number = (EditText) findViewById(R.id.number);

            button_minus = (Button) findViewById(R.id.button_minus);
            button_minus.setOnClickListener(new View.OnClickListener() {
                public void onClick(View view) {
                    int count = Integer.parseInt(number.getText().toString());
                    count--;
                    number.setText(String.valueOf(count));
                }
            });

            button_plus = (Button) findViewById(R.id.button_plus);
            button_plus.setOnClickListener(new View.OnClickListener() {
                public void onClick(View view) {
                    int count = Integer.parseInt(number.getText().toString());
                    count++;
                    number.setText(String.valueOf(count));
                }
            });
    }

So the changes were:

1.) added <merge> to remove the duplicate layout

2.) added the remaining 3 constructors for the view in case the framework calls them

3.) added String.valueOf() around your int so that it's not perceived as a resource identifier by setText().

Upvotes: 1

P. Jairaj
P. Jairaj

Reputation: 1033

Try this:

View v = LayoutInflater.from(context).inflate(R.layout.numberpicker_horizontal, this, true);

And replace all findViewById by v.findViewById

Upvotes: -1

Related Questions