X-Git-Url: http://git.chise.org/gitweb/?p=chise%2Fxemacs-chise.git.1;a=blobdiff_plain;f=src%2Fframe-x.c;h=780367d757bd9400aa5f5f1cf1f2c62a6f93b8fa;hp=2aa7d59c28bbaa12e8ce2f4346996d911228f642;hb=f7019bf646d0d4e750e0186d6e912ec7a3b9da90;hpb=113b194be934327de99a168d809271db252c07c4 diff --git a/src/frame-x.c b/src/frame-x.c index 2aa7d59..780367d 100644 --- a/src/frame-x.c +++ b/src/frame-x.c @@ -23,6 +23,8 @@ Boston, MA 02111-1307, USA. */ /* Substantially rewritten for XEmacs. */ +/* 7-8-00 !!#### This file needs definite Mule review. */ + #include #include "lisp.h" @@ -50,6 +52,7 @@ Boston, MA 02111-1307, USA. */ #include "faces.h" #include "frame.h" #include "window.h" +#include "gutter.h" #ifdef HAVE_DRAGNDROP #include "dragdrop.h" @@ -103,19 +106,34 @@ x_window_to_frame (struct device *d, Window wdesc) struct frame * x_any_window_to_frame (struct device *d, Window wdesc) { - Lisp_Object tail, frame; - struct frame *f; - + Widget w; assert (DEVICE_X_P (d)); + w = XtWindowToWidget (DEVICE_X_DISPLAY (d), wdesc); + + if (!w) + return 0; + + /* We used to map over all frames here and then map over all widgets + belonging to that frame. However it turns out that this was very fragile + as it requires our display structures to be in sync _and_ that the + loop is told about every new widget somebody adds. Therefore we + now let Xt find it for us (which does a bottom-up search which + could even be faster) */ + return x_any_widget_or_parent_to_frame (d, w); +} + +static struct frame * +x_find_frame_for_window (struct device *d, Window wdesc) +{ + Lisp_Object tail, frame; + struct frame *f; /* This function was previously written to accept only a window argument (and to loop over all devices looking for a matching window), but that is incorrect because window ID's are not unique across displays. */ for (tail = DEVICE_FRAME_LIST (d); CONSP (tail); tail = XCDR (tail)) { - int i; - frame = XCAR (tail); f = XFRAME (frame); /* This frame matches if the window is any of its widgets. */ @@ -138,18 +156,18 @@ x_any_window_to_frame (struct device *d, Window wdesc) would incorrectly get sucked away by Emacs if this function matched on psheet widgets. */ - for (i = 0; i < FRAME_X_NUM_TOP_WIDGETS (f); i++) - { - Widget wid = FRAME_X_TOP_WIDGETS (f)[i]; - if (wid && XtIsManaged (wid) && wdesc == XtWindow (wid)) - return f; - } - -#ifdef HAVE_SCROLLBARS - /* Match if the window is one of this frame's scrollbars. */ - if (x_window_is_scrollbar (f, wdesc)) - return f; -#endif + /* Note: that this called only from + x_any_widget_or_parent_to_frame it is unnecessary to iterate + over the top level widgets. */ + + /* Note: we use to special case scrollbars but this turns out to be a bad idea + because + 1. We sometimes get events for _unmapped_ scrollbars and our + callers don't want us to fail. + 2. Starting with the 21.2 widget stuff there are now loads of + widgets to check and it is easy to forget adding them in a loop here. + See x_any_window_to_frame + 3. We pick up all widgets now anyway. */ } return 0; @@ -160,7 +178,7 @@ x_any_widget_or_parent_to_frame (struct device *d, Widget widget) { while (widget) { - struct frame *f = x_any_window_to_frame (d, XtWindow (widget)); + struct frame *f = x_find_frame_for_window (d, XtWindow (widget)); if (f) return f; widget = XtParent (widget); @@ -192,14 +210,14 @@ decode_x_frame (Lisp_Object frame) void x_wm_mark_shell_size_user_specified (Widget wmshell) { - if (! XtIsWMShell (wmshell)) abort (); + if (! XtIsWMShell (wmshell)) ABORT (); EmacsShellSetSizeUserSpecified (wmshell); } void x_wm_mark_shell_position_user_specified (Widget wmshell) { - if (! XtIsWMShell (wmshell)) abort (); + if (! XtIsWMShell (wmshell)) ABORT (); EmacsShellSetPositionUserSpecified (wmshell); } @@ -208,7 +226,7 @@ x_wm_mark_shell_position_user_specified (Widget wmshell) void x_wm_set_shell_iconic_p (Widget shell, int iconic_p) { - if (! XtIsWMShell (shell)) abort (); + if (! XtIsWMShell (shell)) ABORT (); /* Because of questionable logic in Shell.c, this sequence can't work: @@ -238,9 +256,9 @@ x_wm_set_cell_size (Widget wmshell, int cw, int ch) Arg al [2]; if (!XtIsWMShell (wmshell)) - abort (); + ABORT (); if (cw <= 0 || ch <= 0) - abort (); + ABORT (); XtSetArg (al [0], XtNwidthInc, cw); XtSetArg (al [1], XtNheightInc, ch); @@ -253,7 +271,7 @@ x_wm_set_variable_size (Widget wmshell, int width, int height) Arg al [2]; if (!XtIsWMShell (wmshell)) - abort (); + ABORT (); #ifdef DEBUG_GEOMETRY_MANAGEMENT /* See comment in EmacsShell.c */ printf ("x_wm_set_variable_size: %d %d\n", width, height); @@ -320,7 +338,7 @@ x_wm_store_class_hints (Widget shell, char *frame_name) XClassHint classhint; if (!XtIsWMShell (shell)) - abort (); + ABORT (); XtGetApplicationNameAndClass (dpy, &app_name, &app_class); classhint.res_name = frame_name; @@ -336,7 +354,7 @@ x_wm_maybe_store_wm_command (struct frame *f) struct device *d = XDEVICE (FRAME_DEVICE (f)); if (!XtIsWMShell (w)) - abort (); + ABORT (); if (NILP (DEVICE_X_WM_COMMAND_FRAME (d))) { @@ -421,9 +439,9 @@ static void init_x_prop_symbols (void) { #define def(sym, rsrc) \ - pure_put (sym, Qx_resource_name, build_string (rsrc)) + Fput (sym, Qx_resource_name, build_string (rsrc)) #define defi(sym,rsrc) \ - def (sym, rsrc); pure_put (sym, Qintegerp, Qt) + def (sym, rsrc); Fput (sym, Qintegerp, Qt) #if 0 /* this interferes with things. #### fix this right */ def (Qminibuffer, XtNminibuffer); @@ -644,15 +662,15 @@ x_set_frame_text_value (struct frame *f, Bufbyte *value, for (ptr = value; *ptr; ptr++) if (!BYTE_ASCII_P (*ptr)) { - CONST char * tmp; + const char * tmp; encoding = DEVICE_XATOM_COMPOUND_TEXT (XDEVICE (FRAME_DEVICE (f))); - GET_C_CHARPTR_EXT_CTEXT_DATA_ALLOCA ((CONST char *) value, tmp); + C_STRING_TO_EXTERNAL (value, tmp, Qctext); new_XtValue = (String) tmp; break; } #endif /* MULE */ - /* ### Caching is device-independent - belongs in update_frame_title. */ + /* #### Caching is device-independent - belongs in update_frame_title. */ Xt_GET_VALUE (FRAME_X_SHELL_WIDGET (f), Xt_resource_name, &old_XtValue); if (!old_XtValue || strcmp (new_XtValue, old_XtValue)) { @@ -743,18 +761,20 @@ x_set_frame_properties (struct frame *f, Lisp_Object plist) if (STRINGP (prop)) { - CONST char *extprop; + const char *extprop; if (XSTRING_LENGTH (prop) == 0) continue; - GET_C_STRING_CTEXT_DATA_ALLOCA (prop, extprop); + LISP_STRING_TO_EXTERNAL (prop, extprop, Qctext); if (STRINGP (val)) { - CONST Extbyte *extval; + const Extbyte *extval; Extcount extvallen; - GET_STRING_CTEXT_DATA_ALLOCA (val, extval, extvallen); + TO_EXTERNAL_FORMAT (LISP_STRING, val, + ALLOCA, (extval, extvallen), + Qctext); XtVaSetValues (w, XtVaTypedArg, extprop, XtRString, extval, extvallen + 1, (XtArgVal) NULL); @@ -1088,7 +1108,7 @@ WARNING: can only handle plain/text and file: transfers! unsigned int modifier = 0, state = 0; char *Ctext; int numItems = 0, textlen = 0, pos = 0; - struct Lisp_Event *lisp_event = XEVENT(event); + Lisp_Event *lisp_event = XEVENT (event); Lisp_Object item = Qnil; struct gcpro gcpro1; @@ -1125,12 +1145,12 @@ WARNING: can only handle plain/text and file: transfers! x_event.xbutton.y_root = lisp_event->event.button.y; } 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; + if (modifier & XEMACS_MOD_SHIFT) state |= ShiftMask; + if (modifier & XEMACS_MOD_CONTROL) state |= ControlMask; + if (modifier & XEMACS_MOD_META) state |= xd->MetaMask; + if (modifier & XEMACS_MOD_SUPER) state |= xd->SuperMask; + if (modifier & XEMACS_MOD_HYPER) state |= xd->HyperMask; + if (modifier & XEMACS_MOD_ALT) state |= xd->AltMask; state |= Button1Mask << (lisp_event->event.button.button-1); x_event.xbutton.state = state; @@ -1170,7 +1190,7 @@ WARNING: can only handle plain/text and file: transfers! Ctext=NULL; break; } - strcpy (Ctext+pos, (CONST char *)XSTRING_DATA (XCAR (item))); + strcpy (Ctext+pos, (const char *)XSTRING_DATA (XCAR (item))); pos += XSTRING_LENGTH (XCAR (item)) + 1; item = XCDR (item); } @@ -1240,7 +1260,7 @@ x_cde_transfer_callback (Widget widget, XtPointer clientData, { filePath = transferInfo->dropData->data.files[ii]; hurl = dnd_url_hexify_string ((char *)filePath, "file:"); - /* ### Mule-izing required */ + /* #### Mule-izing required */ l_data = Fcons (make_string ((Bufbyte* )hurl, strlen (hurl)), l_data); @@ -1315,7 +1335,7 @@ The type defaults to DndText (4). char *dnd_data = NULL; unsigned long dnd_len = 0; int dnd_typ = DndText, dnd_dealloc = 0; - struct Lisp_Event *lisp_event = XEVENT(event); + Lisp_Event *lisp_event = XEVENT (event); /* only drag if this is really a press */ if (EVENT_TYPE(lisp_event) != button_press_event) @@ -1346,7 +1366,7 @@ The type defaults to DndText (4). } len = XSTRING_LENGTH (XCAR (run)) + 1; dnd_data = (char *) xrealloc (dnd_data, dnd_len + len); - strcpy (dnd_data + dnd_len - 1, (CONST char *)XSTRING_DATA (XCAR (run))); + strcpy (dnd_data + dnd_len - 1, (const char *)XSTRING_DATA (XCAR (run))); dnd_len += len; run = XCDR (run); } @@ -1391,12 +1411,12 @@ The type defaults to DndText (4). } 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; + if (modifier & XEMACS_MOD_SHIFT) state |= ShiftMask; + if (modifier & XEMACS_MOD_CONTROL) state |= ControlMask; + if (modifier & XEMACS_MOD_META) state |= xd->MetaMask; + if (modifier & XEMACS_MOD_SUPER) state |= xd->SuperMask; + if (modifier & XEMACS_MOD_HYPER) state |= xd->HyperMask; + if (modifier & XEMACS_MOD_ALT) state |= xd->AltMask; state |= Button1Mask << (lisp_event->event.button.button-1); x_event.xbutton.state = state; @@ -1529,13 +1549,16 @@ x_initialize_frame_size (struct frame *f) { struct window *win = XWINDOW (f->root_window); - WINDOW_LEFT (win) = FRAME_LEFT_BORDER_END (f); - WINDOW_TOP (win) = FRAME_TOP_BORDER_END (f); + WINDOW_LEFT (win) = FRAME_LEFT_BORDER_END (f) + + FRAME_LEFT_GUTTER_BOUNDS (f); + WINDOW_TOP (win) = FRAME_TOP_BORDER_END (f) + + FRAME_TOP_GUTTER_BOUNDS (f); if (!NILP (f->minibuffer_window)) { win = XWINDOW (f->minibuffer_window); - WINDOW_LEFT (win) = FRAME_LEFT_BORDER_END (f); + WINDOW_LEFT (win) = FRAME_LEFT_BORDER_END (f) + + FRAME_LEFT_GUTTER_BOUNDS (f); } } @@ -1614,7 +1637,7 @@ x_initialize_frame_size (struct frame *f) /* OK, we're a top-level shell. */ if (!XtIsWMShell (wmshell)) - abort (); + ABORT (); /* If the EmacsFrame doesn't have a geometry but the shell does, treat that as the geometry of the frame. @@ -1788,10 +1811,14 @@ x_layout_widgets (Widget w, XtPointer client_data, XtPointer call_data) #endif /* finally the text area */ - XtConfigureWidget (text, text_x, text_y, - width - 2*textbord, - height - text_y - 2*textbord, - textbord); + { + Dimension nw = width - 2*textbord; + Dimension nh = height - text_y - 2*textbord; + + if (nh != f->pixheight || nw != f->pixwidth) + MARK_FRAME_SIZE_SLIPPED (f); + XtConfigureWidget (text, text_x, text_y, nw, nh, textbord); + } } static void @@ -1840,7 +1867,7 @@ x_create_widgets (struct frame *f, Lisp_Object lisp_window_id, #ifdef EXTERNAL_WIDGET Window window_id = 0; #endif - CONST char *name; + const char *name; Arg al [25]; int ac = 0; Widget text, container, shell; @@ -1851,7 +1878,7 @@ x_create_widgets (struct frame *f, Lisp_Object lisp_window_id, #endif if (STRINGP (f->name)) - GET_C_STRING_CTEXT_DATA_ALLOCA (f->name, name); + LISP_STRING_TO_EXTERNAL (f->name, name, Qctext); else name = "emacs"; @@ -1880,7 +1907,7 @@ x_create_widgets (struct frame *f, Lisp_Object lisp_window_id, char *string; CHECK_STRING (lisp_window_id); - string = (char *) (XSTRING_DATA (lisp_window_id)); + string = (char *) XSTRING_DATA (lisp_window_id); if (string[0] == '0' && (string[1] == 'x' || string[1] == 'X')) sscanf (string+2, "%lxu", &window_id); #if 0 @@ -2190,10 +2217,10 @@ x_init_frame_3 (struct frame *f) } static void -x_mark_frame (struct frame *f, void (*markobj) (Lisp_Object)) +x_mark_frame (struct frame *f) { - markobj (FRAME_X_ICON_PIXMAP (f)); - markobj (FRAME_X_ICON_PIXMAP_MASK (f)); + mark_object (FRAME_X_ICON_PIXMAP (f)); + mark_object (FRAME_X_ICON_PIXMAP_MASK (f)); } static void @@ -2463,6 +2490,18 @@ x_lower_frame (struct frame *f) } } +static void +x_enable_frame (struct frame *f) +{ + XtSetSensitive (FRAME_X_SHELL_WIDGET (f), True); +} + +static void +x_disable_frame (struct frame *f) +{ + XtSetSensitive (FRAME_X_SHELL_WIDGET (f), False); +} + /* Change from withdrawn state to mapped state. */ static void x_make_frame_visible (struct frame *f) @@ -2619,7 +2658,7 @@ x_focus_on_frame (struct frame *f) XFlush (XtDisplay (shell_widget)); /* hey, I'd like to DEBUG this... */ } -/* Destroy the X window of frame S. */ +/* Destroy the X window of frame F. */ static void x_delete_frame (struct frame *f) { @@ -2638,18 +2677,18 @@ x_delete_frame (struct frame *f) dpy = XtDisplay (FRAME_X_SHELL_WIDGET (f)); #ifdef EXTERNAL_WIDGET - expect_x_error (XtDisplay (FRAME_X_SHELL_WIDGET (f))); + expect_x_error (dpy); /* for obscure reasons having (I think) to do with the internal window-to-widget hierarchy maintained by Xt, we have to call XtUnrealizeWidget() here. Xt can really suck. */ if (f->being_deleted) XtUnrealizeWidget (FRAME_X_SHELL_WIDGET (f)); XtDestroyWidget (FRAME_X_SHELL_WIDGET (f)); - x_error_occurred_p (XtDisplay (FRAME_X_SHELL_WIDGET (f))); + x_error_occurred_p (dpy); #else XtDestroyWidget (FRAME_X_SHELL_WIDGET (f)); /* make sure the windows are really gone! */ - /* ### Is this REALLY necessary? */ + /* #### Is this REALLY necessary? */ XFlush (dpy); #endif /* EXTERNAL_WIDGET */ @@ -2709,12 +2748,14 @@ x_update_frame_external_traits (struct frame* frm, Lisp_Object name) Lisp_Object font = FACE_FONT (Vdefault_face, frame, Vcharset_ascii); if (!EQ (font, Vthe_null_font_instance)) - XtSetArg (al[ac], XtNfont, - (void *) FONT_INSTANCE_X_FONT (XFONT_INSTANCE (font))); - ac++; + { + XtSetArg (al[ac], XtNfont, + (void *) FONT_INSTANCE_X_FONT (XFONT_INSTANCE (font))); + ac++; + } } else - abort (); + ABORT (); XtSetValues (FRAME_X_TEXT_WIDGET (frm), al, ac); @@ -2766,6 +2807,8 @@ console_type_create_frame_x (void) CONSOLE_HAS_METHOD (x, set_mouse_position); CONSOLE_HAS_METHOD (x, raise_frame); CONSOLE_HAS_METHOD (x, lower_frame); + CONSOLE_HAS_METHOD (x, enable_frame); + CONSOLE_HAS_METHOD (x, disable_frame); CONSOLE_HAS_METHOD (x, make_frame_visible); CONSOLE_HAS_METHOD (x, make_frame_invisible); CONSOLE_HAS_METHOD (x, iconify_frame);