Google Tag Manager

2009/12/21

snap to ticks drag JSlider

Code

slider.setUI(new MetalSliderUI() {
  protected TrackListener createTrackListener(final JSlider slider) {
    return new TrackListener() {
      public void mouseDragged(MouseEvent e) {
        if(!slider.getSnapToTicks() || slider.getMajorTickSpacing()==0) {
          super.mouseDragged(e);
          return;
        }
        //case JSlider.HORIZONTAL:
        int halfThumbWidth    = thumbRect.width / 2;
        int trackLength = trackRect.width;
        int trackLeft  = trackRect.x-halfThumbWidth;
        int trackRight = trackRect.x+(trackRect.width-1)+halfThumbWidth;
        int xPos = e.getX();
        int snappedPos = xPos;
        if (xPos < = trackLeft) {
          snappedPos = trackLeft;
        } else if (xPos > = trackRight) {
          snappedPos = trackRight;
        } else {
          //int tickSpacing = slider.getMajorTickSpacing();
          //float actualPixelsForOneTick = trackLength * tickSpacing
          //                                 / (float)slider.getMaximum();
          // a problem if you choose to set a negative MINIMUM for
          // the JSlider; the calculated drag-positions are wrong.
          // Fixed by bobndrew:
          int possibleTickPositions=slider.getMaximum()-slider.getMinimum();
          int tickSpacing = (slider.getMinorTickSpacing()==0)
                            ? slider.getMajorTickSpacing()
                            : slider.getMinorTickSpacing();
          float actualPixelsForOneTick = trackLength * tickSpacing
                                         / (float)possibleTickPositions;
          xPos -= trackLeft;
          snappedPos=(int)(
            (Math.round(xPos/actualPixelsForOneTick)*actualPixelsForOneTick)+0.5)
            +trackLeft;
          offset = 0;
        }
        MouseEvent me = new MouseEvent(
          e.getComponent(), e.getID(), e.getWhen(), e.getModifiers(),
          snappedPos, e.getY(),
          e.getXOnScreen(), e.getYOnScreen(),
          e.getClickCount(), e.isPopupTrigger(), e.getButton());
        super.mouseDragged(me);
      }
    };
  }
});

References

2009/11/30

Jump to clicked position JSlider

Code

slider.setUI(new MetalSliderUI() {
  @Override protected TrackListener createTrackListener(JSlider slider) {
    return new TrackListener() {
      @Override public void mousePressed(MouseEvent e) {
        if (UIManager.getBoolean("Slider.onlyLeftMouseButtonDrag")
              && SwingUtilities.isLeftMouseButton(e)) {
          JSlider slider = (JSlider) e.getComponent();
          switch (slider.getOrientation()) {
          case SwingConstants.VERTICAL:
            slider.setValue(valueForYPosition(e.getY()));
            break;
          case SwingConstants.HORIZONTAL:
            slider.setValue(valueForXPosition(e.getX()));
            break;
          default:
            throw new IllegalArgumentException("orientation must be one of: VERTICAL, HORIZONTAL");
          }
          super.mousePressed(e); //isDragging = true;
          super.mouseDragged(e);
        } else {
          super.mousePressed(e);
        }
      }
      @Override public boolean shouldScroll(int direction) {
        return false;
      }
    };
  }
});

References

2009/11/13

add JInternalFrame to Undecorated JFrame

Code

