Cut, copy, and paste operations are commonly used to transfer data across applications. This is especially true for Microsoft Windows. Since Java is platform neutral, however, such operations can be complex. Java 2 provides this functionality with the help of the system clipboard and its drag-and-drop functionality.
Java 2 provides new classes and interfaces to provide support for data transfer. This article introduces them, and demonstrates their use. It also provides practical examples of data transfer techniques: Java-to-Java, Java-to-native (i.e. platform-specific), and vice versa. There are also discussions of several types of data transfer using the clipboard and drag-and-drop features.
It also focuses on the use of the system clipboard for transferring text from a native application (e.g. Microsoft Word) to a Java application, or vice versa. It demonstrate dragging a text file from Windows Explorer to a Java application. The dropped file is opened for reading, its contents displayed to the user. Then it shows how to drag an image from your browser and paste it on to a Java application.
Similarly, the technique of transferring a file object from a Java application to a native application is explained and demonstrated with an example. It's illustrated that, if you drag a *.doc file from a Java application to Microsoft Word, the file will be opened in the native application. Similarly, dragging an Excel file to Microsoft Excel opens it for editing.
Finally, the article demonstrates a technique for transferring any user-defined Java object between Java applications. This is illustrated with a Java Clock object being transferred from one application to another. The latter application, after receiving the dropped Clock object, displays the clock (with the current time) to the user.
To understand data transfer in Java, it's first necessary to study the relevant interfaces and classes defined in Java 2. Let's briefly describe these interfaces and classes before delving into the details of the data transfer mechanism.
The Clipboard ClassThe Clipboard class provides the mechanism for transferring data between two Java applications or between a Java application and a native application. Data can be transferred using the local clipboard or the system clipboard. The local clipboard is used if you want to cut, copy, or paste data within a Java application. The system clipboard is used for transferring data between two Java applications or between a Java application and a native application. If you're transferring data to a native application, the type of data that can be transferred is decided by the MIME format supported by the native application.
To transfer data between a Java application and a native application, you first need to obtain a reference to the system clipboard. You obtain the reference using the getSystemClipboard method of the Toolkit class. Once a reference to the clipboard is obtained, you set the contents of the clipboard using its setContents method. To retrieve the current contents of the clipboard you use the getContents method.
The ClipboardOwner InterfaceAny Java object that provides data to the clipboard must implement this interface, which declares a method named lostOwnership. If any other application places data in the clipboard, this method is called. The method receives a reference to the previous clipboard object and its data.
The Transferable InterfaceAn object that supports data transfer, using either the clipboard or drag and drop, implements this interface, which provides three methods: getTransferDataFlavors, isDataFlavorSupported, and getTransferData. The getTransferDataFlavors method returns the supported data flavors, the isDataFlavorSupported method accepts a DataFlavor as an argument and returns a boolean. The getTransferData method returns the reference to the transferred data.
The DataFlavor ClassThe DataFlavor class is used for representing data formats. The JDK provides pre-defined DataFlavors to represent standard data formats, which are used while transferring the data, using the clipboard or a drag-and-drop operation. stringFlavor is one such class that represents the java.lang.String class and uses a MIME type as "application/x-java-serialized-object." The plainTextFlavor class uses the Java InputStream class as the representation class, and uses MIME type as "text/plain; charset=unicode." Similarly, the javaFileListFlavor class is used for transferring files from a Java application to a native application (and vice versa), and uses java.util.List as its representation class.
The StringSelection ClassThe StringSelection class implements the Transferable interface, and is used for transferring string objects or plain text through the clipboard. It supports two pre-defined DataFlavors: stringFlavor and plainTextFlavor.
Having seen some of the important interfaces and classes, let's now look into the data transfer mechanism using the clipboard.
Clipboard Data TransfersAs mentioned earlier, you use the Java Clipboard class for transferring data using the clipboard. The reference to the system clipboard is obtained using the following statement:
Clipboard clipboard = getToolkit().getSystemClipboard();
Once a reference to the clipboard is obtained, its contents are assigned by calling the setContents method. The method takes two parameters: the first represents the object to be transferred; the second specifies the clipboard's owner.
As seen earlier, the object to be transferred must implement the Transferable interface. The StringSelection class implements this interface and can be used for transferring Java strings, or plain text:
Clipboard.setContents(new
StringSelection("Test String"), ...);
To retrieve the contents of the clipboard, the application calls its getContents method. The getContents method expects one parameter - the reference to the clipboard owner object. The method returns a Transferable object, which is usually typecast to the desired data type:
StringSelection s =
(StringSelection)Clipboard.getContents(...);
The actual string can be retrieved from a StringSelection object by calling its getTransferData method. The getTransferData method takes a parameter of DataFlavor type:
String str = (String)
s.getTransferData(DataFlavor.stringFlavor);
To illustrate the use of these classes, we've created a simple Java application that allows you to cut, copy, and paste data using the system clipboard. The application creates a JList control with a few city names filled in. The application provides Cut, Copy, and Paste menu options. When the user clicks on the Cut menu, the current selection from the list box is copied to the system clipboard, and the entry is removed from the list control. In a Copy operation, the selected entry is copied to the clipboard and not removed from the list box. When the user clicks on the Paste menu item, the current contents of the clipboard are retrieved using its getContents method and added to the list box.
Because the application uses the system clipboard, it can be used for copying data from a native application, such as Word or Excel, and pasting it in the list box. Similarly, you may cut and/or copy data from the list box and paste it into a native application.
The source for the example application is shown in
Listing One. The datatransfer class implements the ClipboardOwner interface. The class constructor creates the user interface for the application. The application displays an object of ListCopy class that is extended from a JList class. As seen earlier, the ClipboardOwner interface declares one method, lostOwnership, which is implemented by our datatransfer class:public void lostOwnership(Clipboard c, Transferable t)
The lostOwnership method is called whenever another application changes the contents of the clipboard. It takes two parameters. The first parameter gives the clipboard a reference that is lost by our application, and the second parameter provides the old Transferable object.
The Cut and Copy menu items get the current selection from the ListCopy control and set the clipboard contents with the currently selected string. The program constructs the StringSelection object and passes it as a parameter to the setContents method:
Clipboard.setContents(
new
StringSelection((String)lcopy.getSelectedValue()),this);
Similarly, the Paste operation obtains the current clipboard contents using the getContents method and typecasts it to the StringSelection class. We use getTransferData method on the returned StringSelection object to retrieve the Java String object, which we add to our ListCopy object. The getTransferData method assumes the stringFlavor for the input object:
StringSelection s =
(StringSelection)Clipboard.getContents(this);
String str = (String)
s.getTransferData(DataFlavor.stringFlavor);
The ListCopy class is shown in Listing Two (ListCopy.java). It's derived from the JList class and constructs a simple list control with a few items filled in. The ListCopy class also implements the drag-and-drop feature, which we'll discuss later.
Clipboard Data TransferIf you wish to cut, copy, or paste data within a Java application, you can use the local clipboard, rather than the system clipboard. To create a local clipboard, create an instance of the Clipboard class:
Clipboard clipboard = new
clipboard("MyClipboard");
where MyClipboard is the name given to the local clipboard. Once you create a clipboard object, you may use its setContents and getContents methods to copy or paste the data. Your application may create any number of local clipboard objects.
The local clipboard can be used for transferring any type of Java object and isn't restricted to the pre-defined MIME types. For example, you could easily cut or copy an image from a panel in your Java application and put it on the local clipboard. The image can later be pasted on another panel within your application from this clipboard. To do this, you'll need to create a custom data flavor using a statement similar to the one shown here:
DataFlavor imageFlavor =
new
DataFlavor(Class.forName(java.awt.Image),"Image");
The first parameter specifies the MIME type. In this case the MIME type and the Representation class are as follows:
MimeType =
"application/x-java-serialized-object"
Representation class =
java.awt.Image
You'll also need to create another class (say ImageSelection), which implements the Transferable interface. Once this is done, you can use code similar to that shown below to copy the image onto the local clipboard:
Image image =
Toolkit.getDefaultToolkit().getImage("abcom.gif");
ImageSelection imageSelection = new ImageSelection(image);
Clipboard.setContents(imageSelection, this);
To paste the image from the local clipboard to a Java Panel object, you'll need code similar to this:
Transferable transferable = clipboard.getContents(...);
if
(transferable.isDataFlavorSupported(imageFlavor))
Image image = (Image)
transferable.getTransferData(imageFlavor);
If you wish to transfer any other type of Java object, you'll need to create a custom data flavor (as previously shown), and use the getContents and setContents methods on the clipboard object to achieve the data transfer.
Having seen the use of the local and system clipboards for data transfer, we'll now look into the drag-and-drop mechanism.
Drag and DropThe functionality for drag and drop is available through the use of the java.awt.dnd package that defines several interfaces and classes. A Java application may support only the drag operation, the drop operation, or both. An application is said to be drop-aware if it's capable of accepting the objects dragged from another application. An application may behave as a drag source whereby the application allows its objects to be dragged to another drop-aware application.
Creating Drop-aware ApplicationsTo make the application drop-aware, you need to
implement the DropTargetListener interface and set the application
as a probable drop target. The DropTargetListener interface
declares several methods, such as dragEnter, and dragOver.
One important method is the drop method. This is where all the
action takes place when an object is dropped onto the application. For the
rest of the methods, you may simply provide null implementations. The
drop method receives an event object of type
DropTargetDropEvent. In the method implementation (again, see
Listing Two), we decide whether to accept the drop:
if ((e.getSourceActions() &
DnDConstants.ACTION_COPY) != 0)
e.acceptDrop(DnDConstants.ACTION_COPY);
else
{
e.rejectDrop();
return;
}
Once we decide to accept the drop, we retrieve the associated data flavors from the event object:
DataFlavor[] dataFlavors = e.getCurrentDataFlavors();
We then try matching the data flavor supported by our drop-aware application with the list of flavors retrieved from the event object. For example, if our drop-aware application supports only the plain-text flavor, we'll search for this flavor in the list of available flavors:
for (int i = 0; i < dataFlavors.length; i++)
if
(DataFlavor.plainTextFlavor.equals(dataFlavors[i]))
...
If the desired data flavor is found, we proceed to retrieve the transferable object from the event object:
Transferable t = e.getTransferable();
We then retrieve the actual data from the Transferable object by calling its getTransferData method. We pass the desired data flavor as a parameter to this method:
InputStream is =
(InputStream)t.getTransferData(transferDataFlavor);
Once the object is retrieved, we complete the event handler by calling the dropComplete method.
In addition to providing the implementation for the drop method, we need to set our application as a possible target for the drag-and-drop operation. We do this by calling the setDropTarget method of the Component class:
this.setDropTarget(new DropTarget(this,this));
Creating Drag-aware Applications
To make the application drag-aware, we need to implement the DragSourceListener and DragGestureListener interfaces (again, see Listing Two). The DragSourceListener interface declares five methods. The dragDropEnd method of this interface is invoked whenever the object being dragged is dropped on the target. Thus, the source receives an intimation of the successful completion of drag-and-drop operation with the help of this method. The other methods are generally used to change the cursor shape depending on the current status of the drag operation.
The DragGestureListener interface declares one method, named dragGestureRecognized. This method is invoked whenever the user makes a drag gesture on the source. Clicking on the source object and dragging it makes the drag gesture. In this event handler, we create the transferable object and call the startDrag method on the event object to begin the drag operation. In the example below, the ListDrag class represents a transferable object:
ListDrag stringTransfer = new
ListDrag((String)getSelectedValue());
e.startDrag(null,
stringTransfer, this);
Also, to make the application drag-aware, you'll need to create a default dragGestureRecognizer. You create the recognizer by calling the createDefaultDragGestureRecognizer method on the default DragSource object:
DragSource ds =
DragSource.getDefaultDragSource();
ds.createDefaultDragGestureRecognizer(
this,
DnDConstants.ACTION_COPY, this);
As mentioned before, the datatransfer application supports data transfer using the drag-and-drop operation. The ListCopy class that extends JList implements functionality for the drag source and drop listener. You'll be able to drag an item from the list box and drop it onto any other drop-aware native application. Similarly, you'll be able to drag a string object from a native application, such as Word or Excel, and drop it on our ListCopy object. Because the ListCopy object acts as a source and a listener, it's possible to start dragging an item from the list and drop it onto itself. In this case, a copy of the string will be appended to the existing list.
For supporting a drag-and-drop operation, you will need to define one more class that implements the Transferable interface. The class implementing this interface will have to define the various DataFlavor objects that it's going to support. The constructor for DataFlavor class takes two parameters: the first specifies the MIME format, and the second specifies the human representative name:
static DataFlavor iso =
new
DataFlavor("text/plain; charset=iso8859-1", "String");
The Transferable interface declares three methods. The getTransferDataFlavors method returns the list of DataFlavors supported by this object. The implementation of the isDataFlavorSupported method receives a DataFlavor as an object and searches through the list of pre-defined flavors and returns the boolean result of the search to the caller. The getTransferData method first checks whether the data flavor is supported by this object, and throws an exception of type UnsupportedFlavorException if it doesn't.
The method creates an input stream and serializes the
desired data on this stream. The reference to the input stream object is
returned to the caller. The caller will retrieve the data from this input
stream. The implementation of our data transfer class is shown in Figure
1.
import
java.awt.datatransfer.*;
import java.awt.dnd.*
import java.io.*;
import java.util.*;
//
******************************************************************
// Class implemented :
ListDrag
// Derived
from :
None
//
Implements :
Transferable
//
******************************************************************
public
class ListDrag
implements Transferable
{
String str;
// Define two new
DataFlavors with character sets as ascii
// and iso8859-1.
static DataFlavor
iso =
new DataFlavor("text/plain;
charset=iso8859-1",
"String");
static DataFlavor
ascii =
new
DataFlavor("text/plain; charset=ascii",
"String");
// Define a DataFlavor
array.
private
static DataFlavor[] FlavorArray = {iso,ascii};
ListDrag(String string)
{
// Store the
string in the current object as str.
this.str = string;
}
public Object
getTransferData(DataFlavor tdf)
throws
UnsupportedFlavorException , IOException
{
// Check if the
DataFlavor being asked for is supported by
the
// current
transferable object.
if
(!isDataFlavorSupported(tdf))
throw new
UnsupportedFlavorException(tdf);
// Create a new
StringBufferInputStream
// and return it
as the transfer data.
StringBufferInputStream sbis =
new StringBufferInputStream(str);
return
sbis;
}
public DataFlavor[]
getTransferDataFlavors()
{
// Returns the
DataFlavors supported as a DataFlavor array.
return
FlavorArray;
}
public
boolean isDataFlavorSupported(DataFlavor sdf)
{
// Check if the
DataFlavor being asked for sdf is among the data
// flavors
supported by this object.
for
(int i = 0 ; i < FlavorArray.length;
i++)
if (FlavorArray[i].equals(sdf)
return
true;
return
false;
}
}
Figure 1: Implementation of our data transfer class.
Dropping a Text File from Native to Java ApplicationsThe datatransfer application previously discussed transfers data using the plain-text flavor. We'll now illustrate the use of yet another data flavor: javaFileListFlavor. The FileDrop application demonstrates the use of this data flavor class shown in Listing Three. The FileDrop application is drop-aware and can accept files dragged from Windows Explorer. We program our FileDrop application to parse a dropped text file and display its contents to the user.
As in the earlier example, we first create the desired data flavor in the implementation of the drop method. The DataFlavor object uses the MIME string as shown below:
DataFlavor fileFlavor = new
DataFlavor(
"application/x-java-file-list;
class=java.util.List", "File");
The program then retrieves the Transferable object:
java.util.List list =
(java.util.List)t.getTransferData(fileFlavor);
The data received from the source is an object of the Java List class. We retrieve the elements in the list by using its toArray method. We open the file for reading using the first element of the array:
Object[] ob =
list.toArray(); & nbsp;
BufferedReader reader =
new BufferedReader(new FileReader((File)ob[0]));
The rest of the code reads the file and displays its contents to the user.
Dropping an Image from a BrowserThe GIFDrop application is shown in Listing Four. It allows you to drag a .GIF image from a browser and display it on our drop-aware Java application. The GIFDrop application is a drop-listener application that understands dragged .GIF images. The drop event handler, as in the earlier case, receives the name of the file from the dropped object. The program creates the image from this file name and displays it to the user:
image = getToolkit().getImage(obj[0].toString());Dragging a File from Java to Native Applications
The FileDrag application creates a Java application that displays the list of files to the user; it's shown in Listing Five. The user can select and drag a file name and drop it on any drop-aware native application. For example, you may drag a file with the .DOC extension to Word and the Word application will open the file for editing. Likewise, if you drag a file with the .XLS extension to Excel, it will be opened for editing in Excel.
In the FileDrag application, the transferable object is created in the DragClass class. The class first creates a DataFlavor using MIME string, as in the case of the FileDrop application. The implementation of the getTransferData method creates a Java Vector object and adds the selected file name to it. Note that the representation class in this case is java.util.List and the Java Vector class implements the List interface. Thus, the getTransferData method returns the Vector object to the caller. The main application creates files of three different types and adds them to the JTree control. The user drags a file from any of the nodes of the tree and drops it on to a respective native application.
So far we have considered the data transfers using MIME types supported by the native applications. Now we will consider a Java-to-Java transfer of any Java object using a customized MIME type.
Transferring Java Objects Using Drag and DropIn this application, we'll demonstrate how to drag a user-defined Java object from a drag-enabled Java application to another drop-aware Java application. The TimeDrag application displays the current time, as well as a clock icon, to the user (see Figure 2).
import java.awt.*;
import java.awt.event.*;
//
******************************************************************
// Class implemented :
TimeDrag
// Derived
from : Frame
//
Implements :
None
//
Description : The TimeDrag class
defines the user interface
// of
the application.
//
******************************************************************
public
class TimeDrag extends
Fram
{
private TimeControl
sourceTime
private Clock
clock;
public
TimeDrag()
{
// Name the
application as TimeDrag.
super("TimeDrag");
// Instantiate
the Clock object.
clock =
new Clock();
// Create a new
Panel and pass it the Clock object
// to be
transferred.
sourceTime =
new TimeControl(clock);
// Set the
Layout to GridLayout.
this.setLayout(new GridLayout(1, 2, 10,
10));
// Add the
canvas to the Frame.
add(clock.timeCanvas) // Add the
Panel to the Frame.
add(sourceTime);
// Set the
display of the Frame on the screen.
setBounds(0,0,160,120);
this.setResizable(false);
}
public
static void main(String
s[])
{
new
TimeDrag().setVisible(true);
}
// Override the handle
event method of the Frame.
public
boolean handleEvent(Event event)
{
// Check if the
event id is WINDOW_DESTROY;
// exit if it
is.
if
(event.id == Event.WINDOW_DESTROY)
{
System.exit(0);
return true;
}
else
return false; }
}
Figure 2: Displaying the current time and a clock icon.
The user can drag the clock icon to another drop-aware application. The TimeDrop application shown in Listing Six is a drop-aware application and understands the dropped Clock object. After receiving the dropped object, the application displays the current time to the user.
The TimeDrag application, shown in Listing Seven, uses a TimeSelection class that implements the Transferable interface.
The class constructor creates a new data flavor using the following statement:
timeFlavor = new
DataFlavor(Class.forName("Clock"), "Time");
The first parameter to the DataFlavor constructor is a Class object representing our Clock class. It's shown in Listing Eight. The second parameter is the human readable name for the data flavor. The getTransferData method returns the Clock object to the caller.
The TimeDrag application also uses a Panel class called TimeControl, as shown in Listing Nine, that acts as drag source. The TimeControl class implements DragSourceListener and DragGestureListener interfaces. The class constructor receives a Clock object as a parameter. In the dragGestureRecognized event handler, we create the instance of our transferable object (TimeSelection) by sending Clock as an input parameter in the class constructor. We then initiate the drag by calling startDrag method that uses the newly constructed transferable object as a parameter. The Clock class is derived from Thread, and uses a custom Canvas to display the current time to the user.
The TimeDrop application is a drop-aware application that understands a dropped Clock object. The TimeDrop class implements DropTargetListener interface. In the drop event handler, we construct the custom data flavor using the statement:
DataFlavor transferDataFlavor =
new
DataFlavor(Class.forName("Clock"), "Time");
We then retrieve the transferable object, and call getTransferData method on it to retrieve the Clock object:
Transferable t =
e.getTransferable();
Clock clock =
(Clock)t.getTransferData(transferDataFlavor);
After retrieving the Clock object, we call its start method to start the thread. The clock is then added to the frame and displayed to the user (see Figure 3).
Figure 3: The clock icon on display.
JavaSoft has provided a number of interfaces and classes that allow the transfer of data using the clipboard or drag-and-drop features to support data transfers in Java applications. We discussed the use of a number of interfaces and classes, as well as techniques for data transfers using both local and system clipboards. We also covered data transfer using drag and drop between Java-to-Java and native-to-Java applications, and the use of various pre-defined data flavors. The support for data transfer between two applications is an important part of today's application development.
The example files described in this article are available for download.
Dr P.G. Sarang is president and CEO of ABCOM Information Systems Pvt. Ltd. ABCOM is a consulting firm that specializes in Internet programming using Java, JavaScript, and ISAPI, and Windows-based application development using Visual Basic, Visual C++, Microsoft Access, and Microsoft SQL Server
Kamal Shah is in his final year of studying computer engineering. He is a very good Java programmer and possesses interest in distributed computing using Java/CORBA. He plans to continue his studies and obtain a Master's degree in Computer Engineering. He can be reached at kamal@abcom.com.
Begin Listing One - datatransfer.javaimport java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import java.awt.dnd.*
import
java.awt.datatransfer.*;
//
******************************************************************
// Class implemented :
datatransfer
// Derived
from : JFrame
//
Implements :
ActionListener, ClipboardOwner
//
******************************************************************
public
class datatransfer extends JFrame
implements ActionListener,ClipboardOwner
{
private clipboard
clipboard;
private ListCopy
lcopy;
private JMenuItem
cut,copy,paste,exit;
public
datatransfer()
{
super("Data Transfer ");
JComponent jcomp =
(JComponent)getContentPane();
// Set the
Layout of the JFrame to BorderLayout.
jcomp.setLayout(
new BorderLayout());
// Create a new
instance of the ListCopy class.
lcopy =
new ListCopy();
// Set the
first item as the selected item.
lcopy.setSelectedIndex(0);
// Create a new
menubar to which two menus,
// file and
edit, are added.
JMenuBar menubar =
new JMenuBar();
JMenu edit =
new JMenu("Edit");
JMenu file =
new JMenu("File");
// Create
MenuItem instances.
copy =
new JMenuItem("Copy");
paste =
new JMenuItem("Paste");
cut =
new JMenuItem("Cut");
exit =
new JMenuItem("Exit");
// Add action
listener to all the menu items.
cut.addActionListener(
this);
copy.addActionListener(
this);
paste.addActionListener(
this);
exit.addActionListener(
this);
// Add cut,
copy and paste menu items to the edit menu.
edit.add(cut);
edit.add(copy);
edit.add(paste);
// Add exit
menu item to the file menu.
file.add(exit);
// Add the
menus file and edit to the menubar.
menubar.add(file);
menubar.add(edit);
// Add the
menubar and the JList to the JFrame.
jcomp.add("North",menubar); &n bsp;
jcomp.add("Center",lcopy); &nb sp;
// Obtain a
reference to the System clipboard.
clipboard =
getToolkit().getSystemClipboard();
// Set the size
of the JFrame on the screen.
Dimension dimension =
getToolkit().getScreenSize();
setBounds(0,0,dimension.width/2,dimension.heigh t);
}
public
static void main(String
s[])
{
new
datatransfer().setVisible(true);
}
s method is invoked
when one of the menu items is clicked.
public
void actionPerformed(ActionEvent e)
{
// Check if the
cut menu item is clicked.
if
(e.getSource() == cut)
{
//
Check if an item is selected on the JList.
//
If nothing is selected, there is nothing to cut.
if
(!lcopy.isSelectionEmpty())
{
// Get the index of the selected item.
int index = lcopy.getSelectedIndex();
// 1. Get selected value as a string.
// 2. Convert string to a transferable object
using
/ & nbsp;
the StringSelection class.
// 3. Copy the transferable object to the clipboard.
clipboard.setContents(
new
StringSelection((String)lcopy.getSelectedValue()),
this);
// Remove the selected value from the JList, which
is
//
equivalent to the cut operation.
String
temp[] = new
String[lcopy.stringArray.length];
for (int i = 0; i <
lcopy.stringArray.length; ++i)
{
if (index != i)
;temp[i]
=
lcopy.stringArray[i]; & nbsp;
}
lcopy.setListData(temp) ;
lcopy.stringArray
= temp;
lcopy.setSelectedIndex( 0);
}
}
// Check if the
copy menu item is clicked.
if
(e.getSource() == copy)
{
//
Check to see if an item is selected on the JList.
//
If nothing is selected, there's nothing to cut.
if
(!lcopy.isSelectionEmpty())
{
clipboard.setContents(
new
StringSelection((String)lcopy.getSelectedValue()),
this);
} &nbs p;
}
// Check if the
paste menu item is clicked.
if
(e.getSource() == paste)
{
try
{
// Get the contents of the clipboard as transferable
object
// only if the contents of the clipboard are of the string
// format we can typecast as a StringSelection object.
StringSelection
s =
(StringSelection)Clipboard.getContents(
this);
// Gets the string being transferred.
String str
=
(String)s.getTransferData(DataFlavor.stringFlavor);
// Add the string to the JList.
lcopy.addToJList(str);& nbsp;
}
catch (Exception err)
{
System.out.println(
"Contents
of the clipboard are not in the String Format");
} &nbs p;
}
// Check to see
if the exit menu item is clicked.
if
(e.getSource() == exit)
{
System.exit(0);
}
}
public
void lostOwnership(Clipboard c, Transferable t)
{
}
// Override the
processWindowEvent of the JFrame.
protected
void processWindowEvent(WindowEvent e)
{
super.processWindowEvent(e);
// Check for
event ID, if it is WINDOW_CLOSING then exit.
if
(e.getID() == WindowEvent.WINDOW_CLOSING)
System.exit(0); &n bsp;
}
}
End Listing One
Begin Listing Two -
ListCopy.java
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import java.awt.dnd.*;
import
java.awt.datatransfer.*;
import java.io.*;
//
******************************************************************
// Class implemented :
ListCopy
// Derived
from : JFrame
//
Implements :
DragSourceListener, DragGestureListener,
// DropTargetListener
//
******************************************************************
public
class ListCopy extends
JList
implements
DragSourceListener, DragGestureListener,
  ; DropTargetListener
{
//
Initialize the string array.
static String[]
stringArray = {"Mumbai","Fort Collins","Lexington",
"Denton","Binghamton","College
Station","Amherst","Notre Dame",
"AMES","Berlin","London","Paris"};
public
ListCopy()
{
// Initialize
the JList.
super(stringArray);
// Obtain a
default drag source.
DragSource ds =
DragSource.getDefaultDragSource();
// Create a
default drag gesture recognizer, which is the
//
MouseDragGestureRecognizer.
// Associate
the recognizer with the JList and a
//
DragGestureListener.
ds.createDefaultDragGestureRecognizer(
this, DnDConstants.ACTION_COPY,
this);
this.setDropTarget(new DropTarget(
this,this));
}
//------------------------------------------------------
// This is invoked when the
user drags on the JList.
public
void dragGestureRecognized(DragGestureEvent e)
{
// Check for a
selected value.
if
(getSelectedValue() != null)
{
//
Create the transferable object for dragging.
ListDrag stringTransfer
=
new ListDrag((String)getSelectedValue());
//
Initiate drag.
e.startDrag(
null, stringTransfer,
this);
}
}
//------------------------------------------------------
// The five methods below
are implemented for the drag source listener.
// This method is called
when the drop operation is completed.
public
void dragDropEnd(DragSourceDropEvent e)
{
}
// This method is called
when the drag cursor enters
// a potential drop target.
public
void dragEnter(DragSourceDragEvent e)
{
}
// This method is called
when the drag cursor leaves a drop target,
// or when a drop occurs on
a drop target.
public
void dragExit(DragSourceEvent e)
{
}
// This method is called
when the drag cursor is on a drop target.
public
void dragOver(DragSourceDragEvent e)
{
}
public
void dropActionChanged(DragSourceDragEvent e)
{
}
//------------------------------------------------------
//The methods below are
implemented for Drop Target Listener.
// This method is called
when the drag cursor is on the drop target.
public
void dragEnter(DropTargetDragEvent e)
{
}
// This method is called
when the drag cursor stays
// on the drop target.
public
void dragOver(DropTargetDragEvent e)
{
}
// This method is called
when the drag cursor leaves the
// drop target, or when a
drop occurs.
public
void dragExit(DropTargetEvent e)
{
}
public
void dragScroll(DropTargetDragEvent e)
{
}
public
void dropActionChanged(DropTargetDragEvent e)
{
}
// Called when a drop
occurs.
public
void drop(DropTargetDropEvent e)
{
// We need a
DropTargetContext to tell the DragSourceListener
// when the Drop
is complete.
DropTargetContext targetContext =
e.getDropTargetContext();
// Check if the
action associated with the particular
// drag and drop
operation is ACTION_COPY.
if
((e.getSourceActions() & DnDConstants.ACTION_COPY) != 0)
e.acceptDrop(DnDConstants.ACTION_COPY);
else
{
e.rejectDrop();
return;
}
// Get the data
flavors associated with the current drag and drop
// operation.
DataFlavor[] dataFlavors =
e.getCurrentDataFlavors();
DataFlavor transferDataFlavor =
null;
// Checks if
any of the data flavors associated with the current
// drag and
drop operation is of plainTextFlavor.
for
(int i = 0; i < dataFlavors.length;
i++)
{
if (DataFlavor.plainTextFlavor.equals(dataFlavors[i]))
{ &nbs p;
transferDataFlavor
= dataFlavors[i];
break;
}
}
if
(transferDataFlavor != null)
{
//
Get the transferable object associated with the current
//
drag and drop operation.
Transferable
t = e.getTransferable();
InputStream is =
null;
try
{
// Get the data being transferred. This data is
of
//
plainTextFlavor and it returns an InputStream Object.
is =
(InputStream)t.getTransferData(transferDataFlavor);
if (is != null)
{
// Create a new instance of a string writer to write
the
//
transferred data in.
StringWrite r
writer = new StringWriter();
byte[] buffer = new
byte[256];
// Read from InputStream and write to the StringWriter.
while (true)
{
  ;
int c = is.read(buffer,0,buffer.length);
  ;
if (c != -1)
  ; writer.write(
new String(buffer,0,c));
  ;
else
  ;
break;
}
// Add a string to the JList
addToJList( writer.toString().trim());
}
}
catch (Exception ioe)
{
System.err.println(ioe. getMessage());
return;
}
}
targetContext.dropComplete(
true);
}
// Add a string to the
JList.
public
void addToJList(String string)
{
String[] str =
new String[stringArray.length+1];
int
i;
for (i
= 0; i < stringArray.length; ++i)
{
str[i] =
stringArray[i];
}
str[i] = string;
stringArray =
null;
stringArray = str;
// Set the data
of the list by adding the new item.
this.setListData(str);
// Set the item
selected as the last item.
this.setSelectedIndex(str.length-1);
}
}
End Listing TwoBegin Listing Three - FileDrop.java
import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
import java.awt.dnd.*;
import
java.awt.datatransfer.*;
import java.io.*;
// *****************************************************************
// Class implemented :
FileDrop
// Derived
from : JFrame
// Implements :
DropTargetListener
// *****************************************************************
public
class FileDrop
extends JFrame
implements DropTargetListener
{
JTextArea fileDisplay;
public
FileDrop()
{
// Name the
JFrame as GIFDrop.
super("FileDrop");
// Get the
JFrame's content pane.
JComponent jcomp =
(JComponent)getContentPane();
// Sets the
layout to BorderLayout.
jcomp.setLayout(
new BorderLayout());
// Instantiate
a new JTextArea, which is to used as the DropTarget.
fileDisplay =
new JTextArea();
// Add the
fileDisplay to the scrollpane.
JScrollPane scrollpane =
new JScrollPane(fileDisplay);
jcomp.add(scrollpane,
BorderLayout.CENTER);
// Set the drop
target to fileDisplay and associate a
//
DropTargetListener with the DropTarget.
DropTarget dropTarget =
new DropTarget(fileDisplay,
this);
// Set the size
of the JFrame on the screen.
Dimension dimension =
getToolkit().getScreenSize();
setBounds(0,0,dimension.width/2,dimension.height);
}
public
static void main(String
s[])
{
new
FileDrop().setVisible(true);
}
// Override the
processWindowEvent of the JFrame.
protected
void processWindowEvent(WindowEvent
e)
{
super.processWindowEvent(e);
// Check for
event ID; if it is WINDOW_CLOSING, then exit.
if
(e.getID() == WindowEvent.WINDOW_CLOSING)
System.exit(0);
}
//-----------------------------------------------------------------
// The following five
methods are implemented for
// the DropTargetListener.
// Called when drag cursor
first enters the drop target.
public
void dragEnter(DropTargetDragEvent e)
{
}
// Called when drag cursor
is on the drop target.
public
void dragOver(DropTargetDragEvent e)
{
}
// Called when drag cursor
leaves the drop target.
public
void dragExit(DropTargetEvent e)
{
}
// Called when a drop
occurs on the drop target.
public
void drop(DropTargetDropEvent e)
{
// Clear the
JTextArea.
fileDisplay.setText(");
// We need a
DropTargetContext to tell the DragSourceListener
// when the drop
is complete.
DropTargetContext
targetContext = e.getDropTargetContext();
// Check if the
action associated with the particular
// drag and drop
operation is ACTION_COPY.
if
((e.getSourceActions() & DnDConstants.ACTION_COPY) != 0)
e.acceptDrop(DnDConstants.ACTION_COPY);
else
{
//
Reject the drop if the Source action is not ACTION_COPY.
e.rejectDrop();
System.out.println("Drop
rejected");
return;
}
try
{
//
Get the transferable object associated with the current
//
drag and drop operation.
Transferable t =
e.getTransferable();
//
Define a new DataFlavor for transferring files.
DataFlavor fileFlavor
= new DataFlavor(
"application/x-java-file-list;class=java.util.List","File");
//
Check if the fileFlavor is supported by the transferable
//
object.
if
(t.isDataFlavorSupported(fileFlavor))
{
// Get the data being transferred. This data is in
the
//
fileFlavor and it returns a java.util.List Object.
java.util.List
list =
(java.util.List)t.getTransferData(fileFlavor);
targetContext.dropComplete(
true);
// Converts the contents of the list to an object array.
Object[] o =
list.toArray();
// Opens the file for reading.
BufferedReader
reader =
new BufferedReader(new
FileReader((File)o[0]));
while (true)
{
// Read one line of text.
String
line = reader.readLine();
if (line != null)
// Append the text to fileDisplay.
fileDisplay.append(line+"\n");
else
break;
}
}
else
targetContext.dropComplete(
false);
}
catch
(Exception fsd)
{
return;
}
}
public
void dragScroll(DropTargetDragEvent e)
{
}
public
void dropActionChanged(DropTargetDragEvent e)
{
}
}
End Listing Three
Begin Listing Four -
GIFDrop.java
import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
import
java.awt.datatransfer.*;
import java.awt.dnd.*;
//
******************************************************************
// Class implemented :
GIFDrop
// Derived
from : JFrame
//
Implements :
None
//
******************************************************************
public
class GIFDrop extends
JFrame
{
private GIFControl
gifControl;
GIFDrop()
{
// Name the
JFrame as GIFDrop.
super("GIFDrop");
// Obtain the
JFrame's content Pane.
JComponent jcomp =
(JComponent)getContentPane();
// Instantiate
GIFControl.
gifControl =
new GIFControl();
// Set Layout
to BorderLayout.
jcomp.setLayout(
new BorderLayout());
// Add the
Panel.
jcomp.add(gifControl,BorderLayout.CENTER);
// Set the size
of the JFrame on the screen.
Dimension dimension =
getToolkit().getScreenSize();
setBounds(0, 0, dimension.width/2,
dimension.height/2);
}
// Override the
processWindowEvent of the JFrame.
protected
void processWindowEvent(WindowEvent e)
{
super.processWindowEvent(e);
if
(e.getID() == WindowEvent.WINDOW_CLOSING)
System.exit(0);
}
public
static void main(String
s[])
{
new
GIFDrop().setVisible(true);
}
}
//
******************************************************************
// Class implemented :
GIFControl
// Derived
from : JPanel
//
Implements :
DropTargetListener
//
******************************************************************
class GIFControl
extends JPanel
implements DropTargetListener
{
Image image =
null;
public
GIFControl()
{
super();
// It sets the
drop target to the JPanel and associates a
//
DropTargetListener with the DropTarget.
this.setDropTarget(new DropTarget(
this,this));
}
//-----------------------------------------------------------------
// The following five
methods are implemented for
// the DropTargetListener.
// Called when drag cursor
first enters the drop target.
public
void dragEnter(DropTargetDragEvent e)
{
}
// Called when drag cursor
is on the drop target.
public
void dragOver(DropTargetDragEvent e)
{
}
// Called when drag cursor
leaves the drop target, or a
// drop occurs on the drop
target.
public
void dragExit(DropTargetEvent e)
{
}
// Called when a drop
occurs on the drop target.
public
void drop(DropTargetDropEvent e)
{
// We need a
DropTargetContext to tell the DragSourceListener
// when the drop
is complete.
DropTargetContext targetContext =
e.getDropTargetContext();
// Check if the
action associated with the particular
// drag and drop
operation is ACTION_COPY.
if
((e.getSourceActions() & DnDConstants.ACTION_COPY) != 0)
e.acceptDrop(DnDConstants.ACTION_COPY);
else
{
//
Reject the drop if the Source action is not ACTION_COPY.
e.rejectDrop();
System.out.println("Drop
rejected");
return;
}
try
{
//
Get the transferable object associated with the current
//
drag and drop operation.
Transferable
t = e.getTransferable();
//
Get the DataFlavors asociated with the transferable object.
DataFlavor[] df =
t.getTransferDataFlavors();
//
Define a new DataFlavor for transferring files.
DataFlavor gifFlavor =
new DataFlavor(
"application/x-java-file-list;class=java.util.List","File");
//
Check if the gifFlavor is supported by the transferable object.
if
(t.isDataFlavorSupported(gifFlavor))
{
// Get the data being transferred. This data is of
gifFlavor
// and
returns a java.util.List object.
java.util.List
list =
(java.util.List)t.getTransferData(gifFlavor);
// Convert the list to an Object array.
Object[] obj
= list.toArray();
// Get the image.
image =
getToolkit().getImage(obj[0].toString());
repaint();
}
targetContext.dropComplete(
true);
}
catch
(Exception fsd)
{
targetContext.dropComplete(
true);
return;
}
}
public
void dragScroll(DropTargetDragEvent e)
{
}
public
void dropActionChanged(DropTargetDragEvent e)
{
}
// Clip the old image and
paste the new image.
public
void paint(Graphics g)
{
if
(image != null)
{
Rectangle rect =
new Rectangle();
this.computeVisibleRect(rect);
g.clearRect(rect.x,
rect.y, rect.width, rect.height);
g.drawImage(image,50,50,
this);
}
}
}
End Listing Four
Begin Listing Five -
FileDrag.java
import javax.swing.*;
import java.io.*;
import javax.swing.tree.*;
import java.awt.event.*;
import java.awt.dnd.*;
import
java.awt.datatransfer.*;
import java.awt.*;
import java.util.*;
// ******************************************************************************
// Class implemented :
FileDrag
// Derived
from : JFrame
// Implements :
DragSourceListener, DragGestureListener
// ******************************************************************************
public
class FileDrag extends
JFrame
implements
DragSourceListener, DragGestureListener
{
JTree tree;
public
FileDrag()
{
// Name the
JFrame as FileDrag.
super("FileDrag");
// This is the
root node of the JTree.
DefaultMutableTreeNode root =
new DefaultMutableTreeNode("Root",
true);
// Constructs
three new File Objects which are to be dragged.
File word =
new File("word.doc");
File Excel =
new File("Excel.xls");
File text =
new File("text.txt");
// Construct
three nodes for the JTree,
// and pass a
file to each node.
DefaultMutableTreeNode wordnode
=
new DefaultMutableTreeNode(word);
DefaultMutableTreeNode Excelnode
=
new DefaultMutableTreeNode(Excel);
DefaultMutableTreeNode textnode
=
new DefaultMutableTreeNode(text);
try
{
//
Write to the three files.
new FileOutputStream(word).write(
new String("ABCOM Information
Systems").getBytes());
new FileOutputStream(Excel).write(
new String("ABCOM Information
Systems").getBytes());
new FileOutputStream(text).write(
new String("ABCOM Information
Systems").getBytes());
}
catch
(Exception ex)
{
ex.printStackTrace();
}
// Add the
three nodes to the root.
root.add(wordnode);
root.add(Excelnode);
root.add(textnode);
// Construct a
new JTree.
tree =
new JTree(root);
// Add the
JTree to the scrollpane.
JScrollPane scroll =
new JScrollPane(tree);
// Set the
content pane of the JFrame.
this.setContentPane(scroll);
// Create a
default drag source.
DragSource ds =
DragSource.getDefaultDragSource();
// Create a
default drag gesture recognizer which is the
//
MouseDragGestureRecognizer; it associates the recognizer with
// the JTree and
a DragGestureListener.
ds.createDefaultDragGestureRecognizer(
tree,
DnDConstants.ACTION_COPY, this);
// Set the size
of display on the screen.
Dimension dimension =
getToolkit().getScreenSize();
setBounds(0,0,dimension.width/3,dimension.height/4);
}
// Override the
processWindowEvent of the JFrame.
protected
void processWindowEvent(WindowEvent e)
{
super.processWindowEvent(e);
// Check for
event ID, if it is WINDOW_CLOSING, then exit.
if
(e.getID() == WindowEvent.WINDOW_CLOSING)
System.exit(0);
}
public
static void
main(String[] str)
{
new
FileDrag().setVisible(true);
}
//-------------------------------------------------------
// This method is invoked
when the user drags on the JTree.
public
void dragGestureRecognized(DragGestureEvent
e)
{
// Get the path
of the selected node on the JTree.
TreePath path =
tree.getSelectionPath();
// Get the last
element in the path asd a node.
DefaultMutableTreeNode selection =
(DefaultMutableTreeNode)path.getLastPathComponent();
// Get the user
object associated with the node, and create
// a
transferable object for dragging.
DragClass fileTransfer =
new DragClass((File)selection.getUserObject());
// Initiate the
drag.
e.startDrag(
null, fileTransfer,
this);
}
//------------------------------------------------------
// The five methods below
are implemented
// for the drag source
listener.
public
void dragDropEnd (DragSourceDropEvent e)
{
}
// This method is called
when the drag cursor enters
// a potential drop target.
public
void dragEnter(DragSourceDragEvent e)
{
}
// This method is called
when the drag cursor leaves a drop target,
// or when a drop occurs on
a drop target.
public
void dragExit(DragSourceEvent e)
{
}
// This method is called
when the drag cursor is on a drop target.
public
void dragOver(DragSourceDragEvent e)
{
}
public
void dropActionChanged(DragSourceDragEvent
e)
{
}
}
// *****************************************************************
// Class implemented :
DragClass
// Derived
from : None
// Implements :
Transferable
// *****************************************************************
class DragClass
implements Transferable
{
File file;
// Define a new data flavor
to transfer files.
static DataFlavor
fileFlavor = new DataFlavor(
"application/x-java-file-list;class=java.util.List","File");
// Create a data flavor
array.
private
static DataFlavor[] FlavorArray
= {fileFlavor};
DragClass(File file)
{
this.file = file;
}
public Object
getTransferData(DataFlavor tdf)
throws
UnsupportedFlavorException, IOException
{
// Check to see
if the DataFlavor being asked for is supported
// by the
current transferable object.
if
(isDataFlavorSupported(tdf))
{
//
Create a new vector object.
Vector vector =
new Vector();
//
Add the file element to the vector.
vector.addElement(file);
//
Return the vector.
return vector;
}
else
throw new
UnsupportedFlavorException(tdf);
}
public DataFlavor[]
getTransferDataFlavors()
{
// Return the
FlavorArray.
return
FlavorArray;
}
public
boolean isDataFlavorSupported(DataFlavor sdf)
{
// Check to see
if the file flavor is supported.
for
(int i = 0; i < FlavorArray.length;
i++)
if (FlavorArray[i].equals(sdf))
return
true;
return
false;
}
}
End Listing Five
Begin Listing Six -
TimeDrop.java
import java.awt.*;
import java.awt.dnd.*;
import
java.awt.datatransfer.*;
import Clock;
//
******************************************************************
// Class implemented :
TimeDrop
// Derived
from : Frame
//
Implements :
DropTargetListener
//
******************************************************************
public
class TimeDrop extends
Frame implements DropTargetListener
{
TimeDrop()
{
// Set the name
of the frame.
super("TimeDrop");
this.setDropTarget(new DropTarget(
this,this));
// Set the
display on the screen.
Dimension dimension =
getToolkit().getScreenSize();
setBounds(0,0,dimension.width/4,dimension.height/8);
}
public
static void main(String
s[])
{
new
TimeDrop().setVisible(true);
}
public
boolean handleEvent(Event event)
{
// Check if the
event id is WINDOW_DESTROY. If it is, then exit.
if
(event.id == Event.WINDOW_DESTROY)
{
System.exit(0);
return true;
}
else
return false;
}
// Called when a drop
occurs on the drop target.
public
void drop(DropTargetDropEvent e)
{
// We need a
DropTargetContext to tell the DragSourceListener
// when the drop
is complete.
DropTargetContext targetContext =
e.getDropTargetContext();
// Check if the
action associated with the particular
// drag and drop
operation is ACTION_COPY.
if
((e.getSourceActions() & DnDConstants.ACTION_COPY) != 0)
e.acceptDrop(DnDConstants.ACTION_COPY);
else
{
//
Reject the drop if the Source action is not ACTION_COPY.
e.rejectDrop();
System.out.println("Drop
rejected");
return;
}
try
{
//
DataFlavor[] dataFlavors = e.getCurrentDataFlavors();
//
Define a new DataFlavor for transferring the clock object.
DataFlavor
transferDataFlavor =
new DataFlavor(Class.forName("Clock"), "Time");
//
Get the transferable object associated with the current
//
drag and drop operation.
Transferable
t = e.getTransferable();
//
Get the data being transferred; this data is of clockFlavor
//
and returns a clock object.
Clock clock = (Clock)
t.getTransferData(transferDataFlavor);
targetContext.dropComplete(
true);
//
Start the clock thread.
clock.start();
//
Get the canvas and add it to the Panel.
add(clock.timeCanvas,BorderLayout.CENTER);
doLayout();
invalidate();
repaint();
}
catch
(Exception fsd)
{
return;
}
}
// Called when drag cursor
first enters the drop target.
public
void dragEnter(DropTargetDragEvent e)
{
}
// Called when drag cursor
is on the drop target.
public
void dragOver(DropTargetDragEvent e)
{
}
// Called when drag cursor
leaves the drop target, or a
// drop occurs on the drop
target.
public
void dragExit(DropTargetEvent e)
{
}
public
void dragScroll(DropTargetDragEvent e)
{
}
public
void dropActionChanged(DropTargetDragEvent e)
{
}
}
End Listing Six
Begin Listing Seven -
TimeSelection.java
import java.awt.*;
import java.awt.dnd.*;
import
java.awt.datatransfer.*;
import Clock;
//
******************************************************************
// Class implemented :
TimeDrop
// Derived
from : Frame
//
Implements :
DropTargetListener
//
******************************************************************
public
class TimeDrop extends
Frame implements DropTargetListener
{
TimeDrop()
{
// Set the name
of the frame.
super("TimeDrop");
this.setDropTarget(new DropTarget(
this,this));
// Sets the
display on the screen.
Dimension dimension =
getToolkit().getScreenSize();
setBounds(0,0,dimension.width/4,dimension.height/8);
}
public
static void main(String
s[])
{
new
TimeDrop().setVisible(true);
}
public
boolean handleEvent(Event event)
{
// Check if the
event id is WINDOW_DESTROY; if it is, then exit.
if
(event.id == Event.WINDOW_DESTROY)
{
System.exit(0);
return true;
}
else
return false;
}
// Called when a drop
occurs on the drop target.
public
void drop(DropTargetDropEvent e)
{
// We need a
DropTargetContext to tell the DragSourceListener
// when the drop
is complete.
DropTargetContext targetContext =
e.getDropTargetContext();
// Check to see
if the action associated with the particular
// drag and
drop operation is ACTION_COPY.
if
((e.getSourceActions() & DnDConstants.ACTION_COPY) != 0)
e.acceptDrop(DnDConstants.ACTION_COPY);
else
{
//
Reject the drop if the Source action is not ACTION_COPY.
e.rejectDrop();
System.out.println("Drop
rejected");
return;
}
try
{
//
DataFlavor[] dataFlavors = e.getCurrentDataFlavors();
//
Define a new DataFlavor for transferring the clock object.
DataFlavor
transferDataFlavor =
new DataFlavor(Class.forName("Clock"), "Time");
//
Get the transferable object associated with the current
//
drag and drop operation.
Transferable
t = e.getTransferable();
//
Gets the data being transferred; this data is in the
//
clockFlavor and it returns a clock object
Clock clock =
(Clock)t.getTransferData(transferDataFlavor);
targetContext.dropComplete(
true);
//
start the clock thread.
clock.start();
//
Obtain the canvas and add it to the Panel.
add(clock.timeCanvas,BorderLayout.CENTER);
doLayout();
invalidate();
repaint();
}
catch
(Exception fsd)
{
return;
}
}
// Called when drag cursor
first enters the Drop Target.
public
void dragEnter(DropTargetDragEvent e)
{
}
// Called when drag cursor
is on the Drop Target.
public
void dragOver(DropTargetDragEvent e)
{
}
// Called when drag cursor
leaves the Drop Target,
// or a drop occurs on the
drop target.
public
void dragExit(DropTargetEvent e)
{
}
public
void dragScroll(DropTargetDragEvent e)
{
}
public
void dropActionChanged(DropTargetDragEvent e)
{
}
}
End Listing Seven
Begin Listing Eight -
Clock.java
import java.awt.*;
import java.io.*;
import java.util.*;
import java.text.DateFormat;
//
******************************************************************
// Class implemented : Clock
// Derived
from : Thread
//
Implements :
Serializable
//
******************************************************************
public
class Clock extends
Thread implements Serializable
{
public TimeCanvas
timeCanvas;
public Clock()
{
// Create a new
Canvas object.
timeCanvas =
new TimeCanvas();
// Start the
current thread.
this.start();
}
public
void run()
{
try
{
while (true)
{
// The thread sleeps for 1 second.
this.sleep(1000);
// It updates the time on the Canvas.
timeCanvas.repaint();
}
}
catch
(Exception e)
{
System.out.println("Error :
"+e.getMessage());
}
}
}
//
******************************************************************
// Class implemented :
TimeCanvas
// Derived
from : Canvas
//
Implements :
None
//
******************************************************************
class TimeCanvas
extends Canvas
{
public
TimeCanvas()
{
// Sets the
size of the canvas.
setBounds(0,0,100,25);
}
public
void paint(Graphics g)
{
Rectangle boundsRect =
this.getBounds();
FontMetrics tm =
this.getFontMetrics(
this.getFont());
String strDisplay =
this.getSystemTime();
int
strWidth = tm.stringWidth(strDisplay);
g.drawString(
this.getSystemTime(),
boundsRect.width/2
- strWidth/2,
boundsRect.height/2);
}
// Get the time from the
system.
private String
getSystemTime()
{
// Get the
current time in milliseconds.
long
time = System.currentTimeMillis();
// Create a
date object for the current time.
Date date =
new Date(time);
// Get the time
instance of DateFormat.
DateFormat dateFormat =
DateFormat.getTimeInstance();
// Get the
default time zone.
TimeZone timeZone =
TimeZone.getDefault();
// Set the time
zone of the date format object.
dateFormat.setTimeZone(timeZone);
// Format the
date and returns it as a string.
return
dateFormat.format(date);
}
}
End Listing Eight
Begin Listing Nine -
TimeControl.java
import java.awt.*;
import java.awt.dnd.*;
import
java.awt.datatransfer.*;
//
******************************************************************
// Class implemented :
TimeControl
// Derived
from : Panel
//
Implements :
DragSourceListener, DragGestureListener
//
******************************************************************
public
class TimeControl
extends Panel
implements
DragSourceListener, DragGestureListener
{
private
java.awt.Image image = null;
public Clock
clock;
public
TimeControl(Clock clock)
{
super();
// Create a
default drag source.
DragSource ds =
DragSource.getDefaultDragSource();
// Create a
default drag gesture recognizer which is the
//
MouseDragGestureRecognizer it associates the recognizer
// with the
Panel and a DragGestureListener.
ds.createDefaultDragGestureRecognizer(
this, DnDConstants.ACTION_COPY,
this);
this.clock = clock;
// Get the
image.
image =
Toolkit.getDefaultToolkit().getImage("TimeIcon.gif");
// Called to
add the image to the Panel
//
repaint();
}
public
void paint(Graphics g)
{
if
(image != null)
{
//
Draws the image on the Panel.
int width = image.getWidth(this);
int height = image.getHeight(
this);
Rectangle boundsRect =
this.getBounds();
g.drawImage(image,
boundsRect.width/2
- width/2,
boundsRect.height/2
- height/2,
width,
height, this);
}
}
//--------------------------------------------------------
// Is invoked when the user
drags on the Panel.
public
void dragGestureRecognized(DragGestureEvent e)
{
// Create a
transferable object.
TimeSelection is =
new TimeSelection(clock);
// Initiate the
drag passing it the transferable object.
e.startDrag(
null, is,
this);
}
//------------------------------------------------------
// The five methods below
are implemented for the
// drag source listener.
public
void dragDropEnd(DragSourceDropEvent e)
{
}
// This method is called
when the drag cursor enters
// a potential drop target.
public
void dragEnter(DragSourceDragEvent e)
{
}
// This method is called
when the drag cursor leaves a drop target,
// or when a drop occurs on
a drop target.
public
void dragExit(DragSourceEvent e)
{
}
// This method is called
when the drag cursor stays on the drop target.
public
void dragOver(DragSourceDragEvent e)
{
}
public
void
dropActionChanged(DragSourceDragEvent e)
{
}
}
End Listing Nine
|