Swing/EditInternalFrameTitle のバックアップ(No.1)
- バックアップ一覧
- 差分 を表示
- 現在との差分 を表示
- 現在との差分 - Visual を表示
- ソース を表示
- Swing/EditInternalFrameTitle へ行く。
- 1 (2021-08-30 (月) 02:51:09)
- category: swing folder: EditInternalFrameTitle title: JInternalFrameにJPopupMenuを設定してタイトルを変更する tags: [JInternalFrame, JPopupMenu] author: aterai pubdate: 2021-08-30T02:48:24+09:00 description: JInternalFrameのタイトルをタイトルバーやアイコン化された状態のJDesktopIconからJPopupMenuを開いて変更します。 image: https://drive.google.com/uc?id=1OBg1GInat6Dbj4WK5tRYaSihXxU2E32R
概要
JInternalFrameのタイトルをタイトルバーやアイコン化された状態のJDesktopIconからJPopupMenuを開いて変更します。
Screenshot
Advertisement
サンプルコード
private static JInternalFrame createFrame(String t, int i) {
JInternalFrame f = new JInternalFrame(t + i, true, true, true, true);
f.setSize(200, 100);
f.setLocation(5 + 40 * i, 5 + 50 * i);
JPopupMenu popup = new InternalFramePopupMenu();
f.setComponentPopupMenu(popup);
// ((BasicInternalFrameUI) f.getUI()).getNorthPane().setComponentPopupMenu(popup);
((BasicInternalFrameUI) f.getUI()).getNorthPane().setInheritsPopupMenu(true);
f.getDesktopIcon().setComponentPopupMenu(popup);
EventQueue.invokeLater(() -> f.setVisible(true));
return f;
}
class InternalFramePopupMenu extends JPopupMenu {
protected InternalFramePopupMenu() {
super();
JTextField field = new JTextField(24); // { ... };
String cmd = "Edit Title";
add(cmd).addActionListener(e -> {
Component c = getInternalFrame(getInvoker());
if (c instanceof JInternalFrame) {
JInternalFrame frame = (JInternalFrame) c;
field.setText(frame.getTitle());
Container p = frame.getDesktopPane();
int ret = JOptionPane.showConfirmDialog(
p, field, cmd, JOptionPane.OK_CANCEL_OPTION, JOptionPane.PLAIN_MESSAGE);
if (ret == JOptionPane.OK_OPTION) {
renameInternalFrameTitle(frame, field.getText().trim());
}
}
});
}
// ...
}
private static Component getInternalFrame(Component c) {
Component f;
if (c instanceof JInternalFrame.JDesktopIcon) {
f = ((JInternalFrame.JDesktopIcon) c).getInternalFrame();
} else if (c instanceof JInternalFrame) {
f = c;
} else { // if (c instanceof BasicInternalFrameTitlePane) {
f = SwingUtilities.getAncestorOfClass(JInternalFrame.class, c);
}
return f;
}
View in GitHub: Java, Kotlin解説
上記のサンプルでは、JInternalFrame
やそのアイコン化状態でのコンポーネントであるJInternalFrame.JDesktopIcon
にsetComponentPopupMenu(...)
メソッドでJPopupMenu
を設定し、このJPopupMenu
からJOptionPane
を開いてJInternalFrame
のタイトルを変更しています。
Windows
環境でJInternalFrame
のタイトルバーを右クリックした場合の動作はLookAndFeel
で異なるNimbusLookAndFeel
- デフォルトでは左端のタイトル(下向き三角)アイコンをクリックしたときに表示されるシステムポップアップメニューが表示される
JInternalFrame
にJPopupMenu
を設定した場合、SynthInternalFrameTitlePane
に設定されたJPopupMenu
を開くSynthInternalFrameTitlePane#isInheritsPopupMenu() == true
なので親JInternalFrame
のJPopupMenu
が開くSynthInternalFrameTitlePane
から任意(デフォルトのシステムポップアップメニューを含む)のJPopupMenu
を開き、Escキーや別コンポーネントをクリックしてポップアップ表示をキャンセルすると内部的にJInternalFrame
が移動状態が継続して再度タイトルバーを左クリックするまでJInternalFrame
のリサイズが不可能になる(リサイズカーソルのままJInternalFrame
が移動する)
WindowsLookAndFeel
- デフォルトではタイトルバーのシングル右クリックは無視され(システムメニューは表示されない)、左右どのマウスボタンのダブルクリックでも
JInternalFrame
の最大化、復元が実行される - デフォルトは
WindowsInternalFrameTitlePane#isInheritsPopupMenu() == true
なので、WindowsInternalFrameTitlePane#setInheritsPopupMenu(true)
などの設定で右クリックはポップアップ表示に変更可能(右マウスボタンのダブルクリックは無効になる)
- デフォルトではタイトルバーのシングル右クリックは無視され(システムメニューは表示されない)、左右どのマウスボタンのダブルクリックでも