Pergunta

I have simple custom button:

public class myButton extends Button {
    public myButton (Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);
        commonConstructorCode();
    }


    public myButton (Context context, AttributeSet attrs) {
        super(context, attrs);
        commonConstructorCode();
    }

  public myButton (Context context) {
    super(context);
    commonConstructorCode();
  }

      private void commonConstructorCode() {
                this.setOnTouchListener(new OnTouchListener() {
      @Override
      public boolean onTouch(View v, MotionEvent event) {
                int action = event.getAction(); 

                    if(action == MotionEvent.ACTION_DOWN) 
                    {
                      //Just to be sure that we removed all callbacks, 
                      // which should have occurred in the ACTION_UP
                      removeCallbacks(repeatClickWhileButtonHeldRunnable);

                      //Perform the default click action.
                      performClick();
                      //if(v.isEnabled()){
                      //Schedule the start of repetitions after a one half second delay.
                      postDelayed(repeatClickWhileButtonHeldRunnable, initialRepeatDelay);
                      //} else {
                        //  removeCallbacks(repeatClickWhileButtonHeldRunnable);
                      //}
                    }
                    else if(action == MotionEvent.ACTION_UP) {
                      //Cancel any repetition in progress.
                      removeCallbacks(repeatClickWhileButtonHeldRunnable);
                    }
                //Returning true here prevents performClick() from getting called 
                // in the usual manner, which would be redundant, given that we are 
                // already calling it above.
                return true;
      }
    });
      }
}

with selector

<?xml version="1.0" encoding="utf-8"?>
 <selector xmlns:android="http://schemas.android.com/apk/res/android">
     <item android:state_pressed="true"
           android:drawable="@drawable/button_pressed" /> <!-- pressed -->
     <item android:state_focused="true"
           android:drawable="@android:color/white" /> <!-- focused -->
     <item android:drawable="@drawable/button_standard" /> <!-- default -->
 </selector>

set by

<com.blabla.myButton
    ...
    background="@drawable/button_selector" />

Background in "normal" state is fine. But other states don't work at all. What is strange - when I change

<com.blabla.myButton

to

<Button

selector works perfectly fine.

Any ideas?

Edit: I added commonConstructorCode().

Foi útil?

Solução

I replicated your code and got the custom button selector working but setting:

        @Override
        public boolean onTouch(View v, MotionEvent event) {
            // Blah blah blah....
            return false; // this was return true
        }
    });

According to the android docs, public boolean onTouch(),

Returns: True if the listener has consumed the event, false otherwise.

So returning true indicates your method has consumed the event and seems to stop it perculating up the hierarchy and triggering the selector states.

Outras dicas

You could try setting this on the custom xml view.

android:focusable = "true" 

I had a similar issue and setting focusable to true allowed the view to read the correct state and apply the selector.

In constructor of your class, use following code:

this.setBackgroundResource(drawable.button_selector);

I try it. Works perfectly

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top