I want to use Ctrl-F6 to switch between a JTable and an associated JTree. Ctrl-F6 however starts the JTable's cell editor. JTable only has one default key listener: a javax.swing.ToolTipManager$AccessibilityKeyListener... but removing this didn't solve the problem. So I tried to find out whether this was a key binding and where it might reside... so I wrote this simple function (in Jython but should be perfectly intelligible to Java-ists):
def print_comp_maps( comp, name ):
# list all task tree's system-set hotkeys
# NB respective values here: 0, 1, 2
input_map_conditions = [ JComponent.WHEN_FOCUSED, JComponent.WHEN_ANCESTOR_OF_FOCUSED_COMPONENT, JComponent.WHEN_IN_FOCUSED_WINDOW ]
input_map_names = [ "focused", "ancestor", "in focused window" ]
print( "=== comp: %s" % name )
for condition in input_map_conditions:
print( " === condition: %s" % input_map_names[ condition ])
i_map = comp.getInputMap( condition )
depth = 0
while i_map:
depth += 1
print( " %s=== imap %s:" % ( " " * depth, i_map ))
keys = i_map.keys()
if keys:
for keystroke in keys:
print( " %s=== keystroke %s value %s" % ( " " * ( depth + 1 ), keystroke, i_map.get( keystroke ) ) )
i_map = i_map.parent
The results for the JTable are:
=== comp: date_table
=== condition: focused
=== imap javax.swing.InputMap@1a8a84f:
=== condition: ancestor
=== imap javax.swing.InputMap@1c1edd9:
=== imap javax.swing.plaf.InputMapUIResource@e674b9:
=== keystroke ctrl pressed DOWN value selectNextRowChangeLead
=== keystroke shift pressed UP value selectPreviousRowExtendSelection
=== keystroke shift pressed INSERT value paste
=== keystroke ctrl pressed RIGHT value selectNextColumnChangeLead
=== keystroke shift ctrl pressed LEFT value selectPreviousColumnExtendSe
lection
=== keystroke shift pressed KP_UP value selectPreviousRowExtendSelection
=== keystroke pressed DOWN value selectNextRow
=== keystroke ctrl pressed UP value selectPreviousRowChangeLead
=== keystroke ctrl pressed LEFT value selectPreviousColumnChangeLead
=== keystroke pressed CUT value cut
=== keystroke pressed END value selectLastColumn
=== keystroke shift pressed PAGE_UP value scrollUpExtendSelection
=== keystroke pressed KP_UP value selectPreviousRow
=== keystroke shift ctrl pressed UP value selectPreviousRowExtendSelecti
on
=== keystroke ctrl pressed HOME value selectFirstRow
=== keystroke ctrl pressed INSERT value copy
=== keystroke shift pressed LEFT value selectPreviousColumnExtendSelecti
on
=== keystroke ctrl pressed END value selectLastRow
=== keystroke ctrl pressed PAGE_DOWN value scrollRightChangeSelection
=== keystroke shift ctrl pressed RIGHT value selectNextColumnExtendSelec
tion
=== keystroke pressed LEFT value selectPreviousColumn
=== keystroke ctrl pressed PAGE_UP value scrollLeftChangeSelection
=== keystroke pressed KP_LEFT value selectPreviousColumn
=== keystroke shift pressed KP_RIGHT value selectNextColumnExtendSelecti
on
=== keystroke pressed SPACE value addToSelection
=== keystroke ctrl pressed SPACE value toggleAndAnchor
=== keystroke shift pressed SPACE value extendTo
=== keystroke shift ctrl pressed SPACE value moveSelectionTo
=== keystroke shift ctrl pressed DOWN value selectNextRowExtendSelection
=== keystroke ctrl pressed BACK_SLASH value clearSelection
=== keystroke pressed ESCAPE value cancel
=== keystroke shift pressed DELETE value cut
=== keystroke shift pressed HOME value selectFirstColumnExtendSelection
=== keystroke pressed ENTER value selectNextRowCell
=== keystroke shift pressed ENTER value selectPreviousRowCell
=== keystroke pressed F8 value focusHeader
=== keystroke pressed RIGHT value selectNextColumn
=== keystroke shift ctrl pressed PAGE_UP value scrollLeftExtendSelection
=== keystroke shift pressed DOWN value selectNextRowExtendSelection
=== keystroke shift ctrl pressed KP_UP value selectPreviousRowExtendSele
ction
=== keystroke pressed PAGE_DOWN value scrollDownChangeSelection
=== keystroke shift pressed KP_LEFT value selectPreviousColumnExtendSele
ction
=== keystroke ctrl pressed X value cut
=== keystroke shift ctrl pressed PAGE_DOWN value scrollRightExtendSelect
ion
=== keystroke ctrl pressed SLASH value selectAll
=== keystroke ctrl pressed C value copy
=== keystroke ctrl pressed KP_RIGHT value selectNextColumnChangeLead
=== keystroke shift pressed END value selectLastColumnExtendSelection
=== keystroke shift ctrl pressed KP_DOWN value selectNextRowExtendSelect
ion
=== keystroke shift pressed TAB value selectPreviousColumnCell
=== keystroke ctrl pressed KP_LEFT value selectPreviousColumnChangeLead
=== keystroke pressed HOME value selectFirstColumn
=== keystroke ctrl pressed V value paste
=== keystroke pressed KP_DOWN value selectNextRow
=== keystroke ctrl pressed KP_DOWN value selectNextRowChangeLead
=== keystroke shift pressed RIGHT value selectNextColumnExtendSelection
=== keystroke ctrl pressed A value selectAll
=== keystroke shift ctrl pressed END value selectLastRowExtendSelection
=== keystroke pressed COPY value copy
=== keystroke ctrl pressed KP_UP value selectPreviousRowChangeLead
=== keystroke shift ctrl pressed KP_LEFT value selectPreviousColumnExten
dSelection
=== keystroke shift pressed KP_DOWN value selectNextRowExtendSelection
=== keystroke pressed TAB value selectNextColumnCell
=== keystroke pressed UP value selectPreviousRow
=== keystroke shift ctrl pressed HOME value selectFirstRowExtendSelectio
n
=== keystroke shift pressed PAGE_DOWN value scrollDownExtendSelection
=== keystroke pressed KP_RIGHT value selectNextColumn
=== keystroke shift ctrl pressed KP_RIGHT value selectNextColumnExtendSe
lection
=== keystroke pressed F2 value startEditing
=== keystroke pressed PAGE_UP value scrollUpChangeSelection
=== keystroke pressed PASTE value paste
=== condition: in focused window
=== imap javax.swing.ComponentInputMap@fa5f28:
... no sign of any F6 or Ctrl-F6 key-binding... has anyone got any idea what's going on?
later
by the way, it's perfectly possible to add a Ctrl-F6 binding to (for example) the JTable's "WHEN ANCESTOR OF ..." InputMap (for example, first generation, i.e. javax.swing.InputMap@1c1edd9 in the above listing). Then add a binding between the Object there and an Action in the ActionMap. Ctrl-F6 then fires the Action. But, as one might expect perhaps, this in no way inhibits the "startEditing" Action. The mystery of mysteries is: where the ferkin is this binding located??? I have explored the JScrollPane (no joy, no surprise) and even the JTextField object submitted to the constructor of the DefaultCellEditor... (no joy, and even less surprise). Stumped. Anyone know a bindings super-geek?
even later
Although Yarik has sorted out the main thing I still have a problem: when the table is realised and focus is then put on a previously selected row programmatically (i.e. not using mouse), F2 does not initially work... it is only after you navigate (e.g. with up/down keys) that you then find that F2 starts editing. SSCCE illustrating problem:
import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.event.ActionEvent;
import java.lang.Runnable;
import javax.swing.*;
public class TableCellEditProb {
public static void main(String args[]) {
Runnable show_frame = new Runnable(){
public void run(){
JFrame main_frame = new JFrame( "F2 no effect on first realisation!");
main_frame.setDefaultCloseOperation( JFrame.EXIT_ON_CLOSE );
final JTable table = new JTable( 5, 2 );
table.setPreferredSize( new Dimension( 400, 200 ));
table.setRowSelectionInterval( 2, 2 );
table.putClientProperty("JTable.autoStartsEdit", false );
JPanel panel = new JPanel( new BorderLayout());
AbstractAction button_action = new AbstractAction(){
public void actionPerformed(ActionEvent e){
System.out.println( "button pressed");
table.requestFocus();
}
};
button_action.putValue( AbstractAction.NAME, "Click (or press spacebar) to change focus to table..." );
JButton button = new JButton( button_action );
panel.add( table, BorderLayout.WEST );
panel.add( button, BorderLayout.EAST );
main_frame.getContentPane().add( panel );
main_frame.pack();
button.requestFocus();
main_frame.setVisible( true );
}
};
java.awt.EventQueue.invokeLater( show_frame );
}
}