Swing/EditTabTitle のバックアップソース(No.28)
- バックアップ一覧
- 差分 を表示
- 現在との差分 を表示
- 現在との差分 - Visual を表示
- バックアップ を表示
- Swing/EditTabTitle へ行く。
- 1 (2006-04-11 (火) 12:24:38)
- 2 (2006-04-12 (水) 19:43:05)
- 3 (2006-04-19 (水) 16:05:39)
- 4 (2006-05-11 (木) 15:06:05)
- 5 (2006-05-24 (水) 08:29:00)
- 6 (2006-07-21 (金) 16:27:39)
- 7 (2006-09-01 (金) 15:04:00)
- 8 (2006-11-10 (金) 00:19:51)
- 9 (2006-11-10 (金) 03:34:07)
- 10 (2007-01-23 (火) 12:39:47)
- 11 (2007-05-15 (火) 17:50:24)
- 12 (2007-07-03 (火) 19:22:58)
- 13 (2008-09-08 (月) 13:51:59)
- 14 (2010-08-10 (火) 16:49:52)
- 15 (2013-03-13 (水) 15:31:34)
- 16 (2013-05-03 (金) 23:48:10)
- 17 (2013-07-26 (金) 01:09:04)
- 18 (2013-08-20 (火) 14:21:48)
- 19 (2013-08-29 (木) 01:15:23)
- 20 (2013-10-11 (金) 12:50:30)
- 21 (2014-11-25 (火) 03:03:31)
- 22 (2014-11-28 (金) 16:26:40)
- 23 (2015-02-17 (火) 22:27:08)
- 24 (2015-03-28 (土) 15:36:28)
- 25 (2016-05-20 (金) 19:21:44)
- 26 (2016-05-27 (金) 13:12:04)
- 27 (2016-09-02 (金) 13:30:20)
- 28 (2017-01-20 (金) 13:21:51)
- 29 (2017-12-14 (木) 16:31:10)
- 30 (2018-02-24 (土) 19:51:30)
- 31 (2019-01-18 (金) 17:29:11)
- 32 (2020-11-28 (土) 13:32:36)
- 33 (2023-02-22 (水) 11:06:41)
--- category: swing folder: EditTabTitle title: JTabbedPaneのタブタイトルを変更 tags: [JTabbedPane, GlassPane, JTextField] author: aterai pubdate: 2006-03-27T01:01:49+09:00 description: JTabbedPaneのタブタイトルを直接編集します。 image: https://lh5.googleusercontent.com/_9Z4BYR88imo/TQTMGR-jIQI/AAAAAAAAAYo/g3tGLp5zrdY/s800/EditTabTitle.png hreflang: href: http://java-swing-tips.blogspot.com/2008/09/double-click-on-each-tab-and-change-its.html lang: en --- * 概要 [#summary] `JTabbedPane`のタブタイトルを直接編集します。 #download(https://lh5.googleusercontent.com/_9Z4BYR88imo/TQTMGR-jIQI/AAAAAAAAAYo/g3tGLp5zrdY/s800/EditTabTitle.png) * サンプルコード [#sourcecode] #code(link){{ class EditableTabbedPane extends JTabbedPane { private final JComponent glassPane = new EditorGlassPane(); private final JTextField editor = new JTextField(); private final Action startEditing = new AbstractAction() { @Override public void actionPerformed(ActionEvent e) { getRootPane().setGlassPane(glassPane); Rectangle rect = getUI().getTabBounds( EditableTabbedPane.this, getSelectedIndex()); Point p = SwingUtilities.convertPoint( EditableTabbedPane.this, rect.getLocation(), glassPane); //rect.setBounds(p.x + 2, p.y + 2, rect.width - 4, rect.height - 4); rect.setLocation(p); rect.grow(-2, -2); editor.setBounds(rect); editor.setText(getTitleAt(getSelectedIndex())); editor.selectAll(); glassPane.add(editor); glassPane.setVisible(true); editor.requestFocusInWindow(); } }; private final Action cancelEditing = new AbstractAction() { @Override public void actionPerformed(ActionEvent e) { glassPane.setVisible(false); } }; private final Action renameTab = new AbstractAction() { @Override public void actionPerformed(ActionEvent e) { if (!editor.getText().trim().isEmpty()) { setTitleAt(getSelectedIndex(), editor.getText()); //java 1.6.0 ----> Component c = getTabComponentAt(getSelectedIndex()); if (c instanceof JComponent) { ((JComponent) c).revalidate(); } //<---- } glassPane.setVisible(false); } }; protected EditableTabbedPane() { super(); editor.setBorder(BorderFactory.createEmptyBorder(0, 3, 0, 3)); editor.getInputMap(JComponent.WHEN_FOCUSED).put( KeyStroke.getKeyStroke(KeyEvent.VK_ENTER, 0), "rename-tab"); editor.getActionMap().put("rename-tab", renameTab); editor.getInputMap(JComponent.WHEN_FOCUSED).put( KeyStroke.getKeyStroke(KeyEvent.VK_ESCAPE, 0), "cancel-editing"); editor.getActionMap().put("cancel-editing", cancelEditing); addMouseListener(new MouseAdapter() { @Override public void mouseClicked(MouseEvent e) { if (e.getClickCount() == 2) { startEditing.actionPerformed(null); } } }); getInputMap(JComponent.WHEN_FOCUSED).put( KeyStroke.getKeyStroke(KeyEvent.VK_ENTER, 0), "start-editing"); getActionMap().put("start-editing", startEditing); } private class EditorGlassPane extends JComponent { protected EditorGlassPane() { super(); setOpaque(false); setFocusTraversalPolicy(new DefaultFocusTraversalPolicy() { @Override public boolean accept(Component c) { return Objects.equals(c, editor); } }); addMouseListener(new MouseAdapter() { @Override public void mouseClicked(MouseEvent e) { //if (Objects.nonNull(rect) && !rect.contains(e.getPoint())) { if (!editor.getBounds().contains(e.getPoint())) { renameTab.actionPerformed(null); } } }); } @Override public void setVisible(boolean flag) { super.setVisible(flag); setFocusTraversalPolicyProvider(flag); setFocusCycleRoot(flag); } } } }} * 解説 [#explanation] `Excel`風に`JTabbedPane`のタブタイトルを直接編集しています。 編集が開始されると、対象となるタブ上に`JTextField`をレイアウトした`GlassPane`を表示しています。この`GlassPane`には、編集中はフォーカスの移動が起こらないようにするための`FocusTraversalPolicy`などを設定しています。 - 操作方法 -- マウスでタブをダブルクリック、またはタブを選択してKBD{Enter}キーで編集開始 -- 編集中に入力欄以外をクリック、またはKBD{Enter}キーでタイトル文字列が確定 -- 編集中はKBD{Tab}キーを押しても無視 -- KBD{Esc}キーで編集をキャンセル -- `0`文字で確定した場合も、キャンセル扱い * 参考リンク [#reference] - [[Cursorを砂時計に変更>Swing/WaitCursor]] - [[JTabbedPaneのタブにJTextFieldを配置してタイトルを編集>Swing/TabTitleEditor]] -- `JDK 6`で追加された`JTabbedPane#setTabComponentAt`メソッドで、タブに`JTextField`を配置し、同様のことを行うサンプル - [https://community.oracle.com/thread/1359811 Swing - Floating text field] -- `JPopupMenu`に`JTextField`を配置することで、同様のことを行うコードをKelVarnsonさんが投稿している * コメント [#comment] #comment - `1.4`系だと編集開始時にうまく選択状態にできない場合があるようです。 -- &user(aterai); &new{2006-03-27 (月) 15:03:01}; -- 上記の問題と、選択状態がマウスの移動で外れてしまうバグを修正しました。 -- &user(aterai); &new{2006-03-29 (水) 03:26:56}; - 余白などを追加するとエディタがずれるバグを修正しました。 -- &user(aterai); &new{2006-09-01 (金) 15:04:00}; - `setTabComponentAt(...)`メソッドで閉じるボタンなどと併用していた場合、編集後に文字列の長さがおかしくなるので、`revalidate()`するように修正。 -- &user(aterai); &new{2010-08-10 (火) 16:49:52}; #comment