1
2
3
4
5
6
7
8
9
10
11
12 #include <stdio.h>
13 #include <errno.h>
14 #include <limits.h>
15 #include <string.h>
16 #include <stdlib.h>
17 #include <sys/types.h>
18 #include <sys/stat.h>
19 #include <sys/param.h>
20 #include <fcntl.h>
21 #include <Xm/Xm.h>
22 #include <Xm/AtomMgr.h>
23 #include "../source/textBuf.h"
24 #include "../source/nedit.h"
25 #include "../source/window.h"
26
27 #include "../source/file.h"
28 #include "../source/preferences.h"
29 #include "dragAndDrop.h"
30 #include "DialogF.h"
31 #ifdef CDE
32 #include <Dt/Dnd.h>
33 #else
34 #include <Xm/DragDrop.h>
35
36 static Atom xa_targets[
10];
37 static int n_targets =
0;
38
39 static void TransferDone(Widget transfer, XtPointer client_data,
40 Atom * selection, Atom * type, XtPointer value,
41 unsigned long *length,
int *format);
42 #endif
43
44
45
46 static char *dndgeom =
NULL;
47
48
49
50
51 static void editdatafile(Widget w,
char *filePath) {
52
53 char *params[
2];
54 params[
0] = filePath;
55 params[
1] =
NULL;
56 XtCallActionProc(w,
"open",
NULL, params,
1);
57 }
58
59
60
61
62 static void newdatafile(Widget widget,
char *buffer) {
63 WindowInfo *window = WidgetToWindow(widget);
64 int openInTab = GetPrefOpenInTab();
65
66 if (window->filenameSet || window->fileChanged) {
67 window = EditNewFile(openInTab? window :
NULL,
NULL, False,
NULL, window->path);
68 }
69
70 BufInsert(window->buffer,
0, buffer);
71 }
72
73 #ifdef CDE
74
75
76
77
78
79 void fileTransferCallback(Widget widget, XtPointer clientData, XtPointer callData) {
80 DtDndTransferCallbackStruct *transferInfo =
81 (DtDndTransferCallbackStruct *) callData;
82 char *filePath, *name, *path;
83 int ii;
84
85 if (transferInfo ==
NULL) {
86 return;
87 }
88
89
90 if (transferInfo->dropData->protocol != DtDND_FILENAME_TRANSFER ||
91 transferInfo->reason != DtCR_DND_TRANSFER_DATA) {
92 return;
93 }
94
95
96 for (ii =
0; ii < transferInfo->dropData->numItems; ii++) {
97 editdatafile(widget, transferInfo->dropData->data.files[ii]);
98 }
99 }
100
101
102
103
104
105 void dataTransferCallback(Widget widget, XtPointer clientData, XtPointer callData) {
106 DtDndTransferCallbackStruct *transferInfo =
107 (DtDndTransferCallbackStruct *) callData;
108 int ii;
109
110 if (transferInfo ==
NULL)
return;
111
112
113 if (transferInfo->dropData->protocol != DtDND_BUFFER_TRANSFER ||
114 transferInfo->reason != DtCR_DND_TRANSFER_DATA) {
115 return;
116 }
117
118 for (ii =
0; ii < transferInfo->dropData->numItems; ii++) {
119 WindowInfo *window, *w;
120 int i;
121 char name[
20];
122 char *p, *q;
123 char *string = (
char *) transferInfo->dropData->data.buffers[ii].bp;
124 p = strstr(string,
"file:");
125 #ifdef DBGS
126 printf(
"STRING: %s\nwidget: %s", string, XtName(widget));
127 #endif
128 if (p) {
129 while (p) {
130 q = strchr(p,
'\r');
131 *q =
'\0';
132 editdatafile(widget, p +
5);
133 p = strstr(q +
1,
"file:");
134 }
135 }
else {
136 newdatafile(widget, string);
137 }
138 }
139 }
140 #endif
141
142
143 #ifndef CDE
144
145
146
147
148
149
150 static void TransferDone(Widget transfer, XtPointer client_data,
151 Atom *selection, Atom *type, XtPointer value,
152 unsigned long *length,
int *format) {
153 Widget widget = (Widget) client_data;
154 String string =
NULL;
155
156 #ifdef DBGS
157 printf(
"TransferDone: Type %s format %d, Selection: %s\n",
158 XmGetAtomName(XtDisplay(widget), *type),
159 *format, XmGetAtomName(XtDisplay(widget), *selection));
160 #endif
161 if (*format ==
8) {
162 if (*type == xa_targets[
3] || *type == xa_targets[
0]) {
163 char *p, *q;
164 string = (
char *) value;
165 p = strstr(string,
"file:");
166 #ifdef DBGS
167 printf(
"STRING: %s\nwidget: %s", string, XtName(widget));
168 #endif
169 if (p) {
170 while (p) {
171 q = strchr(p,
'\r');
172 *q =
'\0';
173 editdatafile(widget, p +
5);
174 p = strstr(q +
1,
"file:");
175 }
176 }
else
177 newdatafile(widget, string);
178 }
else if (*type == xa_targets[
2]) {
179 char *p, *q;
180 int dlen;
181 char path[
1024];
182 q = (
char *) value;
183 #ifdef DBGS
184 printf(
"FILES: %s\nwidget: %s", q, XtName(widget));
185 #endif
186 p = strchr(q,
' ');
187 dlen = p - q;
188 while (p) {
189 memset(path,
0,
1024);
190 strncpy(path, (
char *) value, dlen);
191 strcat(path,
"/");
192 q = p +
1;
193 p = strchr(q,
' ');
194 if (p) strncat(path, q, p - q);
195 else strcat(path, q);
196 #ifdef DBGS
197 printf(
"FILE: %s\n", path);
198 #endif
199 editdatafile(widget, path);
200 }
201 }
else if (*type == xa_targets[
1]) {
202 string = (
char *) value;
203 #ifdef DBGS
204 printf(
"FILE_NAME: %s\n", string);
205 #endif
206 editdatafile(widget, string);
207 }
208 }
else {
209 XtVaSetValues(transfer,
210 XmNtransferStatus, XmTRANSFER_FAILURE,
211 XmNnumDropTransfers,
0,
212 NULL);
213 DialogF(
DF_INF, widget,
1,
"Transfer Done",
"Dropped data is corrupted. Type %s format %d",
214 "Ok!", XmGetAtomName(XtDisplay(widget), *type), *format);
215 return;
216 }
217
218 }
219 #endif
220
221
222
223
224
225 void neditDropCallback(Widget widget, XtPointer clientData, XtPointer callData) {
226 #ifndef CDE
227 XmDropProcCallbackStruct *dropInfo =
228 (XmDropProcCallbackStruct *) callData;
229 Arg args[
8];
230 Arg get_args[
4];
231 Atom *exports;
232 int i =
0, n =
0;
233 Cardinal num_targets =
0;
234 Cardinal num_transfer =
0;
235 XmDropTransferEntryRec target_data[
2];
236 unsigned char status;
237
238 XtSetArg(get_args[i], XmNexportTargets, &exports);
239 i++;
240 XtSetArg(get_args[i], XmNnumExportTargets, &num_targets);
241 i++;
242 XtGetValues(dropInfo->dragContext, get_args, i);
243 if (dropInfo->dropSiteStatus == XmVALID_DROP_SITE) {
244 int targ_ix = num_targets;
245 dropInfo->operation = XmDROP_COPY;
246 for (i =
0; i < num_targets; i++) {
247 #ifdef DBGS
248 printf(
"%s: target %d of %d: %s\n", XtName(widget), i, num_targets,
249 XmGetAtomName(XtDisplay(widget), exports[i]));
250 #endif
251 if (exports[i] == xa_targets[
0]
252 || exports[i] == xa_targets[
1]
253 || exports[i] == xa_targets[
2]
254 || exports[i] == xa_targets[
3]) {
255 targ_ix = i;
256 break;
257 }
258 }
259 if (targ_ix < num_targets) {
260 status = XmTRANSFER_SUCCESS;
261 num_transfer =
1;
262 target_data[
0].target = exports[targ_ix];
263 target_data[
0].client_data = (XtPointer) widget;
264 XtSetArg(args[n], XmNtransferProc, TransferDone);
265 n++;
266 XtSetArg(args[n], XmNdropTransfers, target_data);
267 n++;
268 #ifdef DBGS
269 printf(
"selected target is %d (%s)\n", targ_ix,
270 XmGetAtomName(XtDisplay(widget), exports[targ_ix]));
271 #endif
272 }
else {
273 char *msg = (num_targets >
0 ? XmGetAtomName(XtDisplay(widget), exports[
0]) : strdup(
""));
274 DialogF(
DF_WARN, widget,
1,
"DropCallback",
"Non Identified Object \"%s\" is Dropped.",
275 "Ok!", msg);
276 status = XmTRANSFER_FAILURE;
277 num_transfer =
0;
278 XFree(msg);
279 }
280 }
else {
281 char *msg = (num_targets >
0 ? XmGetAtomName(XtDisplay(widget), exports[
0]) : strdup(
""));
282 DialogF(
DF_WARN, widget,
1,
"DropCallback",
"Not a vaild drop site. Non Identified Object \"%s\" is Dropped.",
283 "Ok!", msg);
284 status = XmTRANSFER_FAILURE;
285 num_transfer =
0;
286 XFree(msg);
287 }
288 XtSetArg(args[n], XmNnumDropTransfers, num_transfer);
289 n++;
290 XtSetArg(args[n], XmNtransferStatus, status);
291 n++;
292 XmDropTransferStart(dropInfo->dragContext, args, n);
293
294 #else
295 DtDndTransferCallbackStruct *transferInfo =
296 (DtDndTransferCallbackStruct *) callData;
297
298 if (transferInfo ==
NULL) {
299 return;
300 }
301
302 switch (transferInfo->dropData->protocol) {
303 case DtDND_FILENAME_TRANSFER:
304 fileTransferCallback(widget, clientData, callData);
305 break;
306 case DtDND_BUFFER_TRANSFER:
307 dataTransferCallback(widget, clientData, callData);
308 break;
309 }
310 #endif
311 }
312
313 void neditDropInit(Widget w,
char *geometry) {
314 #ifndef CDE
315 #ifdef DBGS
316 printf(
"neditDropInit w=%s, n_targets=%d, geom=%s\n", XtName(w), n_targets,
317 (geometry ? geometry :
"<no geometry>"));
318 #endif
319 if (n_targets ==
0) {
320 xa_targets[n_targets++] = XmInternAtom(XtDisplay(w),
"text/uri-list", False);
321 xa_targets[n_targets++] = XmInternAtom(XtDisplay(w), XmSFILE_NAME, False);
322 xa_targets[n_targets++] = XmInternAtom(XtDisplay(w),
"FILES", False);
323 xa_targets[n_targets++] = XmInternAtom(XtDisplay(w),
"STRING", False);
324 }
325 #endif
326 dndgeom = geometry;
327 }
328
329
330
331
332 void neditDropWidget(Widget w) {
333 #ifndef CDE
334 Arg args[
10];
335 Cardinal n =
0;
336
337 if (n_targets ==
0) neditDropInit(w,
NULL);
338 #ifdef DBGS
339 printf(
"neditDropWidget dropDraw=%s, %x\n", XtName(w), w);
340 #endif
341 XtSetArg(args[n], XmNdropSiteOperations, XmDROP_COPY);
342 n++;
343 XtSetArg(args[n], XmNdropSiteActivity, XmDROP_SITE_ACTIVE);
344 n++;
345 XtSetArg(args[n], XmNdropSiteType, XmDROP_SITE_COMPOSITE);
346 n++;
347 XtSetArg(args[n], XmNimportTargets, xa_targets);
348 n++;
349 XtSetArg(args[n], XmNnumImportTargets, n_targets);
350 n++;
351 XtSetArg(args[n], XmNdragProc,
NULL);
352 n++;
353 XtSetArg(args[n], XmNdropProc, neditDropCallback);
354 n++;
355 XmDropSiteRegister(w, args, n);
356 #else
357 static XtCallbackRec transferCBRec[] ={
358 {neditDropCallback,
NULL},
359 {
NULL,
NULL}
360 };
361 DtDndVaDropRegister(w,
362 DtDND_FILENAME_TRANSFER | DtDND_BUFFER_TRANSFER,
363 XmDROP_LINK | XmDROP_COPY,
364 transferCBRec,
365 DtNtextIsBuffer, True,
366 DtNpreserveRegistration, False,
367 NULL);
368 #endif
369 }
370