kind of MetaClass-y

I wanted to do something with a closure where my action listener didn’t have to know what events to use… e.g. normally, you’d tell the implemented ActionListener that if (event.name) == “bob” or whatever then perform an action

in this case, we’re going to use a simple ActionListener that doesn’t care about the event, just does whatever we tell it.

In this case, I want my swing ActionListener on a button to printout information to the console. Normally, I’d just tell the ActionListener System.out.println(“text”). We’re going to do something a little different.

We’re going to declare an ActionListener that has no idea what it’s doing until we tell it in the main code and not anywhere else. Basically, our implementation is “blind” in a way. It doesn’t care what it gets as long as we have told it what to do.

We’ll start with GButton extending JButton

import javax.swing.JButton

public class GButton extends JButton {
/**
* Construct a new ‘anonymous’ action
* and register it with the button.
*/
public void addActionListener(Closure code) {
addActionListener(new GAction(code));
}

as you can see, we’ve overloaded addActionListener so it takes a Closure, that then places an AbstractAction into the Button.

The GAction implements ActionListener

import javax.swing.AbstractAction;

import java.awt.event.ActionEvent;
import groovy.lang.Closure;

public class GAction extends AbstractAction {
Closure code;

GAction(Closure c) { code= c; }

public void actionPerformed(ActionEvent e) { code(); }
}

This is a little confusing, but not really. What we’ve done is overload the constructor to take a closure that we’re going to set locally. When the actionPerformed is called it will simply run the closure code. Make sense? Instead of hardcoding our action in another class, we’ve given a virtual call, more or less.

import javax.swing.JFrame;
import javax.swing.JButton;

def f = new JFrame();
def b = new GButton();

b.setText(“press me”);

b.addActionListener{ println ‘hello world’ } // <– cool!

f.getContentPane().add(b);
f.pack()
f.show()
f.setVisible(true);

Here, as you can see, we’ve put this into action.

When the actionListener is called by the button, it will printout hello world to hte console. You could do anything… like have it call another class, or whatever. Doesn’t matter… just another example of how Groovy is awesome

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s

This site uses Akismet to reduce spam. Learn how your comment data is processed.