[Schmitzm-commits] r2153 - in trunk/schmitzm-core/src/main/java/de/schmitzm/swing: . dnd
scm-commit at wald.intevation.org
scm-commit at wald.intevation.org
Sat Dec 8 18:06:18 CET 2012
Author: mojays
Date: 2012-12-08 18:06:18 +0100 (Sat, 08 Dec 2012)
New Revision: 2153
Added:
trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/
trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JListDropTargetListener.java
trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JListTransferHandler.java
trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JTableDropTargetListener.java
trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JTableTransferHandler.java
trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/ListingDropTargetListener.java
trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/ListingTransferHandler.java
Log:
ListingTransferHandler, JListTransferHandler, JTableTransferHandler: Generic drag and drop implementation between tables and lists
Added: trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JListDropTargetListener.java
===================================================================
--- trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JListDropTargetListener.java (rev 0)
+++ trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JListDropTargetListener.java 2012-12-08 17:06:18 UTC (rev 2153)
@@ -0,0 +1,68 @@
+/**
+ * Copyright (c) 2009 Martin O. J. Schmitz.
+ *
+ * This file is part of the SCHMITZM library - a collection of utility
+ * classes based on Java 1.6, focusing (not only) on Java Swing
+ * and the Geotools library.
+ *
+ * The SCHMITZM project is hosted at:
+ * http://wald.intevation.org/projects/schmitzm/
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 3
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License (license.txt)
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ * or try this link: http://www.gnu.org/licenses/lgpl.html
+ *
+ * Contributors:
+ * Martin O. J. Schmitz - initial API and implementation
+ * Stefan A. Tzeggai - additional utility classes
+ */
+package de.schmitzm.swing.dnd;
+
+import java.awt.Point;
+import java.awt.dnd.DropTargetListener;
+
+import javax.swing.JList;
+import javax.swing.ListModel;
+
+/**
+ * {@link DropTargetListener} for {@link JList}. Sub classes only have to
+ * implement {@link #addListItems(int)} to insert the dropped items into
+ * the individual {@link ListModel}.
+ * @author Martin O.J. Schmitz
+ *
+ * @deprecated Simple but not reliable implementation. Use {@link JListTransferHandler}
+ * instead
+ */
+public abstract class JListDropTargetListener extends ListingDropTargetListener<JList> {
+
+ /**
+ * Creates a new {@link DropTargetListener}.
+ * @param dropList table which acts as drop destination
+ */
+ public JListDropTargetListener(JList dropList) {
+ super(dropList);
+ }
+
+ /**
+ * Converts a location (relatively to {@link #dropListingComp}) to
+ * list index.
+ * @param loc location
+ * @see JList#locationToIndex(Point)
+ */
+ @Override
+ public int convertLocationToListIndex(Point loc) {
+ return getDropListingComponent().locationToIndex( loc );
+ }
+
+}
Added: trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JListTransferHandler.java
===================================================================
--- trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JListTransferHandler.java (rev 0)
+++ trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JListTransferHandler.java 2012-12-08 17:06:18 UTC (rev 2153)
@@ -0,0 +1,179 @@
+/**
+ * Copyright (c) 2009 Martin O. J. Schmitz.
+ *
+ * This file is part of the SCHMITZM library - a collection of utility
+ * classes based on Java 1.6, focusing (not only) on Java Swing
+ * and the Geotools library.
+ *
+ * The SCHMITZM project is hosted at:
+ * http://wald.intevation.org/projects/schmitzm/
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 3
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License (license.txt)
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ * or try this link: http://www.gnu.org/licenses/lgpl.html
+ *
+ * Contributors:
+ * Martin O. J. Schmitz - initial API and implementation
+ * Stefan A. Tzeggai - additional utility classes
+ */
+package de.schmitzm.swing.dnd;
+
+import java.util.Arrays;
+import java.util.Collection;
+
+import javax.swing.DropMode;
+import javax.swing.JList;
+import javax.swing.TransferHandler;
+
+/**
+ * {@link ListingTransferHandler} implementation for {@link JList}.
+ * Implementations only have to implement {@link #reorderListItems(JList, int[], int, int)}
+ * and {@link #moveListItems(JList, int[], int, JList, int)}.
+ * @author Martin O.J. Schmitz
+ *
+ */
+public abstract class JListTransferHandler extends ListingTransferHandler<JList> {
+
+ /**
+ * Creates new {@link ListingTransferHandler} for {@link JList} with drag
+ * and drop within the same list component (reorder) is NOT allowed..
+ * @param listComp list components between which drag and drop is allowed
+ */
+ public JListTransferHandler(JList... listComp) {
+ super(listComp);
+ }
+
+ /**
+ * Creates new {@link ListingTransferHandler} for {@link JList} with drag
+ * and drop within the same list component (reorder) is NOT allowed..
+ * @param listComp list components between which drag and drop is allowed
+ */
+ public JListTransferHandler(Collection<JList> listComp) {
+ super(listComp);
+ }
+
+ /**
+ * Creates new {@link ListingTransferHandler} for {@link JList}.
+ * @param innerListDragAllowed indicates whether drag and drop within the same list component
+ * is allowed (to reorder the elements)
+ * @param listComp list components between which drag and drop is allowed
+ */
+ public JListTransferHandler(boolean innerListDragAllowed, JList... listComp) {
+ super(innerListDragAllowed, Arrays.asList(listComp) );
+ }
+
+ /**
+ * Creates new {@link ListingTransferHandler} for {@link JList}.
+ * @param innerListDragAllowed indicates whether drag and drop within the same list component
+ * is allowed (to reorder the elements)
+ * @param listComp list components between which drag and drop is allowed
+ */
+ public JListTransferHandler(boolean innerListDragAllowed, Collection<JList> listComp) {
+ super(innerListDragAllowed,listComp);
+ }
+
+ /**
+ * Simply calls {@link JList#getSelectedIndices()}.
+ */
+ @Override
+ protected int[] getSelectedRows(JList listComp) {
+ return listComp.getSelectedIndices();
+ }
+
+ /**
+ * Simply calls {@link JList#getSelectedIndex()}.
+ */
+ @Override
+ protected int getSelectedRow(JList listComp) {
+ return listComp.getSelectedIndex();
+ }
+
+ /**
+ * Simply calls {@link JList#getSize()}.
+ */
+ @Override
+ protected int getRowCount(JList listComp) {
+ return listComp.getModel().getSize();
+ }
+
+
+ /**
+ * Treats the given drop location as {@link JList.DropLocation} and
+ * returns {@link JList.DropLocation#getIndex()}.
+ */
+ @Override
+ protected int getDropRow(JList listComp, DropLocation dl) {
+ int index = ((JList.DropLocation)dl).getIndex();
+ return index;
+ }
+
+ /**
+ * Simply calls {@link JList#setTransferHandler(TransferHandler)}.
+ * @param listComp {@link JList} component
+ * @param transferHandler {@link TransferHandler} to be set (normally {@code this})
+ */
+ @Override
+ public void setTransferHandler(JList listComp, TransferHandler transferHandler) {
+ listComp.setTransferHandler(transferHandler);
+ }
+
+ /**
+ * Simply calls {@link JList#getTransferHandler()()}.
+ * @param listComp {@link JList} component
+ */
+ @Override
+ public TransferHandler getTransferHandler(JList listComp) {
+ return listComp.getTransferHandler();
+
+ }
+
+ /**
+ * Simply calls {@link JList#setDropMode(DropMode)}.
+ * @param listComp {@link JList} component
+ * @param dropMode {@link DropMode} to be set
+ */
+ @Override
+ public void setDropMode(JList listComp, DropMode dropMode) {
+ listComp.setDropMode(dropMode);
+ }
+
+ /**
+ * Simply calls {@link JList#getDropMode()}.
+ * @param listComp {@link JList} component
+ */
+ @Override
+ public DropMode getDropMode(JList listComp) {
+ return listComp.getDropMode();
+ }
+
+ /**
+ * Simply calls {@link JList#setDragEnabled(boolean)}.
+ * @param listComp {@link JList} component
+ * @param enabled indicates whether drag is enabled
+ */
+ @Override
+ public void setDragEnabled(JList listComp, boolean enabled) {
+ listComp.setDragEnabled(enabled);
+ }
+
+ /**
+ * Simply calls {@link JList#getDragEnabled()}.
+ * @param listComp {@link JList} component
+ */
+ @Override
+ public boolean getDragEnabled(JList listComp) {
+ return listComp.getDragEnabled();
+ }
+
+}
Added: trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JTableDropTargetListener.java
===================================================================
--- trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JTableDropTargetListener.java (rev 0)
+++ trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JTableDropTargetListener.java 2012-12-08 17:06:18 UTC (rev 2153)
@@ -0,0 +1,68 @@
+/**
+ * Copyright (c) 2009 Martin O. J. Schmitz.
+ *
+ * This file is part of the SCHMITZM library - a collection of utility
+ * classes based on Java 1.6, focusing (not only) on Java Swing
+ * and the Geotools library.
+ *
+ * The SCHMITZM project is hosted at:
+ * http://wald.intevation.org/projects/schmitzm/
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 3
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License (license.txt)
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ * or try this link: http://www.gnu.org/licenses/lgpl.html
+ *
+ * Contributors:
+ * Martin O. J. Schmitz - initial API and implementation
+ * Stefan A. Tzeggai - additional utility classes
+ */
+package de.schmitzm.swing.dnd;
+
+import java.awt.Point;
+import java.awt.dnd.DropTargetListener;
+
+import javax.swing.JTable;
+import javax.swing.table.TableModel;
+
+/**
+ * {@link DropTargetListener} for {@link JTable}. Sub classes only have to
+ * implement {@link #addListItems(int)} to insert the dropped items into
+ * the individual {@link TableModel}.
+ * @author Martin O.J. Schmitz
+ *
+ * @deprecated Simple but not reliable implementation. Use {@link JTableTransferHandler}
+ * instead
+ */
+public abstract class JTableDropTargetListener extends ListingDropTargetListener<JTable> {
+
+ /**
+ * Creates a new {@link DropTargetListener}.
+ * @param dropTable table which acts as drop destination
+ */
+ public JTableDropTargetListener(JTable dropTable) {
+ super(dropTable);
+ }
+
+ /**
+ * Converts a location (relatively to {@link #dropListingComp}) to
+ * table row.
+ * @param loc location
+ * @see JTable#rowAtPoint(Point)
+ */
+ @Override
+ public int convertLocationToListIndex(Point loc) {
+ return getDropListingComponent().rowAtPoint( loc );
+ }
+
+}
Added: trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JTableTransferHandler.java
===================================================================
--- trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JTableTransferHandler.java (rev 0)
+++ trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/JTableTransferHandler.java 2012-12-08 17:06:18 UTC (rev 2153)
@@ -0,0 +1,181 @@
+/**
+ * Copyright (c) 2009 Martin O. J. Schmitz.
+ *
+ * This file is part of the SCHMITZM library - a collection of utility
+ * classes based on Java 1.6, focusing (not only) on Java Swing
+ * and the Geotools library.
+ *
+ * The SCHMITZM project is hosted at:
+ * http://wald.intevation.org/projects/schmitzm/
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 3
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License (license.txt)
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ * or try this link: http://www.gnu.org/licenses/lgpl.html
+ *
+ * Contributors:
+ * Martin O. J. Schmitz - initial API and implementation
+ * Stefan A. Tzeggai - additional utility classes
+ */
+package de.schmitzm.swing.dnd;
+
+import java.util.Arrays;
+import java.util.Collection;
+
+import javax.swing.DropMode;
+import javax.swing.JTable;
+import javax.swing.TransferHandler;
+import javax.swing.table.TableModel;
+
+/**
+ * {@link ListingTransferHandler} implementation for {@link JTable} which
+ * means the drag and drop for <b>complete table rows</b>.
+ * Implementations only have to implement {@link #reorderListItems(JTable, int[], int, int)} and
+ * {@link #moveListItems(JTable, int[], int, JTable, int)}.
+ * @author Martin O.J. Schmitz
+ *
+ */
+public abstract class JTableTransferHandler extends ListingTransferHandler<JTable> {
+
+ /**
+ * Creates new {@link ListingTransferHandler} for {@link JTable} with drag
+ * and drop within the same list component (reorder) is NOT allowed..
+ * @param listComp list components between which drag and drop is allowed
+ */
+ public JTableTransferHandler(JTable... listComp) {
+ super(listComp);
+ }
+
+ /**
+ * Creates new {@link ListingTransferHandler} for {@link JTable} with drag
+ * and drop within the same list component (reorder) is NOT allowed..
+ * @param listComp list components between which drag and drop is allowed
+ */
+ public JTableTransferHandler(Collection<JTable> listComp) {
+ super(listComp);
+ }
+
+ /**
+ * Creates new {@link ListingTransferHandler} for {@link JTable}.
+ * @param innerListDragAllowed indicates whether drag and drop within the same list component
+ * is allowed (to reorder the elements)
+ * @param listComp list components between which drag and drop is allowed
+ */
+ public JTableTransferHandler(boolean innerListDragAllowed, JTable... listComp) {
+ super(innerListDragAllowed, Arrays.asList(listComp) );
+ }
+
+ /**
+ * Creates new {@link ListingTransferHandler} for {@link JTable}.
+ * @param innerListDragAllowed indicates whether drag and drop within the same list component
+ * is allowed (to reorder the elements)
+ * @param listComp list components between which drag and drop is allowed
+ */
+ public JTableTransferHandler(boolean innerListDragAllowed, Collection<JTable> listComp) {
+ super(innerListDragAllowed,listComp);
+ }
+
+ /**
+ * Simply calls {@link JTable#getSelectedRows()}.
+ */
+ @Override
+ protected int[] getSelectedRows(JTable listComp) {
+ return listComp.getSelectedRows();
+ }
+
+ /**
+ * Simply calls {@link JTable#getSelectedRow()}.
+ */
+ @Override
+ protected int getSelectedRow(JTable listComp) {
+ return listComp.getSelectedRow();
+ }
+
+ /**
+ * Simply calls {@link TableModel#getRowCount()}.
+ */
+ @Override
+ protected int getRowCount(JTable listComp) {
+ return listComp.getModel().getRowCount();
+ }
+
+
+ /**
+ * Treats the given drop location as {@link JTable.DropLocation} and
+ * returns {@link JTable.DropLocation#getRow()}.
+ */
+ @Override
+ protected int getDropRow(JTable listComp, DropLocation dl) {
+ int index = ((JTable.DropLocation)dl).getRow();
+ return index;
+ }
+
+ /**
+ * Simply calls {@link JTable#setTransferHandler(TransferHandler)}.
+ * @param listComp {@link JTable} component
+ * @param transferHandler {@link TransferHandler} to be set (normally {@code this})
+ */
+ @Override
+ public void setTransferHandler(JTable listComp, TransferHandler transferHandler) {
+ listComp.setTransferHandler(transferHandler);
+ }
+
+ /**
+ * Simply calls {@link JTable#getTransferHandler()()}.
+ * @param listComp {@link JTable} component
+ */
+ @Override
+ public TransferHandler getTransferHandler(JTable listComp) {
+ return listComp.getTransferHandler();
+
+ }
+
+ /**
+ * Simply calls {@link JTable#setDropMode(DropMode)}.
+ * @param listComp {@link JTable} component
+ * @param dropMode {@link DropMode} to be set
+ */
+ @Override
+ public void setDropMode(JTable listComp, DropMode dropMode) {
+ listComp.setDropMode(dropMode);
+ }
+
+ /**
+ * Simply calls {@link JTable#getDropMode()}.
+ * @param listComp {@link JTable} component
+ */
+ @Override
+ public DropMode getDropMode(JTable listComp) {
+ return listComp.getDropMode();
+ }
+
+ /**
+ * Simply calls {@link JTable#setDragEnabled(boolean)}.
+ * @param listComp {@link JTable} component
+ * @param enabled indicates whether drag is enabled
+ */
+ @Override
+ public void setDragEnabled(JTable listComp, boolean enabled) {
+ listComp.setDragEnabled(enabled);
+ }
+
+ /**
+ * Simply calls {@link JTable#getDragEnabled()}.
+ * @param listComp {@link JTable} component
+ */
+ @Override
+ public boolean getDragEnabled(JTable listComp) {
+ return listComp.getDragEnabled();
+ }
+
+}
Added: trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/ListingDropTargetListener.java
===================================================================
--- trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/ListingDropTargetListener.java (rev 0)
+++ trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/ListingDropTargetListener.java 2012-12-08 17:06:18 UTC (rev 2153)
@@ -0,0 +1,111 @@
+/**
+ * Copyright (c) 2009 Martin O. J. Schmitz.
+ *
+ * This file is part of the SCHMITZM library - a collection of utility
+ * classes based on Java 1.6, focusing (not only) on Java Swing
+ * and the Geotools library.
+ *
+ * The SCHMITZM project is hosted at:
+ * http://wald.intevation.org/projects/schmitzm/
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 3
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License (license.txt)
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ * or try this link: http://www.gnu.org/licenses/lgpl.html
+ *
+ * Contributors:
+ * Martin O. J. Schmitz - initial API and implementation
+ * Stefan A. Tzeggai - additional utility classes
+ */
+package de.schmitzm.swing.dnd;
+
+import java.awt.Component;
+import java.awt.Point;
+import java.awt.dnd.DropTarget;
+import java.awt.dnd.DropTargetAdapter;
+import java.awt.dnd.DropTargetDropEvent;
+import java.awt.dnd.DropTargetListener;
+
+import javax.swing.JScrollPane;
+import javax.swing.JTable;
+import javax.swing.SwingUtilities;
+
+import de.schmitzm.swing.JList;
+
+/**
+ * Abstract super class for several list drop targets ({@link JList} or {@link JTable}).
+ *
+ * @author Martin O.J. Schmitz
+ *
+ * @deprecated Simple but not reliable implementation. Use {@link ListingTransferHandler}
+ * instead
+ */
+public abstract class ListingDropTargetListener<E extends Component> extends DropTargetAdapter {
+ /** Holds the list component (e.g. {@link JTable} or {@link JList})
+ * which acts as destination for the dropped items. Not necessary the
+ * drop component (which may be a {@link JScrollPane}). */
+ protected E dropListingComp;
+
+ /**
+ * Creates a new {@link DropTargetListener}.
+ * @param dropListingComp list component (e.g. {@link JTable} or {@link JList})
+ * which acts as drop destination
+ */
+ public ListingDropTargetListener(E dropListingComp) {
+ super();
+ this.dropListingComp = dropListingComp;
+ }
+
+ /**
+ * Performs the drop.
+ */
+ @Override
+ public void drop(DropTargetDropEvent dtde) {
+ Component dropComp = ((DropTarget)dtde.getSource()).getComponent();
+ Point dropLoc = dtde.getLocation();
+ Point dropLocOnTable = SwingUtilities.convertPoint(dropComp, dropLoc, dropListingComp);
+
+ int row;
+ // if drop was above table, insert items at table head
+ if ( dropLocOnTable.y <= 0 )
+ row = 0;
+ else
+ // determine table row at drop location (-1 if drop was not on table)
+ row = convertLocationToListIndex( dropLocOnTable );
+
+ addListItems(row);
+ }
+
+ /**
+ * Returns the list component (e.g. {@link JTable} or {@link JList})
+ * which acts as drop destination.
+ */
+ public E getDropListingComponent() {
+ return dropListingComp;
+ }
+
+ /**
+ * Converts a location (relatively to {@link #dropListingComp}) to
+ * listing index.
+ * @param loc location
+ */
+ public abstract int convertLocationToListIndex(Point loc);
+
+ /**
+ * Adds items to the {@link #dropListingComp}. Which items (from drag source)
+ * must be inserted, the implementing class must determine itself,
+ * @param idx list index (or row) to add the items at
+ */
+ public abstract void addListItems(int idx);
+
+}
Added: trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/ListingTransferHandler.java
===================================================================
--- trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/ListingTransferHandler.java (rev 0)
+++ trunk/schmitzm-core/src/main/java/de/schmitzm/swing/dnd/ListingTransferHandler.java 2012-12-08 17:06:18 UTC (rev 2153)
@@ -0,0 +1,380 @@
+/**
+ * Copyright (c) 2009 Martin O. J. Schmitz.
+ *
+ * This file is part of the SCHMITZM library - a collection of utility
+ * classes based on Java 1.6, focusing (not only) on Java Swing
+ * and the Geotools library.
+ *
+ * The SCHMITZM project is hosted at:
+ * http://wald.intevation.org/projects/schmitzm/
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 3
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License (license.txt)
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ * or try this link: http://www.gnu.org/licenses/lgpl.html
+ *
+ * Contributors:
+ * Martin O. J. Schmitz - initial API and implementation
+ * Stefan A. Tzeggai - additional utility classes
+ */
+package de.schmitzm.swing.dnd;
+
+import java.awt.Component;
+import java.awt.Cursor;
+import java.awt.datatransfer.DataFlavor;
+import java.awt.datatransfer.Transferable;
+import java.awt.dnd.DragSource;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collection;
+
+import javax.activation.DataHandler;
+import javax.swing.DropMode;
+import javax.swing.JComponent;
+import javax.swing.JList;
+import javax.swing.JTable;
+import javax.swing.TransferHandler;
+
+import org.apache.log4j.Logger;
+
+import de.schmitzm.lang.LangUtil;
+
+/**
+ * Abstract super class for {@link TransferHandler}, which implements drag & drop
+ * between one or more list components ({@link JTable}, {@link JList}, ...).
+ * For each of the list components
+ * <ul>
+ * <li>this {@link TransferHandler} must be set</li>
+ * <li>drag must be enabled, e.g. by {@link JList#setDragEnabled(boolean)}</li>
+ * <li>drop mode must be set, e.g. by {@link JList#setDropMode(javax.swing.DropMode)}
+ * </ul>
+ * To allow drag and drop between all of the lists without any special restriction
+ * {@link #initializeLists()} can be called. Otherwise these properties must be set
+ * individually by the calling application class!
+ * @author Martin O.J. Schmitz
+ *
+ */
+public abstract class ListingTransferHandler<LIST_IMPL extends Component> extends TransferHandler {
+ protected Logger LOGGER = LangUtil.createLogger(this);
+
+ private final DataFlavor localObjectFlavor = new DataFlavor(Integer.class, "Integer Row Index");
+
+ /** Hold the list components between which drag and drop is allowed */
+ protected ArrayList<LIST_IMPL> dndListComp = null;
+ /** Holds the source component (the drag component) */
+ protected LIST_IMPL dragSourceComp = null;
+ /** Holds the destination component (the drop component) */
+ protected LIST_IMPL dropTargetComp = null;
+ /** Indicates whether drag and drop within the same list component is allowed (to
+ * reorder the elements). */
+ protected boolean innerListDragAllowed = false;
+
+
+ /**
+ * Creates new {@link TransferHandler} with drag and drop within the same list
+ * component (reorder) is NOT allowed.
+ * @param listComp list components between which drag and drop is allowed
+ */
+ public ListingTransferHandler(LIST_IMPL... listComp) {
+ this(Arrays.asList(listComp));
+ }
+
+ /**
+ * Creates new {@link TransferHandler} with drag and drop within the same list
+ * component (reorder) is NOT allowed.
+ * @param listComp list components between which drag and drop is allowed
+ */
+ public ListingTransferHandler(Collection<LIST_IMPL> listComp) {
+ this(false, listComp);
+ }
+
+ /**
+ * Creates new {@link TransferHandler}.
+ * @param innerListDragAllowed indicates whether drag and drop within the same list component
+ * is allowed (to reorder the elements)
+ * @param listComp list components between which drag and drop is allowed
+ */
+ public ListingTransferHandler(boolean innerListDragAllowed, LIST_IMPL... listComp) {
+ this(innerListDragAllowed, Arrays.asList(listComp) );
+ }
+
+ /**
+ * Creates new {@link TransferHandler}.
+ * @param innerListDragAllowed indicates whether drag and drop within the same list component
+ * is allowed (to reorder the elements)
+ * @param listComp list components between which drag and drop is allowed
+ */
+ public ListingTransferHandler(boolean innerListDragAllowed, Collection<LIST_IMPL> listComp) {
+ this.dndListComp = new ArrayList<LIST_IMPL>(listComp);
+ this.innerListDragAllowed = innerListDragAllowed;
+ }
+
+ /**
+ * For all list components this method
+ * <ul>
+ * <li>set {@code this} as {@link TransferHandler}</li>
+ * <li>enables drag by {@link #setDragEnabled(Component, boolean)</li>
+ * <li>sets drop mode to {@link DropMode#INSERT} by {@link #setDropMode(Component, DropMode)}
+ * </ul>
+ */
+ public void initializeLists() {
+ for (LIST_IMPL listComp : dndListComp) {
+ setTransferHandler(listComp, this);
+ setDragEnabled(listComp, true);
+ setDropMode(listComp, DropMode.INSERT);
+ }
+ }
+
+ /**
+ * For Debugging.
+ */
+ private void logCompIndex(String prefix, Component c) {
+ String mess = prefix+": "+ dndListComp.indexOf(c);
+ LOGGER.debug(mess);
+ }
+
+ /**
+ * Creates {@link Transferable} on drag start.
+ */
+ @Override
+ protected Transferable createTransferable(JComponent c) {
+ assert (dndListComp.contains(c));
+ return new DataHandler(getSelectedRow((LIST_IMPL)c), localObjectFlavor.getMimeType());
+ }
+
+ /**
+ * Checks whether drop is allowed to component.
+ */
+ @Override
+ public boolean canImport(TransferSupport info) {
+ Component dropComp = info.getComponent();
+ logCompIndex("canImport", dropComp);
+ // Check if drop is allowed to destination component
+ boolean dndAllowed = ( isInnerListDragAllowed() || dropComp != getDragSource() ) &&
+ dndListComp.contains(dropComp) &&
+ checkDragDropAllowed(getDragSource(), (LIST_IMPL)dropComp) &&
+ info.isDrop() &&
+ info.isDataFlavorSupported(localObjectFlavor);
+ if ( dndAllowed ) {
+ // remember target component for easy access
+ this.dropTargetComp = (LIST_IMPL)dropComp;
+ // set cursor for possible drop
+ dropComp.setCursor( DragSource.DefaultMoveDrop );
+ } else
+ // set cursor for impossible drop
+ dropComp.setCursor( DragSource.DefaultMoveNoDrop );
+
+ return dndAllowed;
+ }
+
+ /**
+ * Checks whether drag and drop is allowed between two list components.
+ * This default implementation always returns {@code true}. Sub classes can
+ * override this method to implement special rules.
+ */
+ protected boolean checkDragDropAllowed(LIST_IMPL fromList, LIST_IMPL toList) {
+ return true;
+ }
+
+
+ /**
+ * Returns {@link TransferHandler#COPY_OR_MOVE}.
+ */
+ @Override
+ public int getSourceActions(JComponent c) {
+ logCompIndex("getSourceAction", c);
+ this.dragSourceComp = (LIST_IMPL)c;
+ return TransferHandler.COPY_OR_MOVE;
+ }
+
+ /**
+ * Performs the drop action.
+ */
+ @Override
+ public boolean importData(TransferHandler.TransferSupport info) {
+ LIST_IMPL target = (LIST_IMPL)info.getComponent();
+ LIST_IMPL source = getDragSource();
+
+ logCompIndex("importData from", source);
+ logCompIndex("importData to", target);
+
+
+ int toIdx = getDropRow(target, info.getDropLocation());
+ int maxIdx = getRowCount(target);
+ if (toIdx < 0 || toIdx > maxIdx)
+ toIdx = maxIdx;
+ target.setCursor(Cursor.getPredefinedCursor(Cursor.DEFAULT_CURSOR));
+ try {
+ if ( target == source ) {
+ // REORDER within same list component
+ Integer fromIdx = (Integer)info.getTransferable().getTransferData(localObjectFlavor);
+ if (fromIdx != -1 && fromIdx != toIdx) {
+ reorderListItems(target, getSelectedRows(target), fromIdx, toIdx);
+ return true;
+ }
+ } else {
+ // MOVE from list component to another list
+ Integer fromIdx = (Integer)info.getTransferable().getTransferData(localObjectFlavor);
+ if ( fromIdx != -1 ) {
+ moveListItems(source,getSelectedRows(source), fromIdx, target, toIdx);
+ return true;
+ }
+ }
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ return false;
+ }
+
+ /**
+ * Returns whether drag and drop within the same list component is allowed (to
+ * reorder the elements).
+ */
+ public boolean isInnerListDragAllowed() {
+ return this.innerListDragAllowed;
+ }
+
+ /**
+ * Returns the source list component, the drag is performed on.
+ * @return {@code null} if no drag and drop action is in progress
+ */
+ public LIST_IMPL getDragSource() {
+ return this.dragSourceComp;
+ }
+
+ /**
+ * Returns the target list component, the drop is performed on.
+ * @return {@code null} if no drag and drop action is in progress
+ */
+ public LIST_IMPL getDropTarget() {
+ return this.dropTargetComp;
+ }
+
+
+ /**
+ * Resets cursors and initializes {@link #dropTargetComp} and {@link #dragSourceComp}.
+ */
+ @Override
+ protected void exportDone(JComponent c, Transferable t, int act) {
+ logCompIndex("exportDone", c);
+ // reset cursors
+ c.setCursor(Cursor.getPredefinedCursor(Cursor.DEFAULT_CURSOR));
+ if ( dropTargetComp != null )
+ dropTargetComp.setCursor(Cursor.getPredefinedCursor(Cursor.DEFAULT_CURSOR));
+ // initialize source and target components
+ this.dragSourceComp = null;
+ this.dropTargetComp = null;
+ }
+
+ /**
+ * Returns the number of rows for a list component.
+ */
+ protected abstract int getRowCount(LIST_IMPL listComp);
+
+ /**
+ * Returns the selected rows for a list component.
+ */
+ protected abstract int[] getSelectedRows(LIST_IMPL listComp);
+
+ /**
+ * Returns the selected row for a list component.
+ */
+ protected abstract int getSelectedRow(LIST_IMPL listComp);
+
+ /**
+ * Converts a drop location in a row number for a list component.
+ */
+ protected abstract int getDropRow(LIST_IMPL listComp, DropLocation dl);
+
+ /**
+ * Reorders the rows in a list component. This must be implemented individually
+ * for the underlying list or table model.
+ * @param listComp list component to reorder the elements in
+ * @param selIdx selected row numbers (in table coordinates!)
+ * @param fromIdx row number (in table coordinates!) the element(s) are moved
+ * from
+ * @param toIdx row number (in table coordinates!) the element(s) should be
+ * moved to
+ */
+ protected abstract void reorderListItems(LIST_IMPL listComp, int[] selIdx, int from, int toIdx);
+
+ /**
+ * Reorders the rows in a list component. This must be implemented individually
+ * for the underlying list or table model.
+ * @param fromList source list component to the selected elements come from
+ * @param selIdx selected row numbers in {@code fromList} (in table coordinates!)
+ * @param fromIdx row number in {@code fromList} (in table coordinates!) the element(s)
+ * are moved from
+ * @param toList target list component the selected elements must be inserted in
+ * @param toIdx row number in {@code toList} (in table coordinates!) the element(s)
+ * should be moved to
+ */
+ protected abstract void moveListItems(LIST_IMPL fromList, int[] selIdx, int from, LIST_IMPL toList, int toIdx);
+
+ /**
+ * Because there is no common interface for drag & drop and e.g.
+ * {@link JList} and {@link JTable} each implement {@code setTransferHandler(TransferHandler)}
+ * for their own, we let the subclass implement it (which has knowledge about
+ * {@link LIST_IMPL}).
+ * @param listComp list component
+ * @param transferHandler {@link TransferHandler} to be set (normally {@code this})
+ */
+ public abstract void setTransferHandler(LIST_IMPL listComp, TransferHandler transferHandler);
+
+ /**
+ * Because there is no common interface for drag & drop and e.g.
+ * {@link JList} and {@link JTable} each implement {@code getTransferHandler()}
+ * for their own, we let the subclass implement it (which has knowledge about
+ * {@link LIST_IMPL}).
+ * @param listComp list component
+ */
+ public abstract TransferHandler getTransferHandler(LIST_IMPL listComp);
+
+ /**
+ * Because there is no common interface for drag & drop and e.g.
+ * {@link JList} and {@link JTable} each implement {@code setDropMode(DropMode)}
+ * for their own, we let the subclass implement it (which has knowledge about
+ * {@link LIST_IMPL}).
+ * @param listComp list component
+ * @param dropMode {@link DropMode} to be set
+ */
+ public abstract void setDropMode(LIST_IMPL listComp, DropMode dropMode);
+
+ /**
+ * Because there is no common interface for drag & drop and e.g.
+ * {@link JList} and {@link JTable} each implement {@code getDropMode()}
+ * for their own, we let the subclass implement it (which has knowledge about
+ * {@link LIST_IMPL}).
+ * @param listComp list component
+ */
+ public abstract DropMode getDropMode(LIST_IMPL listComp);
+
+ /**
+ * Because there is no common interface for drag & drop and e.g.
+ * {@link JList} and {@link JTable} each implement {@code setDragEnabled(boolean)}
+ * for their own, we let the subclass implement it (which has knowledge about
+ * {@link LIST_IMPL}).
+ * @param listComp list component
+ * @param enabled indicates whether drag is enabled
+ */
+ public abstract void setDragEnabled(LIST_IMPL listComp, boolean enabled);
+
+ /**
+ * Because there is no common interface for drag & drop and e.g.
+ * {@link JList} and {@link JTable} each implement {@code getDragEnabled()}
+ * for their own, we let the subclass implement it (which has knowledge about
+ * {@link LIST_IMPL}).
+ * @param listComp list component
+ */
+ public abstract boolean getDragEnabled(LIST_IMPL listComp);
+}
More information about the Schmitzm-commits
mailing list