Rodion Altshuler
Rodion Altshuler

Reputation: 1783

How to get access to protected field of a Button?

We have method in Android for setting OnClickListener for a Button (button.setOnClickListener(....), but no .getOnClickListener.

I need to get listener assigned to a Button and save it in variable.

OnClickListener is protected field of Button class, inherited from TextView, inherited from View class. Name of the field "mOnClickListener". I can't get it even through reflection:

    ...
    Button button1 = (Button) findViewById(R.id.button1);
    OnClickListener listener = getListener(button1);
    ...

    public OnClickListener getListener(Button b) {

 java.lang.reflect.Field field =  b.getClass().getSuperclass().getSuperclass().getDeclaredField("mOnClickListener");
...
    }

getting "noSuchFieldException". Any ideas to make it possible?

PS I know other ways to make my app work without reflection, just wondering why it does not work.

Upvotes: 1

Views: 819

Answers (3)

ben75
ben75

Reputation: 28706

You get this error because your are not starting from the button. Instead do this :

 java.lang.reflect.Field field =  View.class.getField("mOnClickListener");

and when you have the field make it accessible:

try{
   field.setAccessible(true);
   Object clickListener = field.get(b);
   field.setAccessible(false);
}catch(Exception e){
    e.printStacktrace();
}

Upvotes: 1

RoflcoptrException
RoflcoptrException

Reputation: 52229

You are calling the method getClass in your class. Instead you should call getClass on an object of the Button class, or use the class field:

Button.class.getSuperClass().getSuperClass().getDeclaredField("mOnClickListener"):

Another way to do that:

Button.class.getField("mOnClickListener");

The method getField includes fields that are inherited from super classes.

Upvotes: 2

Stefan de Bruijn
Stefan de Bruijn

Reputation: 6319

You wanna make the field accessible.

So you'll basically wind up with something like

Field f = obj.getClass().getDeclaredField("mOnClickListener");
f.setAccessible(true);

Upvotes: 1

Related Questions