Mercurial > projects > dwt-mac
comparison dwt/dnd/Clipboard.d @ 0:380af2bdd8e5
Upload of whole dwt tree
author | Jacob Carlborg <doob@me.com> <jacob.carlborg@gmail.com> |
---|---|
date | Sat, 09 Aug 2008 17:00:02 +0200 |
parents | |
children | 1a8b3cb347e0 |
comparison
equal
deleted
inserted
replaced
-1:000000000000 | 0:380af2bdd8e5 |
---|---|
1 /******************************************************************************* | |
2 * Copyright (c) 2000, 2007 IBM Corporation and others. | |
3 * All rights reserved. This program and the accompanying materials | |
4 * are made available under the terms of the Eclipse Public License v1.0 | |
5 * which accompanies this distribution, and is available at | |
6 * http://www.eclipse.org/legal/epl-v10.html | |
7 * | |
8 * Contributors: | |
9 * IBM Corporation - initial API and implementation | |
10 *******************************************************************************/ | |
11 module dwt.dnd; | |
12 | |
13 | |
14 import dwt.*; | |
15 import dwt.widgets.*; | |
16 import dwt.internal.cocoa.OS; | |
17 | |
18 /** | |
19 * The <code>Clipboard</code> provides a mechanism for transferring data from one | |
20 * application to another or within an application. | |
21 * | |
22 * <p>IMPORTANT: This class is <em>not</em> intended to be subclassed.</p> | |
23 */ | |
24 public class Clipboard { | |
25 | |
26 Display display; | |
27 int scrap = 0; | |
28 | |
29 /** | |
30 * Constructs a new instance of this class. Creating an instance of a Clipboard | |
31 * may cause system resources to be allocated depending on the platform. It is therefore | |
32 * mandatory that the Clipboard instance be disposed when no longer required. | |
33 * | |
34 * @param display the display on which to allocate the clipboard | |
35 * | |
36 * @exception DWTException <ul> | |
37 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the parent</li> | |
38 * <li>ERROR_INVALID_SUBCLASS - if this class is not an allowed subclass</li> | |
39 * </ul> | |
40 * | |
41 * @see Clipboard#dispose | |
42 * @see Clipboard#checkSubclass | |
43 */ | |
44 public Clipboard(Display display) { | |
45 checkSubclass (); | |
46 if (display is null) { | |
47 display = Display.getCurrent(); | |
48 if (display is null) { | |
49 display = Display.getDefault(); | |
50 } | |
51 } | |
52 if (display.getThread() !is Thread.currentThread()) { | |
53 DND.error(DWT.ERROR_THREAD_INVALID_ACCESS); | |
54 } | |
55 this.display = display; | |
56 } | |
57 | |
58 /** | |
59 * Checks that this class can be subclassed. | |
60 * <p> | |
61 * The DWT class library is intended to be subclassed | |
62 * only at specific, controlled points. This method enforces this | |
63 * rule unless it is overridden. | |
64 * </p><p> | |
65 * <em>IMPORTANT:</em> By providing an implementation of this | |
66 * method that allows a subclass of a class which does not | |
67 * normally allow subclassing to be created, the implementer | |
68 * agrees to be fully responsible for the fact that any such | |
69 * subclass will likely fail between DWT releases and will be | |
70 * strongly platform specific. No support is provided for | |
71 * user-written classes which are implemented in this fashion. | |
72 * </p><p> | |
73 * The ability to subclass outside of the allowed DWT classes | |
74 * is intended purely to enable those not on the DWT development | |
75 * team to implement patches in order to get around specific | |
76 * limitations in advance of when those limitations can be | |
77 * addressed by the team. Subclassing should not be attempted | |
78 * without an intimate and detailed understanding of the hierarchy. | |
79 * </p> | |
80 * | |
81 * @exception DWTException <ul> | |
82 * <li>ERROR_INVALID_SUBCLASS - if this class is not an allowed subclass</li> | |
83 * </ul> | |
84 */ | |
85 protected void checkSubclass () { | |
86 String name = getClass().getName (); | |
87 String validName = Clipboard.class.getName(); | |
88 if (!validName.opEquals(name)) { | |
89 DND.error (DWT.ERROR_INVALID_SUBCLASS); | |
90 } | |
91 } | |
92 /** | |
93 * Throws an <code>DWTException</code> if the receiver can not | |
94 * be accessed by the caller. This may include both checks on | |
95 * the state of the receiver and more generally on the entire | |
96 * execution context. This method <em>should</em> be called by | |
97 * widget implementors to enforce the standard DWT invariants. | |
98 * <p> | |
99 * Currently, it is an error to invoke any method (other than | |
100 * <code>isDisposed()</code>) on a widget that has had its | |
101 * <code>dispose()</code> method called. It is also an error | |
102 * to call widget methods from any thread that is different | |
103 * from the thread that created the widget. | |
104 * </p><p> | |
105 * In future releases of DWT, there may be more or fewer error | |
106 * checks and exceptions may be thrown for different reasons. | |
107 * </p> | |
108 * | |
109 * @exception DWTException <ul> | |
110 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
111 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
112 * </ul> | |
113 */ | |
114 protected void checkWidget () { | |
115 Display display = this.display; | |
116 if (display is null) DND.error (DWT.ERROR_WIDGET_DISPOSED); | |
117 if (display.getThread() !is Thread.currentThread ()) DND.error (DWT.ERROR_THREAD_INVALID_ACCESS); | |
118 if (display.isDisposed()) DND.error(DWT.ERROR_WIDGET_DISPOSED); | |
119 } | |
120 | |
121 /** | |
122 * If this clipboard is currently the owner of the data on the system clipboard, | |
123 * clear the contents. If this clipboard is not the owner, then nothing is done. | |
124 * Note that there are clipboard assistant applications that take ownership of | |
125 * data or make copies of data when it is placed on the clipboard. In these | |
126 * cases, it may not be possible to clear the clipboard. | |
127 * | |
128 * @exception DWTException <ul> | |
129 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
130 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
131 * </ul> | |
132 * | |
133 * @since 3.1 | |
134 */ | |
135 public void clearContents() { | |
136 clearContents(DND.CLIPBOARD); | |
137 } | |
138 | |
139 /** | |
140 * If this clipboard is currently the owner of the data on the specified | |
141 * clipboard, clear the contents. If this clipboard is not the owner, then | |
142 * nothing is done. | |
143 * | |
144 * <p>Note that there are clipboard assistant applications that take ownership | |
145 * of data or make copies of data when it is placed on the clipboard. In these | |
146 * cases, it may not be possible to clear the clipboard.</p> | |
147 * | |
148 * <p>The clipboards value is either one of the clipboard constants defined in | |
149 * class <code>DND</code>, or must be built by <em>bitwise OR</em>'ing together | |
150 * (that is, using the <code>int</code> "|" operator) two or more | |
151 * of those <code>DND</code> clipboard constants.</p> | |
152 * | |
153 * @param clipboards to be cleared | |
154 * | |
155 * @exception DWTException <ul> | |
156 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
157 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
158 * </ul> | |
159 * | |
160 * @see DND#CLIPBOARD | |
161 * @see DND#SELECTION_CLIPBOARD | |
162 * | |
163 * @since 3.1 | |
164 */ | |
165 public void clearContents(int clipboards) { | |
166 checkWidget(); | |
167 if ((clipboards & DND.CLIPBOARD) is 0 || scrap is 0) return; | |
168 int oldScrap = scrap; | |
169 scrap = 0; | |
170 int[] currentScrap = new int[1]; | |
171 if (OS.GetCurrentScrap(currentScrap) !is OS.noErr) return; | |
172 if (currentScrap[0] is oldScrap) { | |
173 OS.ClearCurrentScrap(); | |
174 } | |
175 } | |
176 | |
177 /** | |
178 * Disposes of the operating system resources associated with the clipboard. | |
179 * The data will still be available on the system clipboard after the dispose | |
180 * method is called. | |
181 * | |
182 * <p>NOTE: On some platforms the data will not be available once the application | |
183 * has exited or the display has been disposed.</p> | |
184 * | |
185 * @exception DWTException <ul> | |
186 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the parent</li> | |
187 * </ul> | |
188 */ | |
189 public void dispose () { | |
190 if (isDisposed()) return; | |
191 if (display.getThread() !is Thread.currentThread()) DND.error(DWT.ERROR_THREAD_INVALID_ACCESS); | |
192 display = null; | |
193 } | |
194 | |
195 /** | |
196 * Retrieve the data of the specified type currently available on the system | |
197 * clipboard. Refer to the specific subclass of <code>Transfer</code> to | |
198 * determine the type of object returned. | |
199 * | |
200 * <p>The following snippet shows text and RTF text being retrieved from the | |
201 * clipboard:</p> | |
202 * | |
203 * <code><pre> | |
204 * Clipboard clipboard = new Clipboard(display); | |
205 * TextTransfer textTransfer = TextTransfer.getInstance(); | |
206 * String textData = (String)clipboard.getContents(textTransfer); | |
207 * if (textData !is null) System.out.println("Text is "+textData); | |
208 * RTFTransfer rtfTransfer = RTFTransfer.getInstance(); | |
209 * String rtfData = (String)clipboard.getContents(rtfTransfer); | |
210 * if (rtfData !is null) System.out.println("RTF Text is "+rtfData); | |
211 * clipboard.dispose(); | |
212 * </code></pre> | |
213 * | |
214 * @param transfer the transfer agent for the type of data being requested | |
215 * @return the data obtained from the clipboard or null if no data of this type is available | |
216 * | |
217 * @exception DWTException <ul> | |
218 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
219 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
220 * </ul> | |
221 * @exception IllegalArgumentException <ul> | |
222 * <li>ERROR_NULL_ARGUMENT - if transfer is null</li> | |
223 * </ul> | |
224 * | |
225 * @see Transfer | |
226 */ | |
227 public Object getContents(Transfer transfer) { | |
228 return getContents(transfer, DND.CLIPBOARD); | |
229 } | |
230 | |
231 /** | |
232 * Retrieve the data of the specified type currently available on the specified | |
233 * clipboard. Refer to the specific subclass of <code>Transfer</code> to | |
234 * determine the type of object returned. | |
235 * | |
236 * <p>The following snippet shows text and RTF text being retrieved from the | |
237 * clipboard:</p> | |
238 * | |
239 * <code><pre> | |
240 * Clipboard clipboard = new Clipboard(display); | |
241 * TextTransfer textTransfer = TextTransfer.getInstance(); | |
242 * String textData = (String)clipboard.getContents(textTransfer); | |
243 * if (textData !is null) System.out.println("Text is "+textData); | |
244 * RTFTransfer rtfTransfer = RTFTransfer.getInstance(); | |
245 * String rtfData = (String)clipboard.getContents(rtfTransfer, DND.CLIPBOARD); | |
246 * if (rtfData !is null) System.out.println("RTF Text is "+rtfData); | |
247 * clipboard.dispose(); | |
248 * </code></pre> | |
249 * | |
250 * <p>The clipboards value is either one of the clipboard constants defined in | |
251 * class <code>DND</code>, or must be built by <em>bitwise OR</em>'ing together | |
252 * (that is, using the <code>int</code> "|" operator) two or more | |
253 * of those <code>DND</code> clipboard constants.</p> | |
254 * | |
255 * @param transfer the transfer agent for the type of data being requested | |
256 * @param clipboards on which to look for data | |
257 * | |
258 * @return the data obtained from the clipboard or null if no data of this type is available | |
259 * | |
260 * @exception DWTException <ul> | |
261 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
262 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
263 * </ul> | |
264 * @exception IllegalArgumentException <ul> | |
265 * <li>ERROR_NULL_ARGUMENT - if transfer is null</li> | |
266 * </ul> | |
267 * | |
268 * @see Transfer | |
269 * @see DND#CLIPBOARD | |
270 * @see DND#SELECTION_CLIPBOARD | |
271 * | |
272 * @since 3.1 | |
273 */ | |
274 public Object getContents(Transfer transfer, int clipboards) { | |
275 checkWidget(); | |
276 if (transfer is null) DND.error(DWT.ERROR_NULL_ARGUMENT); | |
277 if ((clipboards & DND.CLIPBOARD) is 0) return null; | |
278 int[] scrap = new int[1]; | |
279 if (OS.GetCurrentScrap(scrap) !is OS.noErr) return null; | |
280 int[] typeIds = transfer.getTypeIds(); | |
281 int[] size = new int[1]; | |
282 // get data from system clipboard | |
283 for (int i=0; i<typeIds.length; i++) { | |
284 int type = typeIds[i]; | |
285 size[0] = 0; | |
286 if (OS.GetScrapFlavorSize(scrap[0], type, size) is OS.noErr && size[0] > 0) { | |
287 byte[] buffer = new byte[size[0]]; | |
288 if (OS.GetScrapFlavorData(scrap[0], type, size, buffer) is OS.noErr) { | |
289 TransferData tdata = new TransferData(); | |
290 tdata.type = type; | |
291 tdata.data = new byte[1][]; | |
292 tdata.data[0] = buffer; | |
293 return transfer.nativeToJava(tdata); | |
294 } | |
295 } | |
296 } | |
297 return null; // No data available for this transfer | |
298 } | |
299 | |
300 /** | |
301 * Returns <code>true</code> if the clipboard has been disposed, | |
302 * and <code>false</code> otherwise. | |
303 * <p> | |
304 * This method gets the dispose state for the clipboard. | |
305 * When a clipboard has been disposed, it is an error to | |
306 * invoke any other method using the clipboard. | |
307 * </p> | |
308 * | |
309 * @return <code>true</code> when the widget is disposed and <code>false</code> otherwise | |
310 * | |
311 * @since 3.0 | |
312 */ | |
313 public bool isDisposed () { | |
314 return (display is null); | |
315 } | |
316 | |
317 /** | |
318 * Place data of the specified type on the system clipboard. More than one type | |
319 * of data can be placed on the system clipboard at the same time. Setting the | |
320 * data clears any previous data from the system clipboard, regardless of type. | |
321 * | |
322 * <p>NOTE: On some platforms, the data is immediately copied to the system | |
323 * clipboard but on other platforms it is provided upon request. As a result, | |
324 * if the application modifies the data object it has set on the clipboard, that | |
325 * modification may or may not be available when the data is subsequently | |
326 * requested.</p> | |
327 * | |
328 * <p>The following snippet shows text and RTF text being set on the copy/paste | |
329 * clipboard: | |
330 * </p> | |
331 * | |
332 * <code><pre> | |
333 * Clipboard clipboard = new Clipboard(display); | |
334 * String textData = "Hello World"; | |
335 * String rtfData = "{\\rtf1\\b\\i Hello World}"; | |
336 * TextTransfer textTransfer = TextTransfer.getInstance(); | |
337 * RTFTransfer rtfTransfer = RTFTransfer.getInstance(); | |
338 * Transfer[] transfers = new Transfer[]{textTransfer, rtfTransfer}; | |
339 * Object[] data = new Object[]{textData, rtfData}; | |
340 * clipboard.setContents(data, transfers); | |
341 * clipboard.dispose(); | |
342 * </code></pre> | |
343 * | |
344 * @param data the data to be set in the clipboard | |
345 * @param dataTypes the transfer agents that will convert the data to its | |
346 * platform specific format; each entry in the data array must have a | |
347 * corresponding dataType | |
348 * | |
349 * @exception IllegalArgumentException <ul> | |
350 * <li>ERROR_INVALID_ARGUMENT - if data is null or datatypes is null | |
351 * or the length of data is not the same as the length of dataTypes</li> | |
352 * </ul> | |
353 * @exception DWTException <ul> | |
354 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
355 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
356 * </ul> | |
357 * @exception DWTError <ul> | |
358 * <li>ERROR_CANNOT_SET_CLIPBOARD - if the clipboard is locked or otherwise unavailable</li> | |
359 * </ul> | |
360 * | |
361 * <p>NOTE: ERROR_CANNOT_SET_CLIPBOARD should be an DWTException, since it is a | |
362 * recoverable error, but can not be changed due to backward compatibility.</p> | |
363 */ | |
364 public void setContents(Object[] data, Transfer[] dataTypes) { | |
365 setContents(data, dataTypes, DND.CLIPBOARD); | |
366 } | |
367 | |
368 /** | |
369 * Place data of the specified type on the specified clipboard. More than one | |
370 * type of data can be placed on the specified clipboard at the same time. | |
371 * Setting the data clears any previous data from the specified | |
372 * clipboard, regardless of type. | |
373 * | |
374 * <p>NOTE: On some platforms, the data is immediately copied to the specified | |
375 * clipboard but on other platforms it is provided upon request. As a result, | |
376 * if the application modifies the data object it has set on the clipboard, that | |
377 * modification may or may not be available when the data is subsequently | |
378 * requested.</p> | |
379 * | |
380 * <p>The clipboards value is either one of the clipboard constants defined in | |
381 * class <code>DND</code>, or must be built by <em>bitwise OR</em>'ing together | |
382 * (that is, using the <code>int</code> "|" operator) two or more | |
383 * of those <code>DND</code> clipboard constants.</p> | |
384 * | |
385 * <p>The following snippet shows text and RTF text being set on the copy/paste | |
386 * clipboard: | |
387 * </p> | |
388 * | |
389 * <code><pre> | |
390 * Clipboard clipboard = new Clipboard(display); | |
391 * String textData = "Hello World"; | |
392 * String rtfData = "{\\rtf1\\b\\i Hello World}"; | |
393 * TextTransfer textTransfer = TextTransfer.getInstance(); | |
394 * RTFTransfer rtfTransfer = RTFTransfer.getInstance(); | |
395 * Transfer[] transfers = new Transfer[]{textTransfer, rtfTransfer}; | |
396 * Object[] data = new Object[]{textData, rtfData}; | |
397 * clipboard.setContents(data, transfers, DND.CLIPBOARD); | |
398 * clipboard.dispose(); | |
399 * </code></pre> | |
400 * | |
401 * @param data the data to be set in the clipboard | |
402 * @param dataTypes the transfer agents that will convert the data to its | |
403 * platform specific format; each entry in the data array must have a | |
404 * corresponding dataType | |
405 * @param clipboards on which to set the data | |
406 * | |
407 * @exception IllegalArgumentException <ul> | |
408 * <li>ERROR_INVALID_ARGUMENT - if data is null or datatypes is null | |
409 * or the length of data is not the same as the length of dataTypes</li> | |
410 * </ul> | |
411 * @exception DWTException <ul> | |
412 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
413 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
414 * </ul> | |
415 * @exception DWTError <ul> | |
416 * <li>ERROR_CANNOT_SET_CLIPBOARD - if the clipboard is locked or otherwise unavailable</li> | |
417 * </ul> | |
418 * | |
419 * <p>NOTE: ERROR_CANNOT_SET_CLIPBOARD should be an DWTException, since it is a | |
420 * recoverable error, but can not be changed due to backward compatibility.</p> | |
421 * | |
422 * @see DND#CLIPBOARD | |
423 * @see DND#SELECTION_CLIPBOARD | |
424 * | |
425 * @since 3.1 | |
426 */ | |
427 public void setContents(Object[] data, Transfer[] dataTypes, int clipboards) { | |
428 checkWidget(); | |
429 if (data is null || dataTypes is null || data.length !is dataTypes.length || data.length is 0) { | |
430 DND.error(DWT.ERROR_INVALID_ARGUMENT); | |
431 } | |
432 for (int i = 0; i < data.length; i++) { | |
433 if (data[i] is null || dataTypes[i] is null || !dataTypes[i].validate(data[i])) { | |
434 DND.error(DWT.ERROR_INVALID_ARGUMENT); | |
435 } | |
436 } | |
437 if ((clipboards & DND.CLIPBOARD) is 0) return; | |
438 if (OS.ClearCurrentScrap() !is OS.noErr) { | |
439 DND.error(DND.ERROR_CANNOT_SET_CLIPBOARD); | |
440 } | |
441 scrap = 0; | |
442 int[] currentScrap = new int[1]; | |
443 if (OS.GetCurrentScrap(currentScrap) !is OS.noErr) { | |
444 DND.error(DND.ERROR_CANNOT_SET_CLIPBOARD); | |
445 } | |
446 scrap = currentScrap[0]; | |
447 // copy data directly over to System clipboard (not deferred) | |
448 for (int i=0; i<dataTypes.length; i++) { | |
449 int[] typeIds = dataTypes[i].getTypeIds(); | |
450 for (int j=0; j<typeIds.length; j++) { | |
451 TransferData transferData = new TransferData(); | |
452 transferData.type = typeIds[j]; | |
453 dataTypes[i].javaToNative(data[i], transferData); | |
454 if (transferData.result !is OS.noErr) { | |
455 DND.error(DND.ERROR_CANNOT_SET_CLIPBOARD); | |
456 } | |
457 //Drag and Drop can handle multiple items in one transfer but the | |
458 //Clipboard can not. | |
459 byte[] datum = transferData.data[0]; | |
460 if (OS.PutScrapFlavor(scrap, transferData.type, 0, datum.length, datum) !is OS.noErr){ | |
461 DND.error(DND.ERROR_CANNOT_SET_CLIPBOARD); | |
462 } | |
463 } | |
464 } | |
465 } | |
466 | |
467 /** | |
468 * Returns an array of the data types currently available on the system | |
469 * clipboard. Use with Transfer.isSupportedType. | |
470 * | |
471 * @return array of data types currently available on the system clipboard | |
472 * | |
473 * @exception DWTException <ul> | |
474 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
475 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
476 * </ul> | |
477 * | |
478 * @see Transfer#isSupportedType | |
479 * | |
480 * @since 3.0 | |
481 */ | |
482 public TransferData[] getAvailableTypes() { | |
483 return getAvailableTypes(DND.CLIPBOARD); | |
484 } | |
485 | |
486 /** | |
487 * Returns an array of the data types currently available on the specified | |
488 * clipboard. Use with Transfer.isSupportedType. | |
489 * | |
490 * <p>The clipboards value is either one of the clipboard constants defined in | |
491 * class <code>DND</code>, or must be built by <em>bitwise OR</em>'ing together | |
492 * (that is, using the <code>int</code> "|" operator) two or more | |
493 * of those <code>DND</code> clipboard constants.</p> | |
494 * | |
495 * @param clipboards from which to get the data types | |
496 * @return array of data types currently available on the specified clipboard | |
497 * | |
498 * @exception DWTException <ul> | |
499 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
500 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
501 * </ul> | |
502 * | |
503 * @see Transfer#isSupportedType | |
504 * @see DND#CLIPBOARD | |
505 * @see DND#SELECTION_CLIPBOARD | |
506 * | |
507 * @since 3.1 | |
508 */ | |
509 public TransferData[] getAvailableTypes(int clipboards) { | |
510 checkWidget(); | |
511 if ((clipboards & DND.CLIPBOARD) is 0) return new TransferData[0]; | |
512 int[] types = _getAvailableTypes(); | |
513 TransferData[] result = new TransferData[types.length]; | |
514 for (int i = 0; i < types.length; i++) { | |
515 result[i] = new TransferData(); | |
516 result[i].type = types[i]; | |
517 } | |
518 return result; | |
519 } | |
520 | |
521 /** | |
522 * Returns a platform specific list of the data types currently available on the | |
523 * system clipboard. | |
524 * | |
525 * <p>Note: <code>getAvailableTypeNames</code> is a utility for writing a Transfer | |
526 * sub-class. It should NOT be used within an application because it provides | |
527 * platform specific information.</p> | |
528 * | |
529 * @return a platform specific list of the data types currently available on the | |
530 * system clipboard | |
531 * | |
532 * @exception DWTException <ul> | |
533 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
534 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
535 * </ul> | |
536 */ | |
537 public String[] getAvailableTypeNames() { | |
538 checkWidget(); | |
539 int[] types = _getAvailableTypes(); | |
540 String[] names = new String[types.length]; | |
541 for (int i = 0; i < types.length; i++) { | |
542 int type = types[i]; | |
543 StringBuffer sb = new StringBuffer(); | |
544 sb.append((char)((type & 0xff000000) >> 24)); | |
545 sb.append((char)((type & 0x00ff0000) >> 16)); | |
546 sb.append((char)((type & 0x0000ff00) >> 8)); | |
547 sb.append((char)((type & 0x000000ff) >> 0)); | |
548 names[i] = sb.toString(); | |
549 } | |
550 return names; | |
551 } | |
552 | |
553 int[] _getAvailableTypes() { | |
554 int[] types = new int[0]; | |
555 int[] scrap = new int[1]; | |
556 if (OS.GetCurrentScrap(scrap) !is OS.noErr) return types; | |
557 int[] count = new int[1]; | |
558 if (OS.GetScrapFlavorCount(scrap[0], count) !is OS.noErr || count[0] is 0) return types; | |
559 int[] info = new int[count[0] * 2]; | |
560 if (OS.GetScrapFlavorInfoList(scrap[0], count, info) !is OS.noErr) return types; | |
561 types = new int[count[0]]; | |
562 for (int i= 0; i < count [0]; i++) { | |
563 types[i] = info[i*2]; | |
564 } | |
565 return types; | |
566 } | |
567 } |