Search code examples
javaandroidonclicklistenercustom-button

How to set on click listener for a custom button?


I tried to setup my listener for my custom button class. However, it seems that my listener doesn't map to the View. Any idea to combine my button view and my custom button?

I have my fragment with a custom button on a linear layout XML

<LinearLayout>
 ...
<Button>
...
</Button>

<LinearLayout>

I tried to setup a click listener for the button in the fragment at onActivityCreated method.

public class myFragment extend Fragment {

@Override
public void onActivityCreated (){

Button myNewButton = new myButton();
myNewButton = root.findViewByID.(R.id.button);
myNewButton.setOnClickListener(new myButton());

}

}

My custom button class with a setonclicklistener method

public class myButton extend button implements View.onClicklistener {

@Override
public void setOnClickListener (OnClickListener listener){
super.setonClickListener(listener);
}

@Override
public void onClick(View view) {
//action to do after on click
}

}

Solution

  • You seem to be setting another button as the listener for your original button, depending on what actions you hope to do in the listener, this can have unexpected behavior.

    The easier solution would be to set itself as the listener, Whilst you've implemented View.onClicklistener in your MyButton, you haven't set that as the listener to itself. You'll need to do so in the constructor.

    If you wish to support user set onClickListeners along with the MyButton listener, then you'll need to maintain a listener variable in your MyButton class which you can then explicitly call.

    Finally, use your MyButton in your layout directly, instead of using Button as you currently seem to be doing.

    Your final MyButton class should be something along the following lines,

    public class MyButton extends androidx.appcompat.widget.AppCompatButton implements View.OnClickListener {
    
        public MyButton(Context context) {
            super(context);
            init();
        }
    
        public MyButton(Context context, AttributeSet attrs) {
            super(context, attrs);
            init();
        }
    
        public MyButton(Context context, AttributeSet attrs, int defStyleAttr) {
            super(context, attrs, defStyleAttr);
            init();
        }
    
        private void init() {
            setOnClickListener(this);
        }
    
        private View.OnClickListener mUserOnClickListener;
    
        @Override
        public void setOnClickListener(@Nullable OnClickListener l) {
            if (l == this) {
                super.setOnClickListener(l);
            } else {
                mUserOnClickListener = l;
            }
        }
    
        @Override
        public void onClick(View v) {
            //Your actions
            Toast.makeText(getContext(), "MyButton clicked", Toast.LENGTH_SHORT).show();
            if (mUserOnClickListener != null) {
                mUserOnClickListener.onClick(v);
            }
        }
    }
    

    P.S - I'd also suggest you go through naming conventions for Java.