Mercurial > hg > xemacs-beta
diff src/frame-x.c @ 197:acd284d43ca1 r20-3b25
Import from CVS: tag r20-3b25
author | cvs |
---|---|
date | Mon, 13 Aug 2007 10:00:02 +0200 |
parents | ecf6ba7b0a10 |
children | e45d5e7c476e |
line wrap: on
line diff
--- a/src/frame-x.c Mon Aug 13 09:59:07 2007 +0200 +++ b/src/frame-x.c Mon Aug 13 10:00:02 2007 +0200 @@ -51,6 +51,11 @@ #include "frame.h" #include "window.h" +#ifdef HAVE_OFFIX_DND +#include "offix.h" +#include "events-mod.h" +#endif + /* Default properties to use when creating frames. */ Lisp_Object Vdefault_x_frame_plist; @@ -320,6 +325,7 @@ XSetClassHint (dpy, XtWindow (shell), &classhint); } +#ifndef HAVE_SESSION static void x_wm_maybe_store_wm_command (struct frame *f) { @@ -366,12 +372,11 @@ return; f = XFRAME (XCAR (rest)); -#ifndef HAVE_SESSION x_wm_maybe_store_wm_command (f); -#endif /* HAVE_SESSION */ } } +#endif /* !HAVE_SESSION */ static int x_frame_iconified_p (struct frame *f) @@ -1166,124 +1171,83 @@ #endif /* HAVE_CDE */ #ifdef HAVE_OFFIX_DND -#include <OffiX/DragAndDrop.h> - -void -x_offix_drop_event_handler (Widget widget, XtPointer data, XEvent *event, - Boolean *b) -{ - int i, len, Type; - unsigned char *Data; - unsigned long Size; - - Lisp_Object path = Qnil; - Lisp_Object frame = Qnil; - Lisp_Object dnd_data = Qnil; - Lisp_Object dnd_type = Qnil; - - struct gcpro gcpro1, gcpro2, gcpro3, gcpro4; - - if (!DndIsDropMessage(event)) /* the better way */ - { -#if 0 - stderr_out("DndDropHandler: pseudo drop received (ignore me!)\n"); -#endif - return; - } - - Type = DndDataType (event); - DndGetData (&Data, &Size); - - GCPRO4 (path, frame, dnd_data, dnd_type); - - frame = make_frame ((struct frame *) data); -#if 0 - stderr_out("DndDropHandler: valid drop received (T%d S%u)\n",Type,Size); -#endif - switch (Type) - { - case DndFiles: - while (*Data) - { - len = strlen ((char*) Data); - path = make_ext_string ((char*) Data, len, FORMAT_FILENAME); - va_run_hook_with_args (Qdrag_and_drop_functions, 2, frame, path); - Data += len+1; - } - break; - case DndFile: - path = make_ext_string ((char*) Data, strlen(Data), FORMAT_FILENAME); - va_run_hook_with_args (Qdrag_and_drop_functions, 2, frame, path); - break; - case DndText: - dnd_data = make_ext_string ((char *) Data, strlen(Data), FORMAT_FILENAME); - va_run_hook_with_args (Qdrag_and_drop_functions, 3, frame, path, dnd_data); - break; - case DndDir: - case DndLink: - case DndExe: - case DndURL: - case DndMIME: - dnd_type = make_int (Type); - dnd_data = make_ext_string ((char*) Data, strlen(Data), FORMAT_FILENAME); - va_run_hook_with_args (Qdrag_and_drop_functions, 4, - frame, path, dnd_data, dnd_type); - break; - default: /* Unknown, RawData and any other type */ - dnd_type = make_int (Type); - dnd_data = make_ext_string ((char*) Data, Size, FORMAT_BINARY); - va_run_hook_with_args (Qdrag_and_drop_functions, 4, - frame, path, dnd_data, dnd_type); - break; - } - - UNGCPRO; - return; -} DEFUN ("offix-start-drag-internal", Foffix_start_drag_internal, 2, 3, 0, /* First arg is the event that started the drag, -second arg should be some string. +second arg should be some string, and the third +is the type of the data (this should be an int). +The type defaults to DndText (4). Start a OffiX drag from a buffer. -For now this will only drag as DndText. -This fun is heavily stolen from the CDE Dnd stuff. */ (event, data, dtyp)) { - if (EVENTP(event) && STRINGP (data)) + if (EVENTP(event)) { struct frame *f = decode_x_frame (Fselected_frame (Qnil)); XEvent x_event; Widget wid = FRAME_X_TEXT_WIDGET (f); Display *display = XtDisplayOfObject (wid); - Window root_window, child_window; - int root_x, root_y, win_x, win_y; - unsigned int keys_and_buttons; - char *dnd_data; - unsigned long dnd_len; - int dnd_typ; + struct device *d = get_device_from_display (display); + struct x_device *xd = DEVICE_X_DATA (d); + unsigned int modifier = 0, state = 0; + char *dnd_data = NULL; + unsigned long dnd_len = 0; + int dnd_typ = DndText, dnd_dealloc = 0; struct Lisp_Event *lisp_event = XEVENT(event); /* only drag if this is really a press */ if (EVENT_TYPE(lisp_event) != button_press_event) return Qnil; - /* and whats with MULE data ??? */ - dnd_data = XSTRING_DATA (data); - dnd_len = XSTRING_LENGTH (data) + 1; /* the f*cking zero */ - - /* set the type */ + /* get the desired type */ if (!NILP (dtyp) && INTP (dtyp)) dnd_typ = XINT (dtyp); + + if (dnd_typ == DndFiles) + { + Lisp_Object run = data; + int len = 0; + + if (NILP ( Flistp (data))) + return Qnil; + + /* construct the data from a list of files */ + dnd_len = 1; + dnd_data = (char *) xmalloc (1); + *dnd_data = 0; + while (!NILP (run)) + { + if (!STRINGP (XCAR (run))) + { + xfree (dnd_data); + return Qnil; + } + len = XSTRING_LENGTH (XCAR (run)) + 1; + dnd_data = xrealloc (dnd_data, dnd_len + len); + strcpy (dnd_data + dnd_len - 1, XSTRING_DATA (XCAR (run))); + dnd_len += len; + run = XCDR (run); + } + + dnd_data[dnd_len - 1] = 0; /* the list-ending zero */ + dnd_dealloc = 1; + + } else - dnd_typ = DndText; /* the default */ + { + if (!STRINGP (data)) + return Qnil; + + /* and whats with MULE data ??? */ + dnd_data = XSTRING_DATA (data); + dnd_len = XSTRING_LENGTH (data) + 1; /* the zero */ + + } /* * Eek - XEmacs doesn't keep the old X event around so we have to * build a dummy event. This is a truly gross hack. (from CDE) - * - * Perhaps there is some way to hand back the lisp event object? - * Best way: hand through x-event in all Lisp_Events + * but it works... */ x_event.xbutton.type = ButtonPress; @@ -1297,11 +1261,23 @@ x_event.xbutton.y = lisp_event->event.button.y; x_event.xbutton.x_root = lisp_event->event.button.x; /* this is wrong */ x_event.xbutton.y_root = lisp_event->event.button.y; - x_event.xbutton.state = 0; /* calc state from modifier */ + + modifier = lisp_event->event.button.modifiers; + if (modifier && MOD_SHIFT) state |= ShiftMask; + if (modifier && MOD_CONTROL) state |= ControlMask; + if (modifier && MOD_META) state |= xd->MetaMask; + if (modifier && MOD_SUPER) state |= xd->SuperMask; + if (modifier && MOD_HYPER) state |= xd->HyperMask; + if (modifier && MOD_ALT) state |= xd->AltMask; + state |= (Button1Mask << (lisp_event->event.button.button-1)); + + x_event.xbutton.state = state; x_event.xbutton.button = lisp_event->event.button.button; x_event.xkey.same_screen = True; DndSetData(dnd_typ, dnd_data, dnd_len); + if (dnd_dealloc) + xfree (dnd_data); if (DndHandleDragging(wid, &x_event)) return Qt; @@ -2008,16 +1984,6 @@ } #endif /* HAVE_CDE */ -#ifdef HAVE_OFFIX_DND - { - DndInitialize (FRAME_X_SHELL_WIDGET (f)); - DndRegisterDropWidget (FRAME_X_TEXT_WIDGET (f), - x_offix_drop_event_handler, - (XtPointer) f); - - } -#endif - /* Do a stupid property change to force the server to generate a propertyNotify event so that the event_stream server timestamp will be initialized to something relevant to the time we created the window.