Google Tag Manager

Showing posts with label SwingWorker. Show all posts
Showing posts with label SwingWorker. Show all posts

2014/06/02

aterai

How to create a circular progress component

Code

class ProgressCircleUI extends BasicProgressBarUI {
  @Override public Dimension getPreferredSize(JComponent c) {
    Dimension d = super.getPreferredSize(c);
    int v = Math.max(d.width, d.height);
    d.setSize(v, v);
    return d;
  }
  @Override public void paint(Graphics g, JComponent c) {
    Insets b = progressBar.getInsets(); // area for border
    int barRectWidth  = progressBar.getWidth()  - b.right - b.left;
    int barRectHeight = progressBar.getHeight() - b.top - b.bottom;
    if (barRectWidth <= 0 || barRectHeight <= 0) {
      return;
    }

    // draw the cells
    Graphics2D g2 = (Graphics2D) g.create();
    g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
                        RenderingHints.VALUE_ANTIALIAS_ON);
    g2.setPaint(progressBar.getForeground());
    double degree = 360 * progressBar.getPercentComplete();
    double sz = Math.min(barRectWidth, barRectHeight);
    double cx = b.left + barRectWidth  * .5;
    double cy = b.top  + barRectHeight * .5;
    double or = sz * .5;
    double ir = or * .5; //or - 20;
    Shape inner = new Ellipse2D.Double(cx - ir, cy - ir, ir * 2, ir * 2);
    Shape outer = new Arc2D.Double(
        cx - or, cy - or, sz, sz, 90 - degree, degree, Arc2D.PIE);
    Area area = new Area(outer);
    area.subtract(new Area(inner));
    g2.fill(area);
    g2.dispose();

    // Deal with possible text painting
    if (progressBar.isStringPainted()) {
      paintString(g, b.left, b.top, barRectWidth, barRectHeight, 0, b);
    }
  }
}
import java.awt.*;
import javax.swing.*;

public class CircularProgressTest {
  public JComponent makeUI() {
    JProgressBar progress = new JProgressBar();
    // use JProgressBar#setUI(...) method
    progress.setUI(new ProgressCircleUI());
    progress.setBorder(BorderFactory.createEmptyBorder(8, 8, 8, 8));
    progress.setStringPainted(true);
    progress.setFont(progress.getFont().deriveFont(24f));
    progress.setForeground(Color.ORANGE);

    (new Timer(50, e -> {
      int iv = Math.min(100, progress.getValue() + 1);
      progress.setValue(iv);
    })).start();

    JPanel p = new JPanel();
    p.add(progress);
    return p;
  }
  public static void main(String... args) {
    EventQueue.invokeLater(() -> {
      JFrame f = new JFrame();
      f.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
      f.getContentPane().add(new CircularProgressTest().makeUI());
      f.setSize(320, 240);
      f.setLocationRelativeTo(null);
      f.setVisible(true);
    });
  }
}

References

2014/05/01

aterai

JProgressBar in JTable cell render a progress string

Code

class Task extends SwingWorker {
  private final int lengthOfTask;
  private final int sleepDummy = new Random().nextInt(100) + 1;
  public Task(int lengthOfTask) {
    super();
    this.lengthOfTask = lengthOfTask;
  }
  @Override protected Integer doInBackground() {
    int current = 0;
    while (current < lengthOfTask && !isCancelled()) {
      current++;
      try {
        Thread.sleep(sleepDummy);
      } catch (InterruptedException ie) {
        break;
      }
      publish(new ProgressValue(lengthOfTask, current));
    }
    return sleepDummy * lengthOfTask;
  }
}

class ProgressValue {
  private final Integer progress;
  private final Integer lengthOfTask;
  public ProgressValue(Integer lengthOfTask, Integer progress) {
    this.progress = progress;
    this.lengthOfTask = lengthOfTask;
  }
  public Integer getProgress() {
    return progress;
  }
  public Integer getLengthOfTask() {
    return lengthOfTask;
  }
}

class ProgressRenderer extends DefaultTableCellRenderer {
  private final JProgressBar b = new JProgressBar();
  private final JPanel p = new JPanel(new BorderLayout());
  public ProgressRenderer() {
    super();
    setOpaque(true);
    b.setStringPainted(true);
    p.add(b);
  }
  @Override public Component getTableCellRendererComponent(
      JTable table, Object value, boolean isSelected, boolean hasFocus,
      int row, int column) {
    String text = "Done";
    if (value instanceof ProgressValue) {
      ProgressValue pv = (ProgressValue) value;
      Integer current = pv.getProgress();
      Integer lengthOfTask = pv.getLengthOfTask();
      if (current < 0) {
        text = "Canceled";
      } else if (current < lengthOfTask) {
        b.setMaximum(lengthOfTask);
        b.setValue(current);
        b.setString(String.format("%d/%d", current, lengthOfTask));
        return p;
      }
    }
    super.getTableCellRendererComponent(
        table, text, isSelected, hasFocus, row, column);
    return this;
  }
  @Override public void updateUI() {
    super.updateUI();
    if (p != null) {
      SwingUtilities.updateComponentTreeUI(p);
    }
  }
}

