Spec-Zone .ru
спецификации, руководства, описания, API
|
Если Вы реализуете сокращение, копию и вставку, используя один из компонентов Swing, который не является одним из текстовых компонентов, необходимо сделать некоторую дополнительную установку. Во-первых, Вы должны установить сокращение, копию, и действия вставки в карте действия. Следующий метод показывает, как сделать это:
private void setMappings(JList list) { ActionMap map = list.getActionMap(); map.put(TransferHandler.getCutAction().getValue(Action.NAME), TransferHandler.getCutAction()); map.put(TransferHandler.getCopyAction().getValue(Action.NAME), TransferHandler.getCopyAction()); map.put(TransferHandler.getPasteAction().getValue(Action.NAME), TransferHandler.getPasteAction());
Когда Вы устанавливаете меню Edit, можно также хотеть добавлять акселераторы меню, так, чтобы пользователь мог ввести Ctrl-C, чтобы инициировать копию, например. В следующем фрагменте кода полужирный текст показывает, как установить акселератор меню для действия сокращения:
menuItem = new JMenuItem("Cut"); menuItem.setActionCommand((String)TransferHandler.getCutAction(). getValue(Action.NAME)); menuItem.addActionListener(actionListener); menuItem.setAccelerator( KeyStroke.getKeyStroke(KeyEvent.VK_X, ActionEvent.CTRL_MASK)); menuItem.setMnemonic(KeyEvent.VK_T); mainMenu.add(menuItem);
Если Вы установили акселераторы меню для действий CCP, этот следующий шаг избыточен. Если Вы не установили акселераторы меню, Вы должны добавить привязку CCP к входной карте. Следующий фрагмент кода показывает, как это делается:
// only required if you have not set the menu accelerators InputMap imap = this.getInputMap(); imap.put(KeyStroke.getKeyStroke("ctrl X"), TransferHandler.getCutAction().getValue(Action.NAME)); imap.put(KeyStroke.getKeyStroke("ctrl C"), TransferHandler.getCopyAction().getValue(Action.NAME)); imap.put(KeyStroke.getKeyStroke("ctrl V"), TransferHandler.getPasteAction().getValue(Action.NAME));
Как только привязка была установлена, и меню Edit было установлено, есть другая проблема, которая будет адресоваться: Когда пользователь инициирует сокращение, копию или вставку, какой компонент должен получить действие? В случае текстового компонента, DefaultEditorKit
помнит, у какого последнего компонента были фокус и вперед действие к тому компоненту. Следующий class, TransferActionListener
, выполняет ту же самую функцию для нетекста компоненты Swing. Этот class может быть брошен в большинство любого приложения:
public class TransferActionListener implements ActionListener, PropertyChangeListener { private JComponent focusOwner = null; public TransferActionListener() { KeyboardFocusManager manager = KeyboardFocusManager. getCurrentKeyboardFocusManager(); manager.addPropertyChangeListener("permanentFocusOwner", this); } public void propertyChange(PropertyChangeEvent e) { Object o = e.getNewValue(); if (o instanceof JComponent) { focusOwner = (JComponent)o; } else { focusOwner = null; } } public void actionPerformed(ActionEvent e) { if (focusOwner == null) return; String action = (String)e.getActionCommand(); Action a = focusOwner.getActionMap().get(action); if (a != null) { a.actionPerformed(new ActionEvent(focusOwner, ActionEvent.ACTION_PERFORMED, null)); } } }
Наконец, необходимо решить, как обработать вставку. В случае перетаскивания и отбрасывания, Вы вставляете данные в расположении отбрасывания. В случае вставки Вы не обладаете преимуществом пользователя, указывающего на требуемое расположение вставки. Вы должны решить то, что имеет смысл для Вашего приложения — вставка данных прежде или после того, как текущий выбор мог бы быть лучшим решением.
Следующий демонстрационный пример, ListCutPaste, показывает, как реализовать CCP в экземпляре JList
. Как можно видеть в снимке экрана есть три списка, и можно сократить, скопировать, и вставить к или от любого из этих списков. Они также поддерживают, перетаскивают и отбрасывают. Для этого демонстрационного примера вставляемые данные вставляются после текущего выбора. Если нет никакого текущего выбора, данные добавляются до конца списка.