1 /* Generic frame functions.
2 Copyright (C) 1993, 1994, 1995 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. */
26 #include "termhooks.h"
32 /* Evaluate this expression to rebuild the section of syms_of_frame
33 that initializes and staticpros the symbols declared below. Note
34 that Emacs 18 has a bug that keeps C-x C-e from being able to
35 evaluate this expression.
38 ;; Accumulate a list of the symbols we want to initialize from the
39 ;; declarations at the top of the file.
40 (goto-char (point-min))
41 (search-forward "/\*&&& symbols declared here &&&*\/\n")
43 (while (looking-at "Lisp_Object \\(Q[a-z_]+\\)")
45 (cons (buffer-substring (match-beginning 1) (match-end 1))
48 (setq symbol-list (nreverse symbol-list))
49 ;; Delete the section of syms_of_... where we initialize the symbols.
50 (search-forward "\n /\*&&& init symbols here &&&*\/\n")
51 (let ((start (point)))
52 (while (looking-at "^ Q")
54 (kill-region start (point)))
55 ;; Write a new symbol initialization section.
57 (insert (format " %s = intern (\"" (car symbol-list)))
58 (let ((start (point)))
59 (insert (substring (car symbol-list) 1))
60 (subst-char-in-region start (point) ?_ ?-))
61 (insert (format "\");\n staticpro (&%s);\n" (car symbol-list)))
62 (setq symbol-list (cdr symbol-list)))))
65 /*&&& symbols declared here &&&*/
67 Lisp_Object Qframe_live_p
;
70 Lisp_Object Qminibuffer
;
71 Lisp_Object Qmodeline
;
74 Lisp_Object Qunsplittable
;
75 Lisp_Object Qmenu_bar_lines
;
81 Lisp_Object Qbuffer_predicate
;
84 Lisp_Object Vterminal_frame
;
85 Lisp_Object Vdefault_frame_alist
;
90 /*&&& init symbols here &&&*/
91 Qframep
= intern ("framep");
93 Qframe_live_p
= intern ("frame-live-p");
94 staticpro (&Qframe_live_p
);
95 Qheight
= intern ("height");
97 Qicon
= intern ("icon");
99 Qminibuffer
= intern ("minibuffer");
100 staticpro (&Qminibuffer
);
101 Qmodeline
= intern ("modeline");
102 staticpro (&Qmodeline
);
103 Qname
= intern ("name");
105 Qonly
= intern ("only");
107 Qunsplittable
= intern ("unsplittable");
108 staticpro (&Qunsplittable
);
109 Qmenu_bar_lines
= intern ("menu-bar-lines");
110 staticpro (&Qmenu_bar_lines
);
111 Qwidth
= intern ("width");
115 Qwin32
= intern ("win32");
119 Qvisible
= intern ("visible");
120 staticpro (&Qvisible
);
121 Qbuffer_predicate
= intern ("buffer-predicate");
122 staticpro (&Qbuffer_predicate
);
123 Qtitle
= intern ("title");
126 DEFVAR_LISP ("default-frame-alist", &Vdefault_frame_alist
,
127 "Alist of default values for frame creation.\n\
128 These may be set in your init file, like this:\n\
129 (setq default-frame-alist '((width . 80) (height . 55) (menu-bar-lines . 1))\n\
130 These override values given in window system configuration data,\n\
131 including X Windows' defaults database.\n\
132 For values specific to the first Emacs frame, see `initial-frame-alist'.\n\
133 For values specific to the separate minibuffer frame, see\n\
134 `minibuffer-frame-alist'.\n\
135 The `menu-bar-lines' element of the list controls whether new frames\n\
136 have menu bars; `menu-bar-mode' works by altering this element.");
137 Vdefault_frame_alist
= Qnil
;
141 set_menu_bar_lines_1 (window
, n
)
145 struct window
*w
= XWINDOW (window
);
147 XSETFASTINT (w
->last_modified
, 0);
148 XSETFASTINT (w
->top
, XFASTINT (w
->top
) + n
);
149 XSETFASTINT (w
->height
, XFASTINT (w
->height
) - n
);
151 /* Handle just the top child in a vertical split. */
152 if (!NILP (w
->vchild
))
153 set_menu_bar_lines_1 (w
->vchild
, n
);
155 /* Adjust all children in a horizontal split. */
156 for (window
= w
->hchild
; !NILP (window
); window
= w
->next
)
158 w
= XWINDOW (window
);
159 set_menu_bar_lines_1 (window
, n
);
164 set_menu_bar_lines (f
, value
, oldval
)
166 Lisp_Object value
, oldval
;
169 int olines
= FRAME_MENU_BAR_LINES (f
);
171 /* Right now, menu bars don't work properly in minibuf-only frames;
172 most of the commands try to apply themselves to the minibuffer
173 frame itself, and get an error because you can't switch buffers
174 in or split the minibuffer window. */
175 if (FRAME_MINIBUF_ONLY_P (f
))
178 if (INTEGERP (value
))
179 nlines
= XINT (value
);
183 if (nlines
!= olines
)
185 windows_or_buffers_changed
++;
186 FRAME_WINDOW_SIZES_CHANGED (f
) = 1;
187 FRAME_MENU_BAR_LINES (f
) = nlines
;
188 set_menu_bar_lines_1 (f
->root_window
, nlines
- olines
);
194 /* These help us bind and responding to switch-frame events. */
195 #include "commands.h"
196 #include "keyboard.h"
198 Lisp_Object Vemacs_iconified
;
199 Lisp_Object Vframe_list
;
201 extern Lisp_Object Vminibuffer_list
;
202 extern Lisp_Object
get_minibuffer ();
203 extern Lisp_Object
Fhandle_switch_frame ();
204 extern Lisp_Object
Fredirect_frame_focus ();
205 extern Lisp_Object
x_get_focus_frame ();
207 DEFUN ("framep", Fframep
, Sframep
, 1, 1, 0,
208 "Return non-nil if OBJECT is a frame.\n\
209 Value is t for a termcap frame (a character-only terminal),\n\
210 `x' for an Emacs frame that is really an X window,\n\
211 `pc' for a direct-write MS-DOS frame.\n\
212 See also `frame-live-p'.")
216 if (!FRAMEP (object
))
218 switch (XFRAME (object
)->output_method
)
222 case output_x_window
:
226 case output_msdos_raw
:
233 DEFUN ("frame-live-p", Fframe_live_p
, Sframe_live_p
, 1, 1, 0,
234 "Return non-nil if OBJECT is a frame which has not been deleted.\n\
235 Value is nil if OBJECT is not a live frame. If object is a live\n\
236 frame, the return value indicates what sort of output device it is\n\
237 displayed on. Value is t for a termcap frame (a character-only\n\
238 terminal), `x' for an Emacs frame being displayed in an X window.")
242 return ((FRAMEP (object
)
243 && FRAME_LIVE_P (XFRAME (object
)))
253 register struct frame
*f
;
254 register Lisp_Object root_window
;
255 register Lisp_Object mini_window
;
256 register struct Lisp_Vector
*vec
;
259 vec
= allocate_vectorlike ((EMACS_INT
) VECSIZE (struct frame
));
260 for (i
= 0; i
< VECSIZE (struct frame
); i
++)
261 XSETFASTINT (vec
->contents
[i
], 0);
262 vec
->size
= VECSIZE (struct frame
);
263 f
= (struct frame
*)vec
;
264 XSETFRAME (frame
, f
);
268 f
->current_glyphs
= 0;
269 f
->desired_glyphs
= 0;
271 f
->async_visible
= 0;
272 f
->output_data
.nothing
= 0;
274 f
->async_iconified
= 0;
275 f
->wants_modeline
= 1;
280 f
->has_minibuffer
= mini_p
;
281 f
->focus_frame
= Qnil
;
282 f
->explicit_name
= 0;
283 f
->can_have_scroll_bars
= 0;
284 f
->has_vertical_scroll_bars
= 0;
285 f
->param_alist
= Qnil
;
286 f
->scroll_bars
= Qnil
;
287 f
->condemned_scroll_bars
= Qnil
;
288 f
->face_alist
= Qnil
;
289 f
->menu_bar_items
= Qnil
;
290 f
->menu_bar_vector
= Qnil
;
291 f
->menu_bar_items_used
= 0;
292 f
->buffer_predicate
= Qnil
;
294 f
->kboard
= initial_kboard
;
299 root_window
= make_window ();
302 mini_window
= make_window ();
303 XWINDOW (root_window
)->next
= mini_window
;
304 XWINDOW (mini_window
)->prev
= root_window
;
305 XWINDOW (mini_window
)->mini_p
= Qt
;
306 XWINDOW (mini_window
)->frame
= frame
;
307 f
->minibuffer_window
= mini_window
;
312 XWINDOW (root_window
)->next
= Qnil
;
313 f
->minibuffer_window
= Qnil
;
316 XWINDOW (root_window
)->frame
= frame
;
319 just so that there is "something there."
320 Correct size will be set up later with change_frame_size. */
325 XSETFASTINT (XWINDOW (root_window
)->width
, 10);
326 XSETFASTINT (XWINDOW (root_window
)->height
, (mini_p
? 9 : 10));
330 XSETFASTINT (XWINDOW (mini_window
)->width
, 10);
331 XSETFASTINT (XWINDOW (mini_window
)->top
, 9);
332 XSETFASTINT (XWINDOW (mini_window
)->height
, 1);
335 /* Choose a buffer for the frame's root window. */
339 XWINDOW (root_window
)->buffer
= Qt
;
340 buf
= Fcurrent_buffer ();
341 /* If buf is a 'hidden' buffer (i.e. one whose name starts with
342 a space), try to find another one. */
343 if (XSTRING (Fbuffer_name (buf
))->data
[0] == ' ')
344 buf
= Fother_buffer (buf
, Qnil
);
345 Fset_window_buffer (root_window
, buf
);
350 XWINDOW (mini_window
)->buffer
= Qt
;
351 Fset_window_buffer (mini_window
,
352 (NILP (Vminibuffer_list
)
354 : Fcar (Vminibuffer_list
)));
357 f
->root_window
= root_window
;
358 f
->selected_window
= root_window
;
359 /* Make sure this window seems more recently used than
360 a newly-created, never-selected window. */
361 XSETFASTINT (XWINDOW (f
->selected_window
)->use_time
, ++window_select_count
);
366 /* Make a frame using a separate minibuffer window on another frame.
367 MINI_WINDOW is the minibuffer window to use. nil means use the
368 default (the global minibuffer). */
371 make_frame_without_minibuffer (mini_window
, kb
, display
)
372 register Lisp_Object mini_window
;
376 register struct frame
*f
;
379 if (!NILP (mini_window
))
380 CHECK_LIVE_WINDOW (mini_window
, 0);
383 if (!NILP (mini_window
)
384 && XFRAME (XWINDOW (mini_window
)->frame
)->kboard
!= kb
)
385 error ("frame and minibuffer must be on the same display");
388 /* Make a frame containing just a root window. */
391 if (NILP (mini_window
))
393 /* Use default-minibuffer-frame if possible. */
394 if (!FRAMEP (kb
->Vdefault_minibuffer_frame
)
395 || ! FRAME_LIVE_P (XFRAME (kb
->Vdefault_minibuffer_frame
)))
397 Lisp_Object frame_dummy
;
399 XSETFRAME (frame_dummy
, f
);
400 GCPRO1 (frame_dummy
);
401 /* If there's no minibuffer frame to use, create one. */
402 kb
->Vdefault_minibuffer_frame
=
403 call1 (intern ("make-initial-minibuffer-frame"), display
);
407 mini_window
= XFRAME (kb
->Vdefault_minibuffer_frame
)->minibuffer_window
;
410 f
->minibuffer_window
= mini_window
;
412 /* Make the chosen minibuffer window display the proper minibuffer,
413 unless it is already showing a minibuffer. */
414 if (NILP (Fmemq (XWINDOW (mini_window
)->buffer
, Vminibuffer_list
)))
415 Fset_window_buffer (mini_window
,
416 (NILP (Vminibuffer_list
)
418 : Fcar (Vminibuffer_list
)));
422 /* Make a frame containing only a minibuffer window. */
425 make_minibuffer_frame ()
427 /* First make a frame containing just a root window, no minibuffer. */
429 register struct frame
*f
= make_frame (0);
430 register Lisp_Object mini_window
;
431 register Lisp_Object frame
;
433 XSETFRAME (frame
, f
);
438 f
->wants_modeline
= 0;
439 f
->has_minibuffer
= 1;
441 /* Now label the root window as also being the minibuffer.
442 Avoid infinite looping on the window chain by marking next pointer
445 mini_window
= f
->minibuffer_window
= f
->root_window
;
446 XWINDOW (mini_window
)->mini_p
= Qt
;
447 XWINDOW (mini_window
)->next
= Qnil
;
448 XWINDOW (mini_window
)->prev
= Qnil
;
449 XWINDOW (mini_window
)->frame
= frame
;
451 /* Put the proper buffer in that window. */
453 Fset_window_buffer (mini_window
,
454 (NILP (Vminibuffer_list
)
456 : Fcar (Vminibuffer_list
)));
460 /* Construct a frame that refers to the terminal (stdin and stdout). */
462 static int terminal_frame_count
;
465 make_terminal_frame ()
467 register struct frame
*f
;
474 initial_kboard
= (KBOARD
*) xmalloc (sizeof (KBOARD
));
475 init_kboard (initial_kboard
);
476 initial_kboard
->next_kboard
= all_kboards
;
477 all_kboards
= initial_kboard
;
481 /* The first call must initialize Vframe_list. */
482 if (! (NILP (Vframe_list
) || CONSP (Vframe_list
)))
487 XSETFRAME (frame
, f
);
488 Vframe_list
= Fcons (frame
, Vframe_list
);
490 terminal_frame_count
++;
491 if (terminal_frame_count
== 1)
493 f
->name
= build_string ("Emacs");
497 sprintf (name
, "Emacs-%d", terminal_frame_count
);
498 f
->name
= build_string (name
);
501 f
->visible
= 1; /* FRAME_SET_VISIBLE wd set frame_garbaged. */
502 f
->async_visible
= 1; /* Don't let visible be cleared later. */
504 f
->output_data
.x
= &the_only_x_display
;
505 f
->output_method
= output_msdos_raw
;
506 init_frame_faces (f
);
507 #else /* not MSDOS */
508 f
->output_data
.nothing
= 1; /* Nonzero means frame isn't deleted. */
513 DEFUN ("make-terminal-frame", Fmake_terminal_frame
, Smake_terminal_frame
,
514 1, 1, 0, "Create an additional terminal frame.\n\
515 You can create multiple frames on a text-only terminal in this way.\n\
516 Only the selected terminal frame is actually displayed.\n\
517 This function takes one argument, an alist specifying frame parameters.\n\
518 In practice, generally you don't need to specify any parameters.\n\
519 Note that changing the size of one terminal frame automatically affects all.")
527 if (selected_frame
->output_method
!= output_msdos_raw
)
530 if (selected_frame
->output_method
!= output_termcap
)
531 error ("Not using an ASCII terminal now; cannot make a new ASCII frame");
534 f
= make_terminal_frame ();
535 change_frame_size (f
, FRAME_HEIGHT (selected_frame
),
536 FRAME_WIDTH (selected_frame
), 0, 0);
537 remake_frame_glyphs (f
);
539 XSETFRAME (frame
, f
);
540 Fmodify_frame_parameters (frame
, Vdefault_frame_alist
);
541 Fmodify_frame_parameters (frame
, parms
);
542 f
->face_alist
= selected_frame
->face_alist
;
547 do_switch_frame (frame
, no_enter
, track
)
548 Lisp_Object frame
, no_enter
;
551 /* If FRAME is a switch-frame event, extract the frame we should
554 && EQ (XCONS (frame
)->car
, Qswitch_frame
)
555 && CONSP (XCONS (frame
)->cdr
))
556 frame
= XCONS (XCONS (frame
)->cdr
)->car
;
558 /* This used to say CHECK_LIVE_FRAME, but apparently it's possible for
559 a switch-frame event to arrive after a frame is no longer live,
560 especially when deleting the initial frame during startup. */
561 CHECK_FRAME (frame
, 0);
562 if (! FRAME_LIVE_P (XFRAME (frame
)))
565 if (selected_frame
== XFRAME (frame
))
568 /* This is too greedy; it causes inappropriate focus redirection
569 that's hard to get rid of. */
571 /* If a frame's focus has been redirected toward the currently
572 selected frame, we should change the redirection to point to the
573 newly selected frame. This means that if the focus is redirected
574 from a minibufferless frame to a surrogate minibuffer frame, we
575 can use `other-window' to switch between all the frames using
576 that minibuffer frame, and the focus redirection will follow us
582 for (tail
= Vframe_list
; CONSP (tail
); tail
= XCONS (tail
)->cdr
)
586 if (!FRAMEP (XCONS (tail
)->car
))
589 focus
= FRAME_FOCUS_FRAME (XFRAME (XCONS (tail
)->car
));
591 if (FRAMEP (focus
) && XFRAME (focus
) == selected_frame
)
592 Fredirect_frame_focus (XCONS (tail
)->car
, frame
);
596 /* Instead, apply it only to the frame we're pointing to. */
597 #ifdef HAVE_WINDOW_SYSTEM
598 if (track
&& (FRAME_WINDOW_P (XFRAME (frame
))))
600 Lisp_Object focus
, xfocus
;
602 xfocus
= x_get_focus_frame (XFRAME (frame
));
605 focus
= FRAME_FOCUS_FRAME (XFRAME (xfocus
));
606 if (FRAMEP (focus
) && XFRAME (focus
) == selected_frame
)
607 Fredirect_frame_focus (xfocus
, frame
);
610 #endif /* HAVE_X_WINDOWS */
613 selected_frame
= XFRAME (frame
);
614 if (! FRAME_MINIBUF_ONLY_P (selected_frame
))
615 last_nonminibuf_frame
= selected_frame
;
617 Fselect_window (XFRAME (frame
)->selected_window
);
619 /* We want to make sure that the next event generates a frame-switch
620 event to the appropriate frame. This seems kludgy to me, but
621 before you take it out, make sure that evaluating something like
622 (select-window (frame-root-window (new-frame))) doesn't end up
623 with your typing being interpreted in the new frame instead of
624 the one you're actually typing in. */
625 internal_last_event_frame
= Qnil
;
630 DEFUN ("select-frame", Fselect_frame
, Sselect_frame
, 1, 2, "e",
631 "Select the frame FRAME.\n\
632 Subsequent editing commands apply to its selected window.\n\
633 The selection of FRAME lasts until the next time the user does\n\
634 something to select a different frame, or until the next time this\n\
635 function is called.")
637 Lisp_Object frame
, no_enter
;
639 return do_switch_frame (frame
, no_enter
, 1);
643 DEFUN ("handle-switch-frame", Fhandle_switch_frame
, Shandle_switch_frame
, 1, 2, "e",
644 "Handle a switch-frame event EVENT.\n\
645 Switch-frame events are usually bound to this function.\n\
646 A switch-frame event tells Emacs that the window manager has requested\n\
647 that the user's events be directed to the frame mentioned in the event.\n\
648 This function selects the selected window of the frame of EVENT.\n\
650 If EVENT is frame object, handle it as if it were a switch-frame event\n\
653 Lisp_Object event
, no_enter
;
655 /* Preserve prefix arg that the command loop just cleared. */
656 current_kboard
->Vprefix_arg
= Vcurrent_prefix_arg
;
657 call1 (Vrun_hooks
, Qmouse_leave_buffer_hook
);
658 return do_switch_frame (event
, no_enter
, 0);
661 DEFUN ("ignore-event", Fignore_event
, Signore_event
, 0, 0, "",
662 "Do nothing, but preserve any prefix argument already specified.\n\
663 This is a suitable binding for iconify-frame and make-frame-visible.")
666 current_kboard
->Vprefix_arg
= Vcurrent_prefix_arg
;
670 DEFUN ("selected-frame", Fselected_frame
, Sselected_frame
, 0, 0, 0,
671 "Return the frame that is now selected.")
675 XSETFRAME (tem
, selected_frame
);
679 DEFUN ("window-frame", Fwindow_frame
, Swindow_frame
, 1, 1, 0,
680 "Return the frame object that window WINDOW is on.")
684 CHECK_LIVE_WINDOW (window
, 0);
685 return XWINDOW (window
)->frame
;
688 DEFUN ("frame-first-window", Fframe_first_window
, Sframe_first_window
, 0, 1, 0,
689 "Returns the topmost, leftmost window of FRAME.\n\
690 If omitted, FRAME defaults to the currently selected frame.")
697 w
= selected_frame
->root_window
;
700 CHECK_LIVE_FRAME (frame
, 0);
701 w
= XFRAME (frame
)->root_window
;
703 while (NILP (XWINDOW (w
)->buffer
))
705 if (! NILP (XWINDOW (w
)->hchild
))
706 w
= XWINDOW (w
)->hchild
;
707 else if (! NILP (XWINDOW (w
)->vchild
))
708 w
= XWINDOW (w
)->vchild
;
715 DEFUN ("active-minibuffer-window", Factive_minibuffer_window
,
716 Sactive_minibuffer_window
, 0, 0, 0,
717 "Return the currently active minibuffer window, or nil if none.")
720 return minibuf_level
? minibuf_window
: Qnil
;
723 DEFUN ("frame-root-window", Fframe_root_window
, Sframe_root_window
, 0, 1, 0,
724 "Returns the root-window of FRAME.\n\
725 If omitted, FRAME defaults to the currently selected frame.")
730 XSETFRAME (frame
, selected_frame
);
732 CHECK_LIVE_FRAME (frame
, 0);
734 return XFRAME (frame
)->root_window
;
737 DEFUN ("frame-selected-window", Fframe_selected_window
,
738 Sframe_selected_window
, 0, 1, 0,
739 "Return the selected window of frame object FRAME.\n\
740 If omitted, FRAME defaults to the currently selected frame.")
745 XSETFRAME (frame
, selected_frame
);
747 CHECK_LIVE_FRAME (frame
, 0);
749 return XFRAME (frame
)->selected_window
;
752 DEFUN ("set-frame-selected-window", Fset_frame_selected_window
,
753 Sset_frame_selected_window
, 2, 2, 0,
754 "Set the selected window of frame object FRAME to WINDOW.\n\
755 If FRAME is nil, the selected frame is used.\n\
756 If FRAME is the selected frame, this makes WINDOW the selected window.")
758 Lisp_Object frame
, window
;
761 XSETFRAME (frame
, selected_frame
);
763 CHECK_LIVE_FRAME (frame
, 0);
765 CHECK_LIVE_WINDOW (window
, 1);
767 if (! EQ (frame
, WINDOW_FRAME (XWINDOW (window
))))
768 error ("In `set-frame-selected-window', WINDOW is not on FRAME");
770 if (XFRAME (frame
) == selected_frame
)
771 return Fselect_window (window
);
773 return XFRAME (frame
)->selected_window
= window
;
776 DEFUN ("frame-list", Fframe_list
, Sframe_list
,
778 "Return a list of all frames.")
781 return Fcopy_sequence (Vframe_list
);
784 /* Return the next frame in the frame list after FRAME.
785 If MINIBUF is nil, exclude minibuffer-only frames.
786 If MINIBUF is a window, include only its own frame
787 and any frame now using that window as the minibuffer.
788 If MINIBUF is `visible', include all visible frames.
789 If MINIBUF is 0, include all visible and iconified frames.
790 Otherwise, include all frames. */
793 next_frame (frame
, minibuf
)
800 /* There must always be at least one frame in Vframe_list. */
801 if (! CONSP (Vframe_list
))
804 /* If this frame is dead, it won't be in Vframe_list, and we'll loop
805 forever. Forestall that. */
806 CHECK_LIVE_FRAME (frame
, 0);
809 for (tail
= Vframe_list
; CONSP (tail
); tail
= XCONS (tail
)->cdr
)
813 f
= XCONS (tail
)->car
;
816 && FRAME_KBOARD (XFRAME (f
)) == FRAME_KBOARD (XFRAME (frame
)))
818 /* Decide whether this frame is eligible to be returned. */
820 /* If we've looped all the way around without finding any
821 eligible frames, return the original frame. */
825 /* Let minibuf decide if this frame is acceptable. */
828 if (! FRAME_MINIBUF_ONLY_P (XFRAME (f
)))
831 else if (EQ (minibuf
, Qvisible
))
833 FRAME_SAMPLE_VISIBILITY (XFRAME (f
));
834 if (FRAME_VISIBLE_P (XFRAME (f
)))
837 else if (XFASTINT (minibuf
) == 0)
839 FRAME_SAMPLE_VISIBILITY (XFRAME (f
));
840 if (FRAME_VISIBLE_P (XFRAME (f
))
841 || FRAME_ICONIFIED_P (XFRAME (f
)))
844 else if (WINDOWP (minibuf
))
846 if (EQ (FRAME_MINIBUF_WINDOW (XFRAME (f
)), minibuf
)
847 /* Check that F either is, or has forwarded its focus to,
849 && (EQ (WINDOW_FRAME (XWINDOW (minibuf
)), f
)
850 || EQ (WINDOW_FRAME (XWINDOW (minibuf
)),
851 FRAME_FOCUS_FRAME (XFRAME (f
)))))
863 /* Return the previous frame in the frame list before FRAME.
864 If MINIBUF is nil, exclude minibuffer-only frames.
865 If MINIBUF is a window, include only its own frame
866 and any frame now using that window as the minibuffer.
867 If MINIBUF is `visible', include all visible frames.
868 If MINIBUF is 0, include all visible and iconified frames.
869 Otherwise, include all frames. */
872 prev_frame (frame
, minibuf
)
879 /* There must always be at least one frame in Vframe_list. */
880 if (! CONSP (Vframe_list
))
884 for (tail
= Vframe_list
; CONSP (tail
); tail
= XCONS (tail
)->cdr
)
888 f
= XCONS (tail
)->car
;
892 if (EQ (frame
, f
) && !NILP (prev
))
895 if (FRAME_KBOARD (XFRAME (f
)) == FRAME_KBOARD (XFRAME (frame
)))
897 /* Decide whether this frame is eligible to be returned,
898 according to minibuf. */
901 if (! FRAME_MINIBUF_ONLY_P (XFRAME (f
)))
904 else if (WINDOWP (minibuf
))
906 if (EQ (FRAME_MINIBUF_WINDOW (XFRAME (f
)), minibuf
)
907 /* Check that F either is, or has forwarded its focus to,
909 && (EQ (WINDOW_FRAME (XWINDOW (minibuf
)), f
)
910 || EQ (WINDOW_FRAME (XWINDOW (minibuf
)),
911 FRAME_FOCUS_FRAME (XFRAME (f
)))))
914 else if (EQ (minibuf
, Qvisible
))
916 FRAME_SAMPLE_VISIBILITY (XFRAME (f
));
917 if (FRAME_VISIBLE_P (XFRAME (f
)))
920 else if (XFASTINT (minibuf
) == 0)
922 FRAME_SAMPLE_VISIBILITY (XFRAME (f
));
923 if (FRAME_VISIBLE_P (XFRAME (f
))
924 || FRAME_ICONIFIED_P (XFRAME (f
)))
932 /* We've scanned the entire list. */
934 /* We went through the whole frame list without finding a single
935 acceptable frame. Return the original frame. */
938 /* There were no acceptable frames in the list before FRAME; otherwise,
939 we would have returned directly from the loop. Since PREV is the last
940 acceptable frame in the list, return it. */
945 DEFUN ("next-frame", Fnext_frame
, Snext_frame
, 0, 2, 0,
946 "Return the next frame in the frame list after FRAME.\n\
947 It considers only frames on the same terminal as FRAME.\n\
948 By default, skip minibuffer-only frames.\n\
949 If omitted, FRAME defaults to the selected frame.\n\
950 If optional argument MINIFRAME is nil, exclude minibuffer-only frames.\n\
951 If MINIFRAME is a window, include only its own frame\n\
952 and any frame now using that window as the minibuffer.\n\
953 If MINIFRAME is `visible', include all visible frames.\n\
954 If MINIFRAME is 0, include all visible and iconified frames.\n\
955 Otherwise, include all frames.")
957 Lisp_Object frame
, miniframe
;
962 XSETFRAME (frame
, selected_frame
);
964 CHECK_LIVE_FRAME (frame
, 0);
966 return next_frame (frame
, miniframe
);
969 DEFUN ("previous-frame", Fprevious_frame
, Sprevious_frame
, 0, 2, 0,
970 "Return the previous frame in the frame list before FRAME.\n\
971 It considers only frames on the same terminal as FRAME.\n\
972 By default, skip minibuffer-only frames.\n\
973 If omitted, FRAME defaults to the selected frame.\n\
974 If optional argument MINIFRAME is nil, exclude minibuffer-only frames.\n\
975 If MINIFRAME is a window, include only its own frame\n\
976 and any frame now using that window as the minibuffer.\n\
977 If MINIFRAME is `visible', include all visible frames.\n\
978 If MINIFRAME is 0, include all visible and iconified frames.\n\
979 Otherwise, include all frames.")
981 Lisp_Object frame
, miniframe
;
986 XSETFRAME (frame
, selected_frame
);
988 CHECK_LIVE_FRAME (frame
, 0);
990 return prev_frame (frame
, miniframe
);
993 /* Return 1 if it is ok to delete frame F;
994 0 if all frames aside from F are invisible.
995 (Exception: if F is the terminal frame, and we are using X, return 1.) */
998 other_visible_frames (f
)
1001 /* We know the selected frame is visible,
1002 so if F is some other frame, it can't be the sole visible one. */
1003 if (f
== selected_frame
)
1008 for (frames
= Vframe_list
;
1010 frames
= XCONS (frames
)->cdr
)
1014 this = XCONS (frames
)->car
;
1015 /* Verify that the frame's window still exists
1016 and we can still talk to it. And note any recent change
1018 #ifdef HAVE_WINDOW_SYSTEM
1019 if (FRAME_WINDOW_P (XFRAME (this)))
1021 x_sync (XFRAME (this));
1022 FRAME_SAMPLE_VISIBILITY (XFRAME (this));
1026 if (FRAME_VISIBLE_P (XFRAME (this))
1027 || FRAME_ICONIFIED_P (XFRAME (this))
1028 /* Allow deleting the terminal frame when at least
1029 one X frame exists! */
1030 || (FRAME_WINDOW_P (XFRAME (this)) && !FRAME_WINDOW_P (f
)))
1038 DEFUN ("delete-frame", Fdelete_frame
, Sdelete_frame
, 0, 2, "",
1039 "Delete FRAME, permanently eliminating it from use.\n\
1040 If omitted, FRAME defaults to the selected frame.\n\
1041 A frame may not be deleted if its minibuffer is used by other frames.\n\
1042 Normally, you may not delete a frame if all other frames are invisible,\n\
1043 but if the second optional argument FORCE is non-nil, you may do so.")
1045 Lisp_Object frame
, force
;
1048 int minibuffer_selected
;
1050 if (EQ (frame
, Qnil
))
1053 XSETFRAME (frame
, f
);
1057 CHECK_FRAME (frame
, 0);
1061 if (! FRAME_LIVE_P (f
))
1064 if (NILP (force
) && !other_visible_frames (f
))
1065 error ("Attempt to delete the sole visible or iconified frame");
1067 /* Does this frame have a minibuffer, and is it the surrogate
1068 minibuffer for any other frame? */
1069 if (FRAME_HAS_MINIBUF_P (XFRAME (frame
)))
1073 for (frames
= Vframe_list
;
1075 frames
= XCONS (frames
)->cdr
)
1078 this = XCONS (frames
)->car
;
1080 if (! EQ (this, frame
)
1082 WINDOW_FRAME (XWINDOW
1083 (FRAME_MINIBUF_WINDOW (XFRAME (this))))))
1084 error ("Attempt to delete a surrogate minibuffer frame");
1088 minibuffer_selected
= EQ (minibuf_window
, selected_window
);
1090 /* Don't let the frame remain selected. */
1091 if (f
== selected_frame
)
1093 Lisp_Object tail
, frame1
;
1095 /* Look for another visible frame on the same terminal. */
1096 frame1
= next_frame (frame
, Qvisible
);
1098 /* If there is none, find *some* other frame. */
1099 if (NILP (frame1
) || EQ (frame1
, frame
))
1101 FOR_EACH_FRAME (tail
, frame1
)
1103 if (! EQ (frame
, frame1
))
1108 do_switch_frame (frame1
, Qnil
, 0);
1111 /* Don't allow minibuf_window to remain on a deleted frame. */
1112 if (EQ (f
->minibuffer_window
, minibuf_window
))
1114 Fset_window_buffer (selected_frame
->minibuffer_window
,
1115 XWINDOW (minibuf_window
)->buffer
);
1116 minibuf_window
= selected_frame
->minibuffer_window
;
1118 /* If the dying minibuffer window was selected,
1119 select the new one. */
1120 if (minibuffer_selected
)
1121 Fselect_window (minibuf_window
);
1124 /* Clear any X selections for this frame. */
1125 #ifdef HAVE_X_WINDOWS
1127 x_clear_frame_selections (f
);
1130 /* Mark all the windows that used to be on FRAME as deleted, and then
1131 remove the reference to them. */
1132 delete_all_subwindows (XWINDOW (f
->root_window
));
1133 f
->root_window
= Qnil
;
1135 Vframe_list
= Fdelq (frame
, Vframe_list
);
1136 FRAME_SET_VISIBLE (f
, 0);
1140 if (FRAME_CURRENT_GLYPHS (f
))
1141 free_frame_glyphs (f
, FRAME_CURRENT_GLYPHS (f
));
1142 if (FRAME_DESIRED_GLYPHS (f
))
1143 free_frame_glyphs (f
, FRAME_DESIRED_GLYPHS (f
));
1144 if (FRAME_TEMP_GLYPHS (f
))
1145 free_frame_glyphs (f
, FRAME_TEMP_GLYPHS (f
));
1146 if (FRAME_INSERT_COST (f
))
1147 free (FRAME_INSERT_COST (f
));
1148 if (FRAME_DELETEN_COST (f
))
1149 free (FRAME_DELETEN_COST (f
));
1150 if (FRAME_INSERTN_COST (f
))
1151 free (FRAME_INSERTN_COST (f
));
1152 if (FRAME_DELETE_COST (f
))
1153 free (FRAME_DELETE_COST (f
));
1155 /* Since some events are handled at the interrupt level, we may get
1156 an event for f at any time; if we zero out the frame's display
1157 now, then we may trip up the event-handling code. Instead, we'll
1158 promise that the display of the frame must be valid until we have
1159 called the window-system-dependent frame destruction routine. */
1161 /* I think this should be done with a hook. */
1162 #ifdef HAVE_WINDOW_SYSTEM
1163 if (FRAME_WINDOW_P (f
))
1164 x_destroy_window (f
);
1167 f
->output_data
.nothing
= 0;
1169 /* If we've deleted the last_nonminibuf_frame, then try to find
1171 if (f
== last_nonminibuf_frame
)
1175 last_nonminibuf_frame
= 0;
1177 for (frames
= Vframe_list
;
1179 frames
= XCONS (frames
)->cdr
)
1181 f
= XFRAME (XCONS (frames
)->car
);
1182 if (!FRAME_MINIBUF_ONLY_P (f
))
1184 last_nonminibuf_frame
= f
;
1190 /* If we've deleted this keyboard's default_minibuffer_frame, try to
1191 find another one. Prefer minibuffer-only frames, but also notice
1192 frames with other windows. */
1193 if (EQ (frame
, FRAME_KBOARD (f
)->Vdefault_minibuffer_frame
))
1197 /* The last frame we saw with a minibuffer, minibuffer-only or not. */
1198 Lisp_Object frame_with_minibuf
;
1199 /* Some frame we found on the same kboard, or nil if there are none. */
1200 Lisp_Object frame_on_same_kboard
;
1202 frame_on_same_kboard
= Qnil
;
1203 frame_with_minibuf
= Qnil
;
1205 for (frames
= Vframe_list
;
1207 frames
= XCONS (frames
)->cdr
)
1212 this = XCONS (frames
)->car
;
1217 /* Consider only frames on the same kboard
1218 and only those with minibuffers. */
1219 if (FRAME_KBOARD (f
) == FRAME_KBOARD (f1
)
1220 && FRAME_HAS_MINIBUF_P (f1
))
1222 frame_with_minibuf
= this;
1223 if (FRAME_MINIBUF_ONLY_P (f1
))
1227 if (FRAME_KBOARD (f
) == FRAME_KBOARD (f1
))
1228 frame_on_same_kboard
= this;
1231 if (!NILP (frame_on_same_kboard
))
1233 /* We know that there must be some frame with a minibuffer out
1234 there. If this were not true, all of the frames present
1235 would have to be minibufferless, which implies that at some
1236 point their minibuffer frames must have been deleted, but
1237 that is prohibited at the top; you can't delete surrogate
1238 minibuffer frames. */
1239 if (NILP (frame_with_minibuf
))
1242 FRAME_KBOARD (f
)->Vdefault_minibuffer_frame
= frame_with_minibuf
;
1245 /* No frames left on this kboard--say no minibuffer either. */
1246 FRAME_KBOARD (f
)->Vdefault_minibuffer_frame
= Qnil
;
1252 /* Return mouse position in character cell units. */
1254 DEFUN ("mouse-position", Fmouse_position
, Smouse_position
, 0, 0, 0,
1255 "Return a list (FRAME X . Y) giving the current mouse frame and position.\n\
1256 The position is given in character cells, where (0, 0) is the\n\
1257 upper-left corner.\n\
1258 If Emacs is running on a mouseless terminal or hasn't been programmed\n\
1259 to read the mouse position, it returns the selected frame for FRAME\n\
1260 and nil for X and Y.")
1264 Lisp_Object lispy_dummy
;
1265 enum scroll_bar_part party_dummy
;
1268 unsigned long long_dummy
;
1274 /* It's okay for the hook to refrain from storing anything. */
1275 if (mouse_position_hook
)
1276 (*mouse_position_hook
) (&f
, 0,
1277 &lispy_dummy
, &party_dummy
,
1284 pixel_to_glyph_coords (f
, col
, row
, &col
, &row
, NULL
, 1);
1289 XSETFRAME (lispy_dummy
, f
);
1290 return Fcons (lispy_dummy
, Fcons (x
, y
));
1293 DEFUN ("mouse-pixel-position", Fmouse_pixel_position
,
1294 Smouse_pixel_position
, 0, 0, 0,
1295 "Return a list (FRAME X . Y) giving the current mouse frame and position.\n\
1296 The position is given in pixel units, where (0, 0) is the\n\
1297 upper-left corner.\n\
1298 If Emacs is running on a mouseless terminal or hasn't been programmed\n\
1299 to read the mouse position, it returns the selected frame for FRAME\n\
1300 and nil for X and Y.")
1304 Lisp_Object lispy_dummy
;
1305 enum scroll_bar_part party_dummy
;
1308 unsigned long long_dummy
;
1314 /* It's okay for the hook to refrain from storing anything. */
1315 if (mouse_position_hook
)
1316 (*mouse_position_hook
) (&f
, 0,
1317 &lispy_dummy
, &party_dummy
,
1321 XSETFRAME (lispy_dummy
, f
);
1322 return Fcons (lispy_dummy
, Fcons (x
, y
));
1325 DEFUN ("set-mouse-position", Fset_mouse_position
, Sset_mouse_position
, 3, 3, 0,
1326 "Move the mouse pointer to the center of character cell (X,Y) in FRAME.\n\
1327 Note, this is a no-op for an X frame that is not visible.\n\
1328 If you have just created a frame, you must wait for it to become visible\n\
1329 before calling this function on it, like this.\n\
1330 (while (not (frame-visible-p frame)) (sleep-for .5))")
1332 Lisp_Object frame
, x
, y
;
1334 CHECK_LIVE_FRAME (frame
, 0);
1335 CHECK_NUMBER (x
, 2);
1336 CHECK_NUMBER (y
, 1);
1338 /* I think this should be done with a hook. */
1339 #ifdef HAVE_WINDOW_SYSTEM
1340 if (FRAME_WINDOW_P (XFRAME (frame
)))
1341 /* Warping the mouse will cause enternotify and focus events. */
1342 x_set_mouse_position (XFRAME (frame
), x
, y
);
1344 #if defined (MSDOS) && defined (HAVE_MOUSE)
1345 if (FRAME_MSDOS_P (XFRAME (frame
)))
1347 Fselect_frame (frame
, Qnil
);
1348 mouse_moveto (XINT (x
), XINT (y
));
1356 DEFUN ("set-mouse-pixel-position", Fset_mouse_pixel_position
,
1357 Sset_mouse_pixel_position
, 3, 3, 0,
1358 "Move the mouse pointer to pixel position (X,Y) in FRAME.\n\
1359 Note, this is a no-op for an X frame that is not visible.\n\
1360 If you have just created a frame, you must wait for it to become visible\n\
1361 before calling this function on it, like this.\n\
1362 (while (not (frame-visible-p frame)) (sleep-for .5))")
1364 Lisp_Object frame
, x
, y
;
1366 CHECK_LIVE_FRAME (frame
, 0);
1367 CHECK_NUMBER (x
, 2);
1368 CHECK_NUMBER (y
, 1);
1370 /* I think this should be done with a hook. */
1371 #ifdef HAVE_WINDOW_SYSTEM
1372 if (FRAME_WINDOW_P (XFRAME (frame
)))
1373 /* Warping the mouse will cause enternotify and focus events. */
1374 x_set_mouse_pixel_position (XFRAME (frame
), x
, y
);
1376 #if defined (MSDOS) && defined (HAVE_MOUSE)
1377 if (FRAME_MSDOS_P (XFRAME (frame
)))
1379 Fselect_frame (frame
, Qnil
);
1380 mouse_moveto (XINT (x
), XINT (y
));
1388 DEFUN ("make-frame-visible", Fmake_frame_visible
, Smake_frame_visible
,
1390 "Make the frame FRAME visible (assuming it is an X-window).\n\
1391 If omitted, FRAME defaults to the currently selected frame.")
1396 XSETFRAME (frame
, selected_frame
);
1398 CHECK_LIVE_FRAME (frame
, 0);
1400 /* I think this should be done with a hook. */
1401 #ifdef HAVE_WINDOW_SYSTEM
1402 if (FRAME_WINDOW_P (XFRAME (frame
)))
1404 FRAME_SAMPLE_VISIBILITY (XFRAME (frame
));
1405 x_make_frame_visible (XFRAME (frame
));
1409 /* Make menu bar update for the Buffers and Frams menus. */
1410 windows_or_buffers_changed
++;
1415 DEFUN ("make-frame-invisible", Fmake_frame_invisible
, Smake_frame_invisible
,
1417 "Make the frame FRAME invisible (assuming it is an X-window).\n\
1418 If omitted, FRAME defaults to the currently selected frame.\n\
1419 Normally you may not make FRAME invisible if all other frames are invisible,\n\
1420 but if the second optional argument FORCE is non-nil, you may do so.")
1422 Lisp_Object frame
, force
;
1425 XSETFRAME (frame
, selected_frame
);
1427 CHECK_LIVE_FRAME (frame
, 0);
1429 if (NILP (force
) && !other_visible_frames (XFRAME (frame
)))
1430 error ("Attempt to make invisible the sole visible or iconified frame");
1432 #if 0 /* This isn't logically necessary, and it can do GC. */
1433 /* Don't let the frame remain selected. */
1434 if (XFRAME (frame
) == selected_frame
)
1435 do_switch_frame (next_frame (frame
, Qt
), Qnil
, 0)
1438 /* Don't allow minibuf_window to remain on a deleted frame. */
1439 if (EQ (XFRAME (frame
)->minibuffer_window
, minibuf_window
))
1441 Fset_window_buffer (selected_frame
->minibuffer_window
,
1442 XWINDOW (minibuf_window
)->buffer
);
1443 minibuf_window
= selected_frame
->minibuffer_window
;
1446 /* I think this should be done with a hook. */
1447 #ifdef HAVE_WINDOW_SYSTEM
1448 if (FRAME_WINDOW_P (XFRAME (frame
)))
1449 x_make_frame_invisible (XFRAME (frame
));
1452 /* Make menu bar update for the Buffers and Frams menus. */
1453 windows_or_buffers_changed
++;
1458 DEFUN ("iconify-frame", Ficonify_frame
, Siconify_frame
,
1460 "Make the frame FRAME into an icon.\n\
1461 If omitted, FRAME defaults to the currently selected frame.")
1466 XSETFRAME (frame
, selected_frame
);
1468 CHECK_LIVE_FRAME (frame
, 0);
1470 #if 0 /* This isn't logically necessary, and it can do GC. */
1471 /* Don't let the frame remain selected. */
1472 if (XFRAME (frame
) == selected_frame
)
1473 Fhandle_switch_frame (next_frame (frame
, Qt
), Qnil
);
1476 /* Don't allow minibuf_window to remain on a deleted frame. */
1477 if (EQ (XFRAME (frame
)->minibuffer_window
, minibuf_window
))
1479 Fset_window_buffer (selected_frame
->minibuffer_window
,
1480 XWINDOW (minibuf_window
)->buffer
);
1481 minibuf_window
= selected_frame
->minibuffer_window
;
1484 /* I think this should be done with a hook. */
1485 #ifdef HAVE_WINDOW_SYSTEM
1486 if (FRAME_WINDOW_P (XFRAME (frame
)))
1487 x_iconify_frame (XFRAME (frame
));
1490 /* Make menu bar update for the Buffers and Frams menus. */
1491 windows_or_buffers_changed
++;
1496 DEFUN ("frame-visible-p", Fframe_visible_p
, Sframe_visible_p
,
1498 "Return t if FRAME is now \"visible\" (actually in use for display).\n\
1499 A frame that is not \"visible\" is not updated and, if it works through\n\
1500 a window system, it may not show at all.\n\
1501 Return the symbol `icon' if frame is visible only as an icon.")
1505 CHECK_LIVE_FRAME (frame
, 0);
1507 FRAME_SAMPLE_VISIBILITY (XFRAME (frame
));
1509 if (FRAME_VISIBLE_P (XFRAME (frame
)))
1511 if (FRAME_ICONIFIED_P (XFRAME (frame
)))
1516 DEFUN ("visible-frame-list", Fvisible_frame_list
, Svisible_frame_list
,
1518 "Return a list of all frames now \"visible\" (being updated).")
1521 Lisp_Object tail
, frame
;
1526 for (tail
= Vframe_list
; CONSP (tail
); tail
= XCONS (tail
)->cdr
)
1528 frame
= XCONS (tail
)->car
;
1529 if (!FRAMEP (frame
))
1532 if (FRAME_VISIBLE_P (f
))
1533 value
= Fcons (frame
, value
);
1539 DEFUN ("raise-frame", Fraise_frame
, Sraise_frame
, 0, 1, "",
1540 "Bring FRAME to the front, so it occludes any frames it overlaps.\n\
1541 If FRAME is invisible, make it visible.\n\
1542 If you don't specify a frame, the selected frame is used.\n\
1543 If Emacs is displaying on an ordinary terminal or some other device which\n\
1544 doesn't support multiple overlapping frames, this function does nothing.")
1549 XSETFRAME (frame
, selected_frame
);
1551 CHECK_LIVE_FRAME (frame
, 0);
1553 /* Do like the documentation says. */
1554 Fmake_frame_visible (frame
);
1556 if (frame_raise_lower_hook
)
1557 (*frame_raise_lower_hook
) (XFRAME (frame
), 1);
1562 /* Should we have a corresponding function called Flower_Power? */
1563 DEFUN ("lower-frame", Flower_frame
, Slower_frame
, 0, 1, "",
1564 "Send FRAME to the back, so it is occluded by any frames that overlap it.\n\
1565 If you don't specify a frame, the selected frame is used.\n\
1566 If Emacs is displaying on an ordinary terminal or some other device which\n\
1567 doesn't support multiple overlapping frames, this function does nothing.")
1572 XSETFRAME (frame
, selected_frame
);
1574 CHECK_LIVE_FRAME (frame
, 0);
1576 if (frame_raise_lower_hook
)
1577 (*frame_raise_lower_hook
) (XFRAME (frame
), 0);
1583 DEFUN ("redirect-frame-focus", Fredirect_frame_focus
, Sredirect_frame_focus
,
1585 "Arrange for keystrokes typed at FRAME to be sent to FOCUS-FRAME.\n\
1586 In other words, switch-frame events caused by events in FRAME will\n\
1587 request a switch to FOCUS-FRAME, and `last-event-frame' will be\n\
1588 FOCUS-FRAME after reading an event typed at FRAME.\n\
1590 If FOCUS-FRAME is omitted or nil, any existing redirection is\n\
1591 cancelled, and the frame again receives its own keystrokes.\n\
1593 Focus redirection is useful for temporarily redirecting keystrokes to\n\
1594 a surrogate minibuffer frame when a frame doesn't have its own\n\
1595 minibuffer window.\n\
1597 A frame's focus redirection can be changed by select-frame. If frame\n\
1598 FOO is selected, and then a different frame BAR is selected, any\n\
1599 frames redirecting their focus to FOO are shifted to redirect their\n\
1600 focus to BAR. This allows focus redirection to work properly when the\n\
1601 user switches from one frame to another using `select-window'.\n\
1603 This means that a frame whose focus is redirected to itself is treated\n\
1604 differently from a frame whose focus is redirected to nil; the former\n\
1605 is affected by select-frame, while the latter is not.\n\
1607 The redirection lasts until `redirect-frame-focus' is called to change it.")
1608 (frame
, focus_frame
)
1609 Lisp_Object frame
, focus_frame
;
1611 /* Note that we don't check for a live frame here. It's reasonable
1612 to redirect the focus of a frame you're about to delete, if you
1613 know what other frame should receive those keystrokes. */
1614 CHECK_FRAME (frame
, 0);
1616 if (! NILP (focus_frame
))
1617 CHECK_LIVE_FRAME (focus_frame
, 1);
1619 XFRAME (frame
)->focus_frame
= focus_frame
;
1621 if (frame_rehighlight_hook
)
1622 (*frame_rehighlight_hook
) (XFRAME (frame
));
1628 DEFUN ("frame-focus", Fframe_focus
, Sframe_focus
, 1, 1, 0,
1629 "Return the frame to which FRAME's keystrokes are currently being sent.\n\
1630 This returns nil if FRAME's focus is not redirected.\n\
1631 See `redirect-frame-focus'.")
1635 CHECK_LIVE_FRAME (frame
, 0);
1637 return FRAME_FOCUS_FRAME (XFRAME (frame
));
1642 /* Return the value of frame parameter PROP in frame FRAME. */
1645 get_frame_param (frame
, prop
)
1646 register struct frame
*frame
;
1649 register Lisp_Object tem
;
1651 tem
= Fassq (prop
, frame
->param_alist
);
1657 /* Return the buffer-predicate of the selected frame. */
1660 frame_buffer_predicate ()
1662 return selected_frame
->buffer_predicate
;
1665 /* Modify the alist in *ALISTPTR to associate PROP with VAL.
1666 If the alist already has an element for PROP, we change it. */
1669 store_in_alist (alistptr
, prop
, val
)
1670 Lisp_Object
*alistptr
, val
;
1673 register Lisp_Object tem
;
1675 tem
= Fassq (prop
, *alistptr
);
1677 *alistptr
= Fcons (Fcons (prop
, val
), *alistptr
);
1683 store_frame_param (f
, prop
, val
)
1685 Lisp_Object prop
, val
;
1687 register Lisp_Object tem
;
1689 tem
= Fassq (prop
, f
->param_alist
);
1691 f
->param_alist
= Fcons (Fcons (prop
, val
), f
->param_alist
);
1695 if (EQ (prop
, Qbuffer_predicate
))
1696 f
->buffer_predicate
= val
;
1698 if (! FRAME_WINDOW_P (f
))
1699 if (EQ (prop
, Qmenu_bar_lines
))
1700 set_menu_bar_lines (f
, val
, make_number (FRAME_MENU_BAR_LINES (f
)));
1702 if (EQ (prop
, Qminibuffer
) && WINDOWP (val
))
1704 if (! MINI_WINDOW_P (XWINDOW (val
)))
1705 error ("Surrogate minibuffer windows must be minibuffer windows.");
1707 if (FRAME_HAS_MINIBUF_P (f
) || FRAME_MINIBUF_ONLY_P (f
))
1708 error ("can't change the surrogate minibuffer of a frame with its own minibuffer");
1710 /* Install the chosen minibuffer window, with proper buffer. */
1711 f
->minibuffer_window
= val
;
1715 DEFUN ("frame-parameters", Fframe_parameters
, Sframe_parameters
, 0, 1, 0,
1716 "Return the parameters-alist of frame FRAME.\n\
1717 It is a list of elements of the form (PARM . VALUE), where PARM is a symbol.\n\
1718 The meaningful PARMs depend on the kind of frame.\n\
1719 If FRAME is omitted, return information on the currently selected frame.")
1727 if (EQ (frame
, Qnil
))
1731 CHECK_FRAME (frame
, 0);
1735 if (!FRAME_LIVE_P (f
))
1738 alist
= Fcopy_alist (f
->param_alist
);
1740 if (FRAME_MSDOS_P (f
))
1742 static char *colornames
[16] =
1744 "black", "blue", "green", "cyan", "red", "magenta", "brown",
1745 "lightgray", "darkgray", "lightblue", "lightgreen", "lightcyan",
1746 "lightred", "lightmagenta", "yellow", "white"
1748 store_in_alist (&alist
, intern ("foreground-color"),
1749 build_string (colornames
[FRAME_FOREGROUND_PIXEL (f
)]));
1750 store_in_alist (&alist
, intern ("background-color"),
1751 build_string (colornames
[FRAME_BACKGROUND_PIXEL (f
)]));
1753 store_in_alist (&alist
, intern ("font"), build_string ("default"));
1755 store_in_alist (&alist
, Qname
, f
->name
);
1756 height
= (FRAME_NEW_HEIGHT (f
) ? FRAME_NEW_HEIGHT (f
) : FRAME_HEIGHT (f
));
1757 store_in_alist (&alist
, Qheight
, make_number (height
));
1758 width
= (FRAME_NEW_WIDTH (f
) ? FRAME_NEW_WIDTH (f
) : FRAME_WIDTH (f
));
1759 store_in_alist (&alist
, Qwidth
, make_number (width
));
1760 store_in_alist (&alist
, Qmodeline
, (FRAME_WANTS_MODELINE_P (f
) ? Qt
: Qnil
));
1761 store_in_alist (&alist
, Qminibuffer
,
1762 (! FRAME_HAS_MINIBUF_P (f
) ? Qnil
1763 : FRAME_MINIBUF_ONLY_P (f
) ? Qonly
1764 : FRAME_MINIBUF_WINDOW (f
)));
1765 store_in_alist (&alist
, Qunsplittable
, (FRAME_NO_SPLIT_P (f
) ? Qt
: Qnil
));
1767 /* I think this should be done with a hook. */
1768 #ifdef HAVE_WINDOW_SYSTEM
1769 if (FRAME_WINDOW_P (f
))
1770 x_report_frame_params (f
, &alist
);
1774 /* This ought to be correct in f->param_alist for an X frame. */
1776 XSETFASTINT (lines
, FRAME_MENU_BAR_LINES (f
));
1777 store_in_alist (&alist
, Qmenu_bar_lines
, lines
);
1782 DEFUN ("modify-frame-parameters", Fmodify_frame_parameters
,
1783 Smodify_frame_parameters
, 2, 2, 0,
1784 "Modify the parameters of frame FRAME according to ALIST.\n\
1785 ALIST is an alist of parameters to change and their new values.\n\
1786 Each element of ALIST has the form (PARM . VALUE), where PARM is a symbol.\n\
1787 The meaningful PARMs depend on the kind of frame; undefined PARMs are ignored.")
1789 Lisp_Object frame
, alist
;
1792 register Lisp_Object tail
, elt
, prop
, val
;
1794 if (EQ (frame
, Qnil
))
1798 CHECK_LIVE_FRAME (frame
, 0);
1802 /* I think this should be done with a hook. */
1803 #ifdef HAVE_WINDOW_SYSTEM
1804 if (FRAME_WINDOW_P (f
))
1805 x_set_frame_parameters (f
, alist
);
1809 if (FRAME_MSDOS_P (f
))
1810 IT_set_frame_parameters (f
, alist
);
1813 for (tail
= alist
; !EQ (tail
, Qnil
); tail
= Fcdr (tail
))
1818 store_frame_param (f
, prop
, val
);
1824 DEFUN ("frame-char-height", Fframe_char_height
, Sframe_char_height
,
1826 "Height in pixels of a line in the font in frame FRAME.\n\
1827 If FRAME is omitted, the selected frame is used.\n\
1828 For a terminal frame, the value is always 1.")
1838 CHECK_FRAME (frame
, 0);
1842 #ifdef HAVE_WINDOW_SYSTEM
1843 if (FRAME_WINDOW_P (f
))
1844 return make_number (x_char_height (f
));
1847 return make_number (1);
1851 DEFUN ("frame-char-width", Fframe_char_width
, Sframe_char_width
,
1853 "Width in pixels of characters in the font in frame FRAME.\n\
1854 If FRAME is omitted, the selected frame is used.\n\
1855 The width is the same for all characters, because\n\
1856 currently Emacs supports only fixed-width fonts.\n\
1857 For a terminal screen, the value is always 1.")
1867 CHECK_FRAME (frame
, 0);
1871 #ifdef HAVE_WINDOW_SYSTEM
1872 if (FRAME_WINDOW_P (f
))
1873 return make_number (x_char_width (f
));
1876 return make_number (1);
1879 DEFUN ("frame-pixel-height", Fframe_pixel_height
,
1880 Sframe_pixel_height
, 0, 1, 0,
1881 "Return a FRAME's height in pixels.\n\
1882 For a terminal frame, the result really gives the height in characters.\n\
1883 If FRAME is omitted, the selected frame is used.")
1893 CHECK_FRAME (frame
, 0);
1897 #ifdef HAVE_WINDOW_SYSTEM
1898 if (FRAME_WINDOW_P (f
))
1899 return make_number (x_pixel_height (f
));
1902 return make_number (FRAME_HEIGHT (f
));
1905 DEFUN ("frame-pixel-width", Fframe_pixel_width
,
1906 Sframe_pixel_width
, 0, 1, 0,
1907 "Return FRAME's width in pixels.\n\
1908 For a terminal frame, the result really gives the width in characters.\n\
1909 If FRAME is omitted, the selected frame is used.")
1919 CHECK_FRAME (frame
, 0);
1923 #ifdef HAVE_WINDOW_SYSTEM
1924 if (FRAME_WINDOW_P (f
))
1925 return make_number (x_pixel_width (f
));
1928 return make_number (FRAME_WIDTH (f
));
1931 DEFUN ("set-frame-height", Fset_frame_height
, Sset_frame_height
, 2, 3, 0,
1932 "Specify that the frame FRAME has LINES lines.\n\
1933 Optional third arg non-nil means that redisplay should use LINES lines\n\
1934 but that the idea of the actual height of the frame should not be changed.")
1935 (frame
, lines
, pretend
)
1936 Lisp_Object frame
, lines
, pretend
;
1938 register struct frame
*f
;
1940 CHECK_NUMBER (lines
, 0);
1945 CHECK_LIVE_FRAME (frame
, 0);
1949 /* I think this should be done with a hook. */
1950 #ifdef HAVE_WINDOW_SYSTEM
1951 if (FRAME_WINDOW_P (f
))
1953 if (XINT (lines
) != f
->height
)
1954 x_set_window_size (f
, 1, f
->width
, XINT (lines
));
1958 change_frame_size (f
, XINT (lines
), 0, !NILP (pretend
), 0);
1962 DEFUN ("set-frame-width", Fset_frame_width
, Sset_frame_width
, 2, 3, 0,
1963 "Specify that the frame FRAME has COLS columns.\n\
1964 Optional third arg non-nil means that redisplay should use COLS columns\n\
1965 but that the idea of the actual width of the frame should not be changed.")
1966 (frame
, cols
, pretend
)
1967 Lisp_Object frame
, cols
, pretend
;
1969 register struct frame
*f
;
1970 CHECK_NUMBER (cols
, 0);
1975 CHECK_LIVE_FRAME (frame
, 0);
1979 /* I think this should be done with a hook. */
1980 #ifdef HAVE_WINDOW_SYSTEM
1981 if (FRAME_WINDOW_P (f
))
1983 if (XINT (cols
) != f
->width
)
1984 x_set_window_size (f
, 1, XINT (cols
), f
->height
);
1988 change_frame_size (f
, 0, XINT (cols
), !NILP (pretend
), 0);
1992 DEFUN ("set-frame-size", Fset_frame_size
, Sset_frame_size
, 3, 3, 0,
1993 "Sets size of FRAME to COLS by ROWS, measured in characters.")
1995 Lisp_Object frame
, cols
, rows
;
1997 register struct frame
*f
;
2000 CHECK_LIVE_FRAME (frame
, 0);
2001 CHECK_NUMBER (cols
, 2);
2002 CHECK_NUMBER (rows
, 1);
2005 /* I think this should be done with a hook. */
2006 #ifdef HAVE_WINDOW_SYSTEM
2007 if (FRAME_WINDOW_P (f
))
2009 if (XINT (rows
) != f
->height
|| XINT (cols
) != f
->width
2010 || FRAME_NEW_HEIGHT (f
) || FRAME_NEW_WIDTH (f
))
2011 x_set_window_size (f
, 1, XINT (cols
), XINT (rows
));
2015 change_frame_size (f
, XINT (rows
), XINT (cols
), 0, 0);
2020 DEFUN ("set-frame-position", Fset_frame_position
,
2021 Sset_frame_position
, 3, 3, 0,
2022 "Sets position of FRAME in pixels to XOFFSET by YOFFSET.\n\
2023 This is actually the position of the upper left corner of the frame.\n\
2024 Negative values for XOFFSET or YOFFSET are interpreted relative to\n\
2025 the rightmost or bottommost possible position (that stays within the screen).")
2026 (frame
, xoffset
, yoffset
)
2027 Lisp_Object frame
, xoffset
, yoffset
;
2029 register struct frame
*f
;
2032 CHECK_LIVE_FRAME (frame
, 0);
2033 CHECK_NUMBER (xoffset
, 1);
2034 CHECK_NUMBER (yoffset
, 2);
2037 /* I think this should be done with a hook. */
2038 #ifdef HAVE_WINDOW_SYSTEM
2039 if (FRAME_WINDOW_P (f
))
2040 x_set_offset (f
, XINT (xoffset
), XINT (yoffset
), 1);
2051 staticpro (&Vframe_list
);
2053 DEFVAR_LISP ("terminal-frame", &Vterminal_frame
,
2054 "The initial frame-object, which represents Emacs's stdout.");
2056 DEFVAR_LISP ("emacs-iconified", &Vemacs_iconified
,
2057 "Non-nil if all of emacs is iconified and frame updates are not needed.");
2058 Vemacs_iconified
= Qnil
;
2060 DEFVAR_KBOARD ("default-minibuffer-frame", Vdefault_minibuffer_frame
,
2061 "Minibufferless frames use this frame's minibuffer.\n\
2063 Emacs cannot create minibufferless frames unless this is set to an\n\
2064 appropriate surrogate.\n\
2066 Emacs consults this variable only when creating minibufferless\n\
2067 frames; once the frame is created, it sticks with its assigned\n\
2068 minibuffer, no matter what this variable is set to. This means that\n\
2069 this variable doesn't necessarily say anything meaningful about the\n\
2070 current set of frames, or where the minibuffer is currently being\n\
2073 defsubr (&Sactive_minibuffer_window
);
2075 defsubr (&Sframe_live_p
);
2076 defsubr (&Smake_terminal_frame
);
2077 defsubr (&Shandle_switch_frame
);
2078 defsubr (&Signore_event
);
2079 defsubr (&Sselect_frame
);
2080 defsubr (&Sselected_frame
);
2081 defsubr (&Swindow_frame
);
2082 defsubr (&Sframe_root_window
);
2083 defsubr (&Sframe_first_window
);
2084 defsubr (&Sframe_selected_window
);
2085 defsubr (&Sset_frame_selected_window
);
2086 defsubr (&Sframe_list
);
2087 defsubr (&Snext_frame
);
2088 defsubr (&Sprevious_frame
);
2089 defsubr (&Sdelete_frame
);
2090 defsubr (&Smouse_position
);
2091 defsubr (&Smouse_pixel_position
);
2092 defsubr (&Sset_mouse_position
);
2093 defsubr (&Sset_mouse_pixel_position
);
2095 defsubr (&Sframe_configuration
);
2096 defsubr (&Srestore_frame_configuration
);
2098 defsubr (&Smake_frame_visible
);
2099 defsubr (&Smake_frame_invisible
);
2100 defsubr (&Siconify_frame
);
2101 defsubr (&Sframe_visible_p
);
2102 defsubr (&Svisible_frame_list
);
2103 defsubr (&Sraise_frame
);
2104 defsubr (&Slower_frame
);
2105 defsubr (&Sredirect_frame_focus
);
2106 defsubr (&Sframe_focus
);
2107 defsubr (&Sframe_parameters
);
2108 defsubr (&Smodify_frame_parameters
);
2109 defsubr (&Sframe_char_height
);
2110 defsubr (&Sframe_char_width
);
2111 defsubr (&Sframe_pixel_height
);
2112 defsubr (&Sframe_pixel_width
);
2113 defsubr (&Sset_frame_height
);
2114 defsubr (&Sset_frame_width
);
2115 defsubr (&Sset_frame_size
);
2116 defsubr (&Sset_frame_position
);
2121 initial_define_lispy_key (global_map
, "switch-frame", "handle-switch-frame");
2122 initial_define_lispy_key (global_map
, "delete-frame", "handle-delete-frame");
2123 initial_define_lispy_key (global_map
, "iconify-frame", "ignore-event");
2124 initial_define_lispy_key (global_map
, "make-frame-visible", "ignore-event");