References

2013/06/28

aterai

Turn the JProgressBar red with JLayer and RGBImageFilter

Code

class BlockedColorLayerUI extends LayerUI{
  public boolean isPreventing = false;
  private BufferedImage bi;
  private int prevw = -1;
  private int prevh = -1;
  @Override public void paint(Graphics g, JComponent c) {
    if(isPreventing) {
      JLayer jlayer = (JLayer)c;
      JProgressBar progress = (JProgressBar)jlayer.getView();
      int w = progress.getSize().width;
      int h = progress.getSize().height;

      if(bi==null || w!=prevw || h!=prevh) {
        bi = new BufferedImage(w, h, BufferedImage.TYPE_INT_ARGB);
      }
      prevw = w;
      prevh = h;

      Graphics2D g2 = bi.createGraphics();
      super.paint(g2, c);
      g2.dispose();

      Image image = c.createImage(
          new FilteredImageSource(
              bi.getSource(), new RedGreenChannelSwapFilter()));
      //BUG: cause an infinite repaint loop: g.drawImage(image, 0, 0, c);
      g.drawImage(image, 0, 0, null);
    }else{
      super.paint(g, c);
    }
  }
}

class RedGreenChannelSwapFilter extends RGBImageFilter{
  @Override public int filterRGB(int x, int y, int argb) {
    int r = (int)((argb >> 16) & 0xff);
    int g = (int)((argb >>  8) & 0xff);
    int b = (int)((argb    ) & 0xff);
    return (argb & 0xff000000) | (g<<16) | (r<<8) | (b);
  }
}

References

2011/09/29

aterai

JProgressBar in JComboBox

Code

class ProgressCellRenderer extends DefaultListCellRenderer {
  private final JProgressBar bar = new JProgressBar() {
    @Override public Dimension getPreferredSize() {
      return ProgressCellRenderer.this.getPreferredSize();
    }
  };
  @Override public Component getListCellRendererComponent(
      JList list, Object value, int index,
      boolean isSelected, boolean cellHasFocus) {
    if(index < 0 && worker!=null && !worker.isDone()) {
      bar.setFont(list.getFont());
      bar.setBorder(BorderFactory.createEmptyBorder(0,0,0,0));
      bar.setValue(count);
      return bar;
    }else{
      return super.getListCellRendererComponent(
          list,value,index,isSelected,cellHasFocus);
    }
  }
  @Override public void updateUI() {
    super.updateUI();
    if(bar!=null) SwingUtilities.updateComponentTreeUI(bar);
  }
}

//........
button = new JButton(new AbstractAction("load") {
  @Override public void actionPerformed(ActionEvent e) {
    button.setEnabled(false);
    combo.setEnabled(false);
    combo.removeAllItems();
    worker = new SwingWorker<String, String>() {
      private int max = 30;
      @Override public String doInBackground() {
        int current = 0;
        while(current <= max && !isCancelled()) {
          try {
            Thread.sleep(50);
            //setProgress(100 * current / max);
            count = 100 * current / max;
            publish("test: "+current);
          }catch(Exception ie) {
            return "Exception";
          }
          current++;
        }
        return "Done";
      }
      @Override protected void process(java.util.List< String > chunks) {
        DefaultComboBoxModel m = (DefaultComboBoxModel)combo.getModel();
        for(String s: chunks) {
          m.addElement(s);
        }
        combo.setSelectedIndex(-1);
        combo.repaint();
      }
      @Override public void done() {
        String text = null;
        if(!isCancelled()) {
          combo.setSelectedIndex(0);
        }
        combo.setEnabled(true);
        button.setEnabled(true);
        count = 0;
      }
    };
    worker.execute();
  }
});

References

2011/07/29

aterai

Pause and Resume SwingWorker

Code

