001 /* DragSource.java --
002 Copyright (C) 2002 Free Software Foundation, Inc.
003
004 This file is part of GNU Classpath.
005
006 GNU Classpath is free software; you can redistribute it and/or modify
007 it under the terms of the GNU General Public License as published by
008 the Free Software Foundation; either version 2, or (at your option)
009 any later version.
010
011 GNU Classpath is distributed in the hope that it will be useful, but
012 WITHOUT ANY WARRANTY; without even the implied warranty of
013 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
014 General Public License for more details.
015
016 You should have received a copy of the GNU General Public License
017 along with GNU Classpath; see the file COPYING. If not, write to the
018 Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
019 02110-1301 USA.
020
021 Linking this library statically or dynamically with other modules is
022 making a combined work based on this library. Thus, the terms and
023 conditions of the GNU General Public License cover the whole
024 combination.
025
026 As a special exception, the copyright holders of this library give you
027 permission to link this library with independent modules to produce an
028 executable, regardless of the license terms of these independent
029 modules, and to copy and distribute the resulting executable under
030 terms of your choice, provided that you also meet, for each linked
031 independent module, the terms and conditions of the license of that
032 module. An independent module is a module which is not derived from
033 or based on this library. If you modify this library, you may extend
034 this exception to your version of the library, but you are not
035 obligated to do so. If you do not wish to do so, delete this
036 exception statement from your version. */
037
038
039 package java.awt.dnd;
040
041 import gnu.classpath.NotImplementedException;
042
043 import java.awt.Component;
044 import java.awt.Cursor;
045 import java.awt.GraphicsEnvironment;
046 import java.awt.HeadlessException;
047 import java.awt.Image;
048 import java.awt.Point;
049 import java.awt.Toolkit;
050 import java.awt.datatransfer.FlavorMap;
051 import java.awt.datatransfer.SystemFlavorMap;
052 import java.awt.datatransfer.Transferable;
053 import java.awt.dnd.peer.DragSourceContextPeer;
054 import java.io.Serializable;
055 import java.util.EventListener;
056
057 /**
058 * @since 1.2
059 */
060 public class DragSource implements Serializable
061 {
062 /**
063 * Compatible with JDK 1.2+.
064 */
065 private static final long serialVersionUID = 6236096958971414066L;
066
067 public static final Cursor DefaultCopyDrop = null;
068 public static final Cursor DefaultMoveDrop = null;
069 public static final Cursor DefaultLinkDrop = null;
070 public static final Cursor DefaultCopyNoDrop = null;
071 public static final Cursor DefaultMoveNoDrop = null;
072 public static final Cursor DefaultLinkNoDrop = null;
073
074 private transient FlavorMap flavorMap = SystemFlavorMap.getDefaultFlavorMap ();
075 private transient DragSourceListener dragSourceListener;
076 private transient DragSourceMotionListener dragSourceMotionListener;
077
078 private static DragSource ds;
079 private DragSourceContextPeer peer;
080 private DragSourceContext context;
081
082 /**
083 * Initializes the drag source.
084 *
085 * @exception HeadlessException If GraphicsEnvironment.isHeadless() is true.
086 */
087 public DragSource()
088 {
089 if (GraphicsEnvironment.isHeadless())
090 {
091 ds = null;
092 throw new HeadlessException();
093 }
094 }
095
096 /**
097 * Gets the default drag source.
098 *
099 * @exception HeadlessException If GraphicsEnvironment.isHeadless() is true.
100 */
101 public static DragSource getDefaultDragSource()
102 {
103 if (GraphicsEnvironment.isHeadless())
104 {
105 ds = null;
106 throw new HeadlessException();
107 }
108
109 if (ds == null)
110 ds = new DragSource();
111 return ds;
112 }
113
114 public static boolean isDragImageSupported()
115 {
116 // In all cases, Sun returns false here.
117 return false;
118 }
119
120 /**
121 * Start a drag, given the DragGestureEvent that initiated the drag.
122 *
123 * @exception InvalidDnDOperationException If the Drag and Drop system is
124 * unable to initiate a drag operation, or if the user attempts to start
125 * a drag while an existing drag operation is still executing.
126 */
127 public void startDrag(DragGestureEvent trigger, Cursor dragCursor,
128 Image dragImage, Point imageOffset,
129 Transferable trans, DragSourceListener dsl,
130 FlavorMap map)
131 {
132 // http://www.javaworld.com/javaworld/jw-03-1999/jw-03-dragndrop.html
133
134 // This function creates a DragSourceContext object. This object tracks the
135 // state of the operation by listening to a native peer. In this situation,
136 // the DragSource may be obtained from the event or by an instance variable.
137 // This function also creates a new DragSourceContextPeer.
138
139 // This function sends the same message to the context, which then forwards
140 // it to the peer, passing itself as a parameter. Now, the native system has
141 // access to the Transferable through the context.
142
143 try
144 {
145 flavorMap = map;
146
147 if (peer == null)
148 peer = Toolkit.getDefaultToolkit().createDragSourceContextPeer(trigger);
149
150 if (context == null)
151 context = createDragSourceContext(peer, trigger,
152 dragCursor,
153 dragImage,
154 imageOffset, trans,
155 dsl);
156
157 if (peer == null)
158 throw new InvalidDnDOperationException();
159
160 peer.startDrag(context, dragCursor, dragImage, imageOffset);
161 }
162 catch (Exception e)
163 {
164 throw new InvalidDnDOperationException("Drag and Drop system is "
165 + "unable to initiate a drag operation.");
166 }
167 }
168
169 /**
170 * Start a drag, given the DragGestureEvent that initiated the drag.
171 *
172 * @exception InvalidDnDOperationException If the Drag and Drop system is
173 * unable to initiate a drag operation, or if the user attempts to start
174 * a drag while an existing drag operation is still executing.
175 */
176 public void startDrag(DragGestureEvent trigger, Cursor dragCursor,
177 Transferable trans, DragSourceListener dsl,
178 FlavorMap map)
179 {
180 startDrag(trigger, dragCursor, null, null, trans, dsl, map);
181 }
182
183 /**
184 * Start a drag, given the DragGestureEvent that initiated the drag.
185 *
186 * @exception InvalidDnDOperationException If the Drag and Drop system is
187 * unable to initiate a drag operation, or if the user attempts to start
188 * a drag while an existing drag operation is still executing.
189 */
190 public void startDrag(DragGestureEvent trigger, Cursor dragCursor,
191 Image dragImage, Point imageOffset,
192 Transferable trans, DragSourceListener dsl)
193 {
194 startDrag(trigger, dragCursor, dragImage, imageOffset, trans, dsl, null);
195 }
196
197 /**
198 * Start a drag, given the DragGestureEvent that initiated the drag.
199 *
200 * @exception InvalidDnDOperationException If the Drag and Drop system is
201 * unable to initiate a drag operation, or if the user attempts to start
202 * a drag while an existing drag operation is still executing.
203 */
204 public void startDrag(DragGestureEvent trigger, Cursor dragCursor,
205 Transferable trans, DragSourceListener dsl)
206 {
207 startDrag(trigger, dragCursor, null, null, trans, dsl, null);
208 }
209
210 /**
211 * Creates the DragSourceContext to handle this drag.
212 *
213 * @exception IllegalArgumentException
214 * @exception NullPointerException If dscp, dgl, dragImage or t is null.
215 */
216 protected DragSourceContext
217 createDragSourceContext(DragSourceContextPeer peer, DragGestureEvent dge,
218 Cursor cursor, Image image, Point offset,
219 Transferable t, DragSourceListener dsl)
220 {
221 return new DragSourceContext(peer, dge, cursor, image, offset, t, dsl);
222 }
223
224 public FlavorMap getFlavorMap()
225 {
226 return flavorMap;
227 }
228
229 public <T extends DragGestureRecognizer> T
230 createDragGestureRecognizer(Class<T> recognizer,
231 Component c,
232 int actions,
233 DragGestureListener dgl)
234 {
235 return (T) Toolkit.getDefaultToolkit().createDragGestureRecognizer(recognizer,
236 this, c,
237 actions, dgl);
238 }
239
240 public DragGestureRecognizer createDefaultDragGestureRecognizer(Component c,
241 int actions,
242 DragGestureListener dgl)
243 {
244 return createDragGestureRecognizer(MouseDragGestureRecognizer.class, c,
245 actions, dgl);
246 }
247
248 /**
249 * @since 1.4
250 */
251 public void addDragSourceListener(DragSourceListener l)
252 {
253 DnDEventMulticaster.add (dragSourceListener, l);
254 }
255
256 /**
257 * @since 1.4
258 */
259 public void removeDragSourceListener(DragSourceListener l)
260 {
261 DnDEventMulticaster.remove (dragSourceListener, l);
262 }
263
264 /**
265 * @since 1.4
266 */
267 public DragSourceListener[] getDragSourceListeners()
268 {
269 return (DragSourceListener[]) getListeners (DragSourceListener.class);
270 }
271
272 /**
273 * @since 1.4
274 */
275 public void addDragSourceMotionListener(DragSourceMotionListener l)
276 {
277 DnDEventMulticaster.add (dragSourceMotionListener, l);
278 }
279
280 /**
281 * @since 1.4
282 */
283 public void removeDragSourceMotionListener(DragSourceMotionListener l)
284 {
285 DnDEventMulticaster.remove (dragSourceMotionListener, l);
286 }
287
288 /**
289 * @since 1.4
290 */
291 public DragSourceMotionListener[] getDragSourceMotionListeners ()
292 {
293 return (DragSourceMotionListener[]) getListeners
294 (DragSourceMotionListener.class);
295 }
296
297 /**
298 * @since 1.4
299 */
300 public <T extends EventListener> T[] getListeners (Class<T> listenerType)
301 {
302 if (listenerType == DragSourceListener.class)
303 return DnDEventMulticaster.getListeners (dragSourceListener,
304 listenerType);
305
306 if (listenerType == DragSourceMotionListener.class)
307 return DnDEventMulticaster.getListeners (dragSourceMotionListener,
308 listenerType);
309
310 // Return an empty EventListener array.
311 return (T[]) new EventListener [0];
312 }
313
314 /**
315 * TODO
316 * @return TODO
317 *
318 * @since 1.5
319 */
320 public static int getDragThreshold()
321 throws NotImplementedException
322 {
323 // FIXME: Not implemented.
324 return 8;
325 }
326 } // class DragSource