1 /* Generic frame functions.
2 Copyright (C) 1993, 1994, 1995, 1997 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, Inc., 59 Temple Place - Suite 330,
19 Boston, MA 02111-1307, USA. */
29 #ifdef HAVE_WINDOW_SYSTEM
33 #include "termhooks.h"
39 /* Evaluate this expression to rebuild the section of syms_of_frame
40 that initializes and staticpros the symbols declared below. Note
41 that Emacs 18 has a bug that keeps C-x C-e from being able to
42 evaluate this expression.
45 ;; Accumulate a list of the symbols we want to initialize from the
46 ;; declarations at the top of the file.
47 (goto-char (point-min))
48 (search-forward "/\*&&& symbols declared here &&&*\/\n")
50 (while (looking-at "Lisp_Object \\(Q[a-z_]+\\)")
52 (cons (buffer-substring (match-beginning 1) (match-end 1))
55 (setq symbol-list (nreverse symbol-list))
56 ;; Delete the section of syms_of_... where we initialize the symbols.
57 (search-forward "\n /\*&&& init symbols here &&&*\/\n")
58 (let ((start (point)))
59 (while (looking-at "^ Q")
61 (kill-region start (point)))
62 ;; Write a new symbol initialization section.
64 (insert (format " %s = intern (\"" (car symbol-list)))
65 (let ((start (point)))
66 (insert (substring (car symbol-list) 1))
67 (subst-char-in-region start (point) ?_ ?-))
68 (insert (format "\");\n staticpro (&%s);\n" (car symbol-list)))
69 (setq symbol-list (cdr symbol-list)))))
72 /*&&& symbols declared here &&&*/
74 Lisp_Object Qframe_live_p
;
77 Lisp_Object Qminibuffer
;
78 Lisp_Object Qmodeline
;
81 Lisp_Object Qunsplittable
;
82 Lisp_Object Qmenu_bar_lines
;
88 Lisp_Object Qbuffer_predicate
;
89 Lisp_Object Qbuffer_list
;
92 Lisp_Object Vterminal_frame
;
93 Lisp_Object Vdefault_frame_alist
;
98 /*&&& init symbols here &&&*/
99 Qframep
= intern ("framep");
100 staticpro (&Qframep
);
101 Qframe_live_p
= intern ("frame-live-p");
102 staticpro (&Qframe_live_p
);
103 Qheight
= intern ("height");
104 staticpro (&Qheight
);
105 Qicon
= intern ("icon");
107 Qminibuffer
= intern ("minibuffer");
108 staticpro (&Qminibuffer
);
109 Qmodeline
= intern ("modeline");
110 staticpro (&Qmodeline
);
111 Qname
= intern ("name");
113 Qonly
= intern ("only");
115 Qunsplittable
= intern ("unsplittable");
116 staticpro (&Qunsplittable
);
117 Qmenu_bar_lines
= intern ("menu-bar-lines");
118 staticpro (&Qmenu_bar_lines
);
119 Qwidth
= intern ("width");
123 Qw32
= intern ("w32");
127 Qvisible
= intern ("visible");
128 staticpro (&Qvisible
);
129 Qbuffer_predicate
= intern ("buffer-predicate");
130 staticpro (&Qbuffer_predicate
);
131 Qbuffer_list
= intern ("buffer-list");
132 staticpro (&Qbuffer_list
);
133 Qtitle
= intern ("title");
136 DEFVAR_LISP ("default-frame-alist", &Vdefault_frame_alist
,
137 "Alist of default values for frame creation.\n\
138 These may be set in your init file, like this:\n\
139 (setq default-frame-alist '((width . 80) (height . 55) (menu-bar-lines . 1))\n\
140 These override values given in window system configuration data,\n\
141 including X Windows' defaults database.\n\
142 For values specific to the first Emacs frame, see `initial-frame-alist'.\n\
143 For values specific to the separate minibuffer frame, see\n\
144 `minibuffer-frame-alist'.\n\
145 The `menu-bar-lines' element of the list controls whether new frames\n\
146 have menu bars; `menu-bar-mode' works by altering this element.");
147 Vdefault_frame_alist
= Qnil
;
151 set_menu_bar_lines_1 (window
, n
)
155 struct window
*w
= XWINDOW (window
);
157 XSETFASTINT (w
->last_modified
, 0);
158 XSETFASTINT (w
->top
, XFASTINT (w
->top
) + n
);
159 XSETFASTINT (w
->height
, XFASTINT (w
->height
) - n
);
161 /* Handle just the top child in a vertical split. */
162 if (!NILP (w
->vchild
))
163 set_menu_bar_lines_1 (w
->vchild
, n
);
165 /* Adjust all children in a horizontal split. */
166 for (window
= w
->hchild
; !NILP (window
); window
= w
->next
)
168 w
= XWINDOW (window
);
169 set_menu_bar_lines_1 (window
, n
);
174 set_menu_bar_lines (f
, value
, oldval
)
176 Lisp_Object value
, oldval
;
179 int olines
= FRAME_MENU_BAR_LINES (f
);
181 /* Right now, menu bars don't work properly in minibuf-only frames;
182 most of the commands try to apply themselves to the minibuffer
183 frame itself, and get an error because you can't switch buffers
184 in or split the minibuffer window. */
185 if (FRAME_MINIBUF_ONLY_P (f
))
188 if (INTEGERP (value
))
189 nlines
= XINT (value
);
193 if (nlines
!= olines
)
195 windows_or_buffers_changed
++;
196 FRAME_WINDOW_SIZES_CHANGED (f
) = 1;
197 FRAME_MENU_BAR_LINES (f
) = nlines
;
198 set_menu_bar_lines_1 (f
->root_window
, nlines
- olines
);
204 /* These help us bind and responding to switch-frame events. */
205 #include "commands.h"
206 #include "keyboard.h"
208 Lisp_Object Vemacs_iconified
;
209 Lisp_Object Vframe_list
;
211 extern Lisp_Object Vminibuffer_list
;
212 extern Lisp_Object
get_minibuffer ();
213 extern Lisp_Object
Fhandle_switch_frame ();
214 extern Lisp_Object
Fredirect_frame_focus ();
215 extern Lisp_Object
x_get_focus_frame ();
217 DEFUN ("framep", Fframep
, Sframep
, 1, 1, 0,
218 "Return non-nil if OBJECT is a frame.\n\
219 Value is t for a termcap frame (a character-only terminal),\n\
220 `x' for an Emacs frame that is really an X window,\n\
221 `pc' for a direct-write MS-DOS frame.\n\
222 See also `frame-live-p'.")
226 if (!FRAMEP (object
))
228 switch (XFRAME (object
)->output_method
)
232 case output_x_window
:
236 case output_msdos_raw
:
243 DEFUN ("frame-live-p", Fframe_live_p
, Sframe_live_p
, 1, 1, 0,
244 "Return non-nil if OBJECT is a frame which has not been deleted.\n\
245 Value is nil if OBJECT is not a live frame. If object is a live\n\
246 frame, the return value indicates what sort of output device it is\n\
247 displayed on. Value is t for a termcap frame (a character-only\n\
248 terminal), `x' for an Emacs frame being displayed in an X window.")
252 return ((FRAMEP (object
)
253 && FRAME_LIVE_P (XFRAME (object
)))
263 register struct frame
*f
;
264 register Lisp_Object root_window
;
265 register Lisp_Object mini_window
;
266 register struct Lisp_Vector
*vec
;
269 vec
= allocate_vectorlike ((EMACS_INT
) VECSIZE (struct frame
));
270 for (i
= 0; i
< VECSIZE (struct frame
); i
++)
271 XSETFASTINT (vec
->contents
[i
], 0);
272 vec
->size
= VECSIZE (struct frame
);
273 f
= (struct frame
*)vec
;
274 XSETFRAME (frame
, f
);
278 f
->current_glyphs
= 0;
279 f
->desired_glyphs
= 0;
281 f
->async_visible
= 0;
282 f
->output_data
.nothing
= 0;
284 f
->async_iconified
= 0;
285 f
->wants_modeline
= 1;
290 f
->has_minibuffer
= mini_p
;
291 f
->focus_frame
= Qnil
;
292 f
->explicit_name
= 0;
293 f
->can_have_scroll_bars
= 0;
294 f
->vertical_scroll_bar_type
= vertical_scroll_bar_none
;
295 f
->param_alist
= Qnil
;
296 f
->scroll_bars
= Qnil
;
297 f
->condemned_scroll_bars
= Qnil
;
298 f
->face_alist
= Qnil
;
299 f
->menu_bar_items
= Qnil
;
300 f
->menu_bar_vector
= Qnil
;
301 f
->menu_bar_items_used
= 0;
302 f
->buffer_predicate
= Qnil
;
303 f
->buffer_list
= Qnil
;
305 f
->kboard
= initial_kboard
;
310 root_window
= make_window ();
313 mini_window
= make_window ();
314 XWINDOW (root_window
)->next
= mini_window
;
315 XWINDOW (mini_window
)->prev
= root_window
;
316 XWINDOW (mini_window
)->mini_p
= Qt
;
317 XWINDOW (mini_window
)->frame
= frame
;
318 f
->minibuffer_window
= mini_window
;
323 XWINDOW (root_window
)->next
= Qnil
;
324 f
->minibuffer_window
= Qnil
;
327 XWINDOW (root_window
)->frame
= frame
;
330 just so that there is "something there."
331 Correct size will be set up later with change_frame_size. */
333 SET_FRAME_WIDTH (f
, 10);
336 XSETFASTINT (XWINDOW (root_window
)->width
, 10);
337 XSETFASTINT (XWINDOW (root_window
)->height
, (mini_p
? 9 : 10));
341 XSETFASTINT (XWINDOW (mini_window
)->width
, 10);
342 XSETFASTINT (XWINDOW (mini_window
)->top
, 9);
343 XSETFASTINT (XWINDOW (mini_window
)->height
, 1);
346 /* Choose a buffer for the frame's root window. */
350 XWINDOW (root_window
)->buffer
= Qt
;
351 buf
= Fcurrent_buffer ();
352 /* If buf is a 'hidden' buffer (i.e. one whose name starts with
353 a space), try to find another one. */
354 if (XSTRING (Fbuffer_name (buf
))->data
[0] == ' ')
355 buf
= Fother_buffer (buf
, Qnil
);
356 Fset_window_buffer (root_window
, buf
);
358 f
->buffer_list
= Fcons (buf
, Qnil
);
363 XWINDOW (mini_window
)->buffer
= Qt
;
364 Fset_window_buffer (mini_window
,
365 (NILP (Vminibuffer_list
)
367 : Fcar (Vminibuffer_list
)));
370 f
->root_window
= root_window
;
371 f
->selected_window
= root_window
;
372 /* Make sure this window seems more recently used than
373 a newly-created, never-selected window. */
374 XSETFASTINT (XWINDOW (f
->selected_window
)->use_time
, ++window_select_count
);
376 #ifdef HAVE_WINDOW_SYSTEM
377 f
->fontset_data
= alloc_fontset_data ();
383 #ifdef HAVE_WINDOW_SYSTEM
384 /* Make a frame using a separate minibuffer window on another frame.
385 MINI_WINDOW is the minibuffer window to use. nil means use the
386 default (the global minibuffer). */
389 make_frame_without_minibuffer (mini_window
, kb
, display
)
390 register Lisp_Object mini_window
;
394 register struct frame
*f
;
397 if (!NILP (mini_window
))
398 CHECK_LIVE_WINDOW (mini_window
, 0);
401 if (!NILP (mini_window
)
402 && XFRAME (XWINDOW (mini_window
)->frame
)->kboard
!= kb
)
403 error ("frame and minibuffer must be on the same display");
406 /* Make a frame containing just a root window. */
409 if (NILP (mini_window
))
411 /* Use default-minibuffer-frame if possible. */
412 if (!FRAMEP (kb
->Vdefault_minibuffer_frame
)
413 || ! FRAME_LIVE_P (XFRAME (kb
->Vdefault_minibuffer_frame
)))
415 Lisp_Object frame_dummy
;
417 XSETFRAME (frame_dummy
, f
);
418 GCPRO1 (frame_dummy
);
419 /* If there's no minibuffer frame to use, create one. */
420 kb
->Vdefault_minibuffer_frame
=
421 call1 (intern ("make-initial-minibuffer-frame"), display
);
425 mini_window
= XFRAME (kb
->Vdefault_minibuffer_frame
)->minibuffer_window
;
428 f
->minibuffer_window
= mini_window
;
430 /* Make the chosen minibuffer window display the proper minibuffer,
431 unless it is already showing a minibuffer. */
432 if (NILP (Fmemq (XWINDOW (mini_window
)->buffer
, Vminibuffer_list
)))
433 Fset_window_buffer (mini_window
,
434 (NILP (Vminibuffer_list
)
436 : Fcar (Vminibuffer_list
)));
440 /* Make a frame containing only a minibuffer window. */
443 make_minibuffer_frame ()
445 /* First make a frame containing just a root window, no minibuffer. */
447 register struct frame
*f
= make_frame (0);
448 register Lisp_Object mini_window
;
449 register Lisp_Object frame
;
451 XSETFRAME (frame
, f
);
456 f
->wants_modeline
= 0;
457 f
->has_minibuffer
= 1;
459 /* Now label the root window as also being the minibuffer.
460 Avoid infinite looping on the window chain by marking next pointer
463 mini_window
= f
->minibuffer_window
= f
->root_window
;
464 XWINDOW (mini_window
)->mini_p
= Qt
;
465 XWINDOW (mini_window
)->next
= Qnil
;
466 XWINDOW (mini_window
)->prev
= Qnil
;
467 XWINDOW (mini_window
)->frame
= frame
;
469 /* Put the proper buffer in that window. */
471 Fset_window_buffer (mini_window
,
472 (NILP (Vminibuffer_list
)
474 : Fcar (Vminibuffer_list
)));
477 #endif /* HAVE_WINDOW_SYSTEM */
479 /* Construct a frame that refers to the terminal (stdin and stdout). */
481 static int terminal_frame_count
;
484 make_terminal_frame ()
486 register struct frame
*f
;
493 initial_kboard
= (KBOARD
*) xmalloc (sizeof (KBOARD
));
494 init_kboard (initial_kboard
);
495 initial_kboard
->next_kboard
= all_kboards
;
496 all_kboards
= initial_kboard
;
500 /* The first call must initialize Vframe_list. */
501 if (! (NILP (Vframe_list
) || CONSP (Vframe_list
)))
506 XSETFRAME (frame
, f
);
507 Vframe_list
= Fcons (frame
, Vframe_list
);
509 terminal_frame_count
++;
510 sprintf (name
, "F%d", terminal_frame_count
);
511 f
->name
= build_string (name
);
513 f
->visible
= 1; /* FRAME_SET_VISIBLE wd set frame_garbaged. */
514 f
->async_visible
= 1; /* Don't let visible be cleared later. */
516 f
->output_data
.x
= &the_only_x_display
;
517 f
->output_method
= output_msdos_raw
;
518 init_frame_faces (f
);
519 #else /* not MSDOS */
520 f
->output_data
.nothing
= 1; /* Nonzero means frame isn't deleted. */
525 DEFUN ("make-terminal-frame", Fmake_terminal_frame
, Smake_terminal_frame
,
526 1, 1, 0, "Create an additional terminal frame.\n\
527 You can create multiple frames on a text-only terminal in this way.\n\
528 Only the selected terminal frame is actually displayed.\n\
529 This function takes one argument, an alist specifying frame parameters.\n\
530 In practice, generally you don't need to specify any parameters.\n\
531 Note that changing the size of one terminal frame automatically affects all.")
539 if (selected_frame
->output_method
!= output_msdos_raw
)
542 if (selected_frame
->output_method
!= output_termcap
)
543 error ("Not using an ASCII terminal now; cannot make a new ASCII frame");
546 f
= make_terminal_frame ();
547 change_frame_size (f
, FRAME_HEIGHT (selected_frame
),
548 FRAME_WIDTH (selected_frame
), 0, 0);
549 remake_frame_glyphs (f
);
551 XSETFRAME (frame
, f
);
552 Fmodify_frame_parameters (frame
, Vdefault_frame_alist
);
553 Fmodify_frame_parameters (frame
, parms
);
554 f
->face_alist
= selected_frame
->face_alist
;
559 do_switch_frame (frame
, no_enter
, track
)
560 Lisp_Object frame
, no_enter
;
563 /* If FRAME is a switch-frame event, extract the frame we should
566 && EQ (XCONS (frame
)->car
, Qswitch_frame
)
567 && CONSP (XCONS (frame
)->cdr
))
568 frame
= XCONS (XCONS (frame
)->cdr
)->car
;
570 /* This used to say CHECK_LIVE_FRAME, but apparently it's possible for
571 a switch-frame event to arrive after a frame is no longer live,
572 especially when deleting the initial frame during startup. */
573 CHECK_FRAME (frame
, 0);
574 if (! FRAME_LIVE_P (XFRAME (frame
)))
577 if (selected_frame
== XFRAME (frame
))
580 /* This is too greedy; it causes inappropriate focus redirection
581 that's hard to get rid of. */
583 /* If a frame's focus has been redirected toward the currently
584 selected frame, we should change the redirection to point to the
585 newly selected frame. This means that if the focus is redirected
586 from a minibufferless frame to a surrogate minibuffer frame, we
587 can use `other-window' to switch between all the frames using
588 that minibuffer frame, and the focus redirection will follow us
594 for (tail
= Vframe_list
; CONSP (tail
); tail
= XCONS (tail
)->cdr
)
598 if (!FRAMEP (XCONS (tail
)->car
))
601 focus
= FRAME_FOCUS_FRAME (XFRAME (XCONS (tail
)->car
));
603 if (FRAMEP (focus
) && XFRAME (focus
) == selected_frame
)
604 Fredirect_frame_focus (XCONS (tail
)->car
, frame
);
608 /* Instead, apply it only to the frame we're pointing to. */
609 #ifdef HAVE_WINDOW_SYSTEM
610 if (track
&& (FRAME_WINDOW_P (XFRAME (frame
))))
612 Lisp_Object focus
, xfocus
;
614 xfocus
= x_get_focus_frame (XFRAME (frame
));
617 focus
= FRAME_FOCUS_FRAME (XFRAME (xfocus
));
618 if (FRAMEP (focus
) && XFRAME (focus
) == selected_frame
)
619 Fredirect_frame_focus (xfocus
, frame
);
622 #endif /* HAVE_X_WINDOWS */
625 selected_frame
= XFRAME (frame
);
626 if (! FRAME_MINIBUF_ONLY_P (selected_frame
))
627 last_nonminibuf_frame
= selected_frame
;
629 Fselect_window (XFRAME (frame
)->selected_window
);
631 /* We want to make sure that the next event generates a frame-switch
632 event to the appropriate frame. This seems kludgy to me, but
633 before you take it out, make sure that evaluating something like
634 (select-window (frame-root-window (new-frame))) doesn't end up
635 with your typing being interpreted in the new frame instead of
636 the one you're actually typing in. */
637 internal_last_event_frame
= Qnil
;
642 DEFUN ("select-frame", Fselect_frame
, Sselect_frame
, 1, 2, "e",
643 "Select the frame FRAME.\n\
644 Subsequent editing commands apply to its selected window.\n\
645 The selection of FRAME lasts until the next time the user does\n\
646 something to select a different frame, or until the next time this\n\
647 function is called.")
649 Lisp_Object frame
, no_enter
;
651 return do_switch_frame (frame
, no_enter
, 1);
655 DEFUN ("handle-switch-frame", Fhandle_switch_frame
, Shandle_switch_frame
, 1, 2, "e",
656 "Handle a switch-frame event EVENT.\n\
657 Switch-frame events are usually bound to this function.\n\
658 A switch-frame event tells Emacs that the window manager has requested\n\
659 that the user's events be directed to the frame mentioned in the event.\n\
660 This function selects the selected window of the frame of EVENT.\n\
662 If EVENT is frame object, handle it as if it were a switch-frame event\n\
665 Lisp_Object event
, no_enter
;
667 /* Preserve prefix arg that the command loop just cleared. */
668 current_kboard
->Vprefix_arg
= Vcurrent_prefix_arg
;
669 call1 (Vrun_hooks
, Qmouse_leave_buffer_hook
);
670 return do_switch_frame (event
, no_enter
, 0);
673 DEFUN ("ignore-event", Fignore_event
, Signore_event
, 0, 0, "",
674 "Do nothing, but preserve any prefix argument already specified.\n\
675 This is a suitable binding for iconify-frame and make-frame-visible.")
678 current_kboard
->Vprefix_arg
= Vcurrent_prefix_arg
;
682 DEFUN ("selected-frame", Fselected_frame
, Sselected_frame
, 0, 0, 0,
683 "Return the frame that is now selected.")
687 XSETFRAME (tem
, selected_frame
);
691 DEFUN ("window-frame", Fwindow_frame
, Swindow_frame
, 1, 1, 0,
692 "Return the frame object that window WINDOW is on.")
696 CHECK_LIVE_WINDOW (window
, 0);
697 return XWINDOW (window
)->frame
;
700 DEFUN ("frame-first-window", Fframe_first_window
, Sframe_first_window
, 0, 1, 0,
701 "Returns the topmost, leftmost window of FRAME.\n\
702 If omitted, FRAME defaults to the currently selected frame.")
709 w
= selected_frame
->root_window
;
712 CHECK_LIVE_FRAME (frame
, 0);
713 w
= XFRAME (frame
)->root_window
;
715 while (NILP (XWINDOW (w
)->buffer
))
717 if (! NILP (XWINDOW (w
)->hchild
))
718 w
= XWINDOW (w
)->hchild
;
719 else if (! NILP (XWINDOW (w
)->vchild
))
720 w
= XWINDOW (w
)->vchild
;
727 DEFUN ("active-minibuffer-window", Factive_minibuffer_window
,
728 Sactive_minibuffer_window
, 0, 0, 0,
729 "Return the currently active minibuffer window, or nil if none.")
732 return minibuf_level
? minibuf_window
: Qnil
;
735 DEFUN ("frame-root-window", Fframe_root_window
, Sframe_root_window
, 0, 1, 0,
736 "Returns the root-window of FRAME.\n\
737 If omitted, FRAME defaults to the currently selected frame.")
742 XSETFRAME (frame
, selected_frame
);
744 CHECK_LIVE_FRAME (frame
, 0);
746 return XFRAME (frame
)->root_window
;
749 DEFUN ("frame-selected-window", Fframe_selected_window
,
750 Sframe_selected_window
, 0, 1, 0,
751 "Return the selected window of frame object FRAME.\n\
752 If omitted, FRAME defaults to the currently selected frame.")
757 XSETFRAME (frame
, selected_frame
);
759 CHECK_LIVE_FRAME (frame
, 0);
761 return XFRAME (frame
)->selected_window
;
764 DEFUN ("set-frame-selected-window", Fset_frame_selected_window
,
765 Sset_frame_selected_window
, 2, 2, 0,
766 "Set the selected window of frame object FRAME to WINDOW.\n\
767 If FRAME is nil, the selected frame is used.\n\
768 If FRAME is the selected frame, this makes WINDOW the selected window.")
770 Lisp_Object frame
, window
;
773 XSETFRAME (frame
, selected_frame
);
775 CHECK_LIVE_FRAME (frame
, 0);
777 CHECK_LIVE_WINDOW (window
, 1);
779 if (! EQ (frame
, WINDOW_FRAME (XWINDOW (window
))))
780 error ("In `set-frame-selected-window', WINDOW is not on FRAME");
782 if (XFRAME (frame
) == selected_frame
)
783 return Fselect_window (window
);
785 return XFRAME (frame
)->selected_window
= window
;
788 DEFUN ("frame-list", Fframe_list
, Sframe_list
,
790 "Return a list of all frames.")
793 return Fcopy_sequence (Vframe_list
);
796 /* Return the next frame in the frame list after FRAME.
797 If MINIBUF is nil, exclude minibuffer-only frames.
798 If MINIBUF is a window, include only its own frame
799 and any frame now using that window as the minibuffer.
800 If MINIBUF is `visible', include all visible frames.
801 If MINIBUF is 0, include all visible and iconified frames.
802 Otherwise, include all frames. */
805 next_frame (frame
, minibuf
)
812 /* There must always be at least one frame in Vframe_list. */
813 if (! CONSP (Vframe_list
))
816 /* If this frame is dead, it won't be in Vframe_list, and we'll loop
817 forever. Forestall that. */
818 CHECK_LIVE_FRAME (frame
, 0);
821 for (tail
= Vframe_list
; CONSP (tail
); tail
= XCONS (tail
)->cdr
)
825 f
= XCONS (tail
)->car
;
828 && FRAME_KBOARD (XFRAME (f
)) == FRAME_KBOARD (XFRAME (frame
)))
830 /* Decide whether this frame is eligible to be returned. */
832 /* If we've looped all the way around without finding any
833 eligible frames, return the original frame. */
837 /* Let minibuf decide if this frame is acceptable. */
840 if (! FRAME_MINIBUF_ONLY_P (XFRAME (f
)))
843 else if (EQ (minibuf
, Qvisible
))
845 FRAME_SAMPLE_VISIBILITY (XFRAME (f
));
846 if (FRAME_VISIBLE_P (XFRAME (f
)))
849 else if (XFASTINT (minibuf
) == 0)
851 FRAME_SAMPLE_VISIBILITY (XFRAME (f
));
852 if (FRAME_VISIBLE_P (XFRAME (f
))
853 || FRAME_ICONIFIED_P (XFRAME (f
)))
856 else if (WINDOWP (minibuf
))
858 if (EQ (FRAME_MINIBUF_WINDOW (XFRAME (f
)), minibuf
)
859 /* Check that F either is, or has forwarded its focus to,
861 && (EQ (WINDOW_FRAME (XWINDOW (minibuf
)), f
)
862 || EQ (WINDOW_FRAME (XWINDOW (minibuf
)),
863 FRAME_FOCUS_FRAME (XFRAME (f
)))))
875 /* Return the previous frame in the frame list before FRAME.
876 If MINIBUF is nil, exclude minibuffer-only frames.
877 If MINIBUF is a window, include only its own frame
878 and any frame now using that window as the minibuffer.
879 If MINIBUF is `visible', include all visible frames.
880 If MINIBUF is 0, include all visible and iconified frames.
881 Otherwise, include all frames. */
884 prev_frame (frame
, minibuf
)
891 /* There must always be at least one frame in Vframe_list. */
892 if (! CONSP (Vframe_list
))
896 for (tail
= Vframe_list
; CONSP (tail
); tail
= XCONS (tail
)->cdr
)
900 f
= XCONS (tail
)->car
;
904 if (EQ (frame
, f
) && !NILP (prev
))
907 if (FRAME_KBOARD (XFRAME (f
)) == FRAME_KBOARD (XFRAME (frame
)))
909 /* Decide whether this frame is eligible to be returned,
910 according to minibuf. */
913 if (! FRAME_MINIBUF_ONLY_P (XFRAME (f
)))
916 else if (WINDOWP (minibuf
))
918 if (EQ (FRAME_MINIBUF_WINDOW (XFRAME (f
)), minibuf
)
919 /* Check that F either is, or has forwarded its focus to,
921 && (EQ (WINDOW_FRAME (XWINDOW (minibuf
)), f
)
922 || EQ (WINDOW_FRAME (XWINDOW (minibuf
)),
923 FRAME_FOCUS_FRAME (XFRAME (f
)))))
926 else if (EQ (minibuf
, Qvisible
))
928 FRAME_SAMPLE_VISIBILITY (XFRAME (f
));
929 if (FRAME_VISIBLE_P (XFRAME (f
)))
932 else if (XFASTINT (minibuf
) == 0)
934 FRAME_SAMPLE_VISIBILITY (XFRAME (f
));
935 if (FRAME_VISIBLE_P (XFRAME (f
))
936 || FRAME_ICONIFIED_P (XFRAME (f
)))
944 /* We've scanned the entire list. */
946 /* We went through the whole frame list without finding a single
947 acceptable frame. Return the original frame. */
950 /* There were no acceptable frames in the list before FRAME; otherwise,
951 we would have returned directly from the loop. Since PREV is the last
952 acceptable frame in the list, return it. */
957 DEFUN ("next-frame", Fnext_frame
, Snext_frame
, 0, 2, 0,
958 "Return the next frame in the frame list after FRAME.\n\
959 It considers only frames on the same terminal as FRAME.\n\
960 By default, skip minibuffer-only frames.\n\
961 If omitted, FRAME defaults to the selected frame.\n\
962 If optional argument MINIFRAME is nil, exclude minibuffer-only frames.\n\
963 If MINIFRAME is a window, include only its own frame\n\
964 and any frame now using that window as the minibuffer.\n\
965 If MINIFRAME is `visible', include all visible frames.\n\
966 If MINIFRAME is 0, include all visible and iconified frames.\n\
967 Otherwise, include all frames.")
969 Lisp_Object frame
, miniframe
;
974 XSETFRAME (frame
, selected_frame
);
976 CHECK_LIVE_FRAME (frame
, 0);
978 return next_frame (frame
, miniframe
);
981 DEFUN ("previous-frame", Fprevious_frame
, Sprevious_frame
, 0, 2, 0,
982 "Return the previous frame in the frame list before FRAME.\n\
983 It considers only frames on the same terminal as FRAME.\n\
984 By default, skip minibuffer-only frames.\n\
985 If omitted, FRAME defaults to the selected frame.\n\
986 If optional argument MINIFRAME is nil, exclude minibuffer-only frames.\n\
987 If MINIFRAME is a window, include only its own frame\n\
988 and any frame now using that window as the minibuffer.\n\
989 If MINIFRAME is `visible', include all visible frames.\n\
990 If MINIFRAME is 0, include all visible and iconified frames.\n\
991 Otherwise, include all frames.")
993 Lisp_Object frame
, miniframe
;
998 XSETFRAME (frame
, selected_frame
);
1000 CHECK_LIVE_FRAME (frame
, 0);
1002 return prev_frame (frame
, miniframe
);
1005 /* Return 1 if it is ok to delete frame F;
1006 0 if all frames aside from F are invisible.
1007 (Exception: if F is the terminal frame, and we are using X, return 1.) */
1010 other_visible_frames (f
)
1013 /* We know the selected frame is visible,
1014 so if F is some other frame, it can't be the sole visible one. */
1015 if (f
== selected_frame
)
1020 for (frames
= Vframe_list
;
1022 frames
= XCONS (frames
)->cdr
)
1026 this = XCONS (frames
)->car
;
1027 /* Verify that the frame's window still exists
1028 and we can still talk to it. And note any recent change
1030 #ifdef HAVE_WINDOW_SYSTEM
1031 if (FRAME_WINDOW_P (XFRAME (this)))
1033 x_sync (XFRAME (this));
1034 FRAME_SAMPLE_VISIBILITY (XFRAME (this));
1038 if (FRAME_VISIBLE_P (XFRAME (this))
1039 || FRAME_ICONIFIED_P (XFRAME (this))
1040 /* Allow deleting the terminal frame when at least
1041 one X frame exists! */
1042 || (FRAME_WINDOW_P (XFRAME (this)) && !FRAME_WINDOW_P (f
)))
1050 DEFUN ("delete-frame", Fdelete_frame
, Sdelete_frame
, 0, 2, "",
1051 "Delete FRAME, permanently eliminating it from use.\n\
1052 If omitted, FRAME defaults to the selected frame.\n\
1053 A frame may not be deleted if its minibuffer is used by other frames.\n\
1054 Normally, you may not delete a frame if all other frames are invisible,\n\
1055 but if the second optional argument FORCE is non-nil, you may do so.")
1057 Lisp_Object frame
, force
;
1060 int minibuffer_selected
;
1062 if (EQ (frame
, Qnil
))
1065 XSETFRAME (frame
, f
);
1069 CHECK_FRAME (frame
, 0);
1073 if (! FRAME_LIVE_P (f
))
1076 if (NILP (force
) && !other_visible_frames (f
))
1077 error ("Attempt to delete the sole visible or iconified frame");
1080 /* This is a nice idea, but x_connection_closed needs to be able
1081 to delete the last frame, if it is gone. */
1082 if (NILP (XCONS (Vframe_list
)->cdr
))
1083 error ("Attempt to delete the only frame");
1086 /* Does this frame have a minibuffer, and is it the surrogate
1087 minibuffer for any other frame? */
1088 if (FRAME_HAS_MINIBUF_P (XFRAME (frame
)))
1092 for (frames
= Vframe_list
;
1094 frames
= XCONS (frames
)->cdr
)
1097 this = XCONS (frames
)->car
;
1099 if (! EQ (this, frame
)
1101 WINDOW_FRAME (XWINDOW
1102 (FRAME_MINIBUF_WINDOW (XFRAME (this))))))
1103 error ("Attempt to delete a surrogate minibuffer frame");
1107 minibuffer_selected
= EQ (minibuf_window
, selected_window
);
1109 /* Don't let the frame remain selected. */
1110 if (f
== selected_frame
)
1112 Lisp_Object tail
, frame1
;
1114 /* Look for another visible frame on the same terminal. */
1115 frame1
= next_frame (frame
, Qvisible
);
1117 /* If there is none, find *some* other frame. */
1118 if (NILP (frame1
) || EQ (frame1
, frame
))
1120 FOR_EACH_FRAME (tail
, frame1
)
1122 if (! EQ (frame
, frame1
))
1127 do_switch_frame (frame1
, Qnil
, 0);
1130 /* Don't allow minibuf_window to remain on a deleted frame. */
1131 if (EQ (f
->minibuffer_window
, minibuf_window
))
1133 Fset_window_buffer (selected_frame
->minibuffer_window
,
1134 XWINDOW (minibuf_window
)->buffer
);
1135 minibuf_window
= selected_frame
->minibuffer_window
;
1137 /* If the dying minibuffer window was selected,
1138 select the new one. */
1139 if (minibuffer_selected
)
1140 Fselect_window (minibuf_window
);
1143 /* Clear any X selections for this frame. */
1144 #ifdef HAVE_X_WINDOWS
1146 x_clear_frame_selections (f
);
1149 /* Mark all the windows that used to be on FRAME as deleted, and then
1150 remove the reference to them. */
1151 delete_all_subwindows (XWINDOW (f
->root_window
));
1152 f
->root_window
= Qnil
;
1154 Vframe_list
= Fdelq (frame
, Vframe_list
);
1155 FRAME_SET_VISIBLE (f
, 0);
1157 if (echo_area_glyphs
== FRAME_MESSAGE_BUF (f
))
1159 echo_area_glyphs
= 0;
1160 previous_echo_glyphs
= 0;
1165 if (FRAME_CURRENT_GLYPHS (f
))
1166 free_frame_glyphs (f
, FRAME_CURRENT_GLYPHS (f
));
1167 if (FRAME_DESIRED_GLYPHS (f
))
1168 free_frame_glyphs (f
, FRAME_DESIRED_GLYPHS (f
));
1169 if (FRAME_TEMP_GLYPHS (f
))
1170 free_frame_glyphs (f
, FRAME_TEMP_GLYPHS (f
));
1171 if (FRAME_INSERT_COST (f
))
1172 free (FRAME_INSERT_COST (f
));
1173 if (FRAME_DELETEN_COST (f
))
1174 free (FRAME_DELETEN_COST (f
));
1175 if (FRAME_INSERTN_COST (f
))
1176 free (FRAME_INSERTN_COST (f
));
1177 if (FRAME_DELETE_COST (f
))
1178 free (FRAME_DELETE_COST (f
));
1179 if (FRAME_MESSAGE_BUF (f
))
1180 free (FRAME_MESSAGE_BUF (f
));
1182 #ifdef HAVE_WINDOW_SYSTEM
1183 /* Free all fontset data. */
1184 free_fontset_data (FRAME_FONTSET_DATA (f
));
1187 /* Since some events are handled at the interrupt level, we may get
1188 an event for f at any time; if we zero out the frame's display
1189 now, then we may trip up the event-handling code. Instead, we'll
1190 promise that the display of the frame must be valid until we have
1191 called the window-system-dependent frame destruction routine. */
1193 /* I think this should be done with a hook. */
1194 #ifdef HAVE_WINDOW_SYSTEM
1195 if (FRAME_WINDOW_P (f
))
1196 x_destroy_window (f
);
1199 f
->output_data
.nothing
= 0;
1201 /* If we've deleted the last_nonminibuf_frame, then try to find
1203 if (f
== last_nonminibuf_frame
)
1207 last_nonminibuf_frame
= 0;
1209 for (frames
= Vframe_list
;
1211 frames
= XCONS (frames
)->cdr
)
1213 f
= XFRAME (XCONS (frames
)->car
);
1214 if (!FRAME_MINIBUF_ONLY_P (f
))
1216 last_nonminibuf_frame
= f
;
1222 /* If we've deleted this keyboard's default_minibuffer_frame, try to
1223 find another one. Prefer minibuffer-only frames, but also notice
1224 frames with other windows. */
1225 if (EQ (frame
, FRAME_KBOARD (f
)->Vdefault_minibuffer_frame
))
1229 /* The last frame we saw with a minibuffer, minibuffer-only or not. */
1230 Lisp_Object frame_with_minibuf
;
1231 /* Some frame we found on the same kboard, or nil if there are none. */
1232 Lisp_Object frame_on_same_kboard
;
1234 frame_on_same_kboard
= Qnil
;
1235 frame_with_minibuf
= Qnil
;
1237 for (frames
= Vframe_list
;
1239 frames
= XCONS (frames
)->cdr
)
1244 this = XCONS (frames
)->car
;
1249 /* Consider only frames on the same kboard
1250 and only those with minibuffers. */
1251 if (FRAME_KBOARD (f
) == FRAME_KBOARD (f1
)
1252 && FRAME_HAS_MINIBUF_P (f1
))
1254 frame_with_minibuf
= this;
1255 if (FRAME_MINIBUF_ONLY_P (f1
))
1259 if (FRAME_KBOARD (f
) == FRAME_KBOARD (f1
))
1260 frame_on_same_kboard
= this;
1263 if (!NILP (frame_on_same_kboard
))
1265 /* We know that there must be some frame with a minibuffer out
1266 there. If this were not true, all of the frames present
1267 would have to be minibufferless, which implies that at some
1268 point their minibuffer frames must have been deleted, but
1269 that is prohibited at the top; you can't delete surrogate
1270 minibuffer frames. */
1271 if (NILP (frame_with_minibuf
))
1274 FRAME_KBOARD (f
)->Vdefault_minibuffer_frame
= frame_with_minibuf
;
1277 /* No frames left on this kboard--say no minibuffer either. */
1278 FRAME_KBOARD (f
)->Vdefault_minibuffer_frame
= Qnil
;
1281 /* Cause frame titles to update--necessary if we now have just one frame. */
1282 update_mode_lines
= 1;
1287 /* Return mouse position in character cell units. */
1289 DEFUN ("mouse-position", Fmouse_position
, Smouse_position
, 0, 0, 0,
1290 "Return a list (FRAME X . Y) giving the current mouse frame and position.\n\
1291 The position is given in character cells, where (0, 0) is the\n\
1292 upper-left corner.\n\
1293 If Emacs is running on a mouseless terminal or hasn't been programmed\n\
1294 to read the mouse position, it returns the selected frame for FRAME\n\
1295 and nil for X and Y.")
1299 Lisp_Object lispy_dummy
;
1300 enum scroll_bar_part party_dummy
;
1303 unsigned long long_dummy
;
1309 /* It's okay for the hook to refrain from storing anything. */
1310 if (mouse_position_hook
)
1311 (*mouse_position_hook
) (&f
, -1,
1312 &lispy_dummy
, &party_dummy
,
1319 pixel_to_glyph_coords (f
, col
, row
, &col
, &row
, NULL
, 1);
1324 XSETFRAME (lispy_dummy
, f
);
1325 return Fcons (lispy_dummy
, Fcons (x
, y
));
1328 DEFUN ("mouse-pixel-position", Fmouse_pixel_position
,
1329 Smouse_pixel_position
, 0, 0, 0,
1330 "Return a list (FRAME X . Y) giving the current mouse frame and position.\n\
1331 The position is given in pixel units, where (0, 0) is the\n\
1332 upper-left corner.\n\
1333 If Emacs is running on a mouseless terminal or hasn't been programmed\n\
1334 to read the mouse position, it returns the selected frame for FRAME\n\
1335 and nil for X and Y.")
1339 Lisp_Object lispy_dummy
;
1340 enum scroll_bar_part party_dummy
;
1343 unsigned long long_dummy
;
1349 /* It's okay for the hook to refrain from storing anything. */
1350 if (mouse_position_hook
)
1351 (*mouse_position_hook
) (&f
, -1,
1352 &lispy_dummy
, &party_dummy
,
1356 XSETFRAME (lispy_dummy
, f
);
1357 return Fcons (lispy_dummy
, Fcons (x
, y
));
1360 DEFUN ("set-mouse-position", Fset_mouse_position
, Sset_mouse_position
, 3, 3, 0,
1361 "Move the mouse pointer to the center of character cell (X,Y) in FRAME.\n\
1362 Note, this is a no-op for an X frame that is not visible.\n\
1363 If you have just created a frame, you must wait for it to become visible\n\
1364 before calling this function on it, like this.\n\
1365 (while (not (frame-visible-p frame)) (sleep-for .5))")
1367 Lisp_Object frame
, x
, y
;
1369 CHECK_LIVE_FRAME (frame
, 0);
1370 CHECK_NUMBER (x
, 2);
1371 CHECK_NUMBER (y
, 1);
1373 /* I think this should be done with a hook. */
1374 #ifdef HAVE_WINDOW_SYSTEM
1375 if (FRAME_WINDOW_P (XFRAME (frame
)))
1376 /* Warping the mouse will cause enternotify and focus events. */
1377 x_set_mouse_position (XFRAME (frame
), x
, y
);
1379 #if defined (MSDOS) && defined (HAVE_MOUSE)
1380 if (FRAME_MSDOS_P (XFRAME (frame
)))
1382 Fselect_frame (frame
, Qnil
);
1383 mouse_moveto (XINT (x
), XINT (y
));
1391 DEFUN ("set-mouse-pixel-position", Fset_mouse_pixel_position
,
1392 Sset_mouse_pixel_position
, 3, 3, 0,
1393 "Move the mouse pointer to pixel position (X,Y) in FRAME.\n\
1394 Note, this is a no-op for an X frame that is not visible.\n\
1395 If you have just created a frame, you must wait for it to become visible\n\
1396 before calling this function on it, like this.\n\
1397 (while (not (frame-visible-p frame)) (sleep-for .5))")
1399 Lisp_Object frame
, x
, y
;
1401 CHECK_LIVE_FRAME (frame
, 0);
1402 CHECK_NUMBER (x
, 2);
1403 CHECK_NUMBER (y
, 1);
1405 /* I think this should be done with a hook. */
1406 #ifdef HAVE_WINDOW_SYSTEM
1407 if (FRAME_WINDOW_P (XFRAME (frame
)))
1408 /* Warping the mouse will cause enternotify and focus events. */
1409 x_set_mouse_pixel_position (XFRAME (frame
), x
, y
);
1411 #if defined (MSDOS) && defined (HAVE_MOUSE)
1412 if (FRAME_MSDOS_P (XFRAME (frame
)))
1414 Fselect_frame (frame
, Qnil
);
1415 mouse_moveto (XINT (x
), XINT (y
));
1423 DEFUN ("make-frame-visible", Fmake_frame_visible
, Smake_frame_visible
,
1425 "Make the frame FRAME visible (assuming it is an X-window).\n\
1426 If omitted, FRAME defaults to the currently selected frame.")
1431 XSETFRAME (frame
, selected_frame
);
1433 CHECK_LIVE_FRAME (frame
, 0);
1435 /* I think this should be done with a hook. */
1436 #ifdef HAVE_WINDOW_SYSTEM
1437 if (FRAME_WINDOW_P (XFRAME (frame
)))
1439 FRAME_SAMPLE_VISIBILITY (XFRAME (frame
));
1440 x_make_frame_visible (XFRAME (frame
));
1444 /* Make menu bar update for the Buffers and Frams menus. */
1445 windows_or_buffers_changed
++;
1450 DEFUN ("make-frame-invisible", Fmake_frame_invisible
, Smake_frame_invisible
,
1452 "Make the frame FRAME invisible (assuming it is an X-window).\n\
1453 If omitted, FRAME defaults to the currently selected frame.\n\
1454 Normally you may not make FRAME invisible if all other frames are invisible,\n\
1455 but if the second optional argument FORCE is non-nil, you may do so.")
1457 Lisp_Object frame
, force
;
1460 XSETFRAME (frame
, selected_frame
);
1462 CHECK_LIVE_FRAME (frame
, 0);
1464 if (NILP (force
) && !other_visible_frames (XFRAME (frame
)))
1465 error ("Attempt to make invisible the sole visible or iconified frame");
1467 #if 0 /* This isn't logically necessary, and it can do GC. */
1468 /* Don't let the frame remain selected. */
1469 if (XFRAME (frame
) == selected_frame
)
1470 do_switch_frame (next_frame (frame
, Qt
), Qnil
, 0)
1473 /* Don't allow minibuf_window to remain on a deleted frame. */
1474 if (EQ (XFRAME (frame
)->minibuffer_window
, minibuf_window
))
1476 Fset_window_buffer (selected_frame
->minibuffer_window
,
1477 XWINDOW (minibuf_window
)->buffer
);
1478 minibuf_window
= selected_frame
->minibuffer_window
;
1481 /* I think this should be done with a hook. */
1482 #ifdef HAVE_WINDOW_SYSTEM
1483 if (FRAME_WINDOW_P (XFRAME (frame
)))
1484 x_make_frame_invisible (XFRAME (frame
));
1487 /* Make menu bar update for the Buffers and Frams menus. */
1488 windows_or_buffers_changed
++;
1493 DEFUN ("iconify-frame", Ficonify_frame
, Siconify_frame
,
1495 "Make the frame FRAME into an icon.\n\
1496 If omitted, FRAME defaults to the currently selected frame.")
1501 XSETFRAME (frame
, selected_frame
);
1503 CHECK_LIVE_FRAME (frame
, 0);
1505 #if 0 /* This isn't logically necessary, and it can do GC. */
1506 /* Don't let the frame remain selected. */
1507 if (XFRAME (frame
) == selected_frame
)
1508 Fhandle_switch_frame (next_frame (frame
, Qt
), Qnil
);
1511 /* Don't allow minibuf_window to remain on a deleted frame. */
1512 if (EQ (XFRAME (frame
)->minibuffer_window
, minibuf_window
))
1514 Fset_window_buffer (selected_frame
->minibuffer_window
,
1515 XWINDOW (minibuf_window
)->buffer
);
1516 minibuf_window
= selected_frame
->minibuffer_window
;
1519 /* I think this should be done with a hook. */
1520 #ifdef HAVE_WINDOW_SYSTEM
1521 if (FRAME_WINDOW_P (XFRAME (frame
)))
1522 x_iconify_frame (XFRAME (frame
));
1525 /* Make menu bar update for the Buffers and Frams menus. */
1526 windows_or_buffers_changed
++;
1531 DEFUN ("frame-visible-p", Fframe_visible_p
, Sframe_visible_p
,
1533 "Return t if FRAME is now \"visible\" (actually in use for display).\n\
1534 A frame that is not \"visible\" is not updated and, if it works through\n\
1535 a window system, it may not show at all.\n\
1536 Return the symbol `icon' if frame is visible only as an icon.")
1540 CHECK_LIVE_FRAME (frame
, 0);
1542 FRAME_SAMPLE_VISIBILITY (XFRAME (frame
));
1544 if (FRAME_VISIBLE_P (XFRAME (frame
)))
1546 if (FRAME_ICONIFIED_P (XFRAME (frame
)))
1551 DEFUN ("visible-frame-list", Fvisible_frame_list
, Svisible_frame_list
,
1553 "Return a list of all frames now \"visible\" (being updated).")
1556 Lisp_Object tail
, frame
;
1561 for (tail
= Vframe_list
; CONSP (tail
); tail
= XCONS (tail
)->cdr
)
1563 frame
= XCONS (tail
)->car
;
1564 if (!FRAMEP (frame
))
1567 if (FRAME_VISIBLE_P (f
))
1568 value
= Fcons (frame
, value
);
1574 DEFUN ("raise-frame", Fraise_frame
, Sraise_frame
, 0, 1, "",
1575 "Bring FRAME to the front, so it occludes any frames it overlaps.\n\
1576 If FRAME is invisible, make it visible.\n\
1577 If you don't specify a frame, the selected frame is used.\n\
1578 If Emacs is displaying on an ordinary terminal or some other device which\n\
1579 doesn't support multiple overlapping frames, this function does nothing.")
1584 XSETFRAME (frame
, selected_frame
);
1586 CHECK_LIVE_FRAME (frame
, 0);
1588 /* Do like the documentation says. */
1589 Fmake_frame_visible (frame
);
1591 if (frame_raise_lower_hook
)
1592 (*frame_raise_lower_hook
) (XFRAME (frame
), 1);
1597 /* Should we have a corresponding function called Flower_Power? */
1598 DEFUN ("lower-frame", Flower_frame
, Slower_frame
, 0, 1, "",
1599 "Send FRAME to the back, so it is occluded by any frames that overlap it.\n\
1600 If you don't specify a frame, the selected frame is used.\n\
1601 If Emacs is displaying on an ordinary terminal or some other device which\n\
1602 doesn't support multiple overlapping frames, this function does nothing.")
1607 XSETFRAME (frame
, selected_frame
);
1609 CHECK_LIVE_FRAME (frame
, 0);
1611 if (frame_raise_lower_hook
)
1612 (*frame_raise_lower_hook
) (XFRAME (frame
), 0);
1618 DEFUN ("redirect-frame-focus", Fredirect_frame_focus
, Sredirect_frame_focus
,
1620 "Arrange for keystrokes typed at FRAME to be sent to FOCUS-FRAME.\n\
1621 In other words, switch-frame events caused by events in FRAME will\n\
1622 request a switch to FOCUS-FRAME, and `last-event-frame' will be\n\
1623 FOCUS-FRAME after reading an event typed at FRAME.\n\
1625 If FOCUS-FRAME is omitted or nil, any existing redirection is\n\
1626 cancelled, and the frame again receives its own keystrokes.\n\
1628 Focus redirection is useful for temporarily redirecting keystrokes to\n\
1629 a surrogate minibuffer frame when a frame doesn't have its own\n\
1630 minibuffer window.\n\
1632 A frame's focus redirection can be changed by select-frame. If frame\n\
1633 FOO is selected, and then a different frame BAR is selected, any\n\
1634 frames redirecting their focus to FOO are shifted to redirect their\n\
1635 focus to BAR. This allows focus redirection to work properly when the\n\
1636 user switches from one frame to another using `select-window'.\n\
1638 This means that a frame whose focus is redirected to itself is treated\n\
1639 differently from a frame whose focus is redirected to nil; the former\n\
1640 is affected by select-frame, while the latter is not.\n\
1642 The redirection lasts until `redirect-frame-focus' is called to change it.")
1643 (frame
, focus_frame
)
1644 Lisp_Object frame
, focus_frame
;
1646 /* Note that we don't check for a live frame here. It's reasonable
1647 to redirect the focus of a frame you're about to delete, if you
1648 know what other frame should receive those keystrokes. */
1649 CHECK_FRAME (frame
, 0);
1651 if (! NILP (focus_frame
))
1652 CHECK_LIVE_FRAME (focus_frame
, 1);
1654 XFRAME (frame
)->focus_frame
= focus_frame
;
1656 if (frame_rehighlight_hook
)
1657 (*frame_rehighlight_hook
) (XFRAME (frame
));
1663 DEFUN ("frame-focus", Fframe_focus
, Sframe_focus
, 1, 1, 0,
1664 "Return the frame to which FRAME's keystrokes are currently being sent.\n\
1665 This returns nil if FRAME's focus is not redirected.\n\
1666 See `redirect-frame-focus'.")
1670 CHECK_LIVE_FRAME (frame
, 0);
1672 return FRAME_FOCUS_FRAME (XFRAME (frame
));
1677 /* Return the value of frame parameter PROP in frame FRAME. */
1680 get_frame_param (frame
, prop
)
1681 register struct frame
*frame
;
1684 register Lisp_Object tem
;
1686 tem
= Fassq (prop
, frame
->param_alist
);
1692 /* Return the buffer-predicate of the selected frame. */
1695 frame_buffer_predicate ()
1697 return selected_frame
->buffer_predicate
;
1700 /* Return the buffer-list of the selected frame. */
1703 frame_buffer_list ()
1705 return selected_frame
->buffer_list
;
1708 /* Set the buffer-list of the selected frame. */
1711 set_frame_buffer_list (list
)
1714 selected_frame
->buffer_list
= list
;
1717 /* Discard BUFFER from the buffer-list of each frame. */
1720 frames_discard_buffer (buffer
)
1723 Lisp_Object frame
, tail
;
1725 FOR_EACH_FRAME (tail
, frame
)
1727 XFRAME (frame
)->buffer_list
1728 = Fdelq (buffer
, XFRAME (frame
)->buffer_list
);
1732 /* Move BUFFER to the end of the buffer-list of each frame. */
1735 frames_bury_buffer (buffer
)
1738 Lisp_Object frame
, tail
;
1740 FOR_EACH_FRAME (tail
, frame
)
1742 XFRAME (frame
)->buffer_list
1743 = nconc2 (Fdelq (buffer
, XFRAME (frame
)->buffer_list
),
1744 Fcons (buffer
, Qnil
));
1748 /* Modify the alist in *ALISTPTR to associate PROP with VAL.
1749 If the alist already has an element for PROP, we change it. */
1752 store_in_alist (alistptr
, prop
, val
)
1753 Lisp_Object
*alistptr
, val
;
1756 register Lisp_Object tem
;
1758 tem
= Fassq (prop
, *alistptr
);
1760 *alistptr
= Fcons (Fcons (prop
, val
), *alistptr
);
1766 frame_name_fnn_p (str
, len
)
1770 if (len
> 1 && str
[0] == 'F')
1773 long num
= strtol (str
+ 1, &end_ptr
, 10);
1775 if (end_ptr
== str
+ len
)
1781 /* Set the name of the terminal frame. Also used by MSDOS frames.
1782 Modeled after x_set_name which is used for WINDOW frames. */
1785 set_term_frame_name (f
, name
)
1789 f
->explicit_name
= ! NILP (name
);
1791 /* If NAME is nil, set the name to F<num>. */
1796 /* Check for no change needed in this very common case
1797 before we do any consing. */
1798 if (frame_name_fnn_p (XSTRING (f
->name
)->data
,
1799 STRING_BYTES (XSTRING (f
->name
))))
1802 terminal_frame_count
++;
1803 sprintf (namebuf
, "F%d", terminal_frame_count
);
1804 name
= build_string (namebuf
);
1808 CHECK_STRING (name
, 0);
1810 /* Don't change the name if it's already NAME. */
1811 if (! NILP (Fstring_equal (name
, f
->name
)))
1814 /* Don't allow the user to set the frame name to F<num>, so it
1815 doesn't clash with the names we generate for terminal frames. */
1816 if (frame_name_fnn_p (XSTRING (name
)->data
, STRING_BYTES (XSTRING (name
))))
1817 error ("Frame names of the form F<num> are usurped by Emacs");
1821 update_mode_lines
= 1;
1825 store_frame_param (f
, prop
, val
)
1827 Lisp_Object prop
, val
;
1829 register Lisp_Object tem
;
1831 if (EQ (prop
, Qbuffer_list
))
1833 f
->buffer_list
= val
;
1837 tem
= Fassq (prop
, f
->param_alist
);
1839 f
->param_alist
= Fcons (Fcons (prop
, val
), f
->param_alist
);
1843 if (EQ (prop
, Qbuffer_predicate
))
1844 f
->buffer_predicate
= val
;
1846 if (! FRAME_WINDOW_P (f
))
1848 if (EQ (prop
, Qmenu_bar_lines
))
1849 set_menu_bar_lines (f
, val
, make_number (FRAME_MENU_BAR_LINES (f
)));
1850 else if (EQ (prop
, Qname
))
1851 set_term_frame_name (f
, val
);
1854 if (EQ (prop
, Qminibuffer
) && WINDOWP (val
))
1856 if (! MINI_WINDOW_P (XWINDOW (val
)))
1857 error ("Surrogate minibuffer windows must be minibuffer windows.");
1859 if (FRAME_HAS_MINIBUF_P (f
) || FRAME_MINIBUF_ONLY_P (f
)
1860 && !EQ (val
, f
->minibuffer_window
))
1861 error ("Can't change the surrogate minibuffer of a frame with its own minibuffer");
1863 /* Install the chosen minibuffer window, with proper buffer. */
1864 f
->minibuffer_window
= val
;
1868 DEFUN ("frame-parameters", Fframe_parameters
, Sframe_parameters
, 0, 1, 0,
1869 "Return the parameters-alist of frame FRAME.\n\
1870 It is a list of elements of the form (PARM . VALUE), where PARM is a symbol.\n\
1871 The meaningful PARMs depend on the kind of frame.\n\
1872 If FRAME is omitted, return information on the currently selected frame.")
1880 if (EQ (frame
, Qnil
))
1884 CHECK_FRAME (frame
, 0);
1888 if (!FRAME_LIVE_P (f
))
1891 alist
= Fcopy_alist (f
->param_alist
);
1893 if (FRAME_MSDOS_P (f
))
1895 static char *colornames
[16] =
1897 "black", "blue", "green", "cyan", "red", "magenta", "brown",
1898 "lightgray", "darkgray", "lightblue", "lightgreen", "lightcyan",
1899 "lightred", "lightmagenta", "yellow", "white"
1901 store_in_alist (&alist
, intern ("foreground-color"),
1902 build_string (colornames
[FRAME_FOREGROUND_PIXEL (f
)]));
1903 store_in_alist (&alist
, intern ("background-color"),
1904 build_string (colornames
[FRAME_BACKGROUND_PIXEL (f
)]));
1906 store_in_alist (&alist
, intern ("font"), build_string ("default"));
1908 store_in_alist (&alist
, Qname
, f
->name
);
1909 height
= (FRAME_NEW_HEIGHT (f
) ? FRAME_NEW_HEIGHT (f
) : FRAME_HEIGHT (f
));
1910 store_in_alist (&alist
, Qheight
, make_number (height
));
1911 width
= (FRAME_NEW_WIDTH (f
) ? FRAME_NEW_WIDTH (f
) : FRAME_WIDTH (f
));
1912 store_in_alist (&alist
, Qwidth
, make_number (width
));
1913 store_in_alist (&alist
, Qmodeline
, (FRAME_WANTS_MODELINE_P (f
) ? Qt
: Qnil
));
1914 store_in_alist (&alist
, Qminibuffer
,
1915 (! FRAME_HAS_MINIBUF_P (f
) ? Qnil
1916 : FRAME_MINIBUF_ONLY_P (f
) ? Qonly
1917 : FRAME_MINIBUF_WINDOW (f
)));
1918 store_in_alist (&alist
, Qunsplittable
, (FRAME_NO_SPLIT_P (f
) ? Qt
: Qnil
));
1919 store_in_alist (&alist
, Qbuffer_list
, frame_buffer_list ());
1921 /* I think this should be done with a hook. */
1922 #ifdef HAVE_WINDOW_SYSTEM
1923 if (FRAME_WINDOW_P (f
))
1924 x_report_frame_params (f
, &alist
);
1928 /* This ought to be correct in f->param_alist for an X frame. */
1930 XSETFASTINT (lines
, FRAME_MENU_BAR_LINES (f
));
1931 store_in_alist (&alist
, Qmenu_bar_lines
, lines
);
1936 DEFUN ("modify-frame-parameters", Fmodify_frame_parameters
,
1937 Smodify_frame_parameters
, 2, 2, 0,
1938 "Modify the parameters of frame FRAME according to ALIST.\n\
1939 ALIST is an alist of parameters to change and their new values.\n\
1940 Each element of ALIST has the form (PARM . VALUE), where PARM is a symbol.\n\
1941 The meaningful PARMs depend on the kind of frame.\n\
1942 Undefined PARMs are ignored, but stored in the frame's parameter list\n\
1943 so that `frame-parameters' will return them.")
1945 Lisp_Object frame
, alist
;
1948 register Lisp_Object tail
, elt
, prop
, val
;
1950 if (EQ (frame
, Qnil
))
1954 CHECK_LIVE_FRAME (frame
, 0);
1958 /* I think this should be done with a hook. */
1959 #ifdef HAVE_WINDOW_SYSTEM
1960 if (FRAME_WINDOW_P (f
))
1961 x_set_frame_parameters (f
, alist
);
1965 if (FRAME_MSDOS_P (f
))
1966 IT_set_frame_parameters (f
, alist
);
1970 int length
= XINT (Flength (alist
));
1973 = (Lisp_Object
*) alloca (length
* sizeof (Lisp_Object
));
1975 = (Lisp_Object
*) alloca (length
* sizeof (Lisp_Object
));
1977 /* Extract parm names and values into those vectors. */
1980 for (tail
= alist
; CONSP (tail
); tail
= Fcdr (tail
))
1982 Lisp_Object elt
, prop
, val
;
1985 parms
[i
] = Fcar (elt
);
1986 values
[i
] = Fcdr (elt
);
1990 /* Now process them in reverse of specified order. */
1991 for (i
--; i
>= 0; i
--)
1995 store_frame_param (f
, prop
, val
);
2002 DEFUN ("frame-char-height", Fframe_char_height
, Sframe_char_height
,
2004 "Height in pixels of a line in the font in frame FRAME.\n\
2005 If FRAME is omitted, the selected frame is used.\n\
2006 For a terminal frame, the value is always 1.")
2016 CHECK_FRAME (frame
, 0);
2020 #ifdef HAVE_WINDOW_SYSTEM
2021 if (FRAME_WINDOW_P (f
))
2022 return make_number (x_char_height (f
));
2025 return make_number (1);
2029 DEFUN ("frame-char-width", Fframe_char_width
, Sframe_char_width
,
2031 "Width in pixels of characters in the font in frame FRAME.\n\
2032 If FRAME is omitted, the selected frame is used.\n\
2033 The width is the same for all characters, because\n\
2034 currently Emacs supports only fixed-width fonts.\n\
2035 For a terminal screen, the value is always 1.")
2045 CHECK_FRAME (frame
, 0);
2049 #ifdef HAVE_WINDOW_SYSTEM
2050 if (FRAME_WINDOW_P (f
))
2051 return make_number (x_char_width (f
));
2054 return make_number (1);
2057 DEFUN ("frame-pixel-height", Fframe_pixel_height
,
2058 Sframe_pixel_height
, 0, 1, 0,
2059 "Return a FRAME's height in pixels.\n\
2060 This counts only the height available for text lines,\n\
2061 not menu bars on window-system Emacs frames.\n\
2062 For a terminal frame, the result really gives the height in characters.\n\
2063 If FRAME is omitted, the selected frame is used.")
2073 CHECK_FRAME (frame
, 0);
2077 #ifdef HAVE_WINDOW_SYSTEM
2078 if (FRAME_WINDOW_P (f
))
2079 return make_number (x_pixel_height (f
));
2082 return make_number (FRAME_HEIGHT (f
));
2085 DEFUN ("frame-pixel-width", Fframe_pixel_width
,
2086 Sframe_pixel_width
, 0, 1, 0,
2087 "Return FRAME's width in pixels.\n\
2088 For a terminal frame, the result really gives the width in characters.\n\
2089 If FRAME is omitted, the selected frame is used.")
2099 CHECK_FRAME (frame
, 0);
2103 #ifdef HAVE_WINDOW_SYSTEM
2104 if (FRAME_WINDOW_P (f
))
2105 return make_number (x_pixel_width (f
));
2108 return make_number (FRAME_WIDTH (f
));
2111 DEFUN ("set-frame-height", Fset_frame_height
, Sset_frame_height
, 2, 3, 0,
2112 "Specify that the frame FRAME has LINES lines.\n\
2113 Optional third arg non-nil means that redisplay should use LINES lines\n\
2114 but that the idea of the actual height of the frame should not be changed.")
2115 (frame
, lines
, pretend
)
2116 Lisp_Object frame
, lines
, pretend
;
2118 register struct frame
*f
;
2120 CHECK_NUMBER (lines
, 0);
2125 CHECK_LIVE_FRAME (frame
, 0);
2129 /* I think this should be done with a hook. */
2130 #ifdef HAVE_WINDOW_SYSTEM
2131 if (FRAME_WINDOW_P (f
))
2133 if (XINT (lines
) != f
->height
)
2134 x_set_window_size (f
, 1, f
->width
, XINT (lines
));
2138 change_frame_size (f
, XINT (lines
), 0, !NILP (pretend
), 0);
2142 DEFUN ("set-frame-width", Fset_frame_width
, Sset_frame_width
, 2, 3, 0,
2143 "Specify that the frame FRAME has COLS columns.\n\
2144 Optional third arg non-nil means that redisplay should use COLS columns\n\
2145 but that the idea of the actual width of the frame should not be changed.")
2146 (frame
, cols
, pretend
)
2147 Lisp_Object frame
, cols
, pretend
;
2149 register struct frame
*f
;
2150 CHECK_NUMBER (cols
, 0);
2155 CHECK_LIVE_FRAME (frame
, 0);
2159 /* I think this should be done with a hook. */
2160 #ifdef HAVE_WINDOW_SYSTEM
2161 if (FRAME_WINDOW_P (f
))
2163 if (XINT (cols
) != f
->width
)
2164 x_set_window_size (f
, 1, XINT (cols
), f
->height
);
2168 change_frame_size (f
, 0, XINT (cols
), !NILP (pretend
), 0);
2172 DEFUN ("set-frame-size", Fset_frame_size
, Sset_frame_size
, 3, 3, 0,
2173 "Sets size of FRAME to COLS by ROWS, measured in characters.")
2175 Lisp_Object frame
, cols
, rows
;
2177 register struct frame
*f
;
2180 CHECK_LIVE_FRAME (frame
, 0);
2181 CHECK_NUMBER (cols
, 2);
2182 CHECK_NUMBER (rows
, 1);
2185 /* I think this should be done with a hook. */
2186 #ifdef HAVE_WINDOW_SYSTEM
2187 if (FRAME_WINDOW_P (f
))
2189 if (XINT (rows
) != f
->height
|| XINT (cols
) != f
->width
2190 || FRAME_NEW_HEIGHT (f
) || FRAME_NEW_WIDTH (f
))
2191 x_set_window_size (f
, 1, XINT (cols
), XINT (rows
));
2195 change_frame_size (f
, XINT (rows
), XINT (cols
), 0, 0);
2200 DEFUN ("set-frame-position", Fset_frame_position
,
2201 Sset_frame_position
, 3, 3, 0,
2202 "Sets position of FRAME in pixels to XOFFSET by YOFFSET.\n\
2203 This is actually the position of the upper left corner of the frame.\n\
2204 Negative values for XOFFSET or YOFFSET are interpreted relative to\n\
2205 the rightmost or bottommost possible position (that stays within the screen).")
2206 (frame
, xoffset
, yoffset
)
2207 Lisp_Object frame
, xoffset
, yoffset
;
2209 register struct frame
*f
;
2212 CHECK_LIVE_FRAME (frame
, 0);
2213 CHECK_NUMBER (xoffset
, 1);
2214 CHECK_NUMBER (yoffset
, 2);
2217 /* I think this should be done with a hook. */
2218 #ifdef HAVE_WINDOW_SYSTEM
2219 if (FRAME_WINDOW_P (f
))
2220 x_set_offset (f
, XINT (xoffset
), XINT (yoffset
), 1);
2231 staticpro (&Vframe_list
);
2233 DEFVAR_LISP ("terminal-frame", &Vterminal_frame
,
2234 "The initial frame-object, which represents Emacs's stdout.");
2236 DEFVAR_LISP ("emacs-iconified", &Vemacs_iconified
,
2237 "Non-nil if all of emacs is iconified and frame updates are not needed.");
2238 Vemacs_iconified
= Qnil
;
2240 DEFVAR_KBOARD ("default-minibuffer-frame", Vdefault_minibuffer_frame
,
2241 "Minibufferless frames use this frame's minibuffer.\n\
2243 Emacs cannot create minibufferless frames unless this is set to an\n\
2244 appropriate surrogate.\n\
2246 Emacs consults this variable only when creating minibufferless\n\
2247 frames; once the frame is created, it sticks with its assigned\n\
2248 minibuffer, no matter what this variable is set to. This means that\n\
2249 this variable doesn't necessarily say anything meaningful about the\n\
2250 current set of frames, or where the minibuffer is currently being\n\
2253 defsubr (&Sactive_minibuffer_window
);
2255 defsubr (&Sframe_live_p
);
2256 defsubr (&Smake_terminal_frame
);
2257 defsubr (&Shandle_switch_frame
);
2258 defsubr (&Signore_event
);
2259 defsubr (&Sselect_frame
);
2260 defsubr (&Sselected_frame
);
2261 defsubr (&Swindow_frame
);
2262 defsubr (&Sframe_root_window
);
2263 defsubr (&Sframe_first_window
);
2264 defsubr (&Sframe_selected_window
);
2265 defsubr (&Sset_frame_selected_window
);
2266 defsubr (&Sframe_list
);
2267 defsubr (&Snext_frame
);
2268 defsubr (&Sprevious_frame
);
2269 defsubr (&Sdelete_frame
);
2270 defsubr (&Smouse_position
);
2271 defsubr (&Smouse_pixel_position
);
2272 defsubr (&Sset_mouse_position
);
2273 defsubr (&Sset_mouse_pixel_position
);
2275 defsubr (&Sframe_configuration
);
2276 defsubr (&Srestore_frame_configuration
);
2278 defsubr (&Smake_frame_visible
);
2279 defsubr (&Smake_frame_invisible
);
2280 defsubr (&Siconify_frame
);
2281 defsubr (&Sframe_visible_p
);
2282 defsubr (&Svisible_frame_list
);
2283 defsubr (&Sraise_frame
);
2284 defsubr (&Slower_frame
);
2285 defsubr (&Sredirect_frame_focus
);
2286 defsubr (&Sframe_focus
);
2287 defsubr (&Sframe_parameters
);
2288 defsubr (&Smodify_frame_parameters
);
2289 defsubr (&Sframe_char_height
);
2290 defsubr (&Sframe_char_width
);
2291 defsubr (&Sframe_pixel_height
);
2292 defsubr (&Sframe_pixel_width
);
2293 defsubr (&Sset_frame_height
);
2294 defsubr (&Sset_frame_width
);
2295 defsubr (&Sset_frame_size
);
2296 defsubr (&Sset_frame_position
);
2301 initial_define_lispy_key (global_map
, "switch-frame", "handle-switch-frame");
2302 initial_define_lispy_key (global_map
, "delete-frame", "handle-delete-frame");
2303 initial_define_lispy_key (global_map
, "iconify-frame", "ignore-event");
2304 initial_define_lispy_key (global_map
, "make-frame-visible", "ignore-event");