for (int i = 0; i < dataTypes.length; i++) {
Transfer transfer = dataTypes[i];
int[] typeIds = transfer.getTypeIds();
String[] typeNames = transfer.getTypeNames();
for (int j = 0; j < typeIds.length; j++) {
GtkTargetEntry entry = new GtkTargetEntry();
entry.info = typeIds[j];
byte[] buffer = Converter.wcsToMbcs(null, typeNames[j], true);
long /*int*/ pName = OS.g_malloc(buffer.length);
OS.memmove(pName, buffer, buffer.length);
entry.target = pName;
GtkTargetEntry[] tmp = new GtkTargetEntry [entries.length + 1];
System.arraycopy(entries, 0, tmp, 0, entries.length);
tmp[entries.length] = entry;
entries = tmp;
}
}
pTargetsList = OS.g_malloc(GtkTargetEntry.sizeof * entries.length);
int offset = 0;
for (int i = 0; i < entries.length; i++) {
OS.memmove(pTargetsList + offset, entries[i], GtkTargetEntry.sizeof);
offset += GtkTargetEntry.sizeof;
}
if ((clipboards & DND.CLIPBOARD) != 0) {
clipboardData = data;
clipboardDataTypes = dataTypes;
long /*int*/ getFuncProc = getFunc.getAddress();
long /*int*/ clearFuncProc = clearFunc.getAddress();
/*
* Feature in GTK. When the contents are set again, clipboard_set_with_data()
* invokes clearFunc and then, getFunc is not sequentially called.
* If we clear the content before calling set_with_data(), then there is a fair
* chance for other apps like Klipper to claim the ownership of the clipboard.
* The fix is to make sure that the content is not cleared before the data is
* set again. GTK does not invoke clearFunc for clipboard_set_with_owner()
* though we set the data again. So, this API has to be used whenever we
* are setting the contents.
*/
if (!OS.gtk_clipboard_set_with_owner (Clipboard.GTKCLIPBOARD, pTargetsList, entries.length, getFuncProc, clearFuncProc, clipboardOwner)) {
return false;
}
if (OS.GTK_VERSION >= OS.VERSION(2, 6, 0)) {
OS.gtk_clipboard_set_can_store(Clipboard.GTKCLIPBOARD, 0, 0);
}
activeClipboard = owner;
}
if ((clipboards & DND.SELECTION_CLIPBOARD) != 0) {
primaryClipboardData = data;
primaryClipboardDataTypes = dataTypes;
long /*int*/ getFuncProc = getFunc.getAddress();
long /*int*/ clearFuncProc = clearFunc.getAddress();
if (!OS.gtk_clipboard_set_with_owner (Clipboard.GTKPRIMARYCLIPBOARD, pTargetsList, entries.length, getFuncProc, clearFuncProc, clipboardOwner)) {
return false;
}
if (OS.GTK_VERSION >= OS.VERSION(2, 6, 0)) {
OS.gtk_clipboard_set_can_store(Clipboard.GTKPRIMARYCLIPBOARD, 0, 0);
}
activePrimaryClipboard = owner;
}
return true;
} finally {
for (int i = 0; i < entries.length; i++) {
GtkTargetEntry entry = entries[i];
if( entry.target != 0) OS.g_free(entry.target);
}
if (pTargetsList != 0) OS.g_free(pTargetsList);
}
}