View Javadoc

    1   /*
    2    * Created on 2005-maj-07
    3    */
    4   package com.eviware.soapui.support.swing;
    5
    6   import com.eviware.soapui.support.UISupport;
    7
    8   /***
    9    * This is the 3rd version of SwingWorker (also known as
    10   * SwingWorker 3), an abstract class that you subclass to
    11   * perform GUI-related work in a dedicated thread.  For
    12   * instructions on and examples of using this class, see:
    13   *
    14   * http://java.sun.com/docs/books/tutorial/uiswing/misc/threads.html
    15   *
    16   * Note that the API changed slightly in the 3rd version:
    17   * You must now invoke start() on the SwingWorker after
    18   * creating it.
    19   */
    20  public abstract class SwingWorker {
    21      private Object value;  // see getValue(), setValue()
    22
    23      /***
    24       * Class to maintain reference to current worker thread
    25       * under separate synchronization control.
    26       */
    27      private static class ThreadVar {
    28          private Thread thread;
    29          ThreadVar(Thread t) { thread = t; }
    30          synchronized Thread get() { return thread; }
    31          synchronized void clear() { thread = null; }
    32      }
    33
    34      private ThreadVar threadVar;
    35
    36      /***
    37       * Get the value produced by the worker thread, or null if it
    38       * hasn't been constructed yet.
    39       */
    40      public synchronized Object getValue() {
    41          return value;
    42      }
    43
    44      /***
    45       * Set the value produced by worker thread
    46       */
    47      public synchronized void setValue(Object x) {
    48          value = x;
    49      }
    50
    51      /***
    52       * Compute the value to be returned by the <code>get</code> method.
    53       */
    54      public abstract Object construct();
    55
    56      /***
    57       * Called on the event dispatching thread (not on the worker thread)
    58       * after the <code>construct</code> method has returned.
    59       */
    60      public void finished() {
    61      }
    62
    63      /***
    64       * A new method that interrupts the worker thread.  Call this method
    65       * to force the worker to stop what it's doing.
    66       */
    67      public void interrupt() {
    68          Thread t = threadVar.get();
    69          if (t != null) {
    70              t.interrupt();
    71          }
    72          threadVar.clear();
    73      }
    74
    75      /***
    76       * Return the value created by the <code>construct</code> method.
    77       * Returns null if either the constructing thread or the current
    78       * thread was interrupted before a value was produced.
    79       *
    80       * @return the value created by the <code>construct</code> method
    81       */
    82      public Object get() {
    83          while (true) {
    84              Thread t = threadVar.get();
    85              if (t == null) {
    86                  return getValue();
    87              }
    88              try {
    89                  t.join();
    90              }
    91              catch (InterruptedException e) {
    92                  Thread.currentThread().interrupt(); // propagate
    93                  return null;
    94              }
    95          }
    96      }
    97
    98
    99      /***
    100      * Start a thread that will call the <code>construct</code> method
    101      * and then exit.
    102      */
    103     public SwingWorker() {
    104         final Runnable doFinished = new Runnable() {
    105            public void run() { finished(); }
    106         };
    107
    108         Runnable doConstruct = new Runnable() {
    109             public void run() {
    110                 try {
    111                     setValue(construct());
    112                 }
    113                 finally {
    114                     threadVar.clear();
    115                 }
    116
    117                 UISupport.invokeLater(doFinished);
    118             }
    119         };
    120
    121         Thread t = new Thread(doConstruct, "SwingWorker");
    122         threadVar = new ThreadVar(t);
    123     }
    124
    125     /***
    126      * Start the worker thread.
    127      */
    128     public void start() {
    129         Thread t = threadVar.get();
    130         if (t != null) {
    131             t.start();
    132         }
    133     }
    134 }