简体   繁体   中英

Which is the best way to implement ButtonListeners in different classes?

I know 3 ways to create a listener:

1. Anonymous type

 btn.addClickListener(new ButtonClickListener(){
   doSomething();
 })

2. Class inner type

btn.addClickListener(new MyButtonClickListener());
public MyButtonClickListener implements ButtonClickListener{}

3. External class

So the same above but in another class.

Problem

If I have some fields in the class who use the button and I want to do something with buttons, which is the cleanest way?

For example, I have String a = "foo" as a field and when I click the button I want to change this field.

  • Case 1: I can use MyClass.this.foo = "bar";
  • Case 2: The same.
  • Case 3: ? (Create a custom constructor with reference to the field?)

A Listener is as any other class; if you need an instance of the class to manipulate a field of another object, you pass a reference of the latter as a parameter of the constructor and save it as one of the object fields. Later, you use the public interface of the referenced object to manipulate it as you want.

Another way (which decouples the Listener class a little more) is to move all the relevant fields to the Listener class, so it's instances can manipulate them directly. Whenever you need to access those fields from the class that actually uses the Listener (the class where you created it and attached it to some component), you can retrieve them from the instance using it's public interface. Of course, you would need to save a reference of the instance, not just add it as a listener (as you would do with cases 1 and 2)

If I have some fields in the class who use the button and I want to do something with buttons, which is the cleanest way?

In general, it depends. If you look at the java tutorials from sun/oracle, you will see them doing this in different ways, too.
There is even a 4. possibility: implement the interface by the GUI class.

Personally from my experience, I would rate readability over cleverness. This means I would stick to one way and use this consistent in all cases. Only if there is a real good argument, I would think about changing the style. Every reader has an expectation what is happening and the expectation is fulfilled. If they have to start to search around or worry if something else is happening (and where), it makes reading and understanding slower.
Which leads normally to anonymous inner classes for me. They are always set inside an addListeners() method. I do some checking and if some more serious action has to be done, I call some other(outer) class method from inside the listener.

Case 1 (anonymous inner class): I can use MyClass.this.foo = "bar";

Try it. (Yes, you can call even call foo = "bar"; )

Case 2 (inner class): the same

Try it (Same case as anonymous inner class)

Case 3: ? (Create a custom constructor with reference to the field?)

Because of call by value, this will not work. (MyButtonClickListener(String foo) .. foo = "bar" changes only the local foo). You could pass by a reference to the object and call a getter like setField.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM