Java Tutorial/Swing/SwingWorker

Материал из Java эксперт
Перейти к: навигация, поиск

14. extends generic SwingWorker

   <source lang="java">

/*

* Copyright (c) 1995 - 2008 Sun Microsystems, Inc.  All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
*   - Redistributions of source code must retain the above copyright
*     notice, this list of conditions and the following disclaimer.
*
*   - Redistributions in binary form must reproduce the above copyright
*     notice, this list of conditions and the following disclaimer in the
*     documentation and/or other materials provided with the distribution.
*
*   - Neither the name of Sun Microsystems nor the names of its
*     contributors may be used to endorse or promote products derived
*     from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
* IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/

import java.awt.GridBagConstraints; import java.awt.GridBagLayout; import java.awt.Insets; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.util.List; import java.util.Random; import javax.swing.BorderFactory; import javax.swing.JButton; import javax.swing.JFrame; import javax.swing.JTextField; import javax.swing.SwingUtilities; import javax.swing.SwingWorker; import javax.swing.border.Border; public class Flipper extends JFrame implements ActionListener {

 private final GridBagConstraints constraints;
 private final JTextField headsText, totalText, devText;
 private final Border border = BorderFactory.createLoweredBevelBorder();
 private final JButton startButton, stopButton;
 private FlipTask flipTask;
 private JTextField makeText() {
   JTextField t = new JTextField(20);
   t.setEditable(false);
   t.setHorizontalAlignment(JTextField.RIGHT);
   t.setBorder(border);
   getContentPane().add(t, constraints);
   return t;
 }
 private JButton makeButton(String caption) {
   JButton b = new JButton(caption);
   b.setActionCommand(caption);
   b.addActionListener(this);
   getContentPane().add(b, constraints);
   return b;
 }
 public Flipper() {
   super("Flipper");
   setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
   // Make text boxes
   getContentPane().setLayout(new GridBagLayout());
   constraints = new GridBagConstraints();
   constraints.insets = new Insets(3, 10, 3, 10);
   headsText = makeText();
   totalText = makeText();
   devText = makeText();
   // Make buttons
   startButton = makeButton("Start");
   stopButton = makeButton("Stop");
   stopButton.setEnabled(false);
   // Display the window.
   pack();
   setVisible(true);
 }
 private static class FlipPair {
   private final long heads, total;
   FlipPair(long heads, long total) {
     this.heads = heads;
     this.total = total;
   }
 }
 private class FlipTask extends SwingWorker<Void, FlipPair> {
   @Override
   protected Void doInBackground() {
     long heads = 0;
     long total = 0;
     Random random = new Random();
     while (!isCancelled()) {
       total++;
       if (random.nextBoolean()) {
         heads++;
       }
       publish(new FlipPair(heads, total));
     }
     return null;
   }
   @Override
   protected void process(List<FlipPair> pairs) {
     FlipPair pair = pairs.get(pairs.size() - 1);
     headsText.setText(String.format("%d", pair.heads));
     totalText.setText(String.format("%d", pair.total));
     devText.setText(String.format("%.10g", ((double) pair.heads)
         / ((double) pair.total) - 0.5));
   }
 }
 public void actionPerformed(ActionEvent e) {
   if ("Start" == e.getActionCommand()) {
     startButton.setEnabled(false);
     stopButton.setEnabled(true);
     (flipTask = new FlipTask()).execute();
   } else if ("Stop" == e.getActionCommand()) {
     startButton.setEnabled(true);
     stopButton.setEnabled(false);
     flipTask.cancel(true);
     flipTask = null;
   }
 }
 public static void main(String[] args) {
   SwingUtilities.invokeLater(new Runnable() {
     public void run() {
       new Flipper();
     }
   });
 }

}</source>





14. Progress Monitor and Swingworker

   <source lang="java">

/*

* Copyright (c) 1995 - 2008 Sun Microsystems, Inc.  All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
*   - Redistributions of source code must retain the above copyright
*     notice, this list of conditions and the following disclaimer.
*
*   - Redistributions in binary form must reproduce the above copyright
*     notice, this list of conditions and the following disclaimer in the
*     documentation and/or other materials provided with the distribution.
*
*   - Neither the name of Sun Microsystems nor the names of its
*     contributors may be used to endorse or promote products derived
*     from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
* IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/

import java.awt.BorderLayout; import java.awt.Insets; import java.awt.Toolkit; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.beans.PropertyChangeEvent; import java.beans.PropertyChangeListener; import java.util.Random; import javax.swing.BorderFactory; import javax.swing.JButton; import javax.swing.JComponent; import javax.swing.JFrame; import javax.swing.JPanel; import javax.swing.JScrollPane; import javax.swing.JTextArea; import javax.swing.ProgressMonitor; import javax.swing.SwingWorker; public class ProgressMonitorDemo extends JPanel implements ActionListener,

   PropertyChangeListener {
 private ProgressMonitor progressMonitor;
 private JButton startButton;
 private JTextArea taskOutput;
 private Task task;
 class Task extends SwingWorker<Void, Void> {
   @Override
   public Void doInBackground() {
     Random random = new Random();
     int progress = 0;
     setProgress(0);
     try {
       Thread.sleep(1000);
       while (progress < 100 && !isCancelled()) {
         // Sleep for up to one second.
         Thread.sleep(random.nextInt(1000));
         // Make random progress.
         progress += random.nextInt(10);
         setProgress(Math.min(progress, 100));
       }
     } catch (InterruptedException ignore) {
     }
     return null;
   }
   @Override
   public void done() {
     Toolkit.getDefaultToolkit().beep();
     startButton.setEnabled(true);
     progressMonitor.setProgress(0);
   }
 }
 public ProgressMonitorDemo() {
   super(new BorderLayout());
   // Create the demo"s UI.
   startButton = new JButton("Start");
   startButton.setActionCommand("start");
   startButton.addActionListener(this);
   taskOutput = new JTextArea(5, 20);
   taskOutput.setMargin(new Insets(5, 5, 5, 5));
   taskOutput.setEditable(false);
   add(startButton, BorderLayout.PAGE_START);
   add(new JScrollPane(taskOutput), BorderLayout.CENTER);
   setBorder(BorderFactory.createEmptyBorder(20, 20, 20, 20));
 }
 /**
  * Invoked when the user presses the start button.
  */
 public void actionPerformed(ActionEvent evt) {
   progressMonitor = new ProgressMonitor(ProgressMonitorDemo.this,
       "Running a Long Task", "", 0, 100);
   progressMonitor.setProgress(0);
   task = new Task();
   task.addPropertyChangeListener(this);
   task.execute();
   startButton.setEnabled(false);
 }
 /**
  * Invoked when task"s progress property changes.
  */
 public void propertyChange(PropertyChangeEvent evt) {
   if ("progress" == evt.getPropertyName()) {
     int progress = (Integer) evt.getNewValue();
     progressMonitor.setProgress(progress);
     String message = String.format("Completed %d%%.\n", progress);
     progressMonitor.setNote(message);
     taskOutput.append(message);
     if (progressMonitor.isCanceled() || task.isDone()) {
       Toolkit.getDefaultToolkit().beep();
       if (progressMonitor.isCanceled()) {
         task.cancel(true);
         taskOutput.append("Task canceled.\n");
       } else {
         taskOutput.append("Task completed.\n");
       }
       startButton.setEnabled(true);
     }
   }
 }
 /**
  * Create the GUI and show it. For thread safety, this method should be
  * invoked from the event-dispatching thread.
  */
 private static void createAndShowGUI() {
   // Create and set up the window.
   JFrame frame = new JFrame("ProgressMonitorDemo");
   frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
   // Create and set up the content pane.
   JComponent newContentPane = new ProgressMonitorDemo();
   newContentPane.setOpaque(true); // content panes must be opaque
   frame.setContentPane(newContentPane);
   // Display the window.
   frame.pack();
   frame.setVisible(true);
 }
 public static void main(String[] args) {
   // Schedule a job for the event-dispatching thread:
   // creating and showing this application"s GUI.
   javax.swing.SwingUtilities.invokeLater(new Runnable() {
     public void run() {
       createAndShowGUI();
     }
   });
 }

}</source>





14. SwingWorker in Java 6

   <source lang="java">

import java.awt.LayoutManager; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.beans.PropertyChangeEvent; import java.beans.PropertyChangeListener; import java.util.List; import javax.swing.BoxLayout; import javax.swing.JButton; import javax.swing.JFrame; import javax.swing.JPanel; import javax.swing.JProgressBar; import javax.swing.JScrollPane; import javax.swing.JTextArea; import javax.swing.SwingWorker; public class Main{

 public static void main(String[] args) {
   final JProgressBar progressBar = new JProgressBar(0, 10);
   final CounterTask task = new CounterTask();
   task.addPropertyChangeListener(new PropertyChangeListener() {
     public void propertyChange(PropertyChangeEvent evt) {
       if ("progress".equals(evt.getPropertyName())) {
         progressBar.setValue((Integer) evt.getNewValue());
       }
     }
   });
   JButton startButton = new JButton("Start");
   startButton.addActionListener(new ActionListener() {
     public void actionPerformed(ActionEvent e) {
       task.execute();
     }
   });
   JButton cancelButton = new JButton("Cancel");
   cancelButton.addActionListener(new ActionListener() {
     public void actionPerformed(ActionEvent e) {
       task.cancel(true);
     }
   });
   JPanel buttonPanel = new JPanel();
   buttonPanel.add(startButton);
   buttonPanel.add(cancelButton);
   JPanel cp = new JPanel();
   LayoutManager layout = new BoxLayout(cp, BoxLayout.Y_AXIS);
   cp.setLayout(layout);
   cp.add(buttonPanel);
   cp.add(progressBar);
   JFrame frame = new JFrame();
   frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
   frame.setContentPane(cp);
   frame.pack();
   frame.setVisible(true);
 }

} class CounterTask extends SwingWorker<Integer, Integer> {

 int DELAY = 1000;
 @Override
 protected Integer doInBackground() throws Exception {
   int i = 0;
   int count = 10;
   while (!isCancelled() && i < count) {
     i++;
     publish(new Integer[] { i });
     setProgress(count * i / count);
     Thread.sleep(DELAY);
   }
   return count;
 }   
 protected void process(List<Integer> chunks) {
     System.out.println(chunks);
 }
 @Override
 protected void done() {
   if (isCancelled())
     System.out.println("Cancelled !");
   else
     System.out.println("Done !");
 }

}</source>