class RunAction extends AbstractAction{
  public RunAction() {
    super("run");
  }
  @Override public void actionPerformed(ActionEvent evt) {
    final JProgressBar bar1 = new JProgressBar(0, 100);
    final JProgressBar bar2 = new JProgressBar(0, 100);
    runButton.setEnabled(false);
    canButton.setEnabled(true);
    pauseButton.setEnabled(true);
    statusPanel.removeAll();
    statusPanel.add(bar1, BorderLayout.NORTH);
    statusPanel.add(bar2, BorderLayout.SOUTH);
    statusPanel.revalidate();
    worker = new SwingWorker < String, Progress > () {
      @Override public String doInBackground() {
        int current = 0;
        int lengthOfTask = 12; //filelist.size();
        publish(new Progress(Component.LOG, "Length Of Task: " + lengthOfTask));
        publish(new Progress(Component.LOG, "\n---------------------------\n"));
        while(current < lengthOfTask && !isCancelled()) {
          publish(new Progress(Component.LOG, "*"));
          if(!bar1.isDisplayable()) {
            return "Disposed";
          }
          try{
            convertFileToSomething();
          }catch(InterruptedException ie) {
            return "Interrupted";
          }
          publish(new Progress(Component.TOTAL, 100 * current / lengthOfTask));
          current++;
        }
        publish(new Progress(Component.LOG, "\n"));
        return "Done";
      }
      private final Random r = new Random();
      private void convertFileToSomething() throws InterruptedException{
        boolean flag = false;
        int current = 0;
        int lengthOfTask = 10+r.nextInt(50);
        while(current <= lengthOfTask && !isCancelled()) {
          if(isPaused) {
            try{
              Thread.sleep(500);
            }catch(InterruptedException ie) {
              return;
            }
            publish(new Progress(Component.PAUSE, flag));
            flag = !flag;
            continue;
          }
          int iv = 100 * current / lengthOfTask;
          Thread.sleep(20); // dummy
          publish(new Progress(Component.FILE, iv+1));
          current++;
        }
      }
      @Override protected void process(java.util.List < Progress > chunks) {
        for(Progress s: chunks) {
          switch(s.component) {
            case TOTAL: bar1.setValue((Integer)s.value); break;
            case FILE:  bar2.setValue((Integer)s.value); break;
            case LOG:   area.append((String)s.value); break;
            case PAUSE: {
              if((Boolean)s.value) {
                area.append("*");
              }else{
                try{
                  javax.swing.text.Document doc = area.getDocument();
                  doc.remove(area.getDocument().getLength()-1, 1);
                }catch(Exception ex) {
                    ex.printStackTrace();
                }
              }
              break;
            }
          }
        }
      }
      @Override public void done() {
        //...
      }
    };
    worker.execute();
  }
}
private boolean isPaused = false;
class PauseAction extends AbstractAction{
  public PauseAction() {
    super("pause");
  }
  @Override public void actionPerformed(ActionEvent evt) {
    isPaused = (worker!=null && !worker.isCancelled() && !isPaused);
    JButton b = (JButton)evt.getSource();
    b.setText(isPaused?"resume":"pause");
  }
}

References

2008/03/18

aterai

JProgressBar in JTable Cell

Code

class ProgressRenderer extends DefaultTableCellRenderer {
  private final JProgressBar b = new JProgressBar(0, 100);
  public ProgressRenderer() {
    super();
    setOpaque(true);
    b.setBorder(BorderFactory.createEmptyBorder(1, 1, 1, 1));
  }
  public Component getTableCellRendererComponent(JTable table, Object value,
        boolean isSelected, boolean hasFocus, int row, int column) {
    Integer i = (Integer) value;
    String text = "Done";
    if (i < 0) {
      text = "Canceled";
    } else if (i < 100) {
      b.setValue(i);
      return b;
    }
    super.getTableCellRendererComponent(table, text, isSelected, hasFocus, row, column);
    return this;
  }
}
final Executor executor = Executors.newCachedThreadPool();
final int rowNumber = model.getRowCount();
SwingWorker<Integer, Integer> worker = new SwingWorker<Integer, Integer>() {
  private int sleepDummy = new Random().nextInt(100) + 1;
  private int lengthOfTask = 120;
  @Override
  protected Integer doInBackground() {
    int current = 0;
    while (current < lengthOfTask && !isCancelled()) {
      if (!table.isDisplayable()) {
        return -1;
      }
      current++;
      try {
        Thread.sleep(sleepDummy);
      } catch (InterruptedException ie) {
        publish(-1);
        break;
      }
      publish(100 * current / lengthOfTask);
    }
    return sleepDummy * lengthOfTask;
  }
  @Override
  protected void process(List<Integer> chunks) {
    for (Integer value : chunks) {
      model.setValueAt(value, rowNumber, 2);
    }
    // model.fireTableCellUpdated(rowNumber, 2);
  }
  @Override
  protected void done() {
    String text;
    int i = -1;
    if (isCancelled()) {
      text = "Canceled";
    } else {
      try {
        i = get();
        text = (i>=0)?"Done":"Disposed";
      } catch (Exception ignore) {
        ignore.printStackTrace();
        text = ignore.getMessage();
      }
    }
    System.out.println(rowNumber +":"+text+"("+i+"ms)");
  }
};
model.addTest(new Test("example", 0), worker);
executor.execute(worker); // JDK 1.6.0_18
// worker.execute();

References