1

I'm trying to add a shortcut to my JButton. I've read How to Use Key Bindings tutorial and I also have read this page How to use Key Bindings instead of Key Listeners and a loooooooooooooot of other questions about key bindings, but haven't found any answer for me

What I've tried:

public class Example extends JFrame {

    public static void main(String args[]) {
        Example example = new Example();
    }

    Example(){
        Action action = new Action() {
            @Override
            public Object getValue(String key) {
                return null;
            }

            @Override
            public void putValue(String key, Object value) {

            }

            @Override
            public void setEnabled(boolean b) {

            }

            @Override
            public boolean isEnabled() {
                return false;
            }

            @Override
            public void addPropertyChangeListener(PropertyChangeListener listener) {

            }

            @Override
            public void removePropertyChangeListener(PropertyChangeListener listener) {

            }

            @Override
            public void actionPerformed(ActionEvent e) {
                System.out.println("Hello World!");
            }
        };

        JButton button = new JButton("Hello World!");
        button.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW).put(KeyStroke.getKeyStroke("RIGHT"), "doSomething");
        button.getActionMap().put("doSomething", action);
        button.addActionListener(action);

        add(button);
        setVisible(true);
        pack();
    }

}

I've also tried to make it like that: getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW).put(KeyStroke.getKeyStroke(KeyEvent.VK_RIGHT, 0, true), "doSmth");

But nothing seems to be working, what am I doing wrong?

Community
  • 1
  • 1
Ethan
  • 94
  • 1
  • 15
  • Your very first example works for me. What do you mean by "and has `actionPerformed` function"? – Ordous Jul 28 '16 at 12:40
  • 1
    Post a [mcve]. Your problem is not in the code snippets you gave. – user1803551 Jul 28 '16 at 12:41
  • I have edited the question, now it shows `NextCardListener`. I meant that it should do smth, sorry – Ethan Jul 28 '16 at 12:51
  • Tip: Add @user1803551 (or whoever, the `@` is important) to *notify* the person of a new comment. While on the subject, please post the MCVE (before this is closed for lack of one). – Andrew Thompson Jul 28 '16 at 13:20
  • 1
    @EthanGills Pro hint: The `isEnabled()` method is not there for shits and giggles. You want to return `true` there, rather than `false`. A much easier way to do this would be to use `AbstractAction` rather than `Action`, since you apparently don't know how those work. Also, please don't swear in sample code. – Ordous Jul 28 '16 at 13:22
  • BTW - `JButton button = new JButton("Suqa");` should be `JButton button = new JButton(suqaBlyat);` – Andrew Thompson Jul 28 '16 at 13:22
  • @AndrewThompson You'll notice that the button has the action listener explicitly added later. It's perfectly fine to pass in a string to the button for text rather than the action. – Ordous Jul 28 '16 at 13:25
  • @Ordous I've changed `Action` to `AbstractAction` and it works perfectly! Thank you a lot! I've also removed swears from sample code, I'm sorry. – Ethan Jul 28 '16 at 13:34
  • Please don't add things like `[SOLVED]` to a title. I have reverted that edit. Accepting an answer is enough indication. If there is no answer to accept, post your own. – Mark Rotteveel Jul 28 '16 at 13:40
  • @MarkRotteveel okay, I'm sorry – Ethan Jul 28 '16 at 13:43

1 Answers1

3

Your Action has a method called isEnabled that you've implemented. The Javadoc on it states:

/**
 * Returns the enabled state of the <code>Action</code>. When enabled,
 * any component associated with this object is active and
 * able to fire this object's <code>actionPerformed</code> method.
 *
 * @return true if this <code>Action</code> is enabled
 */

Since you return a hardcoded false, the Action is never enabled and the actionPerformed method is never called. Your problem is not the binding, it's the action itself!

A simple fix is to change isEnabled to return true, or, even simpler yet, use AbstractAction in place of Action, and override only actionPerformed (AbstractAction is kind of the "I don't care about all this stuff, just give me the simplest thing possible with one method to implement!")

Ordous
  • 3,844
  • 15
  • 25