//JFrame without close, minimize, maximize buttons.
final JInternalFrame internal = new JInternalFrame();
BasicInternalFrameUI ui = (BasicInternalFrameUI)internal.getUI();
Component title = ui.getNorthPane();
for(MouseMotionListener l:title.getListeners(MouseMotionListener.class)) {
  title.removeMouseMotionListener(l);
}
DragWindowListener dwl = new DragWindowListener();
title.addMouseListener(dwl);
title.addMouseMotionListener(dwl);
JPanel p = new JPanel(new BorderLayout());
p.add(new JScrollPane(new JTree()));
p.add(new JButton(new AbstractAction("close") {
  public void actionPerformed(ActionEvent e) {
    Window w = SwingUtilities.windowForComponent((Component)e.getSource());
    w.getToolkit().getSystemEventQueue().postEvent(
      new WindowEvent(w, WindowEvent.WINDOW_CLOSING));
  }
}), BorderLayout.SOUTH);
internal.getContentPane().add(p);
internal.setVisible(true);
KeyboardFocusManager focusManager = KeyboardFocusManager.getCurrentKeyboardFocusManager();
focusManager.addPropertyChangeListener(new PropertyChangeListener() {
  public void propertyChange(PropertyChangeEvent e) {
    String prop = e.getPropertyName();
    if("activeWindow".equals(prop)) {
      try{
        internal.setSelected(e.getNewValue()!=null);
      }catch(PropertyVetoException ex) {
        ex.printStackTrace();
      }
    }
  }

References

2009/10/29

JCheckBoxMenuItem Icon

Code

UIManager.put("CheckBoxMenuItem.checkIcon", new Icon() {
  public void paintIcon(Component c, Graphics g, int x, int y) {
    Graphics2D g2 = (Graphics2D)g;
    g2.translate(x,y);
    ButtonModel m = ((AbstractButton)c).getModel();
    g2.setPaint(m.isSelected()?Color.ORANGE:Color.GRAY);
    g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
                        RenderingHints.VALUE_ANTIALIAS_ON);
    g2.fillOval( 0, 2, 10, 10 );
    g2.translate(-x,-y);
  }
  public int getIconWidth()  { return 14; }
  public int getIconHeight() { return 14; }
});
menu.add(new JCheckBoxMenuItem("checkIcon test"));

References

2009/10/06

Multiple JButtons in a JTable cell

Code

class ButtonsPanel extends JPanel {
  public final List buttons =
    Arrays.asList(new JButton("view"), new JButton("edit"));
  public ButtonsPanel() {
    super();
    setOpaque(true);
    for(JButton b: buttons) {
      b.setFocusable(false);
      b.setRolloverEnabled(false);
      add(b);
    }
  }
}
class ButtonsRenderer extends ButtonsPanel
                      implements TableCellRenderer {
  public ButtonsRenderer() {
    super();
    setName("Table.cellRenderer");
  }
  @Override public Component getTableCellRendererComponent(JTable table,
        Object value, boolean isSelected, boolean hasFocus, int row, int column) {
    setBackground(isSelected?table.getSelectionBackground():table.getBackground());
    return this;
  }
}
class ButtonsEditor extends ButtonsPanel
                    implements TableCellEditor {
  public ButtonsEditor(final JTable table) {
    super();
    //---->
    //DEBUG: view button click -> control key down + edit button(same cell) press
    //       -> remain selection color
    MouseListener ml = new MouseAdapter() {
      public void mousePressed(MouseEvent e) {
        ButtonModel m = ((JButton)e.getSource()).getModel();
        if(m.isPressed() && table.isRowSelected(table.getEditingRow())
                         && e.isControlDown()) {
          setBackground(table.getBackground());
        }
      }
    };
    buttons.get(0).addMouseListener(ml);
    buttons.get(1).addMouseListener(ml);
    //<----

    buttons.get(0).addActionListener(new ActionListener() {
      @Override public void actionPerformed(ActionEvent e) {
        fireEditingStopped();
        JOptionPane.showMessageDialog(table, "Viewing");
      }
    });

    buttons.get(1).addActionListener(new ActionListener() {
      @Override public void actionPerformed(ActionEvent e) {
        int row = table.convertRowIndexToModel(table.getEditingRow());
        Object o = table.getModel().getValueAt(row, 0);
        fireEditingStopped();
        JOptionPane.showMessageDialog(table, "Editing: "+o);
      }
    });

    addMouseListener(new MouseAdapter() {
      @Override public void mousePressed(MouseEvent e) {
        fireEditingStopped();
      }
    });
  }
  @Override public Component getTableCellEditorComponent(JTable table,
        Object value, boolean isSelected, int row, int column) {
    this.setBackground(table.getSelectionBackground());
    return this;
  }
  @Override public Object getCellEditorValue() {
    return "";
  }
  //Copid from AbstractCellEditor
  //protected EventListenerList listenerList = new EventListenerList();
  transient protected ChangeEvent changeEvent = null;
  @Override public boolean isCellEditable(java.util.EventObject e) {
    return true;
  }
//......

References

2009/09/28

Drag rows from one JTable to another JTable

Code

class TableRowTransferHandler extends TransferHandler {
  private final DataFlavor localObjectFlavor;
  private int[] indices;
  private int addIndex = -1; //Location where items were added
  private int addCount; //Number of items added.
  private JComponent source;
  public TableRowTransferHandler() {
    super();
    localObjectFlavor = new DataFlavor(Object[].class, "Array of items");
  }
  @Override protected Transferable createTransferable(JComponent c) {
    source = c;
    JTable table = (JTable) c;
    DefaultTableModel model = (DefaultTableModel) table.getModel();
    List<Object> list = new ArrayList<>();
    indices = table.getSelectedRows();
    for (int i : indices) {
      list.add(model.getDataVector().elementAt(i));
    }
    Object[] transferedObjects = list.toArray();
    return new Transferable() {
      @Override public DataFlavor[] getTransferDataFlavors() {
        return new DataFlavor[] {FLAVOR};
      }
      @Override public boolean isDataFlavorSupported(DataFlavor flavor) {
        return Objects.equals(FLAVOR, flavor);
      }
      @Override public Object getTransferData(DataFlavor flavor)
            throws UnsupportedFlavorException, IOException {
        if (isDataFlavorSupported(flavor)) {
          return nodes;
        } else {
          throw new UnsupportedFlavorException(flavor);
        }
      }
    };
  }
  @Override public boolean canImport(TransferSupport info) {
    JTable table = (JTable) info.getComponent();
    boolean isDroppable = info.isDrop()
      && info.isDataFlavorSupported(localObjectFlavor);
    //XXX bug?
    table.setCursor(isDroppable ? DragSource.DefaultMoveDrop
                                : DragSource.DefaultMoveNoDrop);
    return isDroppable;
  }
  @Override public int getSourceActions(JComponent c) {
    return TransferHandler.MOVE; //TransferHandler.COPY_OR_MOVE;
  }
  @Override public boolean importData(TransferSupport info) {
    if (!canImport(info)) {
      return false;
    }
    TransferHandler.DropLocation tdl = info.getDropLocation();
    if (!(tdl instanceof JTable.DropLocation)) {
      return false;
    }
    JTable.DropLocation dl = (JTable.DropLocation) tdl;
    JTable target = (JTable) info.getComponent();
    DefaultTableModel model = (DefaultTableModel) target.getModel();
    int index = dl.getRow();
    //boolean insert = dl.isInsert();
    int max = model.getRowCount();
    if (index < 0 || index > max) {
      index = max;
    }
    addIndex = index;
    target.setCursor(Cursor.getPredefinedCursor(Cursor.DEFAULT_CURSOR));
    try {
      Object[] values =
        (Object[]) info.getTransferable().getTransferData(localObjectFlavor);
      if (Objects.equals(source, target)) {
        addCount = values.length;
      }
      for (int i = 0; i < values.length; i++) {
        int idx = index++;
        model.insertRow(idx, (Vector) values[i]);
        target.getSelectionModel().addSelectionInterval(idx, idx);
      }
      return true;
    } catch (UnsupportedFlavorException | IOException ex) {
      ex.printStackTrace();
    }
    return false;
  }
  @Override protected void exportDone(
      JComponent c, Transferable data, int action) {
    cleanup(c, action == MOVE);
  }
  private void cleanup(JComponent c, boolean remove) {
    if (remove && indices != null) {
      c.setCursor(Cursor.getPredefinedCursor(Cursor.DEFAULT_CURSOR));
      DefaultTableModel model = (DefaultTableModel) ((JTable) c).getModel();
      if (addCount > 0) {
        for (int i = 0; i < indices.length; i++) {
          if (indices[i] >= addIndex) {
            indices[i] += addCount;
          }
        }
      }
      for (int i = indices.length - 1; i >= 0; i--) {
        model.removeRow(indices[i]);
      }
    }
    indices = null;
    addCount = 0;
    addIndex = -1;
  }
}

References

2009/08/17

Add JButton and JLabel to the EditorComponent of JComboBox

Code

class SiteComboBoxLayout implements LayoutManager {
  private final JLabel favicon;
  private final JButton feedButton;
  protected SiteComboBoxLayout(JLabel favicon, JButton feedButton) {
    this.favicon = favicon;
    this.feedButton = feedButton;
  }
  @Override public void addLayoutComponent(String name, Component comp) {
    /* not needed */
  }
  @Override public void removeLayoutComponent(Component comp) {
    /* not needed */
  }
  @Override public Dimension preferredLayoutSize(Container parent) {
    return parent.getPreferredSize();
  }
  @Override public Dimension minimumLayoutSize(Container parent) {
    return parent.getMinimumSize();
  }
  @Override public void layoutContainer(Container parent) {
    if (!(parent instanceof JComboBox)) {
      return;
    }
    JComboBox<?> cb = (JComboBox<?>) parent;
    int width = cb.getWidth();
    int height = cb.getHeight();
    Insets insets = cb.getInsets();
    int arrowHeight = height - insets.top - insets.bottom;
    int arrowWidth = arrowHeight;
    int faviconWidth = arrowHeight;
    int feedWidth; // = arrowHeight;

    // Arrow Icon JButton
    JButton arrowButton = (JButton) cb.getComponent(0);
    if (Objects.nonNull(arrowButton)) {
      Insets arrowInsets = arrowButton.getInsets();
      arrowWidth = arrowButton.getPreferredSize().width
        + arrowInsets.left + arrowInsets.right;
      arrowButton.setBounds(width - insets.right - arrowWidth, insets.top,
                            arrowWidth, arrowHeight);
    }

    // Favicon JLabel
    if (Objects.nonNull(favicon)) {
      Insets faviconInsets = favicon.getInsets();
      faviconWidth = favicon.getPreferredSize().width
          + faviconInsets.left + faviconInsets.right;
      favicon.setBounds(insets.left, insets.top, faviconWidth, arrowHeight);
    }


    // Feed Icon JButton
    if (Objects.nonNull(feedButton) && feedButton.isVisible()) {
      Insets feedInsets = feedButton.getInsets();
      feedWidth = feedButton.getPreferredSize().width
          + feedInsets.left + feedInsets.right;
      feedButton.setBounds(width - insets.right - feedWidth - arrowWidth, insets.top,
                           feedWidth, arrowHeight);
    } else {
      feedWidth = 0;
    }

    // JComboBox Editor
    Component editor = cb.getEditor().getEditorComponent();
    if (Objects.nonNull(editor)) {
      editor.setBounds(insets.left + faviconWidth, insets.top,
          width  - insets.left - insets.right - arrowWidth - faviconWidth - feedWidth,
          height - insets.top  - insets.bottom);
    }
  }
}

References

2009/08/12

JMenuBar Background Image

Code

public JMenuBar createMenubar() {
  final TexturePaint texture = makeTexturePaint();
  JMenuBar mb = new JMenuBar() {
    @Override protected void paintComponent(Graphics g) {
      super.paintComponent(g);
      Graphics2D g2 = (Graphics2D)g;
      g2.setPaint(texture);
      g2.fillRect(0, 0, getWidth(), getHeight());
    }
  };
  mb.setOpaque(false);
  String[] menuKeys = {"File", "Edit", "Help"};
  for(String key: menuKeys) {
    JMenu m = createMenu(key);
    if(m != null) mb.add(m);
  }
  return mb;
}
private JMenu createMenu(String key) {
  JMenu menu = new JMenu(key) {
    @Override protected void fireStateChanged() {
      ButtonModel m = getModel();
      if(m.isPressed() && m.isArmed()) {
        setOpaque(true);
      }else if(m.isSelected()) {
        setOpaque(true);
      }else if(isRolloverEnabled() && m.isRollover()) {
        setOpaque(true);
      }else{
        setOpaque(false);
      }
      super.fireStateChanged();
    };
  };
  if("Windows XP".equals(System.getProperty("os.name"))) {
    menu.setBackground(new Color(0,0,0,0)); //XXX Windows XP lnf?
  }
  menu.add("dummy1"); menu.add("dummy2"); menu.add("dummy3");
  return menu;
}

References

2009/06/26

Disable Right Click In JComboBox-Dropdown-List

Code

class BasicComboPopup2 extends BasicComboPopup {
  private Handler2 handler2;
  @Override
  public void uninstallingUI() {
    super.uninstallingUI();
    handler2 = null;
  }
  public BasicComboPopup2(JComboBox combo) {
    super(combo);
  }
  protected MouseListener createListMouseListener() {
    if(handler2==null) handler2 = new Handler2();
    return handler2;
  }
  private class Handler2 implements MouseListener{
    public void mouseEntered(MouseEvent e) {}
    public void mouseExited(MouseEvent e)  {}
    public void mouseClicked(MouseEvent e) {}
    public void mousePressed(MouseEvent e) {}
    public void mouseReleased(MouseEvent e) {
      if(e.getSource() == list) {
        if(list.getModel().getSize() > 0) {
          if(!SwingUtilities.isLeftMouseButton(e) || !comboBox.isEnabled()) return; // <-- ins
          // JList mouse listener
          if(comboBox.getSelectedIndex() == list.getSelectedIndex()) {
            comboBox.getEditor().setItem(list.getSelectedValue());
          }
          comboBox.setSelectedIndex(list.getSelectedIndex());
        }
        comboBox.setPopupVisible(false);
        // workaround for cancelling an edited item (bug 4530953)
        if(comboBox.isEditable() && comboBox.getEditor() != null) {
          comboBox.configureEditor(comboBox.getEditor(), comboBox.getSelectedItem());
        }
      }
    }
  }
}

References

2009/06/10

New Tab Button

Code

class TabLayout implements LayoutManager, java.io.Serializable {
  public void addLayoutComponent(String name, Component comp) {}
  public void removeLayoutComponent(Component comp) {}
  public Dimension preferredLayoutSize(Container parent) {
    synchronized (parent.getTreeLock()) {
      Insets insets = parent.getInsets();
      int last = parent.getComponentCount()-1;
      int w = 0, h = 0;
      if(last >= 0) {
        Component comp = parent.getComponent(last);
        Dimension d = comp.getPreferredSize();
        w = d.width;
        h = d.height;
      }
      return new Dimension(insets.left + insets.right + w,
                           insets.top + insets.bottom + h);
    }
  }

  public Dimension minimumLayoutSize(Container parent) {
    synchronized (parent.getTreeLock()) {
      return new Dimension(100, 24);
    }
  }

  public void layoutContainer(Container parent) {
    synchronized (parent.getTreeLock()) {
      Insets insets = parent.getInsets();
      int ncomponents = parent.getComponentCount();
      int nrows = 1;
      int ncols = ncomponents-1;
      //boolean ltr = parent.getComponentOrientation().isLeftToRight();

      if (ncomponents == 0) {
        return;
      }
      int lastw = parent.getComponent(ncomponents-1).getPreferredSize().width;
      int width = parent.getWidth() - (insets.left + insets.right) - lastw;
      int h = parent.getHeight() - (insets.top + insets.bottom);
      int w = (width > 100*(ncomponents-1))?100:width/ncols;
      int gap = width - w*ncols;
      int x = insets.left;
      int y = insets.top;
      for (int i=0;i < ncomponents;i++) {
        int a = (gap > 0)?1:0;
        gap--;
        int cw = (i==ncols)?lastw:w+a;
        parent.getComponent(i).setBounds(x, y, cw, h);
        x += w + a;
      }
    }
  }
  public String toString() {
    return getClass().getName();
  }
}

References

2009/06/03

Color JComboBox

Code

combo01.setModel(makeModel());
combo01.setRenderer(new MyListCellRenderer(combo01.getRenderer()));
combo01.addItemListener(new ItemListener() {
  public void itemStateChanged(ItemEvent e) {
    if(e.getStateChange()!=ItemEvent.SELECTED) return;
    combo01.setBackground(getOEColor(combo01.getSelectedIndex()));
  }
});
combo01.setSelectedIndex(0);
combo01.setBackground(evenBGColor);

final JTextField field = (JTextField) combo02.getEditor().getEditorComponent();
field.setOpaque(true);
field.setBackground(evenBGColor);
combo02.setEditable(true);
combo02.setModel(makeModel());
combo02.setRenderer(new MyListCellRenderer(combo02.getRenderer()));
combo02.addItemListener(new ItemListener() {
  public void itemStateChanged(ItemEvent e) {
    if(e.getStateChange()!=ItemEvent.SELECTED) return;
    field.setBackground(getOEColor(combo02.getSelectedIndex()));
  }
});
combo02.setSelectedIndex(0);

References

2009/05/19

Left Clipped JComboBox

Code

final JButton arrowButton = getArrowButton(combo02);
combo02.setRenderer(new DefaultListCellRenderer() {
  public Component getListCellRendererComponent(JList list, Object value, int index,
                          boolean isSelected, boolean cellHasFocus) {
    super.getListCellRendererComponent(list,value,index,isSelected,cellHasFocus);
    int itb=0, ilr=0;
    Insets insets = getInsets();
    itb+=insets.top+insets.bottom; ilr+=insets.left+insets.right;
    insets = combo02.getInsets();
    itb+=insets.top+insets.bottom; ilr+=insets.left+insets.right;
    int availableWidth = combo02.getWidth()-ilr;
    if(index < 0) {
      //@see BasicComboBoxUI#rectangleForCurrentValue
      int buttonSize = combo02.getHeight()-itb;
      if(arrowButton!=null) {
        buttonSize = arrowButton.getWidth();
      }
      availableWidth -= buttonSize;
      JTextField tf = (JTextField)combo02.getEditor().getEditorComponent();
      insets = tf.getMargin();
      availableWidth -= (insets.left + insets.right);
    }
    String cellText = (value!=null)?value.toString():"";
    //blockquote
    //@cite http://tips4java.wordpress.com/2008/11/12/left-dot-renderer/
    //@title Left Dot Renderer
    //@auther Rob Camick
    //FontMetrics fm = getFontMetrics(getFont());
    //if(fm.stringWidth(cellText) > availableWidth) {
    //  String dots = "...";
    //  int textWidth = fm.stringWidth(dots);
    //  int nChars = cellText.length() - 1;
    //  while(nChars > 0) {
    //    textWidth += fm.charWidth(cellText.charAt(nChars));
    //    if(textWidth > availableWidth) break;
    //    nChars--;
    //  }
    //  setText(dots+cellText.substring(nChars+1));
    //}
    //blockquote

    // Unicode surrogate programming with the Java language
    // http://www.ibm.com/developerworks/library/j-unicode/index.html
    FontMetrics fm = getFontMetrics(getFont());
    if (fm.stringWidth(cellText) > availableWidth) {
      String dots = "...";
      int textWidth = fm.stringWidth(dots);
      int len = cellText.length();
      int[] acp = new int[cellText.codePointCount(0, len)];
      int j = acp.length;
      for (int i = len; i > 0; i = cellText.offsetByCodePoints(i, -1)) {
        int cp = cellText.codePointBefore(i);
        textWidth += fm.charWidth(cp);
        if (textWidth > availableWidth) {
          break;
        }
        acp[--j] = cp;
      }
      setText(dots + new String(acp, j, acp.length - j));
    }
    return this;
  }
});

References

2009/04/06

Animating JTable Rows

Code

private void testCreateActionPerformed(ActionEvent e) {
  model.addTest(new Test("New name", ""));
  (new javax.swing.Timer(DELAY, new ActionListener() {
    int i = table.convertRowIndexToView(model.getRowCount()-1);
    int h = START_HEIGHT;
    public void actionPerformed(ActionEvent e) {
      if(h < END_HEIGHT) {
        table.setRowHeight(i, h++);
      }else{
        ((javax.swing.Timer)e.getSource()).stop();
      }
    }
  })).start();
}
private void deleteActionPerformed(ActionEvent evt) {
  final int[] selection = table.getSelectedRows();
  if(selection==null || selection.length<=0) return;
  (new javax.swing.Timer(DELAY, new ActionListener() {
    int h = END_HEIGHT;
    public void actionPerformed(ActionEvent e) {
      h--;
      if(h > START_HEIGHT) {
        for(int i=selection.length-1;i >= 0;i--)
          table.setRowHeight(selection[i], h);
      }else{
        ((javax.swing.Timer)e.getSource()).stop();
        for(int i=selection.length-1;i >= 0;i--)
          model.removeRow(table.convertRowIndexToModel(selection[i]));
      }
    }
  })).start();
}

References

2009/03/23

Mouse Dragging ViewPort Scroll

Code

//*
MouseAdapter hsl1 = new HandScrollListener();
vport.addMouseMotionListener(hsl1);
vport.addMouseListener(hsl1);
/*/
MouseAdapter hsl2 = new DragScrollListener();
label.addMouseMotionListener(hsl2);
label.addMouseListener(hsl2);
//*/
class HandScrollListener extends MouseInputAdapter {
  private final Cursor defCursor = Cursor.getPredefinedCursor(Cursor.DEFAULT_CURSOR);
  private final Cursor hndCursor = Cursor.getPredefinedCursor(Cursor.HAND_CURSOR);
  private final Point pp = new Point();
  @Override
  public void mouseDragged(final MouseEvent e) {
    Point cp = e.getPoint();
    Point vp = vport.getViewPosition();
    //= SwingUtilities.convertPoint(vport,0,0,label);
    vp.translate(pp.x-cp.x, pp.y-cp.y);
    if(r1.isSelected()) {
      label.scrollRectToVisible(new Rectangle(vp, vport.getSize()));
    }else{
      vport.setViewPosition(vp);
    }
    pp.setLocation(cp);
  }
  @Override
  public void mousePressed(MouseEvent e) {
    label.setCursor(hndCursor);
    pp.setLocation(e.getPoint());
  }
  @Override
  public void mouseReleased(MouseEvent e) {
    label.setCursor(defCursor);
    label.repaint();
  }
}
class DragScrollListener extends MouseAdapter {
  private final Cursor defCursor = Cursor.getPredefinedCursor(Cursor.DEFAULT_CURSOR);
  private final Cursor hndCursor = Cursor.getPredefinedCursor(Cursor.HAND_CURSOR);
  private final Point pp = new Point();
  @Override public void mouseDragged(MouseEvent e) {
    final JComponent jc = (JComponent)e.getSource();
    Container c = jc.getParent();
    if(c instanceof JViewport) {
      JViewport vport = (JViewport)c;
      Point cp = SwingUtilities.convertPoint(jc,e.getPoint(),vport);
      Point vp = vport.getViewPosition();
      vp.translate(pp.x-cp.x, pp.y-cp.y);
      jc.scrollRectToVisible(new Rectangle(vp, vport.getSize()));
      pp.setLocation(cp);
    }
  }
  @Override public void mousePressed(MouseEvent e) {
    JComponent jc = (JComponent)e.getSource();
    Container c = jc.getParent();
    if(c instanceof JViewport) {
      jc.setCursor(hndCursor);
      JViewport vport = (JViewport)c;
      Point cp = SwingUtilities.convertPoint(jc,e.getPoint(),vport);
      pp.setLocation(cp);
    }
  }
  @Override public void mouseReleased(MouseEvent e) {
    ((JComponent)e.getSource()).setCursor(defCursor);
  }
}

References

2009/03/02

Reset RowFilter before sorting

Code

final RowFilter < TableModel, Integer > filter = new RowFilter () {
  @Override
  public boolean include(Entry < ? extends TableModel, ? extends Integer > entry) {
    int vidx = table.convertRowIndexToView(entry.getIdentifier());
    return vidx < USER_SPECIFIED_NUMBER_OF_ROWS;
  }
};
final TableRowSorter sorter = new TableRowSorter(model) {
  @Override
  public void toggleSortOrder(int column) {
    if(check.isSelected()) {
      //((AbstractTableModel)table.getModel()).fireTableDataChanged();
      allRowsChanged();
      super.toggleSortOrder(column);
      allRowsChanged();
    }else{
      super.toggleSortOrder(column);
    }
  }
};
//final TableRowSorter sorter = new TableRowSorter < TableModel > (model) {
//  @Override
//  public void toggleSortOrder(int column) {
//    if(check.isSelected()) {
//      RowFilter < ? super TableModel, ? super Integer > f = getRowFilter();
//      setRowFilter(null);
//      super.toggleSortOrder(column);
//      setRowFilter(f);
//    }else{
//      super.toggleSortOrder(column);
//    }
//  }
//};
table.setRowSorter(sorter);
sorter.setSortKeys(Arrays.asList(new RowSorter.SortKey(1, SortOrder.DESCENDING)));

References

2009/02/27

HyperLink in JTable Cell

Code

class URLRenderer extends DefaultTableCellRenderer implements MouseListener, MouseMotionListener {
  private int row = -1;
  private int col = -1;
  private boolean isRollover = false;
  public Component getTableCellRendererComponent(JTable table, Object value,
                           boolean isSelected, boolean hasFocus,
                           int row, int column) {
    super.getTableCellRendererComponent(table, value, isSelected, false, row, column);
    if(!table.isEditing() && this.row==row && this.col==column && this.isRollover) {
      setText("< html > < u > < font color='blue' >"+value.toString());
    }else if(hasFocus) {
      setText("< html > < font color='blue' >"+value.toString());
    }else{
      setText(value.toString());
    }
    return this;
  }
  private static boolean isURLColumn(JTable table, int column) {
    return column>=0 && table.getColumnClass(column).equals(URL.class);
  }
  @Override public void mouseMoved(MouseEvent e) {
    JTable table = (JTable)e.getSource();
    Point pt = e.getPoint();
    int prev_row = row;
    int prev_col = col;
    boolean prev_ro = isRollover;
    row = table.rowAtPoint(pt);
    col = table.columnAtPoint(pt);
    isRollover = isURLColumn(table, col); // && pointInsidePrefSize(table, pt);
    if((row==prev_row && col==prev_col && Boolean.valueOf(isRollover).equals(prev_ro)) ||
       (!isRollover && !prev_ro)) {
      return;
    }
//*/ @see SwingSet3: HyperlinkCellRenderer.java
    Rectangle repaintRect;
    if(isRollover) {
      Rectangle r = table.getCellRect(row, col, false);
      repaintRect = prev_ro ? r.union(table.getCellRect(prev_row, prev_col, false)) : r;
    }else{ //if(prev_ro) {
      repaintRect = table.getCellRect(prev_row, prev_col, false);
    }
    table.repaint(repaintRect);
/*/
    //TODO: asks JIDE to show benchmark results.
    table.repaint();
//*/
  }
  @Override public void mouseExited(MouseEvent e)  {
    JTable table = (JTable)e.getSource();
    if(isURLColumn(table, col)) {
      table.repaint(table.getCellRect(row, col, false));
      row = -1;
      col = -1;
      isRollover = false;
    }
  }
  @Override public void mouseClicked(MouseEvent e) {
    JTable table = (JTable)e.getSource();
    Point pt = e.getPoint();
    int ccol = table.columnAtPoint(pt);
    if(isURLColumn(table, ccol)) { // && pointInsidePrefSize(table, pt)) {
      int crow = table.rowAtPoint(pt);
      URL url = (URL)table.getValueAt(crow, ccol);
      System.out.println(url);
      try{
        //Web Start
        //BasicService bs = (BasicService)ServiceManager.lookup("javax.jnlp.BasicService");
        //bs.showDocument(url);
        if(Desktop.isDesktopSupported()) { // JDK 1.6.0
          Desktop.getDesktop().browse(url.toURI());
        }
      }catch(Exception ex) {
        ex.printStackTrace();
      }
    }
  }
//......

References

2009/02/26

Use JScrollBar as JSlider

Code

int step   = 5;
int extent = 20;
int min    = 0;
int max    = extent*10; //200
int value  = 50;
final JScrollBar scrollbar = new JScrollBar(
            JScrollBar.HORIZONTAL, value, extent, min, max+extent);
scrollbar.setUnitIncrement(step);
scrollbar.getModel().addChangeListener(new ChangeListener(){
  public void stateChanged(javax.swing.event.ChangeEvent e) {
    BoundedRangeModel m = (BoundedRangeModel)e.getSource();
    spinner.setValue(m.getValue());
  }
});
final JSpinner spinner = new JSpinner(
            new SpinnerNumberModel(value, min, max, step));
//...

References

2009/02/16

JTableHeader CheckBox

Code

enum Status { SELECTED, DESELECTED, INDETERMINATE }
class HeaderRenderer extends JCheckBox implements TableCellRenderer {
  private final JLabel label = new JLabel("Check All");
  private int targetColumnIndex;
  public HeaderRenderer(JTableHeader header, int index) {
    super((String)null);
    this.targetColumnIndex = index;
    setOpaque(false);
    setFont(header.getFont());
    header.addMouseListener(new MouseAdapter() {
      @Override public void mouseClicked(MouseEvent e) {
        JTableHeader header = (JTableHeader)e.getSource();
        JTable table = header.getTable();
        TableColumnModel columnModel = table.getColumnModel();
        int vci = columnModel.getColumnIndexAtX(e.getX());
        int mci = table.convertColumnIndexToModel(vci);
        if(mci == targetColumnIndex) {
          TableColumn column = columnModel.getColumn(vci);
          Object v = column.getHeaderValue();
          boolean b = Status.DESELECTED.equals(v)?true:false;
          TableModel m = table.getModel();
          for(int i=0; i < m.getRowCount(); i++) m.setValueAt(b, i, mci);
          column.setHeaderValue(b?Status.SELECTED:Status.DESELECTED);
          //header.repaint();
        }
      }
    });
  }
  @Override public Component getTableCellRendererComponent(
      JTable tbl, Object val, boolean isS, boolean hasF, int row, int col) {
    TableCellRenderer r = tbl.getTableHeader().getDefaultRenderer();
    JLabel l =(JLabel)r.getTableCellRendererComponent(tbl,val,isS,hasF,row,col);
    if(targetColumnIndex==tbl.convertColumnIndexToModel(col)) {
      if(val instanceof Status) {
        switch((Status)val) {
          case SELECTED:    setSelected(true);  setEnabled(true);  break;
          case DESELECTED:  setSelected(false); setEnabled(true);  break;
          case INDETERMINATE: setSelected(true);  setEnabled(false); break;
        }
      }else{
        setSelected(true); setEnabled(false);
      }
      label.setIcon(new ComponentIcon(this));
      l.setIcon(new ComponentIcon(label));
      l.setText(null); //XXX: Nimbus???
    }
    return l;
  }
}
class CheckBoxIcon implements Icon{
  private final JCheckBox check;
  public CheckBoxIcon(JCheckBox check) {
    this.check = check;
  }
  @Override public int getIconWidth() {
    return check.getPreferredSize().width;
  }
  @Override public int getIconHeight() {
    return check.getPreferredSize().height;
  }
  @Override public void paintIcon(Component c, Graphics g, int x, int y) {
    SwingUtilities.paintComponent(
        g, check, (Container)c, x, y, getIconWidth(), getIconHeight());
  }
}
model.addTableModelListener(new TableModelListener() {
  @Override public void tableChanged(TableModelEvent e) {
    if(e.getType()==TableModelEvent.UPDATE && e.getColumn()==targetColumnIndex) {
      int vci = table.convertColumnIndexToView(targetColumnIndex);
      TableColumn column = table.getColumnModel().getColumn(vci);
      if(!Status.INDETERMINATE.equals(column.getHeaderValue())) {
        column.setHeaderValue(Status.INDETERMINATE);
      }else{
        boolean selected = true, deselected = true;
        TableModel m = table.getModel();
        for(int i=0; i < m.getRowCount(); i++) {
          Boolean b = (Boolean)m.getValueAt(i, targetColumnIndex);
          selected &= b; deselected &= !b;
          if(selected==deselected) return;
        }
        if(selected) {
          column.setHeaderValue(Status.SELECTED);
        }else if(deselected) {
          column.setHeaderValue(Status.DESELECTED);
        }else{
          return;
        }
      }
      JTableHeader h = table.getTableHeader();
      h.repaint(h.getHeaderRect(vci));
    }
  }
});

References

2009/01/23

create Auto Suggest JComboBox

Code

class ComboKeyHandler extends KeyAdapter {
  private final JComboBox<String> comboBox;
  private final List<String> list = new ArrayList<>();
  private boolean shouldHide;

  public ComboKeyHandler(JComboBox<String> combo) {
    super();
    this.comboBox = combo;
    for (int i = 0; i < comboBox.getModel().getSize(); i++) {
      list.add((String) comboBox.getItemAt(i));
    }
  }
  @Override public void keyTyped(final KeyEvent e) {
    EventQueue.invokeLater(new Runnable() {
      @Override public void run() {
        String text = ((JTextField) e.getComponent()).getText();
        ComboBoxModel<String> m;
        if (text.isEmpty()) {
          String[] array = list.toArray(new String[list.size()]);
          m = new DefaultComboBoxModel<String>(array);
          setSuggestionModel(comboBox, m, "");
          comboBox.hidePopup();
        } else {
          m = getSuggestedModel(list, text);
          if (m.getSize() == 0 || shouldHide) {
            comboBox.hidePopup();
          } else {
            setSuggestionModel(comboBox, m, text);
            comboBox.showPopup();
          }
        }
      }
    });
  }
  @Override public void keyPressed(KeyEvent e) {
    JTextField textField = (JTextField) e.getComponent();
    String text = textField.getText();
    shouldHide = false;
    switch (e.getKeyCode()) {
    case KeyEvent.VK_RIGHT:
      for (String s : list) {
        if (s.startsWith(text)) {
          textField.setText(s);
          return;
        }
      }
      break;
    case KeyEvent.VK_ENTER:
      if (!list.contains(text)) {
        list.add(text);
        Collections.sort(list);
        //setSuggestionModel(comboBox, new DefaultComboBoxModel(list), text);
        setSuggestionModel(comboBox, getSuggestedModel(list, text), text);
      }
      shouldHide = true;
      break;
    case KeyEvent.VK_ESCAPE:
      shouldHide = true;
      break;
    default:
      break;
    }
  }
  private static void setSuggestionModel(
      JComboBox<String> comboBox, ComboBoxModel<String> mdl, String str) {
    comboBox.setModel(mdl);
    comboBox.setSelectedIndex(-1);
    ((JTextField) comboBox.getEditor().getEditorComponent()).setText(str);
  }
  private static ComboBoxModel<String> getSuggestedModel(List<String> list, String text) {
    DefaultComboBoxModel<String> m = new DefaultComboBoxModel<>();
    for (String s : list) {
      if (s.startsWith(text)) {
        m.addElement(s);
      }
    }
    return m;
  }
}

References