Я добавил JPopupMenu
в JTable
с setComponentPopupMenu
. Проблема заключается в том, что, хотя открыт/виден, когда я щелкнул левой кнопкой мыши по строке вне всплывающего меню, меню закрывается, но строка не выбрана, поэтому я должен щелкнуть ее снова, чтобы выделить ее. Есть ли способ исправить это?Принудительный выбор строки JTable, если щелкнуть снаружи видимым JPopupMenu
EDIT
Я добавил примеры кода.
Кстати, это поведение происходит только в Windows LaF. Я только что протестировал его, и похоже, что Java LaF по умолчанию позволяет выбирать строку слева при открытии JPopupMenu.
import java.awt.Dimension;
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.Point;
import javax.swing.BorderFactory;
import javax.swing.JFrame;
import javax.swing.JMenuItem;
import javax.swing.JPanel;
import javax.swing.JPopupMenu;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.SwingUtilities;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
import javax.swing.event.PopupMenuEvent;
import javax.swing.event.PopupMenuListener;
public class TableSTACK {
private static void createAndShowGUI() {
String[] headers = {"Column 1", "Column 2"};
Object[][] data = { {"Row", "1"}, {"Row", "2"},
{"Row", "3"}, {"Row", "4"}, {"Row", "5"},
{"Row", "6"}, {"Row", "7"}, {"Row", "8"}, };
JTable table = new JTable(data, headers);
table.setFillsViewportHeight(true);
table.setPreferredScrollableViewportSize(table.getPreferredSize());
final JMenuItem item1 = new JMenuItem();
item1.setText("Menu Item 1");
final JMenuItem item2 = new JMenuItem();
item2.setText("Menu Item 2");
final JMenuItem item3 = new JMenuItem();
item3.setText("Menu Item 3");
final JPopupMenu popupMenu = new JPopupMenu();
popupMenu.add(item1);
popupMenu.addSeparator();
popupMenu.add(item2);
popupMenu.add(item3);
table.setComponentPopupMenu(popupMenu);
popupMenu.addPopupMenuListener(new PopupMenuListener() {
@Override
public void popupMenuWillBecomeVisible(PopupMenuEvent e) {
SwingUtilities.invokeLater(new Runnable() {
@Override
public void run() {
// force selection of row upon right-click (it works)
int rowAtPoint = table.rowAtPoint(SwingUtilities.convertPoint(popupMenu, new Point(0, 0), table));
if (rowAtPoint > -1) {
table.setRowSelectionInterval(rowAtPoint, rowAtPoint);
}
}
});
}
@Override
public void popupMenuWillBecomeInvisible(PopupMenuEvent e) {
SwingUtilities.invokeLater(new Runnable() {
@Override
public void run() {
// force row selection upon exiting popup menu
// does not work; rowAtPoint always returns -1
int rowAtPoint = table.rowAtPoint(SwingUtilities.convertPoint(null, new Point(0, 0), table));
//int rowAtPoint = table.rowAtPoint(SwingUtilities.convertPoint(popupMenu, new Point(0, 0), table));
if (rowAtPoint > -1) {
table.setRowSelectionInterval(rowAtPoint, rowAtPoint);
}
}
});
}
@Override
public void popupMenuCanceled(PopupMenuEvent e) {
// TODO
}
});
GridBagConstraints gbc = new GridBagConstraints();
gbc.anchor = GridBagConstraints.NORTHWEST;
gbc.gridy = 0;
gbc.weightx = 1.0;
gbc.weighty = 1.0;
gbc.fill = GridBagConstraints.BOTH;
gbc.gridx = 0;
JScrollPane scrollPane = new JScrollPane(table);
JPanel contentPane = new JPanel();
contentPane.setBorder(BorderFactory.createEmptyBorder(15, 15, 15, 15));
contentPane.setLayout(new GridBagLayout());
contentPane.add(scrollPane, gbc);
JFrame frame = new JFrame();
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setContentPane(contentPane);
frame.pack();
frame.setMinimumSize(new Dimension(500, 400));
frame.setVisible(true);
}
public static void main(String[] args) {
javax.swing.SwingUtilities.invokeLater(new Runnable() {
public void run() {
try {
//UIManager.setLookAndFeel(UIManager.getCrossPlatformLookAndFeelClassName());
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (InstantiationException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IllegalAccessException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (UnsupportedLookAndFeelException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
createAndShowGUI();
}
});
}
}
Используйте редактор ячеек, например ['TablePopupEditor'] (http://stackoverflow.com/a/3591230/230513). Если это не дубликат, отредактируйте свой вопрос, включив в него [mcve], который показывает ваш пересмотренный подход. – trashgod
Это было первоначально закрыто как дубликат: http://stackoverflow.com/questions/3590897/jtable-design-to-synchronize-with-back-end-data-structure. Я не думаю, что этот вопрос касается всплывающего редактора. Речь идет об использовании «JPopupMenu» и нажатии на таблицу, когда меню открыто. Я снова открыл вопрос. – camickr
Я отредактировал мой вопрос. – AndroidX