1 /* Functions for the X window system.
2 Copyright (C) 1989, 1992, 1993, 1994 Free Software Foundation.
4 This file is part of GNU Emacs.
6 GNU Emacs is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2, or (at your option)
11 GNU Emacs is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with GNU Emacs; see the file COPYING. If not, write to
18 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
20 /* Completely rewritten by Richard Stallman. */
22 /* Rewritten for X11 by Joseph Arceneaux */
27 /* This makes the fields of a Display accessible, in Xlib header files. */
28 #define XLIB_ILLEGAL_ACCESS
35 #include "dispextern.h"
37 #include "blockinput.h"
44 #if 1 /* Used to be #ifdef EMACS_BITMAP_FILES, but this should always work. */
45 #include "bitmaps/gray.xbm"
47 #include <X11/bitmaps/gray>
50 #include "[.bitmaps]gray.xbm"
54 #include <X11/Shell.h>
56 #include <X11/Xaw/Paned.h>
57 #include <X11/Xaw/Label.h>
60 #undef USG /* ####KLUDGE for Solaris 2.2 and up */
69 #include "../lwlib/lwlib.h"
71 /* Do the EDITRES protocol if running X11R5 */
72 #if (XtSpecificationRelease >= 5)
74 extern void _XEditResCheckMessages ();
75 #endif /* R5 + Athena */
77 /* Unique id counter for widgets created by the Lucid Widget
79 extern LWLIB_ID widget_id_tick
;
81 /* This is part of a kludge--see lwlib/xlwmenu.c. */
82 XFontStruct
*xlwmenu_default_font
;
84 extern void free_frame_menubar ();
85 #endif /* USE_X_TOOLKIT */
87 #define min(a,b) ((a) < (b) ? (a) : (b))
88 #define max(a,b) ((a) > (b) ? (a) : (b))
91 #define MAXREQUEST(dpy) (XMaxRequestSize (dpy))
93 #define MAXREQUEST(dpy) ((dpy)->max_request_size)
96 /* The name we're using in resource queries. */
97 Lisp_Object Vx_resource_name
;
99 /* The background and shape of the mouse pointer, and shape when not
100 over text or in the modeline. */
101 Lisp_Object Vx_pointer_shape
, Vx_nontext_pointer_shape
, Vx_mode_pointer_shape
;
102 /* The shape when over mouse-sensitive text. */
103 Lisp_Object Vx_sensitive_text_pointer_shape
;
105 /* Color of chars displayed in cursor box. */
106 Lisp_Object Vx_cursor_fore_pixel
;
108 /* Nonzero if using X. */
111 /* Non nil if no window manager is in use. */
112 Lisp_Object Vx_no_window_manager
;
114 /* Search path for bitmap files. */
115 Lisp_Object Vx_bitmap_file_path
;
117 /* Evaluate this expression to rebuild the section of syms_of_xfns
118 that initializes and staticpros the symbols declared below. Note
119 that Emacs 18 has a bug that keeps C-x C-e from being able to
120 evaluate this expression.
123 ;; Accumulate a list of the symbols we want to initialize from the
124 ;; declarations at the top of the file.
125 (goto-char (point-min))
126 (search-forward "/\*&&& symbols declared here &&&*\/\n")
128 (while (looking-at "Lisp_Object \\(Q[a-z_]+\\)")
130 (cons (buffer-substring (match-beginning 1) (match-end 1))
133 (setq symbol-list (nreverse symbol-list))
134 ;; Delete the section of syms_of_... where we initialize the symbols.
135 (search-forward "\n /\*&&& init symbols here &&&*\/\n")
136 (let ((start (point)))
137 (while (looking-at "^ Q")
139 (kill-region start (point)))
140 ;; Write a new symbol initialization section.
142 (insert (format " %s = intern (\"" (car symbol-list)))
143 (let ((start (point)))
144 (insert (substring (car symbol-list) 1))
145 (subst-char-in-region start (point) ?_ ?-))
146 (insert (format "\");\n staticpro (&%s);\n" (car symbol-list)))
147 (setq symbol-list (cdr symbol-list)))))
151 /*&&& symbols declared here &&&*/
152 Lisp_Object Qauto_raise
;
153 Lisp_Object Qauto_lower
;
154 Lisp_Object Qbackground_color
;
156 Lisp_Object Qborder_color
;
157 Lisp_Object Qborder_width
;
159 Lisp_Object Qcursor_color
;
160 Lisp_Object Qcursor_type
;
162 Lisp_Object Qforeground_color
;
163 Lisp_Object Qgeometry
;
164 Lisp_Object Qicon_left
;
165 Lisp_Object Qicon_top
;
166 Lisp_Object Qicon_type
;
167 Lisp_Object Qinternal_border_width
;
169 Lisp_Object Qmouse_color
;
171 Lisp_Object Qparent_id
;
172 Lisp_Object Qscroll_bar_width
;
173 Lisp_Object Qsuppress_icon
;
175 Lisp_Object Qundefined_color
;
176 Lisp_Object Qvertical_scroll_bars
;
177 Lisp_Object Qvisibility
;
178 Lisp_Object Qwindow_id
;
179 Lisp_Object Qx_frame_parameter
;
180 Lisp_Object Qx_resource_name
;
181 Lisp_Object Quser_position
;
182 Lisp_Object Quser_size
;
183 Lisp_Object Qdisplay
;
185 /* The below are defined in frame.c. */
186 extern Lisp_Object Qheight
, Qminibuffer
, Qname
, Qonly
, Qwidth
;
187 extern Lisp_Object Qunsplittable
, Qmenu_bar_lines
;
189 extern Lisp_Object Vwindow_system_version
;
192 /* Error if we are not connected to X. */
197 error ("X windows are not in use or not initialized");
200 /* Nonzero if using X for display. */
208 /* Extract a frame as a FRAME_PTR, defaulting to the selected frame
209 and checking validity for X. */
212 check_x_frame (frame
)
221 CHECK_LIVE_FRAME (frame
, 0);
225 error ("non-X frame used");
229 /* Let the user specify an X display with a frame.
230 nil stands for the selected frame--or, if that is not an X frame,
231 the first X display on the list. */
233 static struct x_display_info
*
234 check_x_display_info (frame
)
239 if (FRAME_X_P (selected_frame
))
240 return FRAME_X_DISPLAY_INFO (selected_frame
);
241 else if (x_display_list
!= 0)
242 return x_display_list
;
244 error ("X windows are not in use or not initialized");
246 else if (STRINGP (frame
))
247 return x_display_info_for_name (frame
);
252 CHECK_LIVE_FRAME (frame
, 0);
255 error ("non-X frame used");
256 return FRAME_X_DISPLAY_INFO (f
);
260 /* Return the Emacs frame-object corresponding to an X window.
261 It could be the frame's main window or an icon window. */
263 /* This function can be called during GC, so use GC_xxx type test macros. */
266 x_window_to_frame (wdesc
)
269 Lisp_Object tail
, frame
;
272 for (tail
= Vframe_list
; GC_CONSP (tail
); tail
= XCONS (tail
)->cdr
)
274 frame
= XCONS (tail
)->car
;
275 if (!GC_FRAMEP (frame
))
279 if (f
->display
.nothing
== 1)
281 if ((f
->display
.x
->edit_widget
282 && XtWindow (f
->display
.x
->edit_widget
) == wdesc
)
283 || f
->display
.x
->icon_desc
== wdesc
)
285 #else /* not USE_X_TOOLKIT */
286 if (FRAME_X_WINDOW (f
) == wdesc
287 || f
->display
.x
->icon_desc
== wdesc
)
289 #endif /* not USE_X_TOOLKIT */
295 /* Like x_window_to_frame but also compares the window with the widget's
299 x_any_window_to_frame (wdesc
)
302 Lisp_Object tail
, frame
;
306 for (tail
= Vframe_list
; GC_CONSP (tail
); tail
= XCONS (tail
)->cdr
)
308 frame
= XCONS (tail
)->car
;
309 if (!GC_FRAMEP (frame
))
312 if (f
->display
.nothing
== 1)
315 /* This frame matches if the window is any of its widgets. */
316 if (wdesc
== XtWindow (x
->widget
)
317 || wdesc
== XtWindow (x
->column_widget
)
318 || wdesc
== XtWindow (x
->edit_widget
))
320 /* Match if the window is this frame's menubar. */
321 if (lw_window_is_in_menubar (wdesc
, x
->menubar_widget
))
327 /* Return the frame whose principal (outermost) window is WDESC.
328 If WDESC is some other (smaller) window, we return 0. */
331 x_top_window_to_frame (wdesc
)
334 Lisp_Object tail
, frame
;
338 for (tail
= Vframe_list
; GC_CONSP (tail
); tail
= XCONS (tail
)->cdr
)
340 frame
= XCONS (tail
)->car
;
341 if (!GC_FRAMEP (frame
))
344 if (f
->display
.nothing
== 1)
347 /* This frame matches if the window is its topmost widget. */
348 if (wdesc
== XtWindow (x
->widget
))
350 /* Match if the window is this frame's menubar. */
351 if (x
->menubar_widget
352 && wdesc
== XtWindow (x
->menubar_widget
))
357 #endif /* USE_X_TOOLKIT */
361 /* Code to deal with bitmaps. Bitmaps are referenced by their bitmap
362 id, which is just an int that this section returns. Bitmaps are
363 reference counted so they can be shared among frames.
365 Bitmap indices are guaranteed to be > 0, so a negative number can
366 be used to indicate no bitmap.
368 If you use x_create_bitmap_from_data, then you must keep track of
369 the bitmaps yourself. That is, creating a bitmap from the same
370 data more than once will not be caught. */
373 /* Functions to access the contents of a bitmap, given an id. */
376 x_bitmap_height (f
, id
)
380 return FRAME_X_DISPLAY_INFO (f
)->bitmaps
[id
- 1].height
;
384 x_bitmap_width (f
, id
)
388 return FRAME_X_DISPLAY_INFO (f
)->bitmaps
[id
- 1].width
;
392 x_bitmap_pixmap (f
, id
)
396 return FRAME_X_DISPLAY_INFO (f
)->bitmaps
[id
- 1].pixmap
;
400 /* Allocate a new bitmap record. Returns index of new record. */
403 x_allocate_bitmap_record (f
)
406 struct x_display_info
*dpyinfo
= FRAME_X_DISPLAY_INFO (f
);
409 if (dpyinfo
->bitmaps
== NULL
)
411 dpyinfo
->bitmaps_size
= 10;
413 = (struct x_bitmap_record
*) xmalloc (dpyinfo
->bitmaps_size
* sizeof (struct x_bitmap_record
));
414 dpyinfo
->bitmaps_last
= 1;
418 if (dpyinfo
->bitmaps_last
< dpyinfo
->bitmaps_size
)
419 return ++dpyinfo
->bitmaps_last
;
421 for (i
= 0; i
< dpyinfo
->bitmaps_size
; ++i
)
422 if (dpyinfo
->bitmaps
[i
].refcount
== 0)
425 dpyinfo
->bitmaps_size
*= 2;
427 = (struct x_bitmap_record
*) xrealloc (dpyinfo
->bitmaps
,
428 dpyinfo
->bitmaps_size
* sizeof (struct x_bitmap_record
));
429 return ++dpyinfo
->bitmaps_last
;
432 /* Add one reference to the reference count of the bitmap with id ID. */
435 x_reference_bitmap (f
, id
)
439 ++FRAME_X_DISPLAY_INFO (f
)->bitmaps
[id
- 1].refcount
;
442 /* Create a bitmap for frame F from a HEIGHT x WIDTH array of bits at BITS. */
445 x_create_bitmap_from_data (f
, bits
, width
, height
)
448 unsigned int width
, height
;
450 struct x_display_info
*dpyinfo
= FRAME_X_DISPLAY_INFO (f
);
454 bitmap
= XCreateBitmapFromData (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
455 bits
, width
, height
);
460 id
= x_allocate_bitmap_record (f
);
461 dpyinfo
->bitmaps
[id
- 1].pixmap
= bitmap
;
462 dpyinfo
->bitmaps
[id
- 1].file
= NULL
;
463 dpyinfo
->bitmaps
[id
- 1].refcount
= 1;
464 dpyinfo
->bitmaps
[id
- 1].depth
= 1;
465 dpyinfo
->bitmaps
[id
- 1].height
= height
;
466 dpyinfo
->bitmaps
[id
- 1].width
= width
;
471 /* Create bitmap from file FILE for frame F. */
474 x_create_bitmap_from_file (f
, file
)
478 struct x_display_info
*dpyinfo
= FRAME_X_DISPLAY_INFO (f
);
479 unsigned int width
, height
;
481 int xhot
, yhot
, result
, id
;
486 /* Look for an existing bitmap with the same name. */
487 for (id
= 0; id
< dpyinfo
->bitmaps_last
; ++id
)
489 if (dpyinfo
->bitmaps
[id
].refcount
490 && dpyinfo
->bitmaps
[id
].file
491 && !strcmp (dpyinfo
->bitmaps
[id
].file
, (char *) XSTRING (file
)->data
))
493 ++dpyinfo
->bitmaps
[id
].refcount
;
498 /* Search bitmap-file-path for the file, if appropriate. */
499 fd
= openp (Vx_bitmap_file_path
, file
, "", &found
, 0);
504 filename
= (char *) XSTRING (found
)->data
;
506 result
= XReadBitmapFile (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
507 filename
, &width
, &height
, &bitmap
, &xhot
, &yhot
);
508 if (result
!= BitmapSuccess
)
511 id
= x_allocate_bitmap_record (f
);
512 dpyinfo
->bitmaps
[id
- 1].pixmap
= bitmap
;
513 dpyinfo
->bitmaps
[id
- 1].refcount
= 1;
514 dpyinfo
->bitmaps
[id
- 1].file
= (char *) xmalloc (XSTRING (file
)->size
+ 1);
515 dpyinfo
->bitmaps
[id
- 1].depth
= 1;
516 dpyinfo
->bitmaps
[id
- 1].height
= height
;
517 dpyinfo
->bitmaps
[id
- 1].width
= width
;
518 strcpy (dpyinfo
->bitmaps
[id
- 1].file
, XSTRING (file
)->data
);
523 /* Remove reference to bitmap with id number ID. */
526 x_destroy_bitmap (f
, id
)
530 struct x_display_info
*dpyinfo
= FRAME_X_DISPLAY_INFO (f
);
534 --dpyinfo
->bitmaps
[id
- 1].refcount
;
535 if (dpyinfo
->bitmaps
[id
- 1].refcount
== 0)
537 XFreePixmap (FRAME_X_DISPLAY (f
), dpyinfo
->bitmaps
[id
- 1].pixmap
);
538 if (dpyinfo
->bitmaps
[id
- 1].file
)
540 free (dpyinfo
->bitmaps
[id
- 1].file
);
541 dpyinfo
->bitmaps
[id
- 1].file
= NULL
;
547 /* Free all the bitmaps for the display specified by DPYINFO. */
550 x_destroy_all_bitmaps (dpyinfo
)
551 struct x_display_info
*dpyinfo
;
554 for (i
= 0; i
< dpyinfo
->bitmaps_last
; i
++)
555 if (dpyinfo
->bitmaps
[i
].refcount
> 0)
557 XFreePixmap (dpyinfo
->display
, dpyinfo
->bitmaps
[i
].pixmap
);
558 if (dpyinfo
->bitmaps
[i
].file
)
559 free (dpyinfo
->bitmaps
[i
].file
);
561 dpyinfo
->bitmaps_last
= 0;
564 /* Connect the frame-parameter names for X frames
565 to the ways of passing the parameter values to the window system.
567 The name of a parameter, as a Lisp symbol,
568 has an `x-frame-parameter' property which is an integer in Lisp
569 but can be interpreted as an `enum x_frame_parm' in C. */
573 X_PARM_FOREGROUND_COLOR
,
574 X_PARM_BACKGROUND_COLOR
,
581 X_PARM_INTERNAL_BORDER_WIDTH
,
585 X_PARM_VERT_SCROLL_BAR
,
587 X_PARM_MENU_BAR_LINES
591 struct x_frame_parm_table
594 void (*setter
)( /* struct frame *frame, Lisp_Object val, oldval */ );
597 void x_set_foreground_color ();
598 void x_set_background_color ();
599 void x_set_mouse_color ();
600 void x_set_cursor_color ();
601 void x_set_border_color ();
602 void x_set_cursor_type ();
603 void x_set_icon_type ();
605 void x_set_border_width ();
606 void x_set_internal_border_width ();
607 void x_explicitly_set_name ();
608 void x_set_autoraise ();
609 void x_set_autolower ();
610 void x_set_vertical_scroll_bars ();
611 void x_set_visibility ();
612 void x_set_menu_bar_lines ();
613 void x_set_scroll_bar_width ();
614 void x_set_unsplittable ();
616 static struct x_frame_parm_table x_frame_parms
[] =
618 "foreground-color", x_set_foreground_color
,
619 "background-color", x_set_background_color
,
620 "mouse-color", x_set_mouse_color
,
621 "cursor-color", x_set_cursor_color
,
622 "border-color", x_set_border_color
,
623 "cursor-type", x_set_cursor_type
,
624 "icon-type", x_set_icon_type
,
626 "border-width", x_set_border_width
,
627 "internal-border-width", x_set_internal_border_width
,
628 "name", x_explicitly_set_name
,
629 "auto-raise", x_set_autoraise
,
630 "auto-lower", x_set_autolower
,
631 "vertical-scroll-bars", x_set_vertical_scroll_bars
,
632 "visibility", x_set_visibility
,
633 "menu-bar-lines", x_set_menu_bar_lines
,
634 "scroll-bar-width", x_set_scroll_bar_width
,
635 "unsplittable", x_set_unsplittable
,
638 /* Attach the `x-frame-parameter' properties to
639 the Lisp symbol names of parameters relevant to X. */
641 init_x_parm_symbols ()
645 for (i
= 0; i
< sizeof (x_frame_parms
) / sizeof (x_frame_parms
[0]); i
++)
646 Fput (intern (x_frame_parms
[i
].name
), Qx_frame_parameter
,
650 /* Change the parameters of FRAME as specified by ALIST.
651 If a parameter is not specially recognized, do nothing;
652 otherwise call the `x_set_...' function for that parameter. */
655 x_set_frame_parameters (f
, alist
)
661 /* If both of these parameters are present, it's more efficient to
662 set them both at once. So we wait until we've looked at the
663 entire list before we set them. */
664 Lisp_Object width
, height
;
667 Lisp_Object left
, top
;
669 /* Same with these. */
670 Lisp_Object icon_left
, icon_top
;
672 /* Record in these vectors all the parms specified. */
676 int left_no_change
= 0, top_no_change
= 0;
677 int icon_left_no_change
= 0, icon_top_no_change
= 0;
680 for (tail
= alist
; CONSP (tail
); tail
= Fcdr (tail
))
683 parms
= (Lisp_Object
*) alloca (i
* sizeof (Lisp_Object
));
684 values
= (Lisp_Object
*) alloca (i
* sizeof (Lisp_Object
));
686 /* Extract parm names and values into those vectors. */
689 for (tail
= alist
; CONSP (tail
); tail
= Fcdr (tail
))
691 Lisp_Object elt
, prop
, val
;
694 parms
[i
] = Fcar (elt
);
695 values
[i
] = Fcdr (elt
);
699 width
= height
= top
= left
= Qunbound
;
700 icon_left
= icon_top
= Qunbound
;
702 /* Now process them in reverse of specified order. */
703 for (i
--; i
>= 0; i
--)
705 Lisp_Object prop
, val
;
710 if (EQ (prop
, Qwidth
))
712 else if (EQ (prop
, Qheight
))
714 else if (EQ (prop
, Qtop
))
716 else if (EQ (prop
, Qleft
))
718 else if (EQ (prop
, Qicon_top
))
720 else if (EQ (prop
, Qicon_left
))
724 register Lisp_Object param_index
, old_value
;
726 param_index
= Fget (prop
, Qx_frame_parameter
);
727 old_value
= get_frame_param (f
, prop
);
728 store_frame_param (f
, prop
, val
);
729 if (NATNUMP (param_index
)
730 && (XFASTINT (param_index
)
731 < sizeof (x_frame_parms
)/sizeof (x_frame_parms
[0])))
732 (*x_frame_parms
[XINT (param_index
)].setter
)(f
, val
, old_value
);
736 /* Don't die if just one of these was set. */
737 if (EQ (left
, Qunbound
))
740 if (f
->display
.x
->left_pos
< 0)
741 left
= Fcons (Qplus
, Fcons (make_number (f
->display
.x
->left_pos
), Qnil
));
743 XSETINT (left
, f
->display
.x
->left_pos
);
745 if (EQ (top
, Qunbound
))
748 if (f
->display
.x
->top_pos
< 0)
749 top
= Fcons (Qplus
, Fcons (make_number (f
->display
.x
->top_pos
), Qnil
));
751 XSETINT (top
, f
->display
.x
->top_pos
);
754 /* If one of the icon positions was not set, preserve or default it. */
755 if (EQ (icon_left
, Qunbound
) || ! INTEGERP (icon_left
))
757 icon_left_no_change
= 1;
758 icon_left
= Fcdr (Fassq (Qicon_left
, f
->param_alist
));
759 if (NILP (icon_left
))
760 XSETINT (icon_left
, 0);
762 if (EQ (icon_top
, Qunbound
) || ! INTEGERP (icon_top
))
764 icon_top_no_change
= 1;
765 icon_top
= Fcdr (Fassq (Qicon_top
, f
->param_alist
));
767 XSETINT (icon_top
, 0);
770 /* Don't die if just one of these was set. */
771 if (EQ (width
, Qunbound
))
772 XSETINT (width
, FRAME_WIDTH (f
));
773 if (EQ (height
, Qunbound
))
774 XSETINT (height
, FRAME_HEIGHT (f
));
776 /* Don't set these parameters these unless they've been explicitly
777 specified. The window might be mapped or resized while we're in
778 this function, and we don't want to override that unless the lisp
779 code has asked for it.
781 Don't set these parameters unless they actually differ from the
782 window's current parameters; the window may not actually exist
787 check_frame_size (f
, &height
, &width
);
789 XSETFRAME (frame
, f
);
791 if ((NUMBERP (width
) && XINT (width
) != FRAME_WIDTH (f
))
792 || (NUMBERP (height
) && XINT (height
) != FRAME_HEIGHT (f
)))
793 Fset_frame_size (frame
, width
, height
);
795 if ((!NILP (left
) || !NILP (top
))
796 && ! (left_no_change
&& top_no_change
)
797 && ! (NUMBERP (left
) && XINT (left
) == f
->display
.x
->left_pos
798 && NUMBERP (top
) && XINT (top
) == f
->display
.x
->top_pos
))
803 /* Record the signs. */
804 f
->display
.x
->size_hint_flags
&= ~ (XNegative
| YNegative
);
805 if (EQ (left
, Qminus
))
806 f
->display
.x
->size_hint_flags
|= XNegative
;
807 else if (INTEGERP (left
))
809 leftpos
= XINT (left
);
811 f
->display
.x
->size_hint_flags
|= XNegative
;
813 else if (CONSP (left
) && EQ (XCONS (left
)->car
, Qminus
)
814 && CONSP (XCONS (left
)->cdr
)
815 && INTEGERP (XCONS (XCONS (left
)->cdr
)->car
))
817 leftpos
= - XINT (XCONS (XCONS (left
)->cdr
)->car
);
818 f
->display
.x
->size_hint_flags
|= XNegative
;
820 else if (CONSP (left
) && EQ (XCONS (left
)->car
, Qplus
)
821 && CONSP (XCONS (left
)->cdr
)
822 && INTEGERP (XCONS (XCONS (left
)->cdr
)->car
))
824 leftpos
= XINT (XCONS (XCONS (left
)->cdr
)->car
);
827 if (EQ (top
, Qminus
))
828 f
->display
.x
->size_hint_flags
|= YNegative
;
829 else if (INTEGERP (top
))
833 f
->display
.x
->size_hint_flags
|= YNegative
;
835 else if (CONSP (top
) && EQ (XCONS (top
)->car
, Qminus
)
836 && CONSP (XCONS (top
)->cdr
)
837 && INTEGERP (XCONS (XCONS (top
)->cdr
)->car
))
839 toppos
= - XINT (XCONS (XCONS (top
)->cdr
)->car
);
840 f
->display
.x
->size_hint_flags
|= YNegative
;
842 else if (CONSP (top
) && EQ (XCONS (top
)->car
, Qplus
)
843 && CONSP (XCONS (top
)->cdr
)
844 && INTEGERP (XCONS (XCONS (top
)->cdr
)->car
))
846 toppos
= XINT (XCONS (XCONS (top
)->cdr
)->car
);
850 /* Store the numeric value of the position. */
851 f
->display
.x
->top_pos
= toppos
;
852 f
->display
.x
->left_pos
= leftpos
;
854 f
->display
.x
->win_gravity
= NorthWestGravity
;
856 /* Actually set that position, and convert to absolute. */
857 x_set_offset (f
, leftpos
, toppos
, 0);
860 if ((!NILP (icon_left
) || !NILP (icon_top
))
861 && ! (icon_left_no_change
&& icon_top_no_change
))
862 x_wm_set_icon_position (f
, XINT (icon_left
), XINT (icon_top
));
866 /* Store the screen positions of frame F into XPTR and YPTR.
867 These are the positions of the containing window manager window,
868 not Emacs's own window. */
871 x_real_positions (f
, xptr
, yptr
)
878 /* This is pretty gross, but seems to be the easiest way out of
879 the problem that arises when restarting window-managers. */
882 Window outer
= XtWindow (f
->display
.x
->widget
);
884 Window outer
= f
->display
.x
->window_desc
;
886 Window tmp_root_window
;
887 Window
*tmp_children
;
890 x_catch_errors (FRAME_X_DISPLAY (f
));
893 XQueryTree (FRAME_X_DISPLAY (f
), outer
, &tmp_root_window
,
894 &f
->display
.x
->parent_desc
,
895 &tmp_children
, &tmp_nchildren
);
896 xfree (tmp_children
);
900 /* Find the position of the outside upper-left corner of
901 the inner window, with respect to the outer window. */
902 if (f
->display
.x
->parent_desc
!= FRAME_X_DISPLAY_INFO (f
)->root_window
)
904 XTranslateCoordinates (FRAME_X_DISPLAY (f
),
906 /* From-window, to-window. */
908 XtWindow (f
->display
.x
->widget
),
910 f
->display
.x
->window_desc
,
912 f
->display
.x
->parent_desc
,
914 /* From-position, to-position. */
915 0, 0, &win_x
, &win_y
,
920 win_x
+= f
->display
.x
->border_width
;
921 win_y
+= f
->display
.x
->border_width
;
924 /* It is possible for the window returned by the XQueryNotify
925 to become invalid by the time we call XTranslateCoordinates.
926 That can happen when you restart some window managers.
927 If so, we get an error in XTranslateCoordinates.
928 Detect that and try the whole thing over. */
929 if (! x_had_errors_p (FRAME_X_DISPLAY (f
)))
933 x_uncatch_errors (FRAME_X_DISPLAY (f
));
935 *xptr
= f
->display
.x
->left_pos
- win_x
;
936 *yptr
= f
->display
.x
->top_pos
- win_y
;
939 /* Insert a description of internally-recorded parameters of frame X
940 into the parameter alist *ALISTPTR that is to be given to the user.
941 Only parameters that are specific to the X window system
942 and whose values are not correctly recorded in the frame's
943 param_alist need to be considered here. */
945 x_report_frame_params (f
, alistptr
)
947 Lisp_Object
*alistptr
;
951 store_in_alist (alistptr
, Qleft
, make_number (f
->display
.x
->left_pos
));
952 store_in_alist (alistptr
, Qtop
, make_number (f
->display
.x
->top_pos
));
953 store_in_alist (alistptr
, Qborder_width
,
954 make_number (f
->display
.x
->border_width
));
955 store_in_alist (alistptr
, Qinternal_border_width
,
956 make_number (f
->display
.x
->internal_border_width
));
957 sprintf (buf
, "%ld", (long) FRAME_X_WINDOW (f
));
958 store_in_alist (alistptr
, Qwindow_id
,
960 FRAME_SAMPLE_VISIBILITY (f
);
961 store_in_alist (alistptr
, Qvisibility
,
962 (FRAME_VISIBLE_P (f
) ? Qt
963 : FRAME_ICONIFIED_P (f
) ? Qicon
: Qnil
));
967 /* Decide if color named COLOR is valid for the display associated with
968 the selected frame; if so, return the rgb values in COLOR_DEF.
969 If ALLOC is nonzero, allocate a new colormap cell. */
972 defined_color (f
, color
, color_def
, alloc
)
979 Colormap screen_colormap
;
980 Display
*display
= FRAME_X_DISPLAY (f
);
983 screen_colormap
= DefaultColormap (display
, XDefaultScreen (display
));
985 status
= XParseColor (display
, screen_colormap
, color
, color_def
);
988 status
= XAllocColor (display
, screen_colormap
, color_def
);
991 /* If we got to this point, the colormap is full, so we're
992 going to try and get the next closest color.
993 The algorithm used is a least-squares matching, which is
994 what X uses for closest color matching with StaticColor visuals. */
999 long nearest_delta
, trial_delta
;
1002 no_cells
= XDisplayCells (display
, XDefaultScreen (display
));
1003 cells
= (XColor
*) alloca (sizeof (XColor
) * no_cells
);
1005 for (x
= 0; x
< no_cells
; x
++)
1008 XQueryColors (display
, screen_colormap
, cells
, no_cells
);
1010 /* I'm assuming CSE so I'm not going to condense this. */
1011 nearest_delta
= ((((color_def
->red
>> 8) - (cells
[0].red
>> 8))
1012 * ((color_def
->red
>> 8) - (cells
[0].red
>> 8)))
1014 (((color_def
->green
>> 8) - (cells
[0].green
>> 8))
1015 * ((color_def
->green
>> 8) - (cells
[0].green
>> 8)))
1017 (((color_def
->blue
>> 8) - (cells
[0].blue
>> 8))
1018 * ((color_def
->blue
>> 8) - (cells
[0].blue
>> 8))));
1019 for (x
= 1; x
< no_cells
; x
++)
1021 trial_delta
= ((((color_def
->red
>> 8) - (cells
[x
].red
>> 8))
1022 * ((color_def
->red
>> 8) - (cells
[x
].red
>> 8)))
1024 (((color_def
->green
>> 8) - (cells
[x
].green
>> 8))
1025 * ((color_def
->green
>> 8) - (cells
[x
].green
>> 8))) +
1027 (((color_def
->blue
>> 8) - (cells
[x
].blue
>> 8))
1028 * ((color_def
->blue
>> 8) - (cells
[x
].blue
>> 8))));
1029 if (trial_delta
< nearest_delta
)
1032 nearest_delta
= trial_delta
;
1035 color_def
->red
= cells
[nearest
].red
;
1036 color_def
->green
= cells
[nearest
].green
;
1037 color_def
->blue
= cells
[nearest
].blue
;
1038 status
= XAllocColor (display
, screen_colormap
, color_def
);
1049 /* Given a string ARG naming a color, compute a pixel value from it
1050 suitable for screen F.
1051 If F is not a color screen, return DEF (default) regardless of what
1055 x_decode_color (f
, arg
, def
)
1062 CHECK_STRING (arg
, 0);
1064 if (strcmp (XSTRING (arg
)->data
, "black") == 0)
1065 return BLACK_PIX_DEFAULT (f
);
1066 else if (strcmp (XSTRING (arg
)->data
, "white") == 0)
1067 return WHITE_PIX_DEFAULT (f
);
1069 if (FRAME_X_DISPLAY_INFO (f
)->n_planes
== 1)
1072 /* Ignore the return value of defined_color so that
1073 we use a color close to the one requested
1074 if we can't get the exact request. */
1075 defined_color (f
, XSTRING (arg
)->data
, &cdef
, 1);
1079 /* Functions called only from `x_set_frame_param'
1080 to set individual parameters.
1082 If FRAME_X_WINDOW (f) is 0,
1083 the frame is being created and its X-window does not exist yet.
1084 In that case, just record the parameter's new value
1085 in the standard place; do not attempt to change the window. */
1088 x_set_foreground_color (f
, arg
, oldval
)
1090 Lisp_Object arg
, oldval
;
1092 f
->display
.x
->foreground_pixel
1093 = x_decode_color (f
, arg
, BLACK_PIX_DEFAULT (f
));
1094 if (FRAME_X_WINDOW (f
) != 0)
1097 XSetForeground (FRAME_X_DISPLAY (f
), f
->display
.x
->normal_gc
,
1098 f
->display
.x
->foreground_pixel
);
1099 XSetBackground (FRAME_X_DISPLAY (f
), f
->display
.x
->reverse_gc
,
1100 f
->display
.x
->foreground_pixel
);
1102 recompute_basic_faces (f
);
1103 if (FRAME_VISIBLE_P (f
))
1109 x_set_background_color (f
, arg
, oldval
)
1111 Lisp_Object arg
, oldval
;
1116 f
->display
.x
->background_pixel
1117 = x_decode_color (f
, arg
, WHITE_PIX_DEFAULT (f
));
1119 if (FRAME_X_WINDOW (f
) != 0)
1122 /* The main frame area. */
1123 XSetBackground (FRAME_X_DISPLAY (f
), f
->display
.x
->normal_gc
,
1124 f
->display
.x
->background_pixel
);
1125 XSetForeground (FRAME_X_DISPLAY (f
), f
->display
.x
->reverse_gc
,
1126 f
->display
.x
->background_pixel
);
1127 XSetForeground (FRAME_X_DISPLAY (f
), f
->display
.x
->cursor_gc
,
1128 f
->display
.x
->background_pixel
);
1129 XSetWindowBackground (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
1130 f
->display
.x
->background_pixel
);
1133 for (bar
= FRAME_SCROLL_BARS (f
); !NILP (bar
);
1134 bar
= XSCROLL_BAR (bar
)->next
)
1135 XSetWindowBackground (FRAME_X_DISPLAY (f
),
1136 SCROLL_BAR_X_WINDOW (XSCROLL_BAR (bar
)),
1137 f
->display
.x
->background_pixel
);
1141 recompute_basic_faces (f
);
1143 if (FRAME_VISIBLE_P (f
))
1149 x_set_mouse_color (f
, arg
, oldval
)
1151 Lisp_Object arg
, oldval
;
1153 Cursor cursor
, nontext_cursor
, mode_cursor
, cross_cursor
;
1156 if (!EQ (Qnil
, arg
))
1157 f
->display
.x
->mouse_pixel
1158 = x_decode_color (f
, arg
, BLACK_PIX_DEFAULT (f
));
1159 mask_color
= f
->display
.x
->background_pixel
;
1160 /* No invisible pointers. */
1161 if (mask_color
== f
->display
.x
->mouse_pixel
1162 && mask_color
== f
->display
.x
->background_pixel
)
1163 f
->display
.x
->mouse_pixel
= f
->display
.x
->foreground_pixel
;
1167 /* It's not okay to crash if the user selects a screwy cursor. */
1168 x_catch_errors (FRAME_X_DISPLAY (f
));
1170 if (!EQ (Qnil
, Vx_pointer_shape
))
1172 CHECK_NUMBER (Vx_pointer_shape
, 0);
1173 cursor
= XCreateFontCursor (FRAME_X_DISPLAY (f
), XINT (Vx_pointer_shape
));
1176 cursor
= XCreateFontCursor (FRAME_X_DISPLAY (f
), XC_xterm
);
1177 x_check_errors (FRAME_X_DISPLAY (f
), "bad text pointer cursor: %s");
1179 if (!EQ (Qnil
, Vx_nontext_pointer_shape
))
1181 CHECK_NUMBER (Vx_nontext_pointer_shape
, 0);
1182 nontext_cursor
= XCreateFontCursor (FRAME_X_DISPLAY (f
),
1183 XINT (Vx_nontext_pointer_shape
));
1186 nontext_cursor
= XCreateFontCursor (FRAME_X_DISPLAY (f
), XC_left_ptr
);
1187 x_check_errors (FRAME_X_DISPLAY (f
), "bad nontext pointer cursor: %s");
1189 if (!EQ (Qnil
, Vx_mode_pointer_shape
))
1191 CHECK_NUMBER (Vx_mode_pointer_shape
, 0);
1192 mode_cursor
= XCreateFontCursor (FRAME_X_DISPLAY (f
),
1193 XINT (Vx_mode_pointer_shape
));
1196 mode_cursor
= XCreateFontCursor (FRAME_X_DISPLAY (f
), XC_xterm
);
1197 x_check_errors (FRAME_X_DISPLAY (f
), "bad modeline pointer cursor: %s");
1199 if (!EQ (Qnil
, Vx_sensitive_text_pointer_shape
))
1201 CHECK_NUMBER (Vx_sensitive_text_pointer_shape
, 0);
1203 = XCreateFontCursor (FRAME_X_DISPLAY (f
),
1204 XINT (Vx_sensitive_text_pointer_shape
));
1207 cross_cursor
= XCreateFontCursor (FRAME_X_DISPLAY (f
), XC_crosshair
);
1209 /* Check and report errors with the above calls. */
1210 x_check_errors (FRAME_X_DISPLAY (f
), "can't set cursor shape: %s");
1211 x_uncatch_errors (FRAME_X_DISPLAY (f
));
1214 XColor fore_color
, back_color
;
1216 fore_color
.pixel
= f
->display
.x
->mouse_pixel
;
1217 back_color
.pixel
= mask_color
;
1218 XQueryColor (FRAME_X_DISPLAY (f
),
1219 DefaultColormap (FRAME_X_DISPLAY (f
),
1220 DefaultScreen (FRAME_X_DISPLAY (f
))),
1222 XQueryColor (FRAME_X_DISPLAY (f
),
1223 DefaultColormap (FRAME_X_DISPLAY (f
),
1224 DefaultScreen (FRAME_X_DISPLAY (f
))),
1226 XRecolorCursor (FRAME_X_DISPLAY (f
), cursor
,
1227 &fore_color
, &back_color
);
1228 XRecolorCursor (FRAME_X_DISPLAY (f
), nontext_cursor
,
1229 &fore_color
, &back_color
);
1230 XRecolorCursor (FRAME_X_DISPLAY (f
), mode_cursor
,
1231 &fore_color
, &back_color
);
1232 XRecolorCursor (FRAME_X_DISPLAY (f
), cross_cursor
,
1233 &fore_color
, &back_color
);
1236 if (FRAME_X_WINDOW (f
) != 0)
1238 XDefineCursor (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
), cursor
);
1241 if (cursor
!= f
->display
.x
->text_cursor
&& f
->display
.x
->text_cursor
!= 0)
1242 XFreeCursor (FRAME_X_DISPLAY (f
), f
->display
.x
->text_cursor
);
1243 f
->display
.x
->text_cursor
= cursor
;
1245 if (nontext_cursor
!= f
->display
.x
->nontext_cursor
1246 && f
->display
.x
->nontext_cursor
!= 0)
1247 XFreeCursor (FRAME_X_DISPLAY (f
), f
->display
.x
->nontext_cursor
);
1248 f
->display
.x
->nontext_cursor
= nontext_cursor
;
1250 if (mode_cursor
!= f
->display
.x
->modeline_cursor
1251 && f
->display
.x
->modeline_cursor
!= 0)
1252 XFreeCursor (FRAME_X_DISPLAY (f
), f
->display
.x
->modeline_cursor
);
1253 f
->display
.x
->modeline_cursor
= mode_cursor
;
1254 if (cross_cursor
!= f
->display
.x
->cross_cursor
1255 && f
->display
.x
->cross_cursor
!= 0)
1256 XFreeCursor (FRAME_X_DISPLAY (f
), f
->display
.x
->cross_cursor
);
1257 f
->display
.x
->cross_cursor
= cross_cursor
;
1259 XFlush (FRAME_X_DISPLAY (f
));
1264 x_set_cursor_color (f
, arg
, oldval
)
1266 Lisp_Object arg
, oldval
;
1268 unsigned long fore_pixel
;
1270 if (!EQ (Vx_cursor_fore_pixel
, Qnil
))
1271 fore_pixel
= x_decode_color (f
, Vx_cursor_fore_pixel
,
1272 WHITE_PIX_DEFAULT (f
));
1274 fore_pixel
= f
->display
.x
->background_pixel
;
1275 f
->display
.x
->cursor_pixel
= x_decode_color (f
, arg
, BLACK_PIX_DEFAULT (f
));
1277 /* Make sure that the cursor color differs from the background color. */
1278 if (f
->display
.x
->cursor_pixel
== f
->display
.x
->background_pixel
)
1280 f
->display
.x
->cursor_pixel
= f
->display
.x
->mouse_pixel
;
1281 if (f
->display
.x
->cursor_pixel
== fore_pixel
)
1282 fore_pixel
= f
->display
.x
->background_pixel
;
1284 f
->display
.x
->cursor_foreground_pixel
= fore_pixel
;
1286 if (FRAME_X_WINDOW (f
) != 0)
1289 XSetBackground (FRAME_X_DISPLAY (f
), f
->display
.x
->cursor_gc
,
1290 f
->display
.x
->cursor_pixel
);
1291 XSetForeground (FRAME_X_DISPLAY (f
), f
->display
.x
->cursor_gc
,
1295 if (FRAME_VISIBLE_P (f
))
1297 x_display_cursor (f
, 0);
1298 x_display_cursor (f
, 1);
1303 /* Set the border-color of frame F to value described by ARG.
1304 ARG can be a string naming a color.
1305 The border-color is used for the border that is drawn by the X server.
1306 Note that this does not fully take effect if done before
1307 F has an x-window; it must be redone when the window is created.
1309 Note: this is done in two routines because of the way X10 works.
1311 Note: under X11, this is normally the province of the window manager,
1312 and so emacs' border colors may be overridden. */
1315 x_set_border_color (f
, arg
, oldval
)
1317 Lisp_Object arg
, oldval
;
1322 CHECK_STRING (arg
, 0);
1323 str
= XSTRING (arg
)->data
;
1325 pix
= x_decode_color (f
, arg
, BLACK_PIX_DEFAULT (f
));
1327 x_set_border_pixel (f
, pix
);
1330 /* Set the border-color of frame F to pixel value PIX.
1331 Note that this does not fully take effect if done before
1332 F has an x-window. */
1334 x_set_border_pixel (f
, pix
)
1338 f
->display
.x
->border_pixel
= pix
;
1340 if (FRAME_X_WINDOW (f
) != 0 && f
->display
.x
->border_width
> 0)
1346 XSetWindowBorder (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
1350 if (FRAME_VISIBLE_P (f
))
1356 x_set_cursor_type (f
, arg
, oldval
)
1358 Lisp_Object arg
, oldval
;
1362 FRAME_DESIRED_CURSOR (f
) = bar_cursor
;
1363 f
->display
.x
->cursor_width
= 2;
1365 else if (CONSP (arg
) && EQ (XCONS (arg
)->car
, Qbar
)
1366 && INTEGERP (XCONS (arg
)->cdr
))
1368 FRAME_DESIRED_CURSOR (f
) = bar_cursor
;
1369 f
->display
.x
->cursor_width
= XINT (XCONS (arg
)->cdr
);
1372 /* Treat anything unknown as "box cursor".
1373 It was bad to signal an error; people have trouble fixing
1374 .Xdefaults with Emacs, when it has something bad in it. */
1375 FRAME_DESIRED_CURSOR (f
) = filled_box_cursor
;
1377 /* Make sure the cursor gets redrawn. This is overkill, but how
1378 often do people change cursor types? */
1379 update_mode_lines
++;
1383 x_set_icon_type (f
, arg
, oldval
)
1385 Lisp_Object arg
, oldval
;
1392 if (STRINGP (oldval
) && EQ (Fstring_equal (oldval
, arg
), Qt
))
1395 else if (!STRINGP (oldval
) && EQ (oldval
, Qnil
) == EQ (arg
, Qnil
))
1400 result
= x_text_icon (f
, 0);
1402 result
= x_bitmap_icon (f
, arg
);
1407 error ("No icon window available");
1410 /* If the window was unmapped (and its icon was mapped),
1411 the new icon is not mapped, so map the window in its stead. */
1412 if (FRAME_VISIBLE_P (f
))
1414 #ifdef USE_X_TOOLKIT
1415 XtPopup (f
->display
.x
->widget
, XtGrabNone
);
1417 XMapWindow (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
));
1420 XFlush (FRAME_X_DISPLAY (f
));
1424 /* Return non-nil if frame F wants a bitmap icon. */
1432 tem
= assq_no_quit (Qicon_type
, f
->param_alist
);
1434 return XCONS (tem
)->cdr
;
1439 extern Lisp_Object
x_new_font ();
1442 x_set_font (f
, arg
, oldval
)
1444 Lisp_Object arg
, oldval
;
1448 CHECK_STRING (arg
, 1);
1451 result
= x_new_font (f
, XSTRING (arg
)->data
);
1454 if (EQ (result
, Qnil
))
1455 error ("Font \"%s\" is not defined", XSTRING (arg
)->data
);
1456 else if (EQ (result
, Qt
))
1457 error ("the characters of the given font have varying widths");
1458 else if (STRINGP (result
))
1460 recompute_basic_faces (f
);
1461 store_frame_param (f
, Qfont
, result
);
1468 x_set_border_width (f
, arg
, oldval
)
1470 Lisp_Object arg
, oldval
;
1472 CHECK_NUMBER (arg
, 0);
1474 if (XINT (arg
) == f
->display
.x
->border_width
)
1477 if (FRAME_X_WINDOW (f
) != 0)
1478 error ("Cannot change the border width of a window");
1480 f
->display
.x
->border_width
= XINT (arg
);
1484 x_set_internal_border_width (f
, arg
, oldval
)
1486 Lisp_Object arg
, oldval
;
1489 int old
= f
->display
.x
->internal_border_width
;
1491 CHECK_NUMBER (arg
, 0);
1492 f
->display
.x
->internal_border_width
= XINT (arg
);
1493 if (f
->display
.x
->internal_border_width
< 0)
1494 f
->display
.x
->internal_border_width
= 0;
1496 if (f
->display
.x
->internal_border_width
== old
)
1499 if (FRAME_X_WINDOW (f
) != 0)
1502 x_set_window_size (f
, 0, f
->width
, f
->height
);
1504 x_set_resize_hint (f
);
1506 XFlush (FRAME_X_DISPLAY (f
));
1508 SET_FRAME_GARBAGED (f
);
1513 x_set_visibility (f
, value
, oldval
)
1515 Lisp_Object value
, oldval
;
1518 XSETFRAME (frame
, f
);
1521 Fmake_frame_invisible (frame
, Qt
);
1522 else if (EQ (value
, Qicon
))
1523 Ficonify_frame (frame
);
1525 Fmake_frame_visible (frame
);
1529 x_set_menu_bar_lines_1 (window
, n
)
1533 struct window
*w
= XWINDOW (window
);
1535 XSETFASTINT (w
->top
, XFASTINT (w
->top
) + n
);
1536 XSETFASTINT (w
->height
, XFASTINT (w
->height
) - n
);
1538 /* Handle just the top child in a vertical split. */
1539 if (!NILP (w
->vchild
))
1540 x_set_menu_bar_lines_1 (w
->vchild
, n
);
1542 /* Adjust all children in a horizontal split. */
1543 for (window
= w
->hchild
; !NILP (window
); window
= w
->next
)
1545 w
= XWINDOW (window
);
1546 x_set_menu_bar_lines_1 (window
, n
);
1551 x_set_menu_bar_lines (f
, value
, oldval
)
1553 Lisp_Object value
, oldval
;
1556 int olines
= FRAME_MENU_BAR_LINES (f
);
1558 /* Right now, menu bars don't work properly in minibuf-only frames;
1559 most of the commands try to apply themselves to the minibuffer
1560 frame itslef, and get an error because you can't switch buffers
1561 in or split the minibuffer window. */
1562 if (FRAME_MINIBUF_ONLY_P (f
))
1565 if (INTEGERP (value
))
1566 nlines
= XINT (value
);
1570 #ifdef USE_X_TOOLKIT
1571 FRAME_MENU_BAR_LINES (f
) = 0;
1573 FRAME_EXTERNAL_MENU_BAR (f
) = 1;
1576 if (FRAME_EXTERNAL_MENU_BAR (f
) == 1)
1577 free_frame_menubar (f
);
1578 FRAME_EXTERNAL_MENU_BAR (f
) = 0;
1579 f
->display
.x
->menubar_widget
= 0;
1581 #else /* not USE_X_TOOLKIT */
1582 FRAME_MENU_BAR_LINES (f
) = nlines
;
1583 x_set_menu_bar_lines_1 (f
->root_window
, nlines
- olines
);
1584 #endif /* not USE_X_TOOLKIT */
1587 /* Change the name of frame F to NAME. If NAME is nil, set F's name to
1590 If EXPLICIT is non-zero, that indicates that lisp code is setting the
1591 name; if NAME is a string, set F's name to NAME and set
1592 F->explicit_name; if NAME is Qnil, then clear F->explicit_name.
1594 If EXPLICIT is zero, that indicates that Emacs redisplay code is
1595 suggesting a new name, which lisp code should override; if
1596 F->explicit_name is set, ignore the new name; otherwise, set it. */
1599 x_set_name (f
, name
, explicit)
1604 /* Make sure that requests from lisp code override requests from
1605 Emacs redisplay code. */
1608 /* If we're switching from explicit to implicit, we had better
1609 update the mode lines and thereby update the title. */
1610 if (f
->explicit_name
&& NILP (name
))
1611 update_mode_lines
= 1;
1613 f
->explicit_name
= ! NILP (name
);
1615 else if (f
->explicit_name
)
1618 /* If NAME is nil, set the name to the x_id_name. */
1621 /* Check for no change needed in this very common case
1622 before we do any consing. */
1623 if (!strcmp (FRAME_X_DISPLAY_INFO (f
)->x_id_name
,
1624 XSTRING (f
->name
)->data
))
1626 name
= build_string (FRAME_X_DISPLAY_INFO (f
)->x_id_name
);
1629 CHECK_STRING (name
, 0);
1631 /* Don't change the name if it's already NAME. */
1632 if (! NILP (Fstring_equal (name
, f
->name
)))
1635 if (FRAME_X_WINDOW (f
))
1641 text
.value
= XSTRING (name
)->data
;
1642 text
.encoding
= XA_STRING
;
1644 text
.nitems
= XSTRING (name
)->size
;
1645 #ifdef USE_X_TOOLKIT
1646 XSetWMName (FRAME_X_DISPLAY (f
),
1647 XtWindow (f
->display
.x
->widget
), &text
);
1648 XSetWMIconName (FRAME_X_DISPLAY (f
), XtWindow (f
->display
.x
->widget
),
1650 #else /* not USE_X_TOOLKIT */
1651 XSetWMName (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
), &text
);
1652 XSetWMIconName (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
), &text
);
1653 #endif /* not USE_X_TOOLKIT */
1655 #else /* not HAVE_X11R4 */
1656 XSetIconName (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
1657 XSTRING (name
)->data
);
1658 XStoreName (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
1659 XSTRING (name
)->data
);
1660 #endif /* not HAVE_X11R4 */
1667 /* This function should be called when the user's lisp code has
1668 specified a name for the frame; the name will override any set by the
1671 x_explicitly_set_name (f
, arg
, oldval
)
1673 Lisp_Object arg
, oldval
;
1675 x_set_name (f
, arg
, 1);
1678 /* This function should be called by Emacs redisplay code to set the
1679 name; names set this way will never override names set by the user's
1682 x_implicitly_set_name (f
, arg
, oldval
)
1684 Lisp_Object arg
, oldval
;
1686 x_set_name (f
, arg
, 0);
1690 x_set_autoraise (f
, arg
, oldval
)
1692 Lisp_Object arg
, oldval
;
1694 f
->auto_raise
= !EQ (Qnil
, arg
);
1698 x_set_autolower (f
, arg
, oldval
)
1700 Lisp_Object arg
, oldval
;
1702 f
->auto_lower
= !EQ (Qnil
, arg
);
1706 x_set_unsplittable (f
, arg
, oldval
)
1708 Lisp_Object arg
, oldval
;
1710 f
->no_split
= !NILP (arg
);
1714 x_set_vertical_scroll_bars (f
, arg
, oldval
)
1716 Lisp_Object arg
, oldval
;
1718 if (NILP (arg
) != ! FRAME_HAS_VERTICAL_SCROLL_BARS (f
))
1720 FRAME_HAS_VERTICAL_SCROLL_BARS (f
) = ! NILP (arg
);
1722 /* We set this parameter before creating the X window for the
1723 frame, so we can get the geometry right from the start.
1724 However, if the window hasn't been created yet, we shouldn't
1725 call x_set_window_size. */
1726 if (FRAME_X_WINDOW (f
))
1727 x_set_window_size (f
, 0, FRAME_WIDTH (f
), FRAME_HEIGHT (f
));
1732 x_set_scroll_bar_width (f
, arg
, oldval
)
1734 Lisp_Object arg
, oldval
;
1738 FRAME_SCROLL_BAR_PIXEL_WIDTH (f
) = 0;
1739 FRAME_SCROLL_BAR_COLS (f
) = 2;
1741 else if (INTEGERP (arg
) && XINT (arg
) > 0
1742 && XFASTINT (arg
) != FRAME_SCROLL_BAR_PIXEL_WIDTH (f
))
1744 int wid
= FONT_WIDTH (f
->display
.x
->font
);
1745 FRAME_SCROLL_BAR_PIXEL_WIDTH (f
) = XFASTINT (arg
);
1746 FRAME_SCROLL_BAR_COLS (f
) = (XFASTINT (arg
) + wid
-1) / wid
;
1747 if (FRAME_X_WINDOW (f
))
1748 x_set_window_size (f
, 0, FRAME_WIDTH (f
), FRAME_HEIGHT (f
));
1752 /* Subroutines of creating an X frame. */
1754 /* Make sure that Vx_resource_name is set to a reasonable value. */
1756 validate_x_resource_name ()
1758 if (STRINGP (Vx_resource_name
))
1760 int len
= XSTRING (Vx_resource_name
)->size
;
1761 unsigned char *p
= XSTRING (Vx_resource_name
)->data
;
1764 /* Allow only letters, digits, - and _,
1765 because those are all that X allows. */
1766 for (i
= 0; i
< len
; i
++)
1769 if (! ((c
>= 'a' && c
<= 'z')
1770 || (c
>= 'A' && c
<= 'Z')
1771 || (c
>= '0' && c
<= '9')
1772 || c
== '-' || c
== '_'))
1778 Vx_resource_name
= make_string ("emacs", 5);
1782 extern char *x_get_string_resource ();
1784 DEFUN ("x-get-resource", Fx_get_resource
, Sx_get_resource
, 2, 4, 0,
1785 "Return the value of ATTRIBUTE, of class CLASS, from the X defaults database.\n\
1786 This uses `INSTANCE.ATTRIBUTE' as the key and `Emacs.CLASS' as the\n\
1787 class, where INSTANCE is the name under which Emacs was invoked, or\n\
1788 the name specified by the `-name' or `-rn' command-line arguments.\n\
1790 The optional arguments COMPONENT and SUBCLASS add to the key and the\n\
1791 class, respectively. You must specify both of them or neither.\n\
1792 If you specify them, the key is `INSTANCE.COMPONENT.ATTRIBUTE'\n\
1793 and the class is `Emacs.CLASS.SUBCLASS'.")
1794 (attribute
, class, component
, subclass
)
1795 Lisp_Object attribute
, class, component
, subclass
;
1797 register char *value
;
1800 Lisp_Object resname
;
1804 CHECK_STRING (attribute
, 0);
1805 CHECK_STRING (class, 0);
1807 if (!NILP (component
))
1808 CHECK_STRING (component
, 1);
1809 if (!NILP (subclass
))
1810 CHECK_STRING (subclass
, 2);
1811 if (NILP (component
) != NILP (subclass
))
1812 error ("x-get-resource: must specify both COMPONENT and SUBCLASS or neither");
1814 validate_x_resource_name ();
1815 resname
= Vx_resource_name
;
1817 if (NILP (component
))
1819 /* Allocate space for the components, the dots which separate them,
1820 and the final '\0'. */
1821 name_key
= (char *) alloca (XSTRING (resname
)->size
1822 + XSTRING (attribute
)->size
1824 class_key
= (char *) alloca ((sizeof (EMACS_CLASS
) - 1)
1825 + XSTRING (class)->size
1828 sprintf (name_key
, "%s.%s",
1829 XSTRING (resname
)->data
,
1830 XSTRING (attribute
)->data
);
1831 sprintf (class_key
, "%s.%s",
1833 XSTRING (class)->data
);
1837 name_key
= (char *) alloca (XSTRING (resname
)->size
1838 + XSTRING (component
)->size
1839 + XSTRING (attribute
)->size
1842 class_key
= (char *) alloca ((sizeof (EMACS_CLASS
) - 1)
1843 + XSTRING (class)->size
1844 + XSTRING (subclass
)->size
1847 sprintf (name_key
, "%s.%s.%s",
1848 XSTRING (resname
)->data
,
1849 XSTRING (component
)->data
,
1850 XSTRING (attribute
)->data
);
1851 sprintf (class_key
, "%s.%s.%s",
1853 XSTRING (class)->data
,
1854 XSTRING (subclass
)->data
);
1857 value
= x_get_string_resource (check_x_display_info (Qnil
)->xrdb
,
1858 name_key
, class_key
);
1860 if (value
!= (char *) 0)
1861 return build_string (value
);
1866 /* Used when C code wants a resource value. */
1869 x_get_resource_string (attribute
, class)
1870 char *attribute
, *class;
1872 register char *value
;
1876 /* Allocate space for the components, the dots which separate them,
1877 and the final '\0'. */
1878 name_key
= (char *) alloca (XSTRING (Vinvocation_name
)->size
1879 + strlen (attribute
) + 2);
1880 class_key
= (char *) alloca ((sizeof (EMACS_CLASS
) - 1)
1881 + strlen (class) + 2);
1883 sprintf (name_key
, "%s.%s",
1884 XSTRING (Vinvocation_name
)->data
,
1886 sprintf (class_key
, "%s.%s", EMACS_CLASS
, class);
1888 return x_get_string_resource (FRAME_X_DISPLAY_INFO (selected_frame
)->xrdb
,
1889 name_key
, class_key
);
1892 /* Types we might convert a resource string into. */
1895 number
, boolean
, string
, symbol
1898 /* Return the value of parameter PARAM.
1900 First search ALIST, then Vdefault_frame_alist, then the X defaults
1901 database, using ATTRIBUTE as the attribute name and CLASS as its class.
1903 Convert the resource to the type specified by desired_type.
1905 If no default is specified, return Qunbound. If you call
1906 x_get_arg, make sure you deal with Qunbound in a reasonable way,
1907 and don't let it get stored in any Lisp-visible variables! */
1910 x_get_arg (alist
, param
, attribute
, class, type
)
1911 Lisp_Object alist
, param
;
1914 enum resource_types type
;
1916 register Lisp_Object tem
;
1918 tem
= Fassq (param
, alist
);
1920 tem
= Fassq (param
, Vdefault_frame_alist
);
1926 tem
= Fx_get_resource (build_string (attribute
),
1927 build_string (class),
1936 return make_number (atoi (XSTRING (tem
)->data
));
1939 tem
= Fdowncase (tem
);
1940 if (!strcmp (XSTRING (tem
)->data
, "on")
1941 || !strcmp (XSTRING (tem
)->data
, "true"))
1950 /* As a special case, we map the values `true' and `on'
1951 to Qt, and `false' and `off' to Qnil. */
1954 lower
= Fdowncase (tem
);
1955 if (!strcmp (XSTRING (lower
)->data
, "on")
1956 || !strcmp (XSTRING (lower
)->data
, "true"))
1958 else if (!strcmp (XSTRING (lower
)->data
, "off")
1959 || !strcmp (XSTRING (lower
)->data
, "false"))
1962 return Fintern (tem
, Qnil
);
1975 /* Record in frame F the specified or default value according to ALIST
1976 of the parameter named PARAM (a Lisp symbol).
1977 If no value is specified for PARAM, look for an X default for XPROP
1978 on the frame named NAME.
1979 If that is not found either, use the value DEFLT. */
1982 x_default_parameter (f
, alist
, prop
, deflt
, xprop
, xclass
, type
)
1989 enum resource_types type
;
1993 tem
= x_get_arg (alist
, prop
, xprop
, xclass
, type
);
1994 if (EQ (tem
, Qunbound
))
1996 x_set_frame_parameters (f
, Fcons (Fcons (prop
, tem
), Qnil
));
2000 DEFUN ("x-parse-geometry", Fx_parse_geometry
, Sx_parse_geometry
, 1, 1, 0,
2001 "Parse an X-style geometry string STRING.\n\
2002 Returns an alist of the form ((top . TOP), (left . LEFT) ... ).\n\
2003 The properties returned may include `top', `left', `height', and `width'.\n\
2004 The value of `left' or `top' may be an integer,\n\
2005 or a list (+ N) meaning N pixels relative to top/left corner,\n\
2006 or a list (- N) meaning -N pixels relative to bottom/right corner.")
2011 unsigned int width
, height
;
2014 CHECK_STRING (string
, 0);
2016 geometry
= XParseGeometry ((char *) XSTRING (string
)->data
,
2017 &x
, &y
, &width
, &height
);
2020 if (!!(geometry
& XValue
) != !!(geometry
& YValue
))
2021 error ("Must specify both x and y position, or neither");
2025 if (geometry
& XValue
)
2027 Lisp_Object element
;
2029 if (x
>= 0 && (geometry
& XNegative
))
2030 element
= Fcons (Qleft
, Fcons (Qminus
, Fcons (make_number (-x
), Qnil
)));
2031 else if (x
< 0 && ! (geometry
& XNegative
))
2032 element
= Fcons (Qleft
, Fcons (Qplus
, Fcons (make_number (x
), Qnil
)));
2034 element
= Fcons (Qleft
, make_number (x
));
2035 result
= Fcons (element
, result
);
2038 if (geometry
& YValue
)
2040 Lisp_Object element
;
2042 if (y
>= 0 && (geometry
& YNegative
))
2043 element
= Fcons (Qtop
, Fcons (Qminus
, Fcons (make_number (-y
), Qnil
)));
2044 else if (y
< 0 && ! (geometry
& YNegative
))
2045 element
= Fcons (Qtop
, Fcons (Qplus
, Fcons (make_number (y
), Qnil
)));
2047 element
= Fcons (Qtop
, make_number (y
));
2048 result
= Fcons (element
, result
);
2051 if (geometry
& WidthValue
)
2052 result
= Fcons (Fcons (Qwidth
, make_number (width
)), result
);
2053 if (geometry
& HeightValue
)
2054 result
= Fcons (Fcons (Qheight
, make_number (height
)), result
);
2059 /* Calculate the desired size and position of this window,
2060 and return the flags saying which aspects were specified.
2062 This function does not make the coordinates positive. */
2064 #define DEFAULT_ROWS 40
2065 #define DEFAULT_COLS 80
2068 x_figure_window_size (f
, parms
)
2072 register Lisp_Object tem0
, tem1
, tem2
;
2073 int height
, width
, left
, top
;
2074 register int geometry
;
2075 long window_prompting
= 0;
2077 /* Default values if we fall through.
2078 Actually, if that happens we should get
2079 window manager prompting. */
2080 f
->width
= DEFAULT_COLS
;
2081 f
->height
= DEFAULT_ROWS
;
2082 /* Window managers expect that if program-specified
2083 positions are not (0,0), they're intentional, not defaults. */
2084 f
->display
.x
->top_pos
= 0;
2085 f
->display
.x
->left_pos
= 0;
2087 tem0
= x_get_arg (parms
, Qheight
, 0, 0, number
);
2088 tem1
= x_get_arg (parms
, Qwidth
, 0, 0, number
);
2089 tem2
= x_get_arg (parms
, Quser_size
, 0, 0, number
);
2090 if (! EQ (tem0
, Qunbound
) || ! EQ (tem1
, Qunbound
))
2092 if (!EQ (tem0
, Qunbound
))
2094 CHECK_NUMBER (tem0
, 0);
2095 f
->height
= XINT (tem0
);
2097 if (!EQ (tem1
, Qunbound
))
2099 CHECK_NUMBER (tem1
, 0);
2100 f
->width
= XINT (tem1
);
2102 if (!NILP (tem2
) && !EQ (tem2
, Qunbound
))
2103 window_prompting
|= USSize
;
2105 window_prompting
|= PSize
;
2108 f
->display
.x
->vertical_scroll_bar_extra
2109 = (!FRAME_HAS_VERTICAL_SCROLL_BARS (f
)
2111 : FRAME_SCROLL_BAR_PIXEL_WIDTH (f
) > 0
2112 ? FRAME_SCROLL_BAR_PIXEL_WIDTH (f
)
2113 : (FRAME_SCROLL_BAR_COLS (f
) * FONT_WIDTH (f
->display
.x
->font
)));
2114 f
->display
.x
->pixel_width
= CHAR_TO_PIXEL_WIDTH (f
, f
->width
);
2115 f
->display
.x
->pixel_height
= CHAR_TO_PIXEL_HEIGHT (f
, f
->height
);
2117 tem0
= x_get_arg (parms
, Qtop
, 0, 0, number
);
2118 tem1
= x_get_arg (parms
, Qleft
, 0, 0, number
);
2119 tem2
= x_get_arg (parms
, Quser_position
, 0, 0, number
);
2120 if (! EQ (tem0
, Qunbound
) || ! EQ (tem1
, Qunbound
))
2122 if (EQ (tem0
, Qminus
))
2124 f
->display
.x
->top_pos
= 0;
2125 window_prompting
|= YNegative
;
2127 else if (CONSP (tem0
) && EQ (XCONS (tem0
)->car
, Qminus
)
2128 && CONSP (XCONS (tem0
)->cdr
)
2129 && INTEGERP (XCONS (XCONS (tem0
)->cdr
)->car
))
2131 f
->display
.x
->top_pos
= - XINT (XCONS (XCONS (tem0
)->cdr
)->car
);
2132 window_prompting
|= YNegative
;
2134 else if (CONSP (tem0
) && EQ (XCONS (tem0
)->car
, Qplus
)
2135 && CONSP (XCONS (tem0
)->cdr
)
2136 && INTEGERP (XCONS (XCONS (tem0
)->cdr
)->car
))
2138 f
->display
.x
->top_pos
= XINT (XCONS (XCONS (tem0
)->cdr
)->car
);
2140 else if (EQ (tem0
, Qunbound
))
2141 f
->display
.x
->top_pos
= 0;
2144 CHECK_NUMBER (tem0
, 0);
2145 f
->display
.x
->top_pos
= XINT (tem0
);
2146 if (f
->display
.x
->top_pos
< 0)
2147 window_prompting
|= YNegative
;
2150 if (EQ (tem1
, Qminus
))
2152 f
->display
.x
->left_pos
= 0;
2153 window_prompting
|= XNegative
;
2155 else if (CONSP (tem1
) && EQ (XCONS (tem1
)->car
, Qminus
)
2156 && CONSP (XCONS (tem1
)->cdr
)
2157 && INTEGERP (XCONS (XCONS (tem1
)->cdr
)->car
))
2159 f
->display
.x
->left_pos
= - XINT (XCONS (XCONS (tem1
)->cdr
)->car
);
2160 window_prompting
|= XNegative
;
2162 else if (CONSP (tem1
) && EQ (XCONS (tem1
)->car
, Qplus
)
2163 && CONSP (XCONS (tem1
)->cdr
)
2164 && INTEGERP (XCONS (XCONS (tem1
)->cdr
)->car
))
2166 f
->display
.x
->left_pos
= XINT (XCONS (XCONS (tem1
)->cdr
)->car
);
2168 else if (EQ (tem1
, Qunbound
))
2169 f
->display
.x
->left_pos
= 0;
2172 CHECK_NUMBER (tem1
, 0);
2173 f
->display
.x
->left_pos
= XINT (tem1
);
2174 if (f
->display
.x
->left_pos
< 0)
2175 window_prompting
|= XNegative
;
2178 if (!NILP (tem2
) && ! EQ (tem2
, Qunbound
))
2179 window_prompting
|= USPosition
;
2181 window_prompting
|= PPosition
;
2184 return window_prompting
;
2187 #if !defined (HAVE_X11R4) && !defined (HAVE_XSETWMPROTOCOLS)
2190 XSetWMProtocols (dpy
, w
, protocols
, count
)
2197 prop
= XInternAtom (dpy
, "WM_PROTOCOLS", False
);
2198 if (prop
== None
) return False
;
2199 XChangeProperty (dpy
, w
, prop
, XA_ATOM
, 32, PropModeReplace
,
2200 (unsigned char *) protocols
, count
);
2203 #endif /* not HAVE_X11R4 && not HAVE_XSETWMPROTOCOLS */
2205 #ifdef USE_X_TOOLKIT
2207 /* If the WM_PROTOCOLS property does not already contain WM_TAKE_FOCUS,
2208 WM_DELETE_WINDOW, and WM_SAVE_YOURSELF, then add them. (They may
2209 already be present because of the toolkit (Motif adds some of them,
2210 for example, but Xt doesn't). */
2213 hack_wm_protocols (f
, widget
)
2217 Display
*dpy
= XtDisplay (widget
);
2218 Window w
= XtWindow (widget
);
2219 int need_delete
= 1;
2225 Atom type
, *atoms
= 0;
2227 unsigned long nitems
= 0;
2228 unsigned long bytes_after
;
2230 if (Success
== XGetWindowProperty (dpy
, w
,
2231 FRAME_X_DISPLAY_INFO (f
)->Xatom_wm_protocols
,
2232 0, 100, False
, XA_ATOM
,
2233 &type
, &format
, &nitems
, &bytes_after
,
2234 (unsigned char **) &atoms
)
2235 && format
== 32 && type
== XA_ATOM
)
2239 if (atoms
[nitems
] == FRAME_X_DISPLAY_INFO (f
)->Xatom_wm_delete_window
)
2241 else if (atoms
[nitems
] == FRAME_X_DISPLAY_INFO (f
)->Xatom_wm_take_focus
)
2243 else if (atoms
[nitems
] == FRAME_X_DISPLAY_INFO (f
)->Xatom_wm_save_yourself
)
2246 if (atoms
) XFree ((char *) atoms
);
2252 props
[count
++] = FRAME_X_DISPLAY_INFO (f
)->Xatom_wm_delete_window
;
2254 props
[count
++] = FRAME_X_DISPLAY_INFO (f
)->Xatom_wm_take_focus
;
2256 props
[count
++] = FRAME_X_DISPLAY_INFO (f
)->Xatom_wm_save_yourself
;
2258 XChangeProperty (dpy
, w
, FRAME_X_DISPLAY_INFO (f
)->Xatom_wm_protocols
,
2259 XA_ATOM
, 32, PropModeAppend
,
2260 (unsigned char *) props
, count
);
2266 #ifdef USE_X_TOOLKIT
2268 /* Create and set up the X widget for frame F. */
2271 x_window (f
, window_prompting
, minibuffer_only
)
2273 long window_prompting
;
2274 int minibuffer_only
;
2276 XClassHint class_hints
;
2277 XSetWindowAttributes attributes
;
2278 unsigned long attribute_mask
;
2280 Widget shell_widget
;
2282 Widget frame_widget
;
2289 if (STRINGP (f
->name
))
2290 name
= (char*) XSTRING (f
->name
)->data
;
2295 XtSetArg (al
[ac
], XtNallowShellResize
, 1); ac
++;
2296 XtSetArg (al
[ac
], XtNinput
, 1); ac
++;
2297 shell_widget
= XtAppCreateShell (name
, EMACS_CLASS
,
2298 topLevelShellWidgetClass
,
2299 FRAME_X_DISPLAY (f
), al
, ac
);
2301 f
->display
.x
->widget
= shell_widget
;
2302 /* maybe_set_screen_title_format (shell_widget); */
2304 pane_widget
= lw_create_widget ("main", "pane", widget_id_tick
++,
2305 (widget_value
*) NULL
,
2306 shell_widget
, False
,
2309 (lw_callback
) NULL
);
2311 f
->display
.x
->column_widget
= pane_widget
;
2313 if (!minibuffer_only
&& FRAME_EXTERNAL_MENU_BAR (f
))
2314 initialize_frame_menubar (f
);
2316 /* mappedWhenManaged to false tells to the paned window to not map/unmap
2317 the emacs screen when changing menubar. This reduces flickering. */
2320 XtSetArg (al
[ac
], XtNmappedWhenManaged
, 0); ac
++;
2321 XtSetArg (al
[ac
], XtNshowGrip
, 0); ac
++;
2322 XtSetArg (al
[ac
], XtNallowResize
, 1); ac
++;
2323 XtSetArg (al
[ac
], XtNresizeToPreferred
, 1); ac
++;
2324 XtSetArg (al
[ac
], XtNemacsFrame
, f
); ac
++;
2325 frame_widget
= XtCreateWidget (name
,
2327 pane_widget
, al
, ac
);
2328 lw_set_main_areas (pane_widget
, f
->display
.x
->menubar_widget
, frame_widget
);
2330 f
->display
.x
->edit_widget
= frame_widget
;
2332 if (f
->display
.x
->menubar_widget
)
2333 XtManageChild (f
->display
.x
->menubar_widget
);
2334 XtManageChild (frame_widget
);
2336 /* Do some needed geometry management. */
2339 char *tem
, shell_position
[32];
2343 = (f
->display
.x
->menubar_widget
2344 ? (f
->display
.x
->menubar_widget
->core
.height
2345 + f
->display
.x
->menubar_widget
->core
.border_width
)
2348 if (FRAME_EXTERNAL_MENU_BAR (f
))
2351 XtVaGetValues (pane_widget
, XtNinternalBorderWidth
, &ibw
, NULL
);
2352 menubar_size
+= ibw
;
2355 if (window_prompting
& USPosition
)
2357 int left
= f
->display
.x
->left_pos
;
2358 int xneg
= window_prompting
& XNegative
;
2359 int top
= f
->display
.x
->top_pos
;
2360 int yneg
= window_prompting
& YNegative
;
2365 sprintf (shell_position
, "=%dx%d%c%d%c%d", PIXEL_WIDTH (f
),
2366 PIXEL_HEIGHT (f
) + menubar_size
,
2367 (xneg
? '-' : '+'), left
,
2368 (yneg
? '-' : '+'), top
);
2371 sprintf (shell_position
, "=%dx%d", PIXEL_WIDTH (f
),
2372 PIXEL_HEIGHT (f
) + menubar_size
);
2373 len
= strlen (shell_position
) + 1;
2374 tem
= (char *) xmalloc (len
);
2375 strncpy (tem
, shell_position
, len
);
2376 XtSetArg (al
[ac
], XtNgeometry
, tem
); ac
++;
2377 XtSetValues (shell_widget
, al
, ac
);
2380 x_calc_absolute_position (f
);
2382 XtManageChild (pane_widget
);
2383 XtRealizeWidget (shell_widget
);
2385 FRAME_X_WINDOW (f
) = XtWindow (frame_widget
);
2387 validate_x_resource_name ();
2388 class_hints
.res_name
= (char *) XSTRING (Vx_resource_name
)->data
;
2389 class_hints
.res_class
= EMACS_CLASS
;
2390 XSetClassHint (FRAME_X_DISPLAY (f
), XtWindow (shell_widget
), &class_hints
);
2392 f
->display
.x
->wm_hints
.input
= True
;
2393 f
->display
.x
->wm_hints
.flags
|= InputHint
;
2394 XSetWMHints (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
2395 &f
->display
.x
->wm_hints
);
2397 hack_wm_protocols (f
, shell_widget
);
2400 XtAddEventHandler (shell_widget
, 0, True
, _XEditResCheckMessages
, 0);
2403 /* Do a stupid property change to force the server to generate a
2404 propertyNotify event so that the event_stream server timestamp will
2405 be initialized to something relevant to the time we created the window.
2407 XChangeProperty (XtDisplay (frame_widget
), XtWindow (frame_widget
),
2408 FRAME_X_DISPLAY_INFO (f
)->Xatom_wm_protocols
,
2409 XA_ATOM
, 32, PropModeAppend
,
2410 (unsigned char*) NULL
, 0);
2412 /* Make all the standard events reach the Emacs frame. */
2413 attributes
.event_mask
= STANDARD_EVENT_SET
;
2414 attribute_mask
= CWEventMask
;
2415 XChangeWindowAttributes (XtDisplay (shell_widget
), XtWindow (shell_widget
),
2416 attribute_mask
, &attributes
);
2418 XtMapWidget (frame_widget
);
2420 /* x_set_name normally ignores requests to set the name if the
2421 requested name is the same as the current name. This is the one
2422 place where that assumption isn't correct; f->name is set, but
2423 the X server hasn't been told. */
2426 int explicit = f
->explicit_name
;
2428 f
->explicit_name
= 0;
2431 x_set_name (f
, name
, explicit);
2434 XDefineCursor (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
2435 f
->display
.x
->text_cursor
);
2439 if (FRAME_X_WINDOW (f
) == 0)
2440 error ("Unable to create window");
2443 #else /* not USE_X_TOOLKIT */
2445 /* Create and set up the X window for frame F. */
2451 XClassHint class_hints
;
2452 XSetWindowAttributes attributes
;
2453 unsigned long attribute_mask
;
2455 attributes
.background_pixel
= f
->display
.x
->background_pixel
;
2456 attributes
.border_pixel
= f
->display
.x
->border_pixel
;
2457 attributes
.bit_gravity
= StaticGravity
;
2458 attributes
.backing_store
= NotUseful
;
2459 attributes
.save_under
= True
;
2460 attributes
.event_mask
= STANDARD_EVENT_SET
;
2461 attribute_mask
= (CWBackPixel
| CWBorderPixel
| CWBitGravity
2463 | CWBackingStore
| CWSaveUnder
2469 = XCreateWindow (FRAME_X_DISPLAY (f
),
2470 f
->display
.x
->parent_desc
,
2471 f
->display
.x
->left_pos
,
2472 f
->display
.x
->top_pos
,
2473 PIXEL_WIDTH (f
), PIXEL_HEIGHT (f
),
2474 f
->display
.x
->border_width
,
2475 CopyFromParent
, /* depth */
2476 InputOutput
, /* class */
2477 FRAME_X_DISPLAY_INFO (f
)->visual
,
2478 attribute_mask
, &attributes
);
2480 validate_x_resource_name ();
2481 class_hints
.res_name
= (char *) XSTRING (Vx_resource_name
)->data
;
2482 class_hints
.res_class
= EMACS_CLASS
;
2483 XSetClassHint (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
), &class_hints
);
2485 /* This indicates that we use the "Passive Input" input model.
2486 Unless we do this, we don't get the Focus{In,Out} events that we
2487 need to draw the cursor correctly. Accursed bureaucrats.
2488 XWhipsAndChains (FRAME_X_DISPLAY (f), IronMaiden, &TheRack); */
2490 f
->display
.x
->wm_hints
.input
= True
;
2491 f
->display
.x
->wm_hints
.flags
|= InputHint
;
2492 XSetWMHints (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
2493 &f
->display
.x
->wm_hints
);
2495 /* Request "save yourself" and "delete window" commands from wm. */
2498 protocols
[0] = FRAME_X_DISPLAY_INFO (f
)->Xatom_wm_delete_window
;
2499 protocols
[1] = FRAME_X_DISPLAY_INFO (f
)->Xatom_wm_save_yourself
;
2500 XSetWMProtocols (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
), protocols
, 2);
2503 /* x_set_name normally ignores requests to set the name if the
2504 requested name is the same as the current name. This is the one
2505 place where that assumption isn't correct; f->name is set, but
2506 the X server hasn't been told. */
2509 int explicit = f
->explicit_name
;
2511 f
->explicit_name
= 0;
2514 x_set_name (f
, name
, explicit);
2517 XDefineCursor (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
2518 f
->display
.x
->text_cursor
);
2522 if (FRAME_X_WINDOW (f
) == 0)
2523 error ("Unable to create window");
2526 #endif /* not USE_X_TOOLKIT */
2528 /* Handle the icon stuff for this window. Perhaps later we might
2529 want an x_set_icon_position which can be called interactively as
2537 Lisp_Object icon_x
, icon_y
;
2539 /* Set the position of the icon. Note that twm groups all
2540 icons in an icon window. */
2541 icon_x
= x_get_arg (parms
, Qicon_left
, 0, 0, number
);
2542 icon_y
= x_get_arg (parms
, Qicon_top
, 0, 0, number
);
2543 if (!EQ (icon_x
, Qunbound
) && !EQ (icon_y
, Qunbound
))
2545 CHECK_NUMBER (icon_x
, 0);
2546 CHECK_NUMBER (icon_y
, 0);
2548 else if (!EQ (icon_x
, Qunbound
) || !EQ (icon_y
, Qunbound
))
2549 error ("Both left and top icon corners of icon must be specified");
2553 if (! EQ (icon_x
, Qunbound
))
2554 x_wm_set_icon_position (f
, XINT (icon_x
), XINT (icon_y
));
2556 /* Start up iconic or window? */
2557 x_wm_set_window_state
2558 (f
, (EQ (x_get_arg (parms
, Qvisibility
, 0, 0, symbol
), Qicon
)
2565 /* Make the GC's needed for this window, setting the
2566 background, border and mouse colors; also create the
2567 mouse cursor and the gray border tile. */
2569 static char cursor_bits
[] =
2571 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
2572 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
2573 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
2574 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
2581 XGCValues gc_values
;
2587 /* Create the GC's of this frame.
2588 Note that many default values are used. */
2591 gc_values
.font
= f
->display
.x
->font
->fid
;
2592 gc_values
.foreground
= f
->display
.x
->foreground_pixel
;
2593 gc_values
.background
= f
->display
.x
->background_pixel
;
2594 gc_values
.line_width
= 0; /* Means 1 using fast algorithm. */
2595 f
->display
.x
->normal_gc
= XCreateGC (FRAME_X_DISPLAY (f
),
2597 GCLineWidth
| GCFont
2598 | GCForeground
| GCBackground
,
2601 /* Reverse video style. */
2602 gc_values
.foreground
= f
->display
.x
->background_pixel
;
2603 gc_values
.background
= f
->display
.x
->foreground_pixel
;
2604 f
->display
.x
->reverse_gc
= XCreateGC (FRAME_X_DISPLAY (f
),
2606 GCFont
| GCForeground
| GCBackground
2610 /* Cursor has cursor-color background, background-color foreground. */
2611 gc_values
.foreground
= f
->display
.x
->background_pixel
;
2612 gc_values
.background
= f
->display
.x
->cursor_pixel
;
2613 gc_values
.fill_style
= FillOpaqueStippled
;
2615 = XCreateBitmapFromData (FRAME_X_DISPLAY (f
),
2616 FRAME_X_DISPLAY_INFO (f
)->root_window
,
2617 cursor_bits
, 16, 16);
2618 f
->display
.x
->cursor_gc
2619 = XCreateGC (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
2620 (GCFont
| GCForeground
| GCBackground
2621 | GCFillStyle
| GCStipple
| GCLineWidth
),
2624 /* Create the gray border tile used when the pointer is not in
2625 the frame. Since this depends on the frame's pixel values,
2626 this must be done on a per-frame basis. */
2627 f
->display
.x
->border_tile
2628 = (XCreatePixmapFromBitmapData
2629 (FRAME_X_DISPLAY (f
), FRAME_X_DISPLAY_INFO (f
)->root_window
,
2630 gray_bits
, gray_width
, gray_height
,
2631 f
->display
.x
->foreground_pixel
,
2632 f
->display
.x
->background_pixel
,
2633 DefaultDepth (FRAME_X_DISPLAY (f
),
2634 XScreenNumberOfScreen (FRAME_X_SCREEN (f
)))));
2639 DEFUN ("x-create-frame", Fx_create_frame
, Sx_create_frame
,
2641 "Make a new X window, which is called a \"frame\" in Emacs terms.\n\
2642 Returns an Emacs frame object.\n\
2643 ALIST is an alist of frame parameters.\n\
2644 If the parameters specify that the frame should not have a minibuffer,\n\
2645 and do not specify a specific minibuffer window to use,\n\
2646 then `default-minibuffer-frame' must be a frame whose minibuffer can\n\
2647 be shared by the new frame.\n\
2649 This function is an internal primitive--use `make-frame' instead.")
2654 Lisp_Object frame
, tem
;
2656 int minibuffer_only
= 0;
2657 long window_prompting
= 0;
2659 int count
= specpdl_ptr
- specpdl
;
2660 struct gcpro gcpro1
;
2661 Lisp_Object display
;
2662 struct x_display_info
*dpyinfo
;
2667 display
= x_get_arg (parms
, Qdisplay
, 0, 0, 0);
2668 if (EQ (display
, Qunbound
))
2670 dpyinfo
= check_x_display_info (display
);
2672 name
= x_get_arg (parms
, Qname
, "title", "Title", string
);
2674 && ! EQ (name
, Qunbound
)
2676 error ("Invalid frame name--not a string or nil");
2678 /* See if parent window is specified. */
2679 parent
= x_get_arg (parms
, Qparent_id
, NULL
, NULL
, number
);
2680 if (EQ (parent
, Qunbound
))
2682 if (! NILP (parent
))
2683 CHECK_NUMBER (parent
, 0);
2685 tem
= x_get_arg (parms
, Qminibuffer
, 0, 0, symbol
);
2686 if (EQ (tem
, Qnone
) || NILP (tem
))
2687 f
= make_frame_without_minibuffer (Qnil
);
2688 else if (EQ (tem
, Qonly
))
2690 f
= make_minibuffer_frame ();
2691 minibuffer_only
= 1;
2693 else if (WINDOWP (tem
))
2694 f
= make_frame_without_minibuffer (tem
);
2698 /* Note that X Windows does support scroll bars. */
2699 FRAME_CAN_HAVE_SCROLL_BARS (f
) = 1;
2701 XSETFRAME (frame
, f
);
2704 f
->output_method
= output_x_window
;
2705 f
->display
.x
= (struct x_display
*) xmalloc (sizeof (struct x_display
));
2706 bzero (f
->display
.x
, sizeof (struct x_display
));
2707 f
->display
.x
->icon_bitmap
= -1;
2709 FRAME_X_DISPLAY_INFO (f
) = dpyinfo
;
2711 /* Specify the parent under which to make this X window. */
2715 f
->display
.x
->parent_desc
= parent
;
2716 f
->display
.x
->explicit_parent
= 1;
2720 f
->display
.x
->parent_desc
= FRAME_X_DISPLAY_INFO (f
)->root_window
;
2721 f
->display
.x
->explicit_parent
= 0;
2724 /* Note that the frame has no physical cursor right now. */
2725 f
->phys_cursor_x
= -1;
2727 /* Set the name; the functions to which we pass f expect the name to
2729 if (EQ (name
, Qunbound
) || NILP (name
))
2731 f
->name
= build_string (dpyinfo
->x_id_name
);
2732 f
->explicit_name
= 0;
2737 f
->explicit_name
= 1;
2738 /* use the frame's title when getting resources for this frame. */
2739 specbind (Qx_resource_name
, name
);
2742 /* Extract the window parameters from the supplied values
2743 that are needed to determine window geometry. */
2747 font
= x_get_arg (parms
, Qfont
, "font", "Font", string
);
2749 /* First, try whatever font the caller has specified. */
2751 font
= x_new_font (f
, XSTRING (font
)->data
);
2752 /* Try out a font which we hope has bold and italic variations. */
2753 if (!STRINGP (font
))
2754 font
= x_new_font (f
, "-misc-fixed-medium-r-normal-*-*-140-*-*-c-*-iso8859-1");
2755 if (! STRINGP (font
))
2756 font
= x_new_font (f
, "-*-*-medium-r-normal-*-*-140-*-*-c-*-iso8859-1");
2757 if (! STRINGP (font
))
2758 /* This was formerly the first thing tried, but it finds too many fonts
2759 and takes too long. */
2760 font
= x_new_font (f
, "-*-*-medium-r-*-*-*-*-*-*-c-*-iso8859-1");
2761 /* If those didn't work, look for something which will at least work. */
2762 if (! STRINGP (font
))
2763 font
= x_new_font (f
, "-*-fixed-*-*-*-*-*-140-*-*-c-*-iso8859-1");
2765 if (! STRINGP (font
))
2766 font
= build_string ("fixed");
2768 x_default_parameter (f
, parms
, Qfont
, font
,
2769 "font", "Font", string
);
2772 #ifdef USE_X_TOOLKIT
2773 /* Prevent lwlib/xlwmenu.c from crashing because of a bug
2774 whereby it fails to get any font. */
2775 xlwmenu_default_font
= f
->display
.x
->font
;
2778 x_default_parameter (f
, parms
, Qborder_width
, make_number (2),
2779 "borderwidth", "BorderWidth", number
);
2780 /* This defaults to 2 in order to match xterm. We recognize either
2781 internalBorderWidth or internalBorder (which is what xterm calls
2783 if (NILP (Fassq (Qinternal_border_width
, parms
)))
2787 value
= x_get_arg (parms
, Qinternal_border_width
,
2788 "internalBorder", "BorderWidth", number
);
2789 if (! EQ (value
, Qunbound
))
2790 parms
= Fcons (Fcons (Qinternal_border_width
, value
),
2793 x_default_parameter (f
, parms
, Qinternal_border_width
, make_number (2),
2794 "internalBorderWidth", "BorderWidth", number
);
2795 x_default_parameter (f
, parms
, Qvertical_scroll_bars
, Qt
,
2796 "verticalScrollBars", "ScrollBars", boolean
);
2798 /* Also do the stuff which must be set before the window exists. */
2799 x_default_parameter (f
, parms
, Qforeground_color
, build_string ("black"),
2800 "foreground", "Foreground", string
);
2801 x_default_parameter (f
, parms
, Qbackground_color
, build_string ("white"),
2802 "background", "Background", string
);
2803 x_default_parameter (f
, parms
, Qmouse_color
, build_string ("black"),
2804 "pointerColor", "Foreground", string
);
2805 x_default_parameter (f
, parms
, Qcursor_color
, build_string ("black"),
2806 "cursorColor", "Foreground", string
);
2807 x_default_parameter (f
, parms
, Qborder_color
, build_string ("black"),
2808 "borderColor", "BorderColor", string
);
2810 x_default_parameter (f
, parms
, Qmenu_bar_lines
, make_number (1),
2811 "menuBar", "MenuBar", number
);
2812 x_default_parameter (f
, parms
, Qscroll_bar_width
, Qnil
,
2813 "scrollBarWidth", "ScrollBarWidth", number
);
2815 f
->display
.x
->parent_desc
= FRAME_X_DISPLAY_INFO (f
)->root_window
;
2816 window_prompting
= x_figure_window_size (f
, parms
);
2818 if (window_prompting
& XNegative
)
2820 if (window_prompting
& YNegative
)
2821 f
->display
.x
->win_gravity
= SouthEastGravity
;
2823 f
->display
.x
->win_gravity
= NorthEastGravity
;
2827 if (window_prompting
& YNegative
)
2828 f
->display
.x
->win_gravity
= SouthWestGravity
;
2830 f
->display
.x
->win_gravity
= NorthWestGravity
;
2833 f
->display
.x
->size_hint_flags
= window_prompting
;
2835 #ifdef USE_X_TOOLKIT
2836 x_window (f
, window_prompting
, minibuffer_only
);
2842 init_frame_faces (f
);
2844 /* We need to do this after creating the X window, so that the
2845 icon-creation functions can say whose icon they're describing. */
2846 x_default_parameter (f
, parms
, Qicon_type
, Qnil
,
2847 "bitmapIcon", "BitmapIcon", symbol
);
2849 x_default_parameter (f
, parms
, Qauto_raise
, Qnil
,
2850 "autoRaise", "AutoRaiseLower", boolean
);
2851 x_default_parameter (f
, parms
, Qauto_lower
, Qnil
,
2852 "autoLower", "AutoRaiseLower", boolean
);
2853 x_default_parameter (f
, parms
, Qcursor_type
, Qbox
,
2854 "cursorType", "CursorType", symbol
);
2856 /* Dimensions, especially f->height, must be done via change_frame_size.
2857 Change will not be effected unless different from the current
2861 f
->height
= f
->width
= 0;
2862 change_frame_size (f
, height
, width
, 1, 0);
2864 /* With the toolkit, the geometry management is done in x_window. */
2865 #ifndef USE_X_TOOLKIT
2867 x_wm_set_size_hint (f
, window_prompting
, 0);
2869 #endif /* USE_X_TOOLKIT */
2871 tem
= x_get_arg (parms
, Qunsplittable
, 0, 0, boolean
);
2872 f
->no_split
= minibuffer_only
|| EQ (tem
, Qt
);
2876 /* It is now ok to make the frame official
2877 even if we get an error below.
2878 And the frame needs to be on Vframe_list
2879 or making it visible won't work. */
2880 Vframe_list
= Fcons (frame
, Vframe_list
);
2882 /* Now that the frame is official, it counts as a reference to
2884 FRAME_X_DISPLAY_INFO (f
)->reference_count
++;
2886 /* Make the window appear on the frame and enable display,
2887 unless the caller says not to. However, with explicit parent,
2888 Emacs cannot control visibility, so don't try. */
2889 if (! f
->display
.x
->explicit_parent
)
2891 Lisp_Object visibility
;
2893 visibility
= x_get_arg (parms
, Qvisibility
, 0, 0, symbol
);
2894 if (EQ (visibility
, Qunbound
))
2897 if (EQ (visibility
, Qicon
))
2898 x_iconify_frame (f
);
2899 else if (! NILP (visibility
))
2900 x_make_frame_visible (f
);
2902 /* Must have been Qnil. */
2906 return unbind_to (count
, frame
);
2910 x_get_focus_frame ()
2913 if (! x_focus_frame
)
2916 XSETFRAME (xfocus
, x_focus_frame
);
2920 DEFUN ("focus-frame", Ffocus_frame
, Sfocus_frame
, 1, 1, 0,
2921 "Set the focus on FRAME.")
2925 CHECK_LIVE_FRAME (frame
, 0);
2927 if (FRAME_X_P (XFRAME (frame
)))
2930 x_focus_on_frame (XFRAME (frame
));
2938 DEFUN ("unfocus-frame", Funfocus_frame
, Sunfocus_frame
, 0, 0, 0,
2939 "If a frame has been focused, release it.")
2945 x_unfocus_frame (x_focus_frame
);
2952 DEFUN ("x-list-fonts", Fx_list_fonts
, Sx_list_fonts
, 1, 3, 0,
2953 "Return a list of the names of available fonts matching PATTERN.\n\
2954 If optional arguments FACE and FRAME are specified, return only fonts\n\
2955 the same size as FACE on FRAME.\n\
2957 PATTERN is a string, perhaps with wildcard characters;\n\
2958 the * character matches any substring, and\n\
2959 the ? character matches any single character.\n\
2960 PATTERN is case-insensitive.\n\
2961 FACE is a face name--a symbol.\n\
2963 The return value is a list of strings, suitable as arguments to\n\
2966 Fonts Emacs can't use (i.e. proportional fonts) may or may not be excluded\n\
2967 even if they match PATTERN and FACE.")
2968 (pattern
, face
, frame
)
2969 Lisp_Object pattern
, face
, frame
;
2973 #ifndef BROKEN_XLISTFONTSWITHINFO
2976 XFontStruct
*size_ref
;
2981 CHECK_STRING (pattern
, 0);
2983 CHECK_SYMBOL (face
, 1);
2985 f
= check_x_frame (frame
);
2987 /* Determine the width standard for comparison with the fonts we find. */
2995 /* Don't die if we get called with a terminal frame. */
2996 if (! FRAME_X_P (f
))
2997 error ("non-X frame used in `x-list-fonts'");
2999 face_id
= face_name_id_number (f
, face
);
3001 if (face_id
< 0 || face_id
>= FRAME_N_PARAM_FACES (f
)
3002 || FRAME_PARAM_FACES (f
) [face_id
] == 0)
3003 size_ref
= f
->display
.x
->font
;
3006 size_ref
= FRAME_PARAM_FACES (f
) [face_id
]->font
;
3007 if (size_ref
== (XFontStruct
*) (~0))
3008 size_ref
= f
->display
.x
->font
;
3012 /* See if we cached the result for this particular query. */
3013 list
= Fassoc (pattern
,
3014 XCONS (FRAME_X_DISPLAY_INFO (f
)->name_list_element
)->cdr
);
3016 /* We have info in the cache for this PATTERN. */
3019 Lisp_Object tem
, newlist
;
3021 /* We have info about this pattern. */
3022 list
= XCONS (list
)->cdr
;
3029 /* Filter the cached info and return just the fonts that match FACE. */
3031 for (tem
= list
; CONSP (tem
); tem
= XCONS (tem
)->cdr
)
3033 XFontStruct
*thisinfo
;
3035 thisinfo
= XLoadQueryFont (FRAME_X_DISPLAY (f
),
3036 XSTRING (XCONS (tem
)->car
)->data
);
3038 if (thisinfo
&& same_size_fonts (thisinfo
, size_ref
))
3039 newlist
= Fcons (XCONS (tem
)->car
, newlist
);
3041 XFreeFont (FRAME_X_DISPLAY (f
), thisinfo
);
3051 /* Solaris 2.3 has a bug in XListFontsWithInfo. */
3052 #ifndef BROKEN_XLISTFONTSWITHINFO
3054 names
= XListFontsWithInfo (FRAME_X_DISPLAY (f
),
3055 XSTRING (pattern
)->data
,
3056 2000, /* maxnames */
3057 &num_fonts
, /* count_return */
3058 &info
); /* info_return */
3061 names
= XListFonts (FRAME_X_DISPLAY (f
),
3062 XSTRING (pattern
)->data
,
3063 2000, /* maxnames */
3064 &num_fonts
); /* count_return */
3073 Lisp_Object full_list
;
3075 /* Make a list of all the fonts we got back.
3076 Store that in the font cache for the display. */
3078 for (i
= 0; i
< num_fonts
; i
++)
3079 full_list
= Fcons (build_string (names
[i
]), full_list
);
3080 XCONS (FRAME_X_DISPLAY_INFO (f
)->name_list_element
)->cdr
3081 = Fcons (Fcons (pattern
, full_list
),
3082 XCONS (FRAME_X_DISPLAY_INFO (f
)->name_list_element
)->cdr
);
3084 /* Make a list of the fonts that have the right width. */
3086 for (i
= 0; i
< num_fonts
; i
++)
3094 #ifdef BROKEN_XLISTFONTSWITHINFO
3095 XFontStruct
*thisinfo
;
3098 thisinfo
= XLoadQueryFont (FRAME_X_DISPLAY (f
), names
[i
]);
3101 keeper
= thisinfo
&& same_size_fonts (thisinfo
, size_ref
);
3103 keeper
= same_size_fonts (&info
[i
], size_ref
);
3107 list
= Fcons (build_string (names
[i
]), list
);
3109 list
= Fnreverse (list
);
3112 #ifndef BROKEN_XLISTFONTSWITHINFO
3114 XFreeFontInfo (names
, info
, num_fonts
);
3117 XFreeFontNames (names
);
3125 DEFUN ("x-color-defined-p", Fx_color_defined_p
, Sx_color_defined_p
, 1, 2, 0,
3126 "Return non-nil color COLOR is supported on frame FRAME.\n\
3127 If FRAME is omitted or nil, use the selected frame.")
3129 Lisp_Object color
, frame
;
3132 FRAME_PTR f
= check_x_frame (frame
);
3134 CHECK_STRING (color
, 1);
3136 if (defined_color (f
, XSTRING (color
)->data
, &foo
, 0))
3142 DEFUN ("x-color-values", Fx_color_values
, Sx_color_values
, 1, 2, 0,
3143 "Return a description of the color named COLOR on frame FRAME.\n\
3144 The value is a list of integer RGB values--(RED GREEN BLUE).\n\
3145 These values appear to range from 0 to 65280 or 65535, depending\n\
3146 on the system; white is (65280 65280 65280) or (65535 65535 65535).\n\
3147 If FRAME is omitted or nil, use the selected frame.")
3149 Lisp_Object color
, frame
;
3152 FRAME_PTR f
= check_x_frame (frame
);
3154 CHECK_STRING (color
, 1);
3156 if (defined_color (f
, XSTRING (color
)->data
, &foo
, 0))
3160 rgb
[0] = make_number (foo
.red
);
3161 rgb
[1] = make_number (foo
.green
);
3162 rgb
[2] = make_number (foo
.blue
);
3163 return Flist (3, rgb
);
3169 DEFUN ("x-display-color-p", Fx_display_color_p
, Sx_display_color_p
, 0, 1, 0,
3170 "Return t if the X display supports color.\n\
3171 The optional argument DISPLAY specifies which display to ask about.\n\
3172 DISPLAY should be either a frame or a display name (a string).\n\
3173 If omitted or nil, that stands for the selected frame's display.")
3175 Lisp_Object display
;
3177 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
3179 if (dpyinfo
->n_planes
<= 2)
3182 switch (dpyinfo
->visual
->class)
3195 DEFUN ("x-display-grayscale-p", Fx_display_grayscale_p
, Sx_display_grayscale_p
,
3197 "Return t if the X display supports shades of gray.\n\
3198 The optional argument DISPLAY specifies which display to ask about.\n\
3199 DISPLAY should be either a frame or a display name (a string).\n\
3200 If omitted or nil, that stands for the selected frame's display.")
3202 Lisp_Object display
;
3204 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
3206 if (dpyinfo
->n_planes
<= 2)
3209 return (dpyinfo
->n_planes
> 1
3210 && (dpyinfo
->visual
->class == StaticGray
3211 || dpyinfo
->visual
->class == GrayScale
));
3214 DEFUN ("x-display-pixel-width", Fx_display_pixel_width
, Sx_display_pixel_width
,
3216 "Returns the width in pixels of the X display DISPLAY.\n\
3217 The optional argument DISPLAY specifies which display to ask about.\n\
3218 DISPLAY should be either a frame or a display name (a string).\n\
3219 If omitted or nil, that stands for the selected frame's display.")
3221 Lisp_Object display
;
3223 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
3225 return make_number (dpyinfo
->width
);
3228 DEFUN ("x-display-pixel-height", Fx_display_pixel_height
,
3229 Sx_display_pixel_height
, 0, 1, 0,
3230 "Returns the height in pixels of the X display DISPLAY.\n\
3231 The optional argument DISPLAY specifies which display to ask about.\n\
3232 DISPLAY should be either a frame or a display name (a string).\n\
3233 If omitted or nil, that stands for the selected frame's display.")
3235 Lisp_Object display
;
3237 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
3239 return make_number (dpyinfo
->height
);
3242 DEFUN ("x-display-planes", Fx_display_planes
, Sx_display_planes
,
3244 "Returns the number of bitplanes of the X display DISPLAY.\n\
3245 The optional argument DISPLAY specifies which display to ask about.\n\
3246 DISPLAY should be either a frame or a display name (a string).\n\
3247 If omitted or nil, that stands for the selected frame's display.")
3249 Lisp_Object display
;
3251 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
3253 return make_number (dpyinfo
->n_planes
);
3256 DEFUN ("x-display-color-cells", Fx_display_color_cells
, Sx_display_color_cells
,
3258 "Returns the number of color cells of the X display DISPLAY.\n\
3259 The optional argument DISPLAY specifies which display to ask about.\n\
3260 DISPLAY should be either a frame or a display name (a string).\n\
3261 If omitted or nil, that stands for the selected frame's display.")
3263 Lisp_Object display
;
3265 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
3267 return make_number (DisplayCells (dpyinfo
->display
,
3268 XScreenNumberOfScreen (dpyinfo
->screen
)));
3271 DEFUN ("x-server-max-request-size", Fx_server_max_request_size
,
3272 Sx_server_max_request_size
,
3274 "Returns the maximum request size of the X server of display DISPLAY.\n\
3275 The optional argument DISPLAY specifies which display to ask about.\n\
3276 DISPLAY should be either a frame or a display name (a string).\n\
3277 If omitted or nil, that stands for the selected frame's display.")
3279 Lisp_Object display
;
3281 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
3283 return make_number (MAXREQUEST (dpyinfo
->display
));
3286 DEFUN ("x-server-vendor", Fx_server_vendor
, Sx_server_vendor
, 0, 1, 0,
3287 "Returns the vendor ID string of the X server of display DISPLAY.\n\
3288 The optional argument DISPLAY specifies which display to ask about.\n\
3289 DISPLAY should be either a frame or a display name (a string).\n\
3290 If omitted or nil, that stands for the selected frame's display.")
3292 Lisp_Object display
;
3294 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
3295 char *vendor
= ServerVendor (dpyinfo
->display
);
3297 if (! vendor
) vendor
= "";
3298 return build_string (vendor
);
3301 DEFUN ("x-server-version", Fx_server_version
, Sx_server_version
, 0, 1, 0,
3302 "Returns the version numbers of the X server of display DISPLAY.\n\
3303 The value is a list of three integers: the major and minor\n\
3304 version numbers of the X Protocol in use, and the vendor-specific release\n\
3305 number. See also the function `x-server-vendor'.\n\n\
3306 The optional argument DISPLAY specifies which display to ask about.\n\
3307 DISPLAY should be either a frame or a display name (a string).\n\
3308 If omitted or nil, that stands for the selected frame's display.")
3310 Lisp_Object display
;
3312 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
3313 Display
*dpy
= dpyinfo
->display
;
3315 return Fcons (make_number (ProtocolVersion (dpy
)),
3316 Fcons (make_number (ProtocolRevision (dpy
)),
3317 Fcons (make_number (VendorRelease (dpy
)), Qnil
)));
3320 DEFUN ("x-display-screens", Fx_display_screens
, Sx_display_screens
, 0, 1, 0,
3321 "Returns the number of screens on the X server of display DISPLAY.\n\
3322 The optional argument DISPLAY specifies which display to ask about.\n\
3323 DISPLAY should be either a frame or a display name (a string).\n\
3324 If omitted or nil, that stands for the selected frame's display.")
3326 Lisp_Object display
;
3328 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
3330 return make_number (ScreenCount (dpyinfo
->display
));
3333 DEFUN ("x-display-mm-height", Fx_display_mm_height
, Sx_display_mm_height
, 0, 1, 0,
3334 "Returns the height in millimeters of the X display DISPLAY.\n\
3335 The optional argument DISPLAY specifies which display to ask about.\n\
3336 DISPLAY should be either a frame or a display name (a string).\n\
3337 If omitted or nil, that stands for the selected frame's display.")
3339 Lisp_Object display
;
3341 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
3343 return make_number (HeightMMOfScreen (dpyinfo
->screen
));
3346 DEFUN ("x-display-mm-width", Fx_display_mm_width
, Sx_display_mm_width
, 0, 1, 0,
3347 "Returns the width in millimeters of the X display DISPLAY.\n\
3348 The optional argument DISPLAY specifies which display to ask about.\n\
3349 DISPLAY should be either a frame or a display name (a string).\n\
3350 If omitted or nil, that stands for the selected frame's display.")
3352 Lisp_Object display
;
3354 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
3356 return make_number (WidthMMOfScreen (dpyinfo
->screen
));
3359 DEFUN ("x-display-backing-store", Fx_display_backing_store
,
3360 Sx_display_backing_store
, 0, 1, 0,
3361 "Returns an indication of whether X display DISPLAY does backing store.\n\
3362 The value may be `always', `when-mapped', or `not-useful'.\n\
3363 The optional argument DISPLAY specifies which display to ask about.\n\
3364 DISPLAY should be either a frame or a display name (a string).\n\
3365 If omitted or nil, that stands for the selected frame's display.")
3367 Lisp_Object display
;
3369 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
3371 switch (DoesBackingStore (dpyinfo
->screen
))
3374 return intern ("always");
3377 return intern ("when-mapped");
3380 return intern ("not-useful");
3383 error ("Strange value for BackingStore parameter of screen");
3387 DEFUN ("x-display-visual-class", Fx_display_visual_class
,
3388 Sx_display_visual_class
, 0, 1, 0,
3389 "Returns the visual class of the X display DISPLAY.\n\
3390 The value is one of the symbols `static-gray', `gray-scale',\n\
3391 `static-color', `pseudo-color', `true-color', or `direct-color'.\n\n\
3392 The optional argument DISPLAY specifies which display to ask about.\n\
3393 DISPLAY should be either a frame or a display name (a string).\n\
3394 If omitted or nil, that stands for the selected frame's display.")
3396 Lisp_Object display
;
3398 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
3400 switch (dpyinfo
->visual
->class)
3402 case StaticGray
: return (intern ("static-gray"));
3403 case GrayScale
: return (intern ("gray-scale"));
3404 case StaticColor
: return (intern ("static-color"));
3405 case PseudoColor
: return (intern ("pseudo-color"));
3406 case TrueColor
: return (intern ("true-color"));
3407 case DirectColor
: return (intern ("direct-color"));
3409 error ("Display has an unknown visual class");
3413 DEFUN ("x-display-save-under", Fx_display_save_under
,
3414 Sx_display_save_under
, 0, 1, 0,
3415 "Returns t if the X display DISPLAY supports the save-under feature.\n\
3416 The optional argument DISPLAY specifies which display to ask about.\n\
3417 DISPLAY should be either a frame or a display name (a string).\n\
3418 If omitted or nil, that stands for the selected frame's display.")
3420 Lisp_Object display
;
3422 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
3424 if (DoesSaveUnders (dpyinfo
->screen
) == True
)
3432 register struct frame
*f
;
3434 return PIXEL_WIDTH (f
);
3439 register struct frame
*f
;
3441 return PIXEL_HEIGHT (f
);
3446 register struct frame
*f
;
3448 return FONT_WIDTH (f
->display
.x
->font
);
3453 register struct frame
*f
;
3455 return f
->display
.x
->line_height
;
3459 x_screen_planes (frame
)
3462 return FRAME_X_DISPLAY_INFO (XFRAME (frame
))->n_planes
;
3465 #if 0 /* These no longer seem like the right way to do things. */
3467 /* Draw a rectangle on the frame with left top corner including
3468 the character specified by LEFT_CHAR and TOP_CHAR. The rectangle is
3469 CHARS by LINES wide and long and is the color of the cursor. */
3472 x_rectangle (f
, gc
, left_char
, top_char
, chars
, lines
)
3473 register struct frame
*f
;
3475 register int top_char
, left_char
, chars
, lines
;
3479 int left
= (left_char
* FONT_WIDTH (f
->display
.x
->font
)
3480 + f
->display
.x
->internal_border_width
);
3481 int top
= (top_char
* f
->display
.x
->line_height
3482 + f
->display
.x
->internal_border_width
);
3485 width
= FONT_WIDTH (f
->display
.x
->font
) / 2;
3487 width
= FONT_WIDTH (f
->display
.x
->font
) * chars
;
3489 height
= f
->display
.x
->line_height
/ 2;
3491 height
= f
->display
.x
->line_height
* lines
;
3493 XDrawRectangle (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
3494 gc
, left
, top
, width
, height
);
3497 DEFUN ("x-draw-rectangle", Fx_draw_rectangle
, Sx_draw_rectangle
, 5, 5, 0,
3498 "Draw a rectangle on FRAME between coordinates specified by\n\
3499 numbers X0, Y0, X1, Y1 in the cursor pixel.")
3500 (frame
, X0
, Y0
, X1
, Y1
)
3501 register Lisp_Object frame
, X0
, X1
, Y0
, Y1
;
3503 register int x0
, y0
, x1
, y1
, top
, left
, n_chars
, n_lines
;
3505 CHECK_LIVE_FRAME (frame
, 0);
3506 CHECK_NUMBER (X0
, 0);
3507 CHECK_NUMBER (Y0
, 1);
3508 CHECK_NUMBER (X1
, 2);
3509 CHECK_NUMBER (Y1
, 3);
3519 n_lines
= y1
- y0
+ 1;
3524 n_lines
= y0
- y1
+ 1;
3530 n_chars
= x1
- x0
+ 1;
3535 n_chars
= x0
- x1
+ 1;
3539 x_rectangle (XFRAME (frame
), XFRAME (frame
)->display
.x
->cursor_gc
,
3540 left
, top
, n_chars
, n_lines
);
3546 DEFUN ("x-erase-rectangle", Fx_erase_rectangle
, Sx_erase_rectangle
, 5, 5, 0,
3547 "Draw a rectangle drawn on FRAME between coordinates\n\
3548 X0, Y0, X1, Y1 in the regular background-pixel.")
3549 (frame
, X0
, Y0
, X1
, Y1
)
3550 register Lisp_Object frame
, X0
, Y0
, X1
, Y1
;
3552 register int x0
, y0
, x1
, y1
, top
, left
, n_chars
, n_lines
;
3554 CHECK_LIVE_FRAME (frame
, 0);
3555 CHECK_NUMBER (X0
, 0);
3556 CHECK_NUMBER (Y0
, 1);
3557 CHECK_NUMBER (X1
, 2);
3558 CHECK_NUMBER (Y1
, 3);
3568 n_lines
= y1
- y0
+ 1;
3573 n_lines
= y0
- y1
+ 1;
3579 n_chars
= x1
- x0
+ 1;
3584 n_chars
= x0
- x1
+ 1;
3588 x_rectangle (XFRAME (frame
), XFRAME (frame
)->display
.x
->reverse_gc
,
3589 left
, top
, n_chars
, n_lines
);
3595 /* Draw lines around the text region beginning at the character position
3596 TOP_X, TOP_Y and ending at BOTTOM_X and BOTTOM_Y. GC specifies the
3597 pixel and line characteristics. */
3599 #define line_len(line) (FRAME_CURRENT_GLYPHS (f)->used[(line)])
3602 outline_region (f
, gc
, top_x
, top_y
, bottom_x
, bottom_y
)
3603 register struct frame
*f
;
3605 int top_x
, top_y
, bottom_x
, bottom_y
;
3607 register int ibw
= f
->display
.x
->internal_border_width
;
3608 register int font_w
= FONT_WIDTH (f
->display
.x
->font
);
3609 register int font_h
= f
->display
.x
->line_height
;
3611 int x
= line_len (y
);
3612 XPoint
*pixel_points
3613 = (XPoint
*) alloca (((bottom_y
- top_y
+ 2) * 4) * sizeof (XPoint
));
3614 register XPoint
*this_point
= pixel_points
;
3616 /* Do the horizontal top line/lines */
3619 this_point
->x
= ibw
;
3620 this_point
->y
= ibw
+ (font_h
* top_y
);
3623 this_point
->x
= ibw
+ (font_w
/ 2); /* Half-size for newline chars. */
3625 this_point
->x
= ibw
+ (font_w
* x
);
3626 this_point
->y
= (this_point
- 1)->y
;
3630 this_point
->x
= ibw
;
3631 this_point
->y
= ibw
+ (font_h
* (top_y
+ 1));
3633 this_point
->x
= ibw
+ (font_w
* top_x
);
3634 this_point
->y
= (this_point
- 1)->y
;
3636 this_point
->x
= (this_point
- 1)->x
;
3637 this_point
->y
= ibw
+ (font_h
* top_y
);
3639 this_point
->x
= ibw
+ (font_w
* x
);
3640 this_point
->y
= (this_point
- 1)->y
;
3643 /* Now do the right side. */
3644 while (y
< bottom_y
)
3645 { /* Right vertical edge */
3647 this_point
->x
= (this_point
- 1)->x
;
3648 this_point
->y
= ibw
+ (font_h
* (y
+ 1));
3651 y
++; /* Horizontal connection to next line */
3654 this_point
->x
= ibw
+ (font_w
/ 2);
3656 this_point
->x
= ibw
+ (font_w
* x
);
3658 this_point
->y
= (this_point
- 1)->y
;
3661 /* Now do the bottom and connect to the top left point. */
3662 this_point
->x
= ibw
+ (font_w
* (bottom_x
+ 1));
3665 this_point
->x
= (this_point
- 1)->x
;
3666 this_point
->y
= ibw
+ (font_h
* (bottom_y
+ 1));
3668 this_point
->x
= ibw
;
3669 this_point
->y
= (this_point
- 1)->y
;
3671 this_point
->x
= pixel_points
->x
;
3672 this_point
->y
= pixel_points
->y
;
3674 XDrawLines (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
3676 (this_point
- pixel_points
+ 1), CoordModeOrigin
);
3679 DEFUN ("x-contour-region", Fx_contour_region
, Sx_contour_region
, 1, 1, 0,
3680 "Highlight the region between point and the character under the mouse\n\
3683 register Lisp_Object event
;
3685 register int x0
, y0
, x1
, y1
;
3686 register struct frame
*f
= selected_frame
;
3687 register int p1
, p2
;
3689 CHECK_CONS (event
, 0);
3692 x0
= XINT (Fcar (Fcar (event
)));
3693 y0
= XINT (Fcar (Fcdr (Fcar (event
))));
3695 /* If the mouse is past the end of the line, don't that area. */
3696 /* ReWrite this... */
3701 if (y1
> y0
) /* point below mouse */
3702 outline_region (f
, f
->display
.x
->cursor_gc
,
3704 else if (y1
< y0
) /* point above mouse */
3705 outline_region (f
, f
->display
.x
->cursor_gc
,
3707 else /* same line: draw horizontal rectangle */
3710 x_rectangle (f
, f
->display
.x
->cursor_gc
,
3711 x0
, y0
, (x1
- x0
+ 1), 1);
3713 x_rectangle (f
, f
->display
.x
->cursor_gc
,
3714 x1
, y1
, (x0
- x1
+ 1), 1);
3717 XFlush (FRAME_X_DISPLAY (f
));
3723 DEFUN ("x-uncontour-region", Fx_uncontour_region
, Sx_uncontour_region
, 1, 1, 0,
3724 "Erase any highlighting of the region between point and the character\n\
3725 at X, Y on the selected frame.")
3727 register Lisp_Object event
;
3729 register int x0
, y0
, x1
, y1
;
3730 register struct frame
*f
= selected_frame
;
3733 x0
= XINT (Fcar (Fcar (event
)));
3734 y0
= XINT (Fcar (Fcdr (Fcar (event
))));
3738 if (y1
> y0
) /* point below mouse */
3739 outline_region (f
, f
->display
.x
->reverse_gc
,
3741 else if (y1
< y0
) /* point above mouse */
3742 outline_region (f
, f
->display
.x
->reverse_gc
,
3744 else /* same line: draw horizontal rectangle */
3747 x_rectangle (f
, f
->display
.x
->reverse_gc
,
3748 x0
, y0
, (x1
- x0
+ 1), 1);
3750 x_rectangle (f
, f
->display
.x
->reverse_gc
,
3751 x1
, y1
, (x0
- x1
+ 1), 1);
3759 int contour_begin_x
, contour_begin_y
;
3760 int contour_end_x
, contour_end_y
;
3761 int contour_npoints
;
3763 /* Clip the top part of the contour lines down (and including) line Y_POS.
3764 If X_POS is in the middle (rather than at the end) of the line, drop
3765 down a line at that character. */
3768 clip_contour_top (y_pos
, x_pos
)
3770 register XPoint
*begin
= contour_lines
[y_pos
].top_left
;
3771 register XPoint
*end
;
3772 register int npoints
;
3773 register struct display_line
*line
= selected_frame
->phys_lines
[y_pos
+ 1];
3775 if (x_pos
>= line
->len
- 1) /* Draw one, straight horizontal line. */
3777 end
= contour_lines
[y_pos
].top_right
;
3778 npoints
= (end
- begin
+ 1);
3779 XDrawLines (x_current_display
, contour_window
,
3780 contour_erase_gc
, begin_erase
, npoints
, CoordModeOrigin
);
3782 bcopy (end
, begin
+ 1, contour_last_point
- end
+ 1);
3783 contour_last_point
-= (npoints
- 2);
3784 XDrawLines (x_current_display
, contour_window
,
3785 contour_erase_gc
, begin
, 2, CoordModeOrigin
);
3786 XFlush (x_current_display
);
3788 /* Now, update contour_lines structure. */
3793 register XPoint
*p
= begin
+ 1;
3794 end
= contour_lines
[y_pos
].bottom_right
;
3795 npoints
= (end
- begin
+ 1);
3796 XDrawLines (x_current_display
, contour_window
,
3797 contour_erase_gc
, begin_erase
, npoints
, CoordModeOrigin
);
3800 p
->x
= ibw
+ (font_w
* (x_pos
+ 1));
3802 p
->y
= begin
->y
+ font_h
;
3804 bcopy (end
, begin
+ 3, contour_last_point
- end
+ 1);
3805 contour_last_point
-= (npoints
- 5);
3806 XDrawLines (x_current_display
, contour_window
,
3807 contour_erase_gc
, begin
, 4, CoordModeOrigin
);
3808 XFlush (x_current_display
);
3810 /* Now, update contour_lines structure. */
3814 /* Erase the top horizontal lines of the contour, and then extend
3815 the contour upwards. */
3818 extend_contour_top (line
)
3823 clip_contour_bottom (x_pos
, y_pos
)
3829 extend_contour_bottom (x_pos
, y_pos
)
3833 DEFUN ("x-select-region", Fx_select_region
, Sx_select_region
, 1, 1, "e",
3838 register struct frame
*f
= selected_frame
;
3839 register int point_x
= f
->cursor_x
;
3840 register int point_y
= f
->cursor_y
;
3841 register int mouse_below_point
;
3842 register Lisp_Object obj
;
3843 register int x_contour_x
, x_contour_y
;
3845 x_contour_x
= x_mouse_x
;
3846 x_contour_y
= x_mouse_y
;
3847 if (x_contour_y
> point_y
|| (x_contour_y
== point_y
3848 && x_contour_x
> point_x
))
3850 mouse_below_point
= 1;
3851 outline_region (f
, f
->display
.x
->cursor_gc
, point_x
, point_y
,
3852 x_contour_x
, x_contour_y
);
3856 mouse_below_point
= 0;
3857 outline_region (f
, f
->display
.x
->cursor_gc
, x_contour_x
, x_contour_y
,
3863 obj
= read_char (-1, 0, 0, Qnil
, 0);
3867 if (mouse_below_point
)
3869 if (x_mouse_y
<= point_y
) /* Flipped. */
3871 mouse_below_point
= 0;
3873 outline_region (f
, f
->display
.x
->reverse_gc
, point_x
, point_y
,
3874 x_contour_x
, x_contour_y
);
3875 outline_region (f
, f
->display
.x
->cursor_gc
, x_mouse_x
, x_mouse_y
,
3878 else if (x_mouse_y
< x_contour_y
) /* Bottom clipped. */
3880 clip_contour_bottom (x_mouse_y
);
3882 else if (x_mouse_y
> x_contour_y
) /* Bottom extended. */
3884 extend_bottom_contour (x_mouse_y
);
3887 x_contour_x
= x_mouse_x
;
3888 x_contour_y
= x_mouse_y
;
3890 else /* mouse above or same line as point */
3892 if (x_mouse_y
>= point_y
) /* Flipped. */
3894 mouse_below_point
= 1;
3896 outline_region (f
, f
->display
.x
->reverse_gc
,
3897 x_contour_x
, x_contour_y
, point_x
, point_y
);
3898 outline_region (f
, f
->display
.x
->cursor_gc
, point_x
, point_y
,
3899 x_mouse_x
, x_mouse_y
);
3901 else if (x_mouse_y
> x_contour_y
) /* Top clipped. */
3903 clip_contour_top (x_mouse_y
);
3905 else if (x_mouse_y
< x_contour_y
) /* Top extended. */
3907 extend_contour_top (x_mouse_y
);
3912 unread_command_event
= obj
;
3913 if (mouse_below_point
)
3915 contour_begin_x
= point_x
;
3916 contour_begin_y
= point_y
;
3917 contour_end_x
= x_contour_x
;
3918 contour_end_y
= x_contour_y
;
3922 contour_begin_x
= x_contour_x
;
3923 contour_begin_y
= x_contour_y
;
3924 contour_end_x
= point_x
;
3925 contour_end_y
= point_y
;
3930 DEFUN ("x-horizontal-line", Fx_horizontal_line
, Sx_horizontal_line
, 1, 1, "e",
3935 register Lisp_Object obj
;
3936 struct frame
*f
= selected_frame
;
3937 register struct window
*w
= XWINDOW (selected_window
);
3938 register GC line_gc
= f
->display
.x
->cursor_gc
;
3939 register GC erase_gc
= f
->display
.x
->reverse_gc
;
3941 char dash_list
[] = {6, 4, 6, 4};
3943 XGCValues gc_values
;
3945 register int previous_y
;
3946 register int line
= (x_mouse_y
+ 1) * f
->display
.x
->line_height
3947 + f
->display
.x
->internal_border_width
;
3948 register int left
= f
->display
.x
->internal_border_width
3950 * FONT_WIDTH (f
->display
.x
->font
));
3951 register int right
= left
+ (w
->width
3952 * FONT_WIDTH (f
->display
.x
->font
))
3953 - f
->display
.x
->internal_border_width
;
3957 gc_values
.foreground
= f
->display
.x
->cursor_pixel
;
3958 gc_values
.background
= f
->display
.x
->background_pixel
;
3959 gc_values
.line_width
= 1;
3960 gc_values
.line_style
= LineOnOffDash
;
3961 gc_values
.cap_style
= CapRound
;
3962 gc_values
.join_style
= JoinRound
;
3964 line_gc
= XCreateGC (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
3965 GCLineStyle
| GCJoinStyle
| GCCapStyle
3966 | GCLineWidth
| GCForeground
| GCBackground
,
3968 XSetDashes (FRAME_X_DISPLAY (f
), line_gc
, 0, dash_list
, dashes
);
3969 gc_values
.foreground
= f
->display
.x
->background_pixel
;
3970 gc_values
.background
= f
->display
.x
->foreground_pixel
;
3971 erase_gc
= XCreateGC (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
3972 GCLineStyle
| GCJoinStyle
| GCCapStyle
3973 | GCLineWidth
| GCForeground
| GCBackground
,
3975 XSetDashes (FRAME_X_DISPLAY (f
), erase_gc
, 0, dash_list
, dashes
);
3981 if (x_mouse_y
>= XINT (w
->top
)
3982 && x_mouse_y
< XINT (w
->top
) + XINT (w
->height
) - 1)
3984 previous_y
= x_mouse_y
;
3985 line
= (x_mouse_y
+ 1) * f
->display
.x
->line_height
3986 + f
->display
.x
->internal_border_width
;
3987 XDrawLine (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
3988 line_gc
, left
, line
, right
, line
);
3990 XFlush (FRAME_X_DISPLAY (f
));
3995 obj
= read_char (-1, 0, 0, Qnil
, 0);
3997 || (! EQ (Fcar (Fcdr (Fcdr (obj
))),
3998 Qvertical_scroll_bar
))
4002 XDrawLine (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
4003 erase_gc
, left
, line
, right
, line
);
4005 unread_command_event
= obj
;
4007 XFreeGC (FRAME_X_DISPLAY (f
), line_gc
);
4008 XFreeGC (FRAME_X_DISPLAY (f
), erase_gc
);
4013 while (x_mouse_y
== previous_y
);
4016 XDrawLine (FRAME_X_DISPLAY (f
), FRAME_X_WINDOW (f
),
4017 erase_gc
, left
, line
, right
, line
);
4024 /* These keep track of the rectangle following the pointer. */
4025 int mouse_track_top
, mouse_track_left
, mouse_track_width
;
4027 /* Offset in buffer of character under the pointer, or 0. */
4028 int mouse_buffer_offset
;
4030 DEFUN ("x-track-pointer", Fx_track_pointer
, Sx_track_pointer
, 0, 0, 0,
4031 "Track the pointer.")
4034 static Cursor current_pointer_shape
;
4035 FRAME_PTR f
= x_mouse_frame
;
4038 if (EQ (Vmouse_frame_part
, Qtext_part
)
4039 && (current_pointer_shape
!= f
->display
.x
->nontext_cursor
))
4044 current_pointer_shape
= f
->display
.x
->nontext_cursor
;
4045 XDefineCursor (FRAME_X_DISPLAY (f
),
4047 current_pointer_shape
);
4049 buf
= XBUFFER (XWINDOW (Vmouse_window
)->buffer
);
4050 c
= *(BUF_CHAR_ADDRESS (buf
, mouse_buffer_offset
));
4052 else if (EQ (Vmouse_frame_part
, Qmodeline_part
)
4053 && (current_pointer_shape
!= f
->display
.x
->modeline_cursor
))
4055 current_pointer_shape
= f
->display
.x
->modeline_cursor
;
4056 XDefineCursor (FRAME_X_DISPLAY (f
),
4058 current_pointer_shape
);
4061 XFlush (FRAME_X_DISPLAY (f
));
4067 DEFUN ("x-track-pointer", Fx_track_pointer
, Sx_track_pointer
, 1, 1, "e",
4068 "Draw rectangle around character under mouse pointer, if there is one.")
4072 struct window
*w
= XWINDOW (Vmouse_window
);
4073 struct frame
*f
= XFRAME (WINDOW_FRAME (w
));
4074 struct buffer
*b
= XBUFFER (w
->buffer
);
4077 if (! EQ (Vmouse_window
, selected_window
))
4080 if (EQ (event
, Qnil
))
4084 x_read_mouse_position (selected_frame
, &x
, &y
);
4088 mouse_track_width
= 0;
4089 mouse_track_left
= mouse_track_top
= -1;
4093 if ((x_mouse_x
!= mouse_track_left
4094 && (x_mouse_x
< mouse_track_left
4095 || x_mouse_x
> (mouse_track_left
+ mouse_track_width
)))
4096 || x_mouse_y
!= mouse_track_top
)
4098 int hp
= 0; /* Horizontal position */
4099 int len
= FRAME_CURRENT_GLYPHS (f
)->used
[x_mouse_y
];
4100 int p
= FRAME_CURRENT_GLYPHS (f
)->bufp
[x_mouse_y
];
4101 int tab_width
= XINT (b
->tab_width
);
4102 int ctl_arrow_p
= !NILP (b
->ctl_arrow
);
4104 int mode_line_vpos
= XFASTINT (w
->height
) + XFASTINT (w
->top
) - 1;
4105 int in_mode_line
= 0;
4107 if (! FRAME_CURRENT_GLYPHS (f
)->enable
[x_mouse_y
])
4110 /* Erase previous rectangle. */
4111 if (mouse_track_width
)
4113 x_rectangle (f
, f
->display
.x
->reverse_gc
,
4114 mouse_track_left
, mouse_track_top
,
4115 mouse_track_width
, 1);
4117 if ((mouse_track_left
== f
->phys_cursor_x
4118 || mouse_track_left
== f
->phys_cursor_x
- 1)
4119 && mouse_track_top
== f
->phys_cursor_y
)
4121 x_display_cursor (f
, 1);
4125 mouse_track_left
= x_mouse_x
;
4126 mouse_track_top
= x_mouse_y
;
4127 mouse_track_width
= 0;
4129 if (mouse_track_left
> len
) /* Past the end of line. */
4132 if (mouse_track_top
== mode_line_vpos
)
4138 if (tab_width
<= 0 || tab_width
> 20) tab_width
= 8;
4142 if (len
== f
->width
&& hp
== len
- 1 && c
!= '\n')
4148 mouse_track_width
= tab_width
- (hp
% tab_width
);
4150 hp
+= mouse_track_width
;
4153 mouse_track_left
= hp
- mouse_track_width
;
4159 mouse_track_width
= -1;
4163 if (ctl_arrow_p
&& (c
< 040 || c
== 0177))
4168 mouse_track_width
= 2;
4173 mouse_track_left
= hp
- mouse_track_width
;
4179 mouse_track_width
= 1;
4186 while (hp
<= x_mouse_x
);
4189 if (mouse_track_width
) /* Over text; use text pointer shape. */
4191 XDefineCursor (FRAME_X_DISPLAY (f
),
4193 f
->display
.x
->text_cursor
);
4194 x_rectangle (f
, f
->display
.x
->cursor_gc
,
4195 mouse_track_left
, mouse_track_top
,
4196 mouse_track_width
, 1);
4198 else if (in_mode_line
)
4199 XDefineCursor (FRAME_X_DISPLAY (f
),
4201 f
->display
.x
->modeline_cursor
);
4203 XDefineCursor (FRAME_X_DISPLAY (f
),
4205 f
->display
.x
->nontext_cursor
);
4208 XFlush (FRAME_X_DISPLAY (f
));
4211 obj
= read_char (-1, 0, 0, Qnil
, 0);
4214 while (CONSP (obj
) /* Mouse event */
4215 && EQ (Fcar (Fcdr (Fcdr (obj
))), Qnil
) /* Not scroll bar */
4216 && EQ (Vmouse_depressed
, Qnil
) /* Only motion events */
4217 && EQ (Vmouse_window
, selected_window
) /* In this window */
4220 unread_command_event
= obj
;
4222 if (mouse_track_width
)
4224 x_rectangle (f
, f
->display
.x
->reverse_gc
,
4225 mouse_track_left
, mouse_track_top
,
4226 mouse_track_width
, 1);
4227 mouse_track_width
= 0;
4228 if ((mouse_track_left
== f
->phys_cursor_x
4229 || mouse_track_left
- 1 == f
->phys_cursor_x
)
4230 && mouse_track_top
== f
->phys_cursor_y
)
4232 x_display_cursor (f
, 1);
4235 XDefineCursor (FRAME_X_DISPLAY (f
),
4237 f
->display
.x
->nontext_cursor
);
4238 XFlush (FRAME_X_DISPLAY (f
));
4248 /* Draw a pixmap specified by IMAGE_DATA of dimensions WIDTH and HEIGHT
4249 on the frame F at position X, Y. */
4251 x_draw_pixmap (f
, x
, y
, image_data
, width
, height
)
4253 int x
, y
, width
, height
;
4258 image
= XCreateBitmapFromData (FRAME_X_DISPLAY (f
),
4259 FRAME_X_WINDOW (f
), image_data
,
4261 XCopyPlane (FRAME_X_DISPLAY (f
), image
, FRAME_X_WINDOW (f
),
4262 f
->display
.x
->normal_gc
, 0, 0, width
, height
, x
, y
);
4266 #if 0 /* I'm told these functions are superfluous
4267 given the ability to bind function keys. */
4270 DEFUN ("x-rebind-key", Fx_rebind_key
, Sx_rebind_key
, 3, 3, 0,
4271 "Rebind X keysym KEYSYM, with MODIFIERS, to generate NEWSTRING.\n\
4272 KEYSYM is a string which conforms to the X keysym definitions found\n\
4273 in X11/keysymdef.h, sans the initial XK_. MODIFIERS is nil or a\n\
4274 list of strings specifying modifier keys such as Control_L, which must\n\
4275 also be depressed for NEWSTRING to appear.")
4276 (x_keysym
, modifiers
, newstring
)
4277 register Lisp_Object x_keysym
;
4278 register Lisp_Object modifiers
;
4279 register Lisp_Object newstring
;
4282 register KeySym keysym
;
4283 KeySym modifier_list
[16];
4286 CHECK_STRING (x_keysym
, 1);
4287 CHECK_STRING (newstring
, 3);
4289 keysym
= XStringToKeysym ((char *) XSTRING (x_keysym
)->data
);
4290 if (keysym
== NoSymbol
)
4291 error ("Keysym does not exist");
4293 if (NILP (modifiers
))
4294 XRebindKeysym (x_current_display
, keysym
, modifier_list
, 0,
4295 XSTRING (newstring
)->data
, XSTRING (newstring
)->size
);
4298 register Lisp_Object rest
, mod
;
4301 for (rest
= modifiers
; !NILP (rest
); rest
= Fcdr (rest
))
4304 error ("Can't have more than 16 modifiers");
4307 CHECK_STRING (mod
, 3);
4308 modifier_list
[i
] = XStringToKeysym ((char *) XSTRING (mod
)->data
);
4310 if (modifier_list
[i
] == NoSymbol
4311 || !(IsModifierKey (modifier_list
[i
])
4312 || ((unsigned)(modifier_list
[i
]) == XK_Mode_switch
)
4313 || ((unsigned)(modifier_list
[i
]) == XK_Num_Lock
)))
4315 if (modifier_list
[i
] == NoSymbol
4316 || !IsModifierKey (modifier_list
[i
]))
4318 error ("Element is not a modifier keysym");
4322 XRebindKeysym (x_current_display
, keysym
, modifier_list
, i
,
4323 XSTRING (newstring
)->data
, XSTRING (newstring
)->size
);
4329 DEFUN ("x-rebind-keys", Fx_rebind_keys
, Sx_rebind_keys
, 2, 2, 0,
4330 "Rebind KEYCODE to list of strings STRINGS.\n\
4331 STRINGS should be a list of 16 elements, one for each shift combination.\n\
4332 nil as element means don't change.\n\
4333 See the documentation of `x-rebind-key' for more information.")
4335 register Lisp_Object keycode
;
4336 register Lisp_Object strings
;
4338 register Lisp_Object item
;
4339 register unsigned char *rawstring
;
4340 KeySym rawkey
, modifier
[1];
4342 register unsigned i
;
4345 CHECK_NUMBER (keycode
, 1);
4346 CHECK_CONS (strings
, 2);
4347 rawkey
= (KeySym
) ((unsigned) (XINT (keycode
))) & 255;
4348 for (i
= 0; i
<= 15; strings
= Fcdr (strings
), i
++)
4350 item
= Fcar (strings
);
4353 CHECK_STRING (item
, 2);
4354 strsize
= XSTRING (item
)->size
;
4355 rawstring
= (unsigned char *) xmalloc (strsize
);
4356 bcopy (XSTRING (item
)->data
, rawstring
, strsize
);
4357 modifier
[1] = 1 << i
;
4358 XRebindKeysym (x_current_display
, rawkey
, modifier
, 1,
4359 rawstring
, strsize
);
4364 #endif /* HAVE_X11 */
4367 #ifndef HAVE_XSCREENNUMBEROFSCREEN
4369 XScreenNumberOfScreen (scr
)
4370 register Screen
*scr
;
4372 register Display
*dpy
;
4373 register Screen
*dpyscr
;
4377 dpyscr
= dpy
->screens
;
4379 for (i
= 0; i
< dpy
->nscreens
; i
++, dpyscr
++)
4385 #endif /* not HAVE_XSCREENNUMBEROFSCREEN */
4388 select_visual (dpy
, screen
, depth
)
4391 unsigned int *depth
;
4394 XVisualInfo
*vinfo
, vinfo_template
;
4397 v
= DefaultVisualOfScreen (screen
);
4400 vinfo_template
.visualid
= XVisualIDFromVisual (v
);
4402 vinfo_template
.visualid
= v
->visualid
;
4405 vinfo_template
.screen
= XScreenNumberOfScreen (screen
);
4407 vinfo
= XGetVisualInfo (dpy
,
4408 VisualIDMask
| VisualScreenMask
, &vinfo_template
,
4411 fatal ("Can't get proper X visual info");
4413 if ((1 << vinfo
->depth
) == vinfo
->colormap_size
)
4414 *depth
= vinfo
->depth
;
4418 int n
= vinfo
->colormap_size
- 1;
4427 XFree ((char *) vinfo
);
4431 /* Return the X display structure for the display named NAME.
4432 Open a new connection if necessary. */
4434 struct x_display_info
*
4435 x_display_info_for_name (name
)
4439 struct x_display_info
*dpyinfo
;
4441 CHECK_STRING (name
, 0);
4443 for (dpyinfo
= x_display_list
, names
= x_display_name_list
;
4445 dpyinfo
= dpyinfo
->next
, names
= XCONS (names
)->cdr
)
4448 tem
= Fstring_equal (XCONS (XCONS (names
)->car
)->car
, name
);
4453 validate_x_resource_name ();
4455 dpyinfo
= x_term_init (name
, (unsigned char *)0,
4456 XSTRING (Vx_resource_name
)->data
);
4459 error ("X server %s not responding", XSTRING (name
)->data
);
4462 XSETFASTINT (Vwindow_system_version
, 11);
4467 DEFUN ("x-open-connection", Fx_open_connection
, Sx_open_connection
,
4468 1, 3, 0, "Open a connection to an X server.\n\
4469 DISPLAY is the name of the display to connect to.\n\
4470 Optional second arg XRM-STRING is a string of resources in xrdb format.\n\
4471 If the optional third arg MUST-SUCCEED is non-nil,\n\
4472 terminate Emacs if we can't open the connection.")
4473 (display
, xrm_string
, must_succeed
)
4474 Lisp_Object display
, xrm_string
, must_succeed
;
4476 unsigned int n_planes
;
4477 unsigned char *xrm_option
;
4478 struct x_display_info
*dpyinfo
;
4480 CHECK_STRING (display
, 0);
4481 if (! NILP (xrm_string
))
4482 CHECK_STRING (xrm_string
, 1);
4484 if (! NILP (xrm_string
))
4485 xrm_option
= (unsigned char *) XSTRING (xrm_string
)->data
;
4487 xrm_option
= (unsigned char *) 0;
4489 validate_x_resource_name ();
4491 /* This is what opens the connection and sets x_current_display.
4492 This also initializes many symbols, such as those used for input. */
4493 dpyinfo
= x_term_init (display
, xrm_option
,
4494 XSTRING (Vx_resource_name
)->data
);
4498 if (!NILP (must_succeed
))
4499 fatal ("X server %s not responding.\n\
4500 Check the DISPLAY environment variable or use \"-d\"\n",
4501 XSTRING (display
)->data
);
4503 error ("X server %s not responding", XSTRING (display
)->data
);
4508 XSETFASTINT (Vwindow_system_version
, 11);
4512 DEFUN ("x-close-connection", Fx_close_connection
,
4513 Sx_close_connection
, 1, 1, 0,
4514 "Close the connection to DISPLAY's X server.\n\
4515 For DISPLAY, specify either a frame or a display name (a string).\n\
4516 If DISPLAY is nil, that stands for the selected frame's display.")
4518 Lisp_Object display
;
4520 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
4521 struct x_display_info
*tail
;
4524 if (dpyinfo
->reference_count
> 0)
4525 error ("Display still has frames on it");
4528 /* Free the fonts in the font table. */
4529 for (i
= 0; i
< dpyinfo
->n_fonts
; i
++)
4531 if (dpyinfo
->font_table
[i
].name
)
4532 free (dpyinfo
->font_table
[i
].name
);
4533 /* Don't free the full_name string;
4534 it is always shared with something else. */
4535 XFreeFont (dpyinfo
->display
, dpyinfo
->font_table
[i
].font
);
4537 x_destroy_all_bitmaps (dpyinfo
);
4538 XSetCloseDownMode (dpyinfo
->display
, DestroyAll
);
4540 #ifdef USE_X_TOOLKIT
4541 XtCloseDisplay (dpyinfo
->display
);
4543 XCloseDisplay (dpyinfo
->display
);
4546 x_delete_display (dpyinfo
);
4552 DEFUN ("x-display-list", Fx_display_list
, Sx_display_list
, 0, 0, 0,
4553 "Return the list of display names that Emacs has connections to.")
4556 Lisp_Object tail
, result
;
4559 for (tail
= x_display_name_list
; ! NILP (tail
); tail
= XCONS (tail
)->cdr
)
4560 result
= Fcons (XCONS (XCONS (tail
)->car
)->car
, result
);
4565 DEFUN ("x-synchronize", Fx_synchronize
, Sx_synchronize
, 1, 2, 0,
4566 "If ON is non-nil, report X errors as soon as the erring request is made.\n\
4567 If ON is nil, allow buffering of requests.\n\
4568 Turning on synchronization prohibits the Xlib routines from buffering\n\
4569 requests and seriously degrades performance, but makes debugging much\n\
4571 The optional second argument DISPLAY specifies which display to act on.\n\
4572 DISPLAY should be either a frame or a display name (a string).\n\
4573 If DISPLAY is omitted or nil, that stands for the selected frame's display.")
4575 Lisp_Object display
, on
;
4577 struct x_display_info
*dpyinfo
= check_x_display_info (display
);
4579 XSynchronize (dpyinfo
->display
, !EQ (on
, Qnil
));
4584 /* Wait for responses to all X commands issued so far for frame F. */
4591 XSync (FRAME_X_DISPLAY (f
), False
);
4597 /* This is zero if not using X windows. */
4600 /* The section below is built by the lisp expression at the top of the file,
4601 just above where these variables are declared. */
4602 /*&&& init symbols here &&&*/
4603 Qauto_raise
= intern ("auto-raise");
4604 staticpro (&Qauto_raise
);
4605 Qauto_lower
= intern ("auto-lower");
4606 staticpro (&Qauto_lower
);
4607 Qbackground_color
= intern ("background-color");
4608 staticpro (&Qbackground_color
);
4609 Qbar
= intern ("bar");
4611 Qborder_color
= intern ("border-color");
4612 staticpro (&Qborder_color
);
4613 Qborder_width
= intern ("border-width");
4614 staticpro (&Qborder_width
);
4615 Qbox
= intern ("box");
4617 Qcursor_color
= intern ("cursor-color");
4618 staticpro (&Qcursor_color
);
4619 Qcursor_type
= intern ("cursor-type");
4620 staticpro (&Qcursor_type
);
4621 Qfont
= intern ("font");
4623 Qforeground_color
= intern ("foreground-color");
4624 staticpro (&Qforeground_color
);
4625 Qgeometry
= intern ("geometry");
4626 staticpro (&Qgeometry
);
4627 Qicon_left
= intern ("icon-left");
4628 staticpro (&Qicon_left
);
4629 Qicon_top
= intern ("icon-top");
4630 staticpro (&Qicon_top
);
4631 Qicon_type
= intern ("icon-type");
4632 staticpro (&Qicon_type
);
4633 Qinternal_border_width
= intern ("internal-border-width");
4634 staticpro (&Qinternal_border_width
);
4635 Qleft
= intern ("left");
4637 Qmouse_color
= intern ("mouse-color");
4638 staticpro (&Qmouse_color
);
4639 Qnone
= intern ("none");
4641 Qparent_id
= intern ("parent-id");
4642 staticpro (&Qparent_id
);
4643 Qscroll_bar_width
= intern ("scroll-bar-width");
4644 staticpro (&Qscroll_bar_width
);
4645 Qsuppress_icon
= intern ("suppress-icon");
4646 staticpro (&Qsuppress_icon
);
4647 Qtop
= intern ("top");
4649 Qundefined_color
= intern ("undefined-color");
4650 staticpro (&Qundefined_color
);
4651 Qvertical_scroll_bars
= intern ("vertical-scroll-bars");
4652 staticpro (&Qvertical_scroll_bars
);
4653 Qvisibility
= intern ("visibility");
4654 staticpro (&Qvisibility
);
4655 Qwindow_id
= intern ("window-id");
4656 staticpro (&Qwindow_id
);
4657 Qx_frame_parameter
= intern ("x-frame-parameter");
4658 staticpro (&Qx_frame_parameter
);
4659 Qx_resource_name
= intern ("x-resource-name");
4660 staticpro (&Qx_resource_name
);
4661 Quser_position
= intern ("user-position");
4662 staticpro (&Quser_position
);
4663 Quser_size
= intern ("user-size");
4664 staticpro (&Quser_size
);
4665 Qdisplay
= intern ("display");
4666 staticpro (&Qdisplay
);
4667 /* This is the end of symbol initialization. */
4669 Fput (Qundefined_color
, Qerror_conditions
,
4670 Fcons (Qundefined_color
, Fcons (Qerror
, Qnil
)));
4671 Fput (Qundefined_color
, Qerror_message
,
4672 build_string ("Undefined color"));
4674 init_x_parm_symbols ();
4676 DEFVAR_LISP ("x-bitmap-file-path", &Vx_bitmap_file_path
,
4677 "List of directories to search for bitmap files for X.");
4678 Vx_bitmap_file_path
= Fcons (build_string (PATH_BITMAPS
), Qnil
);
4680 DEFVAR_LISP ("x-pointer-shape", &Vx_pointer_shape
,
4681 "The shape of the pointer when over text.\n\
4682 Changing the value does not affect existing frames\n\
4683 unless you set the mouse color.");
4684 Vx_pointer_shape
= Qnil
;
4686 DEFVAR_LISP ("x-resource-name", &Vx_resource_name
,
4687 "The name Emacs uses to look up X resources; for internal use only.\n\
4688 `x-get-resource' uses this as the first component of the instance name\n\
4689 when requesting resource values.\n\
4690 Emacs initially sets `x-resource-name' to the name under which Emacs\n\
4691 was invoked, or to the value specified with the `-name' or `-rn'\n\
4692 switches, if present.");
4693 Vx_resource_name
= Qnil
;
4695 #if 0 /* This doesn't really do anything. */
4696 DEFVAR_INT ("x-nontext-pointer-shape", &Vx_nontext_pointer_shape
,
4697 "The shape of the pointer when not over text.\n\
4698 This variable takes effect when you create a new frame\n\
4699 or when you set the mouse color.");
4701 Vx_nontext_pointer_shape
= Qnil
;
4703 #if 0 /* This doesn't really do anything. */
4704 DEFVAR_INT ("x-mode-pointer-shape", &Vx_mode_pointer_shape
,
4705 "The shape of the pointer when over the mode line.\n\
4706 This variable takes effect when you create a new frame\n\
4707 or when you set the mouse color.");
4709 Vx_mode_pointer_shape
= Qnil
;
4711 DEFVAR_INT ("x-sensitive-text-pointer-shape",
4712 &Vx_sensitive_text_pointer_shape
,
4713 "The shape of the pointer when over mouse-sensitive text.\n\
4714 This variable takes effect when you create a new frame\n\
4715 or when you set the mouse color.");
4716 Vx_sensitive_text_pointer_shape
= Qnil
;
4718 DEFVAR_LISP ("x-cursor-fore-pixel", &Vx_cursor_fore_pixel
,
4719 "A string indicating the foreground color of the cursor box.");
4720 Vx_cursor_fore_pixel
= Qnil
;
4722 DEFVAR_LISP ("x-no-window-manager", &Vx_no_window_manager
,
4723 "Non-nil if no X window manager is in use.");
4725 #ifdef USE_X_TOOLKIT
4726 Fprovide (intern ("x-toolkit"));
4729 defsubr (&Sx_get_resource
);
4731 defsubr (&Sx_draw_rectangle
);
4732 defsubr (&Sx_erase_rectangle
);
4733 defsubr (&Sx_contour_region
);
4734 defsubr (&Sx_uncontour_region
);
4736 defsubr (&Sx_list_fonts
);
4737 defsubr (&Sx_display_color_p
);
4738 defsubr (&Sx_display_grayscale_p
);
4739 defsubr (&Sx_color_defined_p
);
4740 defsubr (&Sx_color_values
);
4741 defsubr (&Sx_server_max_request_size
);
4742 defsubr (&Sx_server_vendor
);
4743 defsubr (&Sx_server_version
);
4744 defsubr (&Sx_display_pixel_width
);
4745 defsubr (&Sx_display_pixel_height
);
4746 defsubr (&Sx_display_mm_width
);
4747 defsubr (&Sx_display_mm_height
);
4748 defsubr (&Sx_display_screens
);
4749 defsubr (&Sx_display_planes
);
4750 defsubr (&Sx_display_color_cells
);
4751 defsubr (&Sx_display_visual_class
);
4752 defsubr (&Sx_display_backing_store
);
4753 defsubr (&Sx_display_save_under
);
4755 defsubr (&Sx_rebind_key
);
4756 defsubr (&Sx_rebind_keys
);
4757 defsubr (&Sx_track_pointer
);
4758 defsubr (&Sx_grab_pointer
);
4759 defsubr (&Sx_ungrab_pointer
);
4761 defsubr (&Sx_parse_geometry
);
4762 defsubr (&Sx_create_frame
);
4763 defsubr (&Sfocus_frame
);
4764 defsubr (&Sunfocus_frame
);
4766 defsubr (&Sx_horizontal_line
);
4768 defsubr (&Sx_open_connection
);
4769 defsubr (&Sx_close_connection
);
4770 defsubr (&Sx_display_list
);
4771 defsubr (&Sx_synchronize
);
4774 #endif /* HAVE_X_WINDOWS */