6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 26 package javafx.embed.swing; 27 28 import com.sun.javafx.embed.EmbeddedSceneDSInterface; 29 import com.sun.javafx.tk.Toolkit; 30 import java.awt.datatransfer.DataFlavor; 31 import java.awt.datatransfer.Transferable; 32 import java.awt.dnd.DropTargetDragEvent; 33 import java.awt.dnd.DropTargetDropEvent; 34 import java.util.Arrays; 35 import java.util.Collections; 36 import java.util.Map; 37 import java.util.HashMap; 38 import java.util.Set; 39 import javafx.scene.input.TransferMode; 40 import java.io.UnsupportedEncodingException; 41 import javafx.scene.input.Clipboard; 42 import javafx.scene.input.DataFormat; 43 44 /** 45 * A Transferable implementation backed by a Map. 46 * The data can be populated either from AWT Transferable 47 * or from FX Clipboard. 48 */ 49 class CachingTransferable implements Transferable { 50 51 @Override 52 public Object getTransferData(final DataFlavor flavor) throws UnsupportedEncodingException 53 { 54 String mimeType = DataFlavorUtils.getFxMimeType(flavor); 55 return DataFlavorUtils.adjustFxData( 56 flavor, getData(mimeType)); 57 } 58 59 @Override 60 public DataFlavor[] getTransferDataFlavors() { 61 final String mimeTypes[] = getMimeTypes(); 62 return DataFlavorUtils.getDataFlavors(mimeTypes); 63 } 64 65 @Override 66 public boolean isDataFlavorSupported(final DataFlavor flavor) { 67 return isMimeTypeAvailable( 68 DataFlavorUtils.getFxMimeType(flavor)); 69 } 70 71 private Map<String, Object> mimeType2Data = Collections.EMPTY_MAP; 72 73 void updateData(Transferable t, boolean fetchData) { 74 final Map<String, DataFlavor> mimeType2DataFlavor = 75 DataFlavorUtils.adjustSwingDataFlavors( 76 t.getTransferDataFlavors()); 77 78 // If we keep reference to source Transferable in SwingDragSource and 79 // call Transferable#getTransferData() on it from 80 // SwingDragSource#getData() we may run into 81 // "java.awt.dnd.InvalidDnDOperationException" issue as 82 // SwingDragSource#getData() is called from FX user code and from 83 // QuantumClipboard#getContent() (sik!). These calls usually take 84 // place in the context of 85 // EmbeddedSceneDTInterface#handleDragDrop() method as the 86 // normal handling of DnD. 87 // Instead of keeping reference to source Transferable we just read 88 // all its data while in the context safe for calling 89 // Transferable#getTransferData(). 90 // 91 // This observation is true for standard AWT Transferable-s. 92 // Things may be totally broken for custom Transferable-s though. 93 94 // For performance reasons, the DRAG_ENTERED and DRAG_OVER event 95 // handlers pass fetchData == false so as to update the set of 96 // available MIME types only. The DRAG_DROPPED handler passes 97 // fetchData == true which also fetches all the data. 98 // NOTE: Due to JDK-8028585 this code won't be able to fetch data 99 // when invoked from handlers other than DROPPED in any case. 100 101 try { 102 mimeType2Data = DataFlavorUtils.readAllData(t, mimeType2DataFlavor, 103 fetchData); 104 } catch (Exception e) { 105 mimeType2Data = Collections.EMPTY_MAP; 106 } 107 } 108 109 void updateData(Clipboard cb, boolean fetchData) { 110 mimeType2Data = new HashMap<>(); 111 for (DataFormat f : cb.getContentTypes()) { 112 mimeType2Data.put(DataFlavorUtils.getMimeType(f), 113 fetchData ? cb.getContent(f) : null); 114 } 115 } 116 117 public Object getData(final String mimeType) { 118 return mimeType2Data.get(mimeType); 119 } 120 121 public String[] getMimeTypes() { 122 return mimeType2Data.keySet().toArray(new String[0]); 123 } 124 125 public boolean isMimeTypeAvailable(final String mimeType) { 126 return Arrays.asList(getMimeTypes()).contains(mimeType); 127 } 128 } | 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 26 package com.sun.javafx.embed.swing; 27 28 import com.sun.javafx.embed.EmbeddedSceneDSInterface; 29 import com.sun.javafx.tk.Toolkit; 30 import java.awt.datatransfer.DataFlavor; 31 import java.awt.datatransfer.Transferable; 32 import java.awt.dnd.DropTargetDragEvent; 33 import java.awt.dnd.DropTargetDropEvent; 34 import java.util.Arrays; 35 import java.util.Collections; 36 import java.util.Map; 37 import java.util.HashMap; 38 import java.util.Set; 39 import javafx.scene.input.TransferMode; 40 import java.io.UnsupportedEncodingException; 41 import javafx.scene.input.Clipboard; 42 import javafx.scene.input.DataFormat; 43 44 /** 45 * A Transferable implementation backed by a Map. 46 * The data can be populated either from AWT Transferable 47 * or from FX Clipboard. 48 */ 49 public class CachingTransferable implements Transferable { 50 51 @Override 52 public Object getTransferData(final DataFlavor flavor) throws UnsupportedEncodingException 53 { 54 String mimeType = DataFlavorUtils.getFxMimeType(flavor); 55 return DataFlavorUtils.adjustFxData( 56 flavor, getData(mimeType)); 57 } 58 59 @Override 60 public DataFlavor[] getTransferDataFlavors() { 61 final String mimeTypes[] = getMimeTypes(); 62 return DataFlavorUtils.getDataFlavors(mimeTypes); 63 } 64 65 @Override 66 public boolean isDataFlavorSupported(final DataFlavor flavor) { 67 return isMimeTypeAvailable( 68 DataFlavorUtils.getFxMimeType(flavor)); 69 } 70 71 private Map<String, Object> mimeType2Data = Collections.EMPTY_MAP; 72 73 public void updateData(Transferable t, boolean fetchData) { 74 final Map<String, DataFlavor> mimeType2DataFlavor = 75 DataFlavorUtils.adjustSwingDataFlavors( 76 t.getTransferDataFlavors()); 77 78 // If we keep reference to source Transferable in SwingDragSource and 79 // call Transferable#getTransferData() on it from 80 // SwingDragSource#getData() we may run into 81 // "java.awt.dnd.InvalidDnDOperationException" issue as 82 // SwingDragSource#getData() is called from FX user code and from 83 // QuantumClipboard#getContent() (sik!). These calls usually take 84 // place in the context of 85 // EmbeddedSceneDTInterface#handleDragDrop() method as the 86 // normal handling of DnD. 87 // Instead of keeping reference to source Transferable we just read 88 // all its data while in the context safe for calling 89 // Transferable#getTransferData(). 90 // 91 // This observation is true for standard AWT Transferable-s. 92 // Things may be totally broken for custom Transferable-s though. 93 94 // For performance reasons, the DRAG_ENTERED and DRAG_OVER event 95 // handlers pass fetchData == false so as to update the set of 96 // available MIME types only. The DRAG_DROPPED handler passes 97 // fetchData == true which also fetches all the data. 98 // NOTE: Due to JDK-8028585 this code won't be able to fetch data 99 // when invoked from handlers other than DROPPED in any case. 100 101 try { 102 mimeType2Data = DataFlavorUtils.readAllData(t, mimeType2DataFlavor, 103 fetchData); 104 } catch (Exception e) { 105 mimeType2Data = Collections.EMPTY_MAP; 106 } 107 } 108 109 public void updateData(Clipboard cb, boolean fetchData) { 110 mimeType2Data = new HashMap<>(); 111 for (DataFormat f : cb.getContentTypes()) { 112 mimeType2Data.put(DataFlavorUtils.getMimeType(f), 113 fetchData ? cb.getContent(f) : null); 114 } 115 } 116 117 public Object getData(final String mimeType) { 118 return mimeType2Data.get(mimeType); 119 } 120 121 public String[] getMimeTypes() { 122 return mimeType2Data.keySet().toArray(new String[0]); 123 } 124 125 public boolean isMimeTypeAvailable(final String mimeType) { 126 return Arrays.asList(getMimeTypes()).contains(mimeType); 127 } 128 } |