Search code examples
javaswingconcurrencyjtextareaevent-dispatch-thread

Thread interruption and ActionListener Java


I have a function graphics() that creates my JFrame and two JRadioButtons and adds ActionListeners to them. This graphics is called from main() and graphics itself calls game().

public void game() throws Exception
{

    jTextArea1.setLineWrap(true);
    jTextArea1.setWrapStyleWord(true);
    jTextArea1.setText("This is private information.");

    jRadioButton1.setVisible(true);
    jRadioButton2.setVisible(true);
    try {
    t.sleep(40000);
    repaint();
    } catch (InterruptedException e) {
    // We've been interrupted: no more messages.
    return;    
    }

After displaying "This is private information." in the text Area, I want the program execution to pause for 40 seconds, or until the user presses the JRadioButton, whichever is earlier. So I added an ActionListener and called t.interrupt() inside it.

private void jRadioButton1ActionPerformed(java.awt.event.ActionEvent evt) {
     t.interrupt();
    jRadioButton1.setVisible(false);
    jRadioButton2.setVisible(false);
    //System.out.println(t.interrupted());
    jTextArea1.setText("Please wait...");

    }

However, even after choosing the JRadioButton which should trigger the interrupt, that does not happen and t.interrupted returns false.

Any help would be appreciated.


Solution

  • Never, ever call Thread.sleep(...) on the Swing event thread as you will freeze the thread and effectively freeze your program. The solution is to consider use of a Swing Timer for the time-dependent portion of your requirement and using a SelectionListener for the JCheckBox or JRadioButton requirement.

    For example:

    import java.awt.event.ActionEvent;
    import java.awt.event.ActionListener;
    import java.awt.event.ItemEvent;
    import java.awt.event.ItemListener;
    
    import javax.swing.*;
    
    public class PausingExecution extends JPanel {
       private static final String SELECTED_TEXT = "Snafus are Better!!!";
       private static final String UNSELECTED_TEXT = "Fubars Rule!!";
       private static final String TIMES_UP = "Time's Up!!!!";
       private static final int TIMER_DELAY = 10 * 1000;
    
       private JTextField messageField = new JTextField(UNSELECTED_TEXT, 10);
       private JCheckBox checkBox = new JCheckBox("Click Me");
    
       public PausingExecution() {
          add(messageField);
          add(checkBox);
    
          checkBox.addItemListener(new ItemListener() {
    
             @Override
             public void itemStateChanged(ItemEvent iEvt) {
                if (iEvt.getStateChange() == ItemEvent.SELECTED) {
                   messageField.setText(SELECTED_TEXT);
                } else {
                   messageField.setText(UNSELECTED_TEXT);
                }
             }
          });
    
          Timer mySwingTimer = new Timer(TIMER_DELAY, new ActionListener() {
    
             @Override
             public void actionPerformed(ActionEvent e) {
                messageField.setText(TIMES_UP);
                checkBox.setEnabled(false);
             }
          });
    
          mySwingTimer.setRepeats(false);
          mySwingTimer.start();
       }
    
       private static void createAndShowGui() {
          PausingExecution mainPanel = new PausingExecution();
    
          JFrame frame = new JFrame("PausingExecution");
          frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
          frame.getContentPane().add(mainPanel);
          frame.pack();
          frame.setLocationByPlatform(true);
          frame.setVisible(true);
       }
    
       public static void main(String[] args) {
          SwingUtilities.invokeLater(new Runnable() {
             public void run() {
                createAndShowGui();
             }
          });
       }
    }