14. Use SwingWorker to perform background tasks

   <source lang="java">

import java.awt.FlowLayout; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import javax.swing.JButton; import javax.swing.JFrame; import javax.swing.JOptionPane; import javax.swing.SwingWorker; public class Main extends JFrame {

 public Main() {
   this.setLayout(new FlowLayout());
   this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
   JButton processButton = new JButton("Start");
   JButton helloButton = new JButton("Hello");
   processButton.addActionListener(new ActionListener() {
     public void actionPerformed(ActionEvent event) {
       MyTask process = new MyTask();
       try {
         process.execute();
       } catch (Exception e) {
         e.printStackTrace();
       }
     }
   });
   helloButton.addActionListener(new ActionListener() {
     public void actionPerformed(ActionEvent e) {
       JOptionPane.showMessageDialog(null, "Hello There");
     }
   });
   this.getContentPane().add(processButton);
   this.getContentPane().add(helloButton);
   this.pack();
   setVisible(true);
 }
 public static void main(String[] args) {
   new Main();
 }

} class MyTask extends SwingWorker {

 protected Object doInBackground() throws Exception {
   Integer result = new Integer(0);
   for (int i = 0; i < 10; i++) {
     result += i * 10;
     try {
       Thread.sleep(5000);
     } catch (Exception e) {
       e.printStackTrace();
     }
   }
   return result;
 }

}</source>