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, 675 Mass Ave, Cambridge, MA 02139, USA. */
25 #include "termhooks.h"
35 /* These help us bind and responding to switch-frame events. */
39 Lisp_Object Vemacs_iconified
;
40 Lisp_Object Vframe_list
;
41 Lisp_Object Vterminal_frame
;
42 Lisp_Object Vdefault_minibuffer_frame
;
43 Lisp_Object Vdefault_frame_alist
;
45 /* Evaluate this expression to rebuild the section of syms_of_frame
46 that initializes and staticpros the symbols declared below. Note
47 that Emacs 18 has a bug that keeps C-x C-e from being able to
48 evaluate this expression.
51 ;; Accumulate a list of the symbols we want to initialize from the
52 ;; declarations at the top of the file.
53 (goto-char (point-min))
54 (search-forward "/\*&&& symbols declared here &&&*\/\n")
56 (while (looking-at "Lisp_Object \\(Q[a-z_]+\\)")
58 (cons (buffer-substring (match-beginning 1) (match-end 1))
61 (setq symbol-list (nreverse symbol-list))
62 ;; Delete the section of syms_of_... where we initialize the symbols.
63 (search-forward "\n /\*&&& init symbols here &&&*\/\n")
64 (let ((start (point)))
65 (while (looking-at "^ Q")
67 (kill-region start (point)))
68 ;; Write a new symbol initialization section.
70 (insert (format " %s = intern (\"" (car symbol-list)))
71 (let ((start (point)))
72 (insert (substring (car symbol-list) 1))
73 (subst-char-in-region start (point) ?_ ?-))
74 (insert (format "\");\n staticpro (&%s);\n" (car symbol-list)))
75 (setq symbol-list (cdr symbol-list)))))
78 /*&&& symbols declared here &&&*/
80 Lisp_Object Qframe_live_p
;
83 Lisp_Object Qminibuffer
;
84 Lisp_Object Qmodeline
;
87 Lisp_Object Qunsplittable
;
88 Lisp_Object Qmenu_bar_lines
;
92 Lisp_Object Qbuffer_predicate
;
94 extern Lisp_Object Vminibuffer_list
;
95 extern Lisp_Object
get_minibuffer ();
96 extern Lisp_Object
Fhandle_switch_frame ();
97 extern Lisp_Object
Fredirect_frame_focus ();
99 DEFUN ("framep", Fframep
, Sframep
, 1, 1, 0,
100 "Return non-nil if OBJECT is a frame.\n\
101 Value is t for a termcap frame (a character-only terminal),\n\
102 `x' for an Emacs frame that is really an X window,\n\
103 `pc' for a direct-write MS-DOS frame.\n\
104 See also `frame-live-p'.")
108 if (!FRAMEP (object
))
110 switch (XFRAME (object
)->output_method
)
114 case output_x_window
:
116 /* The `pc' case is in the Fframep below. */
122 DEFUN ("frame-live-p", Fframe_live_p
, Sframe_live_p
, 1, 1, 0,
123 "Return non-nil if OBJECT is a frame which has not been deleted.\n\
124 Value is nil if OBJECT is not a live frame. If object is a live\n\
125 frame, the return value indicates what sort of output device it is\n\
126 displayed on. Value is t for a termcap frame (a character-only\n\
127 terminal), `x' for an Emacs frame being displayed in an X window.")
131 return ((FRAMEP (object
)
132 && FRAME_LIVE_P (XFRAME (object
)))
142 register struct frame
*f
;
143 register Lisp_Object root_window
;
144 register Lisp_Object mini_window
;
145 register struct Lisp_Vector
*vec
;
148 vec
= allocate_vectorlike ((EMACS_INT
) VECSIZE (struct frame
));
149 for (i
= 0; i
< VECSIZE (struct frame
); i
++)
150 XSETFASTINT (vec
->contents
[i
], 0);
151 vec
->size
= VECSIZE (struct frame
);
152 f
= (struct frame
*)vec
;
153 XSETFRAME (frame
, f
);
157 f
->current_glyphs
= 0;
158 f
->desired_glyphs
= 0;
160 f
->async_visible
= 0;
161 f
->display
.nothing
= 0;
163 f
->async_iconified
= 0;
164 f
->wants_modeline
= 1;
169 f
->has_minibuffer
= mini_p
;
170 f
->focus_frame
= Qnil
;
171 f
->explicit_name
= 0;
172 f
->can_have_scroll_bars
= 0;
173 f
->has_vertical_scroll_bars
= 0;
174 f
->param_alist
= Qnil
;
175 f
->scroll_bars
= Qnil
;
176 f
->condemned_scroll_bars
= Qnil
;
177 f
->face_alist
= Qnil
;
178 f
->menu_bar_items
= Qnil
;
179 f
->menu_bar_vector
= Qnil
;
180 f
->menu_bar_items_used
= 0;
181 f
->buffer_predicate
= Qnil
;
183 f
->kboard
= initial_kboard
;
187 root_window
= make_window ();
190 mini_window
= make_window ();
191 XWINDOW (root_window
)->next
= mini_window
;
192 XWINDOW (mini_window
)->prev
= root_window
;
193 XWINDOW (mini_window
)->mini_p
= Qt
;
194 XWINDOW (mini_window
)->frame
= frame
;
195 f
->minibuffer_window
= mini_window
;
200 XWINDOW (root_window
)->next
= Qnil
;
201 f
->minibuffer_window
= Qnil
;
204 XWINDOW (root_window
)->frame
= frame
;
207 just so that there is "something there."
208 Correct size will be set up later with change_frame_size. */
213 XSETFASTINT (XWINDOW (root_window
)->width
, 10);
214 XSETFASTINT (XWINDOW (root_window
)->height
, (mini_p
? 9 : 10));
218 XSETFASTINT (XWINDOW (mini_window
)->width
, 10);
219 XSETFASTINT (XWINDOW (mini_window
)->top
, 9);
220 XSETFASTINT (XWINDOW (mini_window
)->height
, 1);
223 /* Choose a buffer for the frame's root window. */
227 XWINDOW (root_window
)->buffer
= Qt
;
228 buf
= Fcurrent_buffer ();
229 /* If buf is a 'hidden' buffer (i.e. one whose name starts with
230 a space), try to find another one. */
231 if (XSTRING (Fbuffer_name (buf
))->data
[0] == ' ')
232 buf
= Fother_buffer (buf
, Qnil
);
233 Fset_window_buffer (root_window
, buf
);
238 XWINDOW (mini_window
)->buffer
= Qt
;
239 Fset_window_buffer (mini_window
,
240 (NILP (Vminibuffer_list
)
242 : Fcar (Vminibuffer_list
)));
245 f
->root_window
= root_window
;
246 f
->selected_window
= root_window
;
247 /* Make sure this window seems more recently used than
248 a newly-created, never-selected window. */
249 XSETFASTINT (XWINDOW (f
->selected_window
)->use_time
, ++window_select_count
);
254 /* Make a frame using a separate minibuffer window on another frame.
255 MINI_WINDOW is the minibuffer window to use. nil means use the
256 default (the global minibuffer). */
259 make_frame_without_minibuffer (mini_window
, kb
)
260 register Lisp_Object mini_window
;
263 register struct frame
*f
;
265 /* Choose the minibuffer window to use. */
266 if (NILP (mini_window
))
268 if (!FRAMEP (Vdefault_minibuffer_frame
))
269 error ("default-minibuffer-frame must be set when creating minibufferless frames");
270 if (! FRAME_LIVE_P (XFRAME (Vdefault_minibuffer_frame
)))
271 error ("default-minibuffer-frame must be a live frame");
272 mini_window
= XFRAME (Vdefault_minibuffer_frame
)->minibuffer_window
;
276 CHECK_LIVE_WINDOW (mini_window
, 0);
280 if (XFRAME (XWINDOW (mini_window
)->frame
)->kboard
!= kb
)
281 error ("frame and minibuffer must be on the same display");
284 /* Make a frame containing just a root window. */
287 /* Install the chosen minibuffer window, with proper buffer. */
288 f
->minibuffer_window
= mini_window
;
289 Fset_window_buffer (mini_window
,
290 (NILP (Vminibuffer_list
)
292 : Fcar (Vminibuffer_list
)));
296 /* Make a frame containing only a minibuffer window. */
299 make_minibuffer_frame ()
301 /* First make a frame containing just a root window, no minibuffer. */
303 register struct frame
*f
= make_frame (0);
304 register Lisp_Object mini_window
;
305 register Lisp_Object frame
;
307 XSETFRAME (frame
, f
);
312 f
->wants_modeline
= 0;
313 f
->has_minibuffer
= 1;
315 /* Now label the root window as also being the minibuffer.
316 Avoid infinite looping on the window chain by marking next pointer
319 mini_window
= f
->minibuffer_window
= f
->root_window
;
320 XWINDOW (mini_window
)->mini_p
= Qt
;
321 XWINDOW (mini_window
)->next
= Qnil
;
322 XWINDOW (mini_window
)->prev
= Qnil
;
323 XWINDOW (mini_window
)->frame
= frame
;
325 /* Put the proper buffer in that window. */
327 Fset_window_buffer (mini_window
,
328 (NILP (Vminibuffer_list
)
330 : Fcar (Vminibuffer_list
)));
334 /* Construct a frame that refers to the terminal (stdin and stdout). */
336 static int terminal_frame_count
;
339 make_terminal_frame ()
341 register struct frame
*f
;
348 initial_kboard
= (KBOARD
*) xmalloc (sizeof (KBOARD
));
349 init_kboard (initial_kboard
);
350 initial_kboard
->next_kboard
= all_kboards
;
351 all_kboards
= initial_kboard
;
355 /* The first call must initialize Vframe_list. */
356 if (! (NILP (Vframe_list
) || CONSP (Vframe_list
)))
361 XSETFRAME (frame
, f
);
362 Vframe_list
= Fcons (frame
, Vframe_list
);
364 terminal_frame_count
++;
365 if (terminal_frame_count
== 1)
367 f
->name
= build_string ("Emacs");
371 sprintf (name
, "Emacs-%d", terminal_frame_count
);
372 f
->name
= build_string (name
);
375 f
->visible
= 1; /* FRAME_SET_VISIBLE wd set frame_garbaged. */
376 f
->async_visible
= 1; /* Don't let visible be cleared later. */
377 f
->display
.nothing
= 1; /* Nonzero means frame isn't deleted. */
381 DEFUN ("make-terminal-frame", Fmake_terminal_frame
, Smake_terminal_frame
,
382 1, 1, 0, "Create an additional terminal frame.\n\
383 You can create multiple frames on a text-only terminal in this way.\n\
384 Only the selected terminal frame is actually displayed.\n\
385 This function takes one argument, an alist specifying frame parameters.\n\
386 In practice, generally you don't need to specify any parameters.\n\
387 Note that changing the size of one terminal frame automatically affects all.")
394 if (selected_frame
->output_method
!= output_termcap
)
395 error ("Not using an ASCII terminal now; cannot make a new ASCII frame");
397 f
= make_terminal_frame ();
398 change_frame_size (f
, FRAME_HEIGHT (selected_frame
),
399 FRAME_WIDTH (selected_frame
), 0, 0);
400 remake_frame_glyphs (f
);
402 XSETFRAME (frame
, f
);
403 Fmodify_frame_parameters (frame
, parms
);
408 do_switch_frame (frame
, no_enter
, track
)
409 Lisp_Object frame
, no_enter
;
412 /* If FRAME is a switch-frame event, extract the frame we should
415 && EQ (XCONS (frame
)->car
, Qswitch_frame
)
416 && CONSP (XCONS (frame
)->cdr
))
417 frame
= XCONS (XCONS (frame
)->cdr
)->car
;
419 /* This used to say CHECK_LIVE_FRAME, but apparently it's possible for
420 a switch-frame event to arrive after a frame is no longer live,
421 especially when deleting the initial frame during startup. */
422 CHECK_FRAME (frame
, 0);
423 if (! FRAME_LIVE_P (XFRAME (frame
)))
426 if (selected_frame
== XFRAME (frame
))
429 /* This is too greedy; it causes inappropriate focus redirection
430 that's hard to get rid of. */
432 /* If a frame's focus has been redirected toward the currently
433 selected frame, we should change the redirection to point to the
434 newly selected frame. This means that if the focus is redirected
435 from a minibufferless frame to a surrogate minibuffer frame, we
436 can use `other-window' to switch between all the frames using
437 that minibuffer frame, and the focus redirection will follow us
443 for (tail
= Vframe_list
; CONSP (tail
); tail
= XCONS (tail
)->cdr
)
447 if (!FRAMEP (XCONS (tail
)->car
))
450 focus
= FRAME_FOCUS_FRAME (XFRAME (XCONS (tail
)->car
));
452 if (FRAMEP (focus
) && XFRAME (focus
) == selected_frame
)
453 Fredirect_frame_focus (XCONS (tail
)->car
, frame
);
457 /* Instead, apply it only to the frame we're pointing to. */
458 #ifdef HAVE_X_WINDOWS
459 if (track
&& FRAME_X_P (XFRAME (frame
)))
461 Lisp_Object focus
, xfocus
;
463 xfocus
= x_get_focus_frame (XFRAME (frame
));
466 focus
= FRAME_FOCUS_FRAME (XFRAME (xfocus
));
467 if (FRAMEP (focus
) && XFRAME (focus
) == selected_frame
)
468 Fredirect_frame_focus (xfocus
, frame
);
471 #endif /* HAVE_X_WINDOWS */
474 if (FRAME_TERMCAP_P (XFRAME (frame
)))
476 /* Since frames on an ASCII terminal share the same display area,
477 switching means we must redisplay the whole thing. */
478 windows_or_buffers_changed
++;
479 SET_FRAME_GARBAGED (XFRAME (frame
));
480 XSETFRAME (Vterminal_frame
, frame
);
483 selected_frame
= XFRAME (frame
);
484 if (! FRAME_MINIBUF_ONLY_P (selected_frame
))
485 last_nonminibuf_frame
= selected_frame
;
487 Fselect_window (XFRAME (frame
)->selected_window
);
488 choose_minibuf_frame ();
490 /* We want to make sure that the next event generates a frame-switch
491 event to the appropriate frame. This seems kludgy to me, but
492 before you take it out, make sure that evaluating something like
493 (select-window (frame-root-window (new-frame))) doesn't end up
494 with your typing being interpreted in the new frame instead of
495 the one you're actually typing in. */
496 internal_last_event_frame
= Qnil
;
501 DEFUN ("select-frame", Fselect_frame
, Sselect_frame
, 1, 2, "e",
502 "Select the frame FRAME.\n\
503 Subsequent editing commands apply to its selected window.\n\
504 The selection of FRAME lasts until the next time the user does\n\
505 something to select a different frame, or until the next time this\n\
506 function is called.")
508 Lisp_Object frame
, no_enter
;
510 return do_switch_frame (frame
, no_enter
, 1);
514 DEFUN ("handle-switch-frame", Fhandle_switch_frame
, Shandle_switch_frame
, 1, 2, "e",
515 "Handle a switch-frame event EVENT.\n\
516 Switch-frame events are usually bound to this function.\n\
517 A switch-frame event tells Emacs that the window manager has requested\n\
518 that the user's events be directed to the frame mentioned in the event.\n\
519 This function selects the selected window of the frame of EVENT.\n\
521 If EVENT is frame object, handle it as if it were a switch-frame event\n\
524 Lisp_Object frame
, no_enter
;
526 return do_switch_frame (frame
, no_enter
, 0);
530 DEFUN ("selected-frame", Fselected_frame
, Sselected_frame
, 0, 0, 0,
531 "Return the frame that is now selected.")
535 XSETFRAME (tem
, selected_frame
);
539 DEFUN ("window-frame", Fwindow_frame
, Swindow_frame
, 1, 1, 0,
540 "Return the frame object that window WINDOW is on.")
544 CHECK_LIVE_WINDOW (window
, 0);
545 return XWINDOW (window
)->frame
;
548 DEFUN ("frame-first-window", Fframe_first_window
, Sframe_first_window
, 0, 1, 0,
549 "Returns the topmost, leftmost window of FRAME.\n\
550 If omitted, FRAME defaults to the currently selected frame.")
557 w
= selected_frame
->root_window
;
560 CHECK_LIVE_FRAME (frame
, 0);
561 w
= XFRAME (frame
)->root_window
;
563 while (NILP (XWINDOW (w
)->buffer
))
565 if (! NILP (XWINDOW (w
)->hchild
))
566 w
= XWINDOW (w
)->hchild
;
567 else if (! NILP (XWINDOW (w
)->vchild
))
568 w
= XWINDOW (w
)->vchild
;
575 DEFUN ("active-minibuffer-window", Factive_minibuffer_window
,
576 Sactive_minibuffer_window
, 0, 0, 0,
577 "Return the currently active minibuffer window, or nil if none.")
580 return minibuf_level
? minibuf_window
: Qnil
;
583 DEFUN ("frame-root-window", Fframe_root_window
, Sframe_root_window
, 0, 1, 0,
584 "Returns the root-window of FRAME.\n\
585 If omitted, FRAME defaults to the currently selected frame.")
590 XSETFRAME (frame
, selected_frame
);
592 CHECK_LIVE_FRAME (frame
, 0);
594 return XFRAME (frame
)->root_window
;
597 DEFUN ("frame-selected-window", Fframe_selected_window
,
598 Sframe_selected_window
, 0, 1, 0,
599 "Return the selected window of frame object FRAME.\n\
600 If omitted, FRAME defaults to the currently selected frame.")
605 XSETFRAME (frame
, selected_frame
);
607 CHECK_LIVE_FRAME (frame
, 0);
609 return XFRAME (frame
)->selected_window
;
612 DEFUN ("set-frame-selected-window", Fset_frame_selected_window
,
613 Sset_frame_selected_window
, 2, 2, 0,
614 "Set the selected window of frame object FRAME to WINDOW.\n\
615 If FRAME is nil, the selected frame is used.\n\
616 If FRAME is the selected frame, this makes WINDOW the selected window.")
618 Lisp_Object frame
, window
;
621 XSETFRAME (frame
, selected_frame
);
623 CHECK_LIVE_FRAME (frame
, 0);
625 CHECK_LIVE_WINDOW (window
, 1);
627 if (! EQ (frame
, WINDOW_FRAME (XWINDOW (window
))))
628 error ("In `set-frame-selected-window', WINDOW is not on FRAME");
630 if (XFRAME (frame
) == selected_frame
)
631 return Fselect_window (window
);
633 return XFRAME (frame
)->selected_window
= window
;
636 DEFUN ("frame-list", Fframe_list
, Sframe_list
,
638 "Return a list of all frames.")
641 return Fcopy_sequence (Vframe_list
);
644 /* Return the next frame in the frame list after FRAME.
645 If MINIBUF is nil, exclude minibuffer-only frames.
646 If MINIBUF is a window, include only its own frame
647 and any frame now using that window as the minibuffer.
648 If MINIBUF is `visible', include all visible frames.
649 If MINIBUF is 0, include all visible and iconified frames.
650 Otherwise, include all frames. */
653 next_frame (frame
, minibuf
)
660 /* There must always be at least one frame in Vframe_list. */
661 if (! CONSP (Vframe_list
))
664 /* If this frame is dead, it won't be in Vframe_list, and we'll loop
665 forever. Forestall that. */
666 CHECK_LIVE_FRAME (frame
, 0);
669 for (tail
= Vframe_list
; CONSP (tail
); tail
= XCONS (tail
)->cdr
)
673 f
= XCONS (tail
)->car
;
676 /* Decide whether this frame is eligible to be returned. */
678 /* If we've looped all the way around without finding any
679 eligible frames, return the original frame. */
683 /* Let minibuf decide if this frame is acceptable. */
686 if (! FRAME_MINIBUF_ONLY_P (XFRAME (f
)))
689 else if (EQ (minibuf
, Qvisible
))
691 FRAME_SAMPLE_VISIBILITY (XFRAME (f
));
692 if (FRAME_VISIBLE_P (XFRAME (f
)))
695 else if (XFASTINT (minibuf
) == 0)
697 FRAME_SAMPLE_VISIBILITY (XFRAME (f
));
698 if (FRAME_VISIBLE_P (XFRAME (f
))
699 || FRAME_ICONIFIED_P (XFRAME (f
)))
702 else if (WINDOWP (minibuf
))
704 if (EQ (FRAME_MINIBUF_WINDOW (XFRAME (f
)), minibuf
)
705 /* Check that F either is, or has forwarded its focus to,
707 && (EQ (WINDOW_FRAME (XWINDOW (minibuf
)), f
)
708 || EQ (WINDOW_FRAME (XWINDOW (minibuf
)),
709 FRAME_FOCUS_FRAME (XFRAME (f
)))))
721 /* Return the previous frame in the frame list before FRAME.
722 If MINIBUF is nil, exclude minibuffer-only frames.
723 If MINIBUF is a window, include only its own frame
724 and any frame now using that window as the minibuffer.
725 If MINIBUF is `visible', include all visible frames.
726 If MINIBUF is 0, include all visible and iconified frames.
727 Otherwise, include all frames. */
730 prev_frame (frame
, minibuf
)
737 /* There must always be at least one frame in Vframe_list. */
738 if (! CONSP (Vframe_list
))
742 for (tail
= Vframe_list
; CONSP (tail
); tail
= XCONS (tail
)->cdr
)
746 f
= XCONS (tail
)->car
;
750 if (EQ (frame
, f
) && !NILP (prev
))
753 /* Decide whether this frame is eligible to be returned,
754 according to minibuf. */
757 if (! FRAME_MINIBUF_ONLY_P (XFRAME (f
)))
760 else if (WINDOWP (minibuf
))
762 if (EQ (FRAME_MINIBUF_WINDOW (XFRAME (f
)), minibuf
)
763 /* Check that F either is, or has forwarded its focus to,
765 && (EQ (WINDOW_FRAME (XWINDOW (minibuf
)), f
)
766 || EQ (WINDOW_FRAME (XWINDOW (minibuf
)),
767 FRAME_FOCUS_FRAME (XFRAME (f
)))))
770 else if (EQ (minibuf
, Qvisible
))
772 FRAME_SAMPLE_VISIBILITY (XFRAME (f
));
773 if (FRAME_VISIBLE_P (XFRAME (f
)))
776 else if (XFASTINT (minibuf
) == 0)
778 FRAME_SAMPLE_VISIBILITY (XFRAME (f
));
779 if (FRAME_VISIBLE_P (XFRAME (f
))
780 || FRAME_ICONIFIED_P (XFRAME (f
)))
787 /* We've scanned the entire list. */
789 /* We went through the whole frame list without finding a single
790 acceptable frame. Return the original frame. */
793 /* There were no acceptable frames in the list before FRAME; otherwise,
794 we would have returned directly from the loop. Since PREV is the last
795 acceptable frame in the list, return it. */
800 DEFUN ("next-frame", Fnext_frame
, Snext_frame
, 0, 2, 0,
801 "Return the next frame in the frame list after FRAME.\n\
802 By default, skip minibuffer-only frames.\n\
803 If omitted, FRAME defaults to the selected frame.\n\
804 If optional argument MINIFRAME is nil, exclude minibuffer-only frames.\n\
805 If MINIBUF is a window, include only its own frame\n\
806 and any frame now using that window as the minibuffer.\n\
807 If MINIFRAME is `visible', include all visible frames.\n\
808 If MINIBUF is 0, include all visible and iconified frames.\n\
809 Otherwise, include all frames.")
811 Lisp_Object frame
, miniframe
;
816 XSETFRAME (frame
, selected_frame
);
818 CHECK_LIVE_FRAME (frame
, 0);
820 return next_frame (frame
, miniframe
);
823 DEFUN ("previous-frame", Fprevious_frame
, Sprevious_frame
, 0, 2, 0,
824 "Return the previous frame in the frame list before FRAME.\n\
825 By default, skip minibuffer-only frames.\n\
826 If omitted, FRAME defaults to the selected frame.\n\
827 If optional argument MINIFRAME is nil, exclude minibuffer-only frames.\n\
828 If MINIBUF is a window, include only its own frame\n\
829 and any frame now using that window as the minibuffer.\n\
830 If MINIFRAME is `visible', include all visible frames.\n\
831 If MINIBUF is 0, include all visible and iconified frames.\n\
832 Otherwise, include all frames.")
834 Lisp_Object frame
, miniframe
;
839 XSETFRAME (frame
, selected_frame
);
841 CHECK_LIVE_FRAME (frame
, 0);
843 return prev_frame (frame
, miniframe
);
846 /* Return 1 if it is ok to delete frame F;
847 0 if all frames aside from F are invisible.
848 (Exception: if F is the terminal frame, and we are using X, return 1.) */
851 other_visible_frames (f
)
854 /* We know the selected frame is visible,
855 so if F is some other frame, it can't be the sole visible one. */
856 if (f
== selected_frame
)
861 for (frames
= Vframe_list
;
863 frames
= XCONS (frames
)->cdr
)
867 this = XCONS (frames
)->car
;
868 /* Verify that the frame's window still exists
869 and we can still talk to it. And note any recent change
871 #ifdef HAVE_X_WINDOWS
872 if (FRAME_X_P (XFRAME (this)))
874 x_sync (XFRAME (this));
875 FRAME_SAMPLE_VISIBILITY (XFRAME (this));
879 if (FRAME_VISIBLE_P (XFRAME (this))
880 || FRAME_ICONIFIED_P (XFRAME (this))
881 /* Allow deleting the terminal frame when at least
882 one X frame exists! */
883 || (FRAME_X_P (XFRAME (this)) && !FRAME_X_P (f
)))
891 DEFUN ("delete-frame", Fdelete_frame
, Sdelete_frame
, 0, 2, "",
892 "Delete FRAME, permanently eliminating it from use.\n\
893 If omitted, FRAME defaults to the selected frame.\n\
894 A frame may not be deleted if its minibuffer is used by other frames.\n\
895 Normally, you may not delete a frame if all other frames are invisible,\n\
896 but if the second optional argument FORCE is non-nil, you may do so.")
898 Lisp_Object frame
, force
;
902 if (EQ (frame
, Qnil
))
905 XSETFRAME (frame
, f
);
909 CHECK_FRAME (frame
, 0);
913 if (! FRAME_LIVE_P (f
))
916 if (NILP (force
) && !other_visible_frames (f
))
917 error ("Attempt to delete the sole visible or iconified frame");
919 /* Does this frame have a minibuffer, and is it the surrogate
920 minibuffer for any other frame? */
921 if (FRAME_HAS_MINIBUF_P (XFRAME (frame
)))
925 for (frames
= Vframe_list
;
927 frames
= XCONS (frames
)->cdr
)
930 this = XCONS (frames
)->car
;
932 if (! EQ (this, frame
)
934 WINDOW_FRAME (XWINDOW
935 (FRAME_MINIBUF_WINDOW (XFRAME (this))))))
936 error ("Attempt to delete a surrogate minibuffer frame");
940 /* Don't let the frame remain selected. */
941 if (f
== selected_frame
)
942 Fhandle_switch_frame (next_frame (frame
, Qt
), Qnil
);
944 /* Don't allow minibuf_window to remain on a deleted frame. */
945 if (EQ (f
->minibuffer_window
, minibuf_window
))
947 Fset_window_buffer (selected_frame
->minibuffer_window
,
948 XWINDOW (minibuf_window
)->buffer
);
949 minibuf_window
= selected_frame
->minibuffer_window
;
952 /* Clear any X selections for this frame. */
953 #ifdef HAVE_X_WINDOWS
955 x_clear_frame_selections (f
);
958 /* Mark all the windows that used to be on FRAME as deleted, and then
959 remove the reference to them. */
960 delete_all_subwindows (XWINDOW (f
->root_window
));
961 f
->root_window
= Qnil
;
963 Vframe_list
= Fdelq (frame
, Vframe_list
);
964 FRAME_SET_VISIBLE (f
, 0);
968 if (FRAME_CURRENT_GLYPHS (f
))
969 free_frame_glyphs (f
, FRAME_CURRENT_GLYPHS (f
));
970 if (FRAME_DESIRED_GLYPHS (f
))
971 free_frame_glyphs (f
, FRAME_DESIRED_GLYPHS (f
));
972 if (FRAME_TEMP_GLYPHS (f
))
973 free_frame_glyphs (f
, FRAME_TEMP_GLYPHS (f
));
974 if (FRAME_INSERT_COST (f
))
975 free (FRAME_INSERT_COST (f
));
976 if (FRAME_DELETEN_COST (f
))
977 free (FRAME_DELETEN_COST (f
));
978 if (FRAME_INSERTN_COST (f
))
979 free (FRAME_INSERTN_COST (f
));
980 if (FRAME_DELETE_COST (f
))
981 free (FRAME_DELETE_COST (f
));
983 /* Since some events are handled at the interrupt level, we may get
984 an event for f at any time; if we zero out the frame's display
985 now, then we may trip up the event-handling code. Instead, we'll
986 promise that the display of the frame must be valid until we have
987 called the window-system-dependent frame destruction routine. */
989 /* I think this should be done with a hook. */
990 #ifdef HAVE_X_WINDOWS
992 x_destroy_window (f
);
995 f
->display
.nothing
= 0;
997 /* If we've deleted the last_nonminibuf_frame, then try to find
999 if (f
== last_nonminibuf_frame
)
1003 last_nonminibuf_frame
= 0;
1005 for (frames
= Vframe_list
;
1007 frames
= XCONS (frames
)->cdr
)
1009 f
= XFRAME (XCONS (frames
)->car
);
1010 if (!FRAME_MINIBUF_ONLY_P (f
))
1012 last_nonminibuf_frame
= f
;
1018 /* If we've deleted Vdefault_minibuffer_frame, try to find another
1019 one. Prefer minibuffer-only frames, but also notice frames
1020 with other windows. */
1021 if (EQ (frame
, Vdefault_minibuffer_frame
))
1025 /* The last frame we saw with a minibuffer, minibuffer-only or not. */
1026 Lisp_Object frame_with_minibuf
;
1028 frame_with_minibuf
= Qnil
;
1029 for (frames
= Vframe_list
;
1031 frames
= XCONS (frames
)->cdr
)
1035 this = XCONS (frames
)->car
;
1040 if (FRAME_HAS_MINIBUF_P (f
))
1042 frame_with_minibuf
= this;
1043 if (FRAME_MINIBUF_ONLY_P (f
))
1048 /* We know that there must be some frame with a minibuffer out
1049 there. If this were not true, all of the frames present
1050 would have to be minibufferless, which implies that at some
1051 point their minibuffer frames must have been deleted, but
1052 that is prohibited at the top; you can't delete surrogate
1053 minibuffer frames. */
1054 if (NILP (frame_with_minibuf
))
1057 Vdefault_minibuffer_frame
= frame_with_minibuf
;
1063 /* Return mouse position in character cell units. */
1065 DEFUN ("mouse-position", Fmouse_position
, Smouse_position
, 0, 0, 0,
1066 "Return a list (FRAME X . Y) giving the current mouse frame and position.\n\
1067 The position is given in character cells, where (0, 0) is the\n\
1068 upper-left corner.\n\
1069 If Emacs is running on a mouseless terminal or hasn't been programmed\n\
1070 to read the mouse position, it returns the selected frame for FRAME\n\
1071 and nil for X and Y.")
1075 Lisp_Object lispy_dummy
;
1076 enum scroll_bar_part party_dummy
;
1079 unsigned long long_dummy
;
1085 /* It's okay for the hook to refrain from storing anything. */
1086 if (mouse_position_hook
)
1087 (*mouse_position_hook
) (&f
, 0,
1088 &lispy_dummy
, &party_dummy
,
1095 pixel_to_glyph_coords (f
, col
, row
, &col
, &row
, 0, 1);
1100 XSETFRAME (lispy_dummy
, f
);
1101 return Fcons (lispy_dummy
, Fcons (x
, y
));
1104 DEFUN ("mouse-pixel-position", Fmouse_pixel_position
,
1105 Smouse_pixel_position
, 0, 0, 0,
1106 "Return a list (FRAME X . Y) giving the current mouse frame and position.\n\
1107 The position is given in pixel units, where (0, 0) is the\n\
1108 upper-left corner.\n\
1109 If Emacs is running on a mouseless terminal or hasn't been programmed\n\
1110 to read the mouse position, it returns the selected frame for FRAME\n\
1111 and nil for X and Y.")
1115 Lisp_Object lispy_dummy
;
1116 enum scroll_bar_part party_dummy
;
1119 unsigned long long_dummy
;
1125 /* It's okay for the hook to refrain from storing anything. */
1126 if (mouse_position_hook
)
1127 (*mouse_position_hook
) (&f
, 0,
1128 &lispy_dummy
, &party_dummy
,
1132 XSETFRAME (lispy_dummy
, f
);
1133 return Fcons (lispy_dummy
, Fcons (x
, y
));
1136 DEFUN ("set-mouse-position", Fset_mouse_position
, Sset_mouse_position
, 3, 3, 0,
1137 "Move the mouse pointer to the center of character cell (X,Y) in FRAME.\n\
1138 WARNING: If you use this under X windows,\n\
1139 you should call `unfocus-frame' afterwards.")
1141 Lisp_Object frame
, x
, y
;
1143 CHECK_LIVE_FRAME (frame
, 0);
1144 CHECK_NUMBER (x
, 2);
1145 CHECK_NUMBER (y
, 1);
1147 /* I think this should be done with a hook. */
1148 #ifdef HAVE_X_WINDOWS
1149 if (FRAME_X_P (XFRAME (frame
)))
1150 /* Warping the mouse will cause enternotify and focus events. */
1151 x_set_mouse_position (XFRAME (frame
), x
, y
);
1157 DEFUN ("set-mouse-pixel-position", Fset_mouse_pixel_position
,
1158 Sset_mouse_pixel_position
, 3, 3, 0,
1159 "Move the mouse pointer to pixel position (X,Y) in FRAME.\n\
1160 WARNING: If you use this under X windows,\n\
1161 you should call `unfocus-frame' afterwards.")
1163 Lisp_Object frame
, x
, y
;
1165 CHECK_LIVE_FRAME (frame
, 0);
1166 CHECK_NUMBER (x
, 2);
1167 CHECK_NUMBER (y
, 1);
1169 /* I think this should be done with a hook. */
1170 #ifdef HAVE_X_WINDOWS
1171 if (FRAME_X_P (XFRAME (frame
)))
1172 /* Warping the mouse will cause enternotify and focus events. */
1173 x_set_mouse_pixel_position (XFRAME (frame
), x
, y
);
1179 DEFUN ("make-frame-visible", Fmake_frame_visible
, Smake_frame_visible
,
1181 "Make the frame FRAME visible (assuming it is an X-window).\n\
1182 If omitted, FRAME defaults to the currently selected frame.")
1187 XSETFRAME (frame
, selected_frame
);
1189 CHECK_LIVE_FRAME (frame
, 0);
1191 /* I think this should be done with a hook. */
1192 #ifdef HAVE_X_WINDOWS
1193 if (FRAME_X_P (XFRAME (frame
)))
1195 FRAME_SAMPLE_VISIBILITY (XFRAME (frame
));
1196 x_make_frame_visible (XFRAME (frame
));
1200 /* Make menu bar update for the Buffers and Frams menus. */
1201 windows_or_buffers_changed
++;
1206 DEFUN ("make-frame-invisible", Fmake_frame_invisible
, Smake_frame_invisible
,
1208 "Make the frame FRAME invisible (assuming it is an X-window).\n\
1209 If omitted, FRAME defaults to the currently selected frame.\n\
1210 Normally you may not make FRAME invisible if all other frames are invisible,\n\
1211 but if the second optional argument FORCE is non-nil, you may do so.")
1213 Lisp_Object frame
, force
;
1216 XSETFRAME (frame
, selected_frame
);
1218 CHECK_LIVE_FRAME (frame
, 0);
1220 if (NILP (force
) && !other_visible_frames (XFRAME (frame
)))
1221 error ("Attempt to make invisible the sole visible or iconified frame");
1223 #if 0 /* This isn't logically necessary, and it can do GC. */
1224 /* Don't let the frame remain selected. */
1225 if (XFRAME (frame
) == selected_frame
)
1226 Fhandle_switch_frame (next_frame (frame
, Qt
), Qnil
);
1229 /* Don't allow minibuf_window to remain on a deleted frame. */
1230 if (EQ (XFRAME (frame
)->minibuffer_window
, minibuf_window
))
1232 Fset_window_buffer (selected_frame
->minibuffer_window
,
1233 XWINDOW (minibuf_window
)->buffer
);
1234 minibuf_window
= selected_frame
->minibuffer_window
;
1237 /* I think this should be done with a hook. */
1238 #ifdef HAVE_X_WINDOWS
1239 if (FRAME_X_P (XFRAME (frame
)))
1240 x_make_frame_invisible (XFRAME (frame
));
1243 /* Make menu bar update for the Buffers and Frams menus. */
1244 windows_or_buffers_changed
++;
1249 DEFUN ("iconify-frame", Ficonify_frame
, Siconify_frame
,
1251 "Make the frame FRAME into an icon.\n\
1252 If omitted, FRAME defaults to the currently selected frame.")
1257 XSETFRAME (frame
, selected_frame
);
1259 CHECK_LIVE_FRAME (frame
, 0);
1261 #if 0 /* This isn't logically necessary, and it can do GC. */
1262 /* Don't let the frame remain selected. */
1263 if (XFRAME (frame
) == selected_frame
)
1264 Fhandle_switch_frame (next_frame (frame
, Qt
), Qnil
);
1267 /* Don't allow minibuf_window to remain on a deleted frame. */
1268 if (EQ (XFRAME (frame
)->minibuffer_window
, minibuf_window
))
1270 Fset_window_buffer (selected_frame
->minibuffer_window
,
1271 XWINDOW (minibuf_window
)->buffer
);
1272 minibuf_window
= selected_frame
->minibuffer_window
;
1275 /* I think this should be done with a hook. */
1276 #ifdef HAVE_X_WINDOWS
1277 if (FRAME_X_P (XFRAME (frame
)))
1278 x_iconify_frame (XFRAME (frame
));
1281 /* Make menu bar update for the Buffers and Frams menus. */
1282 windows_or_buffers_changed
++;
1287 DEFUN ("frame-visible-p", Fframe_visible_p
, Sframe_visible_p
,
1289 "Return t if FRAME is now \"visible\" (actually in use for display).\n\
1290 A frame that is not \"visible\" is not updated and, if it works through\n\
1291 a window system, it may not show at all.\n\
1292 Return the symbol `icon' if frame is visible only as an icon.")
1296 CHECK_LIVE_FRAME (frame
, 0);
1298 FRAME_SAMPLE_VISIBILITY (XFRAME (frame
));
1300 if (FRAME_VISIBLE_P (XFRAME (frame
)))
1302 if (FRAME_ICONIFIED_P (XFRAME (frame
)))
1307 DEFUN ("visible-frame-list", Fvisible_frame_list
, Svisible_frame_list
,
1309 "Return a list of all frames now \"visible\" (being updated).")
1312 Lisp_Object tail
, frame
;
1317 for (tail
= Vframe_list
; CONSP (tail
); tail
= XCONS (tail
)->cdr
)
1319 frame
= XCONS (tail
)->car
;
1320 if (!FRAMEP (frame
))
1323 if (FRAME_VISIBLE_P (f
))
1324 value
= Fcons (frame
, value
);
1330 DEFUN ("raise-frame", Fraise_frame
, Sraise_frame
, 0, 1, "",
1331 "Bring FRAME to the front, so it occludes any frames it overlaps.\n\
1332 If FRAME is invisible, make it visible.\n\
1333 If you don't specify a frame, the selected frame is used.\n\
1334 If Emacs is displaying on an ordinary terminal or some other device which\n\
1335 doesn't support multiple overlapping frames, this function does nothing.")
1340 XSETFRAME (frame
, selected_frame
);
1342 CHECK_LIVE_FRAME (frame
, 0);
1344 /* Do like the documentation says. */
1345 Fmake_frame_visible (frame
);
1347 if (frame_raise_lower_hook
)
1348 (*frame_raise_lower_hook
) (XFRAME (frame
), 1);
1353 /* Should we have a corresponding function called Flower_Power? */
1354 DEFUN ("lower-frame", Flower_frame
, Slower_frame
, 0, 1, "",
1355 "Send FRAME to the back, so it is occluded by any frames that overlap it.\n\
1356 If you don't specify a frame, the selected frame is used.\n\
1357 If Emacs is displaying on an ordinary terminal or some other device which\n\
1358 doesn't support multiple overlapping frames, this function does nothing.")
1363 XSETFRAME (frame
, selected_frame
);
1365 CHECK_LIVE_FRAME (frame
, 0);
1367 if (frame_raise_lower_hook
)
1368 (*frame_raise_lower_hook
) (XFRAME (frame
), 0);
1374 DEFUN ("redirect-frame-focus", Fredirect_frame_focus
, Sredirect_frame_focus
,
1376 "Arrange for keystrokes typed at FRAME to be sent to FOCUS-FRAME.\n\
1377 In other words, switch-frame events caused by events in FRAME will\n\
1378 request a switch to FOCUS-FRAME, and `last-event-frame' will be\n\
1379 FOCUS-FRAME after reading an event typed at FRAME.\n\
1381 If FOCUS-FRAME is omitted or nil, any existing redirection is\n\
1382 cancelled, and the frame again receives its own keystrokes.\n\
1384 Focus redirection is useful for temporarily redirecting keystrokes to\n\
1385 a surrogate minibuffer frame when a frame doesn't have its own\n\
1386 minibuffer window.\n\
1388 A frame's focus redirection can be changed by select-frame. If frame\n\
1389 FOO is selected, and then a different frame BAR is selected, any\n\
1390 frames redirecting their focus to FOO are shifted to redirect their\n\
1391 focus to BAR. This allows focus redirection to work properly when the\n\
1392 user switches from one frame to another using `select-window'.\n\
1394 This means that a frame whose focus is redirected to itself is treated\n\
1395 differently from a frame whose focus is redirected to nil; the former\n\
1396 is affected by select-frame, while the latter is not.\n\
1398 The redirection lasts until `redirect-frame-focus' is called to change it.")
1399 (frame
, focus_frame
)
1400 Lisp_Object frame
, focus_frame
;
1402 /* Note that we don't check for a live frame here. It's reasonable
1403 to redirect the focus of a frame you're about to delete, if you
1404 know what other frame should receive those keystrokes. */
1405 CHECK_FRAME (frame
, 0);
1407 if (! NILP (focus_frame
))
1408 CHECK_LIVE_FRAME (focus_frame
, 1);
1410 XFRAME (frame
)->focus_frame
= focus_frame
;
1412 /* I think this should be done with a hook. */
1413 #ifdef HAVE_X_WINDOWS
1414 if (!NILP (focus_frame
) && ! EQ (focus_frame
, frame
)
1415 && FRAME_X_P (XFRAME (focus_frame
)))
1416 Ffocus_frame (focus_frame
);
1419 if (frame_rehighlight_hook
)
1420 (*frame_rehighlight_hook
) (XFRAME (frame
));
1426 DEFUN ("frame-focus", Fframe_focus
, Sframe_focus
, 1, 1, 0,
1427 "Return the frame to which FRAME's keystrokes are currently being sent.\n\
1428 This returns nil if FRAME's focus is not redirected.\n\
1429 See `redirect-frame-focus'.")
1433 CHECK_LIVE_FRAME (frame
, 0);
1435 return FRAME_FOCUS_FRAME (XFRAME (frame
));
1440 /* Return the value of frame parameter PROP in frame FRAME. */
1443 get_frame_param (frame
, prop
)
1444 register struct frame
*frame
;
1447 register Lisp_Object tem
;
1449 tem
= Fassq (prop
, frame
->param_alist
);
1455 /* Return the buffer-predicate of the selected frame. */
1458 frame_buffer_predicate ()
1460 return selected_frame
->buffer_predicate
;
1463 /* Modify the alist in *ALISTPTR to associate PROP with VAL.
1464 If the alist already has an element for PROP, we change it. */
1467 store_in_alist (alistptr
, prop
, val
)
1468 Lisp_Object
*alistptr
, val
;
1471 register Lisp_Object tem
;
1473 tem
= Fassq (prop
, *alistptr
);
1475 *alistptr
= Fcons (Fcons (prop
, val
), *alistptr
);
1481 store_frame_param (f
, prop
, val
)
1483 Lisp_Object prop
, val
;
1485 register Lisp_Object tem
;
1487 tem
= Fassq (prop
, f
->param_alist
);
1489 f
->param_alist
= Fcons (Fcons (prop
, val
), f
->param_alist
);
1493 if (EQ (prop
, Qbuffer_predicate
))
1494 f
->buffer_predicate
= val
;
1496 if (EQ (prop
, Qminibuffer
) && WINDOWP (val
))
1498 if (! MINI_WINDOW_P (XWINDOW (val
)))
1499 error ("Surrogate minibuffer windows must be minibuffer windows.");
1501 if (FRAME_HAS_MINIBUF_P (f
) || FRAME_MINIBUF_ONLY_P (f
))
1502 error ("can't change the surrogate minibuffer of a frame with its own minibuffer");
1504 /* Install the chosen minibuffer window, with proper buffer. */
1505 f
->minibuffer_window
= val
;
1509 DEFUN ("frame-parameters", Fframe_parameters
, Sframe_parameters
, 0, 1, 0,
1510 "Return the parameters-alist of frame FRAME.\n\
1511 It is a list of elements of the form (PARM . VALUE), where PARM is a symbol.\n\
1512 The meaningful PARMs depend on the kind of frame.\n\
1513 If FRAME is omitted, return information on the currently selected frame.")
1520 if (EQ (frame
, Qnil
))
1524 CHECK_FRAME (frame
, 0);
1528 if (!FRAME_LIVE_P (f
))
1531 alist
= Fcopy_alist (f
->param_alist
);
1532 store_in_alist (&alist
, Qname
, f
->name
);
1533 store_in_alist (&alist
, Qheight
, make_number (FRAME_HEIGHT (f
)));
1534 store_in_alist (&alist
, Qwidth
, make_number (FRAME_WIDTH (f
)));
1535 store_in_alist (&alist
, Qmodeline
, (FRAME_WANTS_MODELINE_P (f
) ? Qt
: Qnil
));
1536 store_in_alist (&alist
, Qminibuffer
,
1537 (! FRAME_HAS_MINIBUF_P (f
) ? Qnil
1538 : FRAME_MINIBUF_ONLY_P (f
) ? Qonly
1539 : FRAME_MINIBUF_WINDOW (f
)));
1540 store_in_alist (&alist
, Qunsplittable
, (FRAME_NO_SPLIT_P (f
) ? Qt
: Qnil
));
1542 /* I think this should be done with a hook. */
1543 #ifdef HAVE_X_WINDOWS
1545 x_report_frame_params (f
, &alist
);
1549 /* This ought to be correct in f->param_alist for an X frame. */
1551 XSETFASTINT (lines
, FRAME_MENU_BAR_LINES (f
));
1552 store_in_alist (&alist
, Qmenu_bar_lines
, lines
);
1557 DEFUN ("modify-frame-parameters", Fmodify_frame_parameters
,
1558 Smodify_frame_parameters
, 2, 2, 0,
1559 "Modify the parameters of frame FRAME according to ALIST.\n\
1560 ALIST is an alist of parameters to change and their new values.\n\
1561 Each element of ALIST has the form (PARM . VALUE), where PARM is a symbol.\n\
1562 The meaningful PARMs depend on the kind of frame; undefined PARMs are ignored.")
1564 Lisp_Object frame
, alist
;
1567 register Lisp_Object tail
, elt
, prop
, val
;
1569 if (EQ (frame
, Qnil
))
1573 CHECK_LIVE_FRAME (frame
, 0);
1577 /* I think this should be done with a hook. */
1578 #ifdef HAVE_X_WINDOWS
1580 x_set_frame_parameters (f
, alist
);
1583 for (tail
= alist
; !EQ (tail
, Qnil
); tail
= Fcdr (tail
))
1588 store_frame_param (f
, prop
, val
);
1594 DEFUN ("frame-char-height", Fframe_char_height
, Sframe_char_height
,
1596 "Height in pixels of a line in the font in frame FRAME.\n\
1597 If FRAME is omitted, the selected frame is used.\n\
1598 For a terminal frame, the value is always 1.")
1608 CHECK_FRAME (frame
, 0);
1612 #ifdef HAVE_X_WINDOWS
1614 return make_number (x_char_height (f
));
1617 return make_number (1);
1621 DEFUN ("frame-char-width", Fframe_char_width
, Sframe_char_width
,
1623 "Width in pixels of characters in the font in frame FRAME.\n\
1624 If FRAME is omitted, the selected frame is used.\n\
1625 The width is the same for all characters, because\n\
1626 currently Emacs supports only fixed-width fonts.\n\
1627 For a terminal screen, the value is always 1.")
1637 CHECK_FRAME (frame
, 0);
1641 #ifdef HAVE_X_WINDOWS
1643 return make_number (x_char_width (f
));
1646 return make_number (1);
1649 DEFUN ("frame-pixel-height", Fframe_pixel_height
,
1650 Sframe_pixel_height
, 0, 1, 0,
1651 "Return a FRAME's height in pixels.\n\
1652 For a terminal frame, the result really gives the height in characters.\n\
1653 If FRAME is omitted, the selected frame is used.")
1663 CHECK_FRAME (frame
, 0);
1667 #ifdef HAVE_X_WINDOWS
1669 return make_number (x_pixel_height (f
));
1672 return make_number (FRAME_HEIGHT (f
));
1675 DEFUN ("frame-pixel-width", Fframe_pixel_width
,
1676 Sframe_pixel_width
, 0, 1, 0,
1677 "Return FRAME's width in pixels.\n\
1678 For a terminal frame, the result really gives the width in characters.\n\
1679 If FRAME is omitted, the selected frame is used.")
1689 CHECK_FRAME (frame
, 0);
1693 #ifdef HAVE_X_WINDOWS
1695 return make_number (x_pixel_width (f
));
1698 return make_number (FRAME_WIDTH (f
));
1701 DEFUN ("set-frame-height", Fset_frame_height
, Sset_frame_height
, 2, 3, 0,
1702 "Specify that the frame FRAME has LINES lines.\n\
1703 Optional third arg non-nil means that redisplay should use LINES lines\n\
1704 but that the idea of the actual height of the frame should not be changed.")
1705 (frame
, rows
, pretend
)
1706 Lisp_Object frame
, rows
, pretend
;
1708 register struct frame
*f
;
1710 CHECK_NUMBER (rows
, 0);
1715 CHECK_LIVE_FRAME (frame
, 0);
1719 /* I think this should be done with a hook. */
1720 #ifdef HAVE_X_WINDOWS
1723 if (XINT (rows
) != f
->height
)
1724 x_set_window_size (f
, 1, f
->width
, XINT (rows
));
1728 change_frame_size (f
, XINT (rows
), 0, !NILP (pretend
), 0);
1732 DEFUN ("set-frame-width", Fset_frame_width
, Sset_frame_width
, 2, 3, 0,
1733 "Specify that the frame FRAME has COLS columns.\n\
1734 Optional third arg non-nil means that redisplay should use COLS columns\n\
1735 but that the idea of the actual width of the frame should not be changed.")
1736 (frame
, cols
, pretend
)
1737 Lisp_Object frame
, cols
, pretend
;
1739 register struct frame
*f
;
1740 CHECK_NUMBER (cols
, 0);
1745 CHECK_LIVE_FRAME (frame
, 0);
1749 /* I think this should be done with a hook. */
1750 #ifdef HAVE_X_WINDOWS
1753 if (XINT (cols
) != f
->width
)
1754 x_set_window_size (f
, 1, XINT (cols
), f
->height
);
1758 change_frame_size (f
, 0, XINT (cols
), !NILP (pretend
), 0);
1762 DEFUN ("set-frame-size", Fset_frame_size
, Sset_frame_size
, 3, 3, 0,
1763 "Sets size of FRAME to COLS by ROWS, measured in characters.")
1765 Lisp_Object frame
, cols
, rows
;
1767 register struct frame
*f
;
1770 CHECK_LIVE_FRAME (frame
, 0);
1771 CHECK_NUMBER (cols
, 2);
1772 CHECK_NUMBER (rows
, 1);
1775 /* I think this should be done with a hook. */
1776 #ifdef HAVE_X_WINDOWS
1779 if (XINT (rows
) != f
->height
|| XINT (cols
) != f
->width
)
1780 x_set_window_size (f
, 1, XINT (cols
), XINT (rows
));
1784 change_frame_size (f
, XINT (rows
), XINT (cols
), 0, 0);
1789 DEFUN ("set-frame-position", Fset_frame_position
,
1790 Sset_frame_position
, 3, 3, 0,
1791 "Sets position of FRAME in pixels to XOFFSET by YOFFSET.\n\
1792 This is actually the position of the upper left corner of the frame.\n\
1793 Negative values for XOFFSET or YOFFSET are interpreted relative to\n\
1794 the rightmost or bottommost possible position (that stays within the screen).")
1795 (frame
, xoffset
, yoffset
)
1796 Lisp_Object frame
, xoffset
, yoffset
;
1798 register struct frame
*f
;
1801 CHECK_LIVE_FRAME (frame
, 0);
1802 CHECK_NUMBER (xoffset
, 1);
1803 CHECK_NUMBER (yoffset
, 2);
1806 /* I think this should be done with a hook. */
1807 #ifdef HAVE_X_WINDOWS
1809 x_set_offset (f
, XINT (xoffset
), XINT (yoffset
), 1);
1816 choose_minibuf_frame ()
1818 /* For lowest-level minibuf, put it on currently selected frame
1819 if frame has a minibuffer. */
1821 if (minibuf_level
== 0
1822 && selected_frame
!= 0
1823 && !EQ (minibuf_window
, selected_frame
->minibuffer_window
))
1825 /* I don't think that any frames may validly have a null minibuffer
1827 if (NILP (selected_frame
->minibuffer_window
))
1830 Fset_window_buffer (selected_frame
->minibuffer_window
,
1831 XWINDOW (minibuf_window
)->buffer
);
1832 minibuf_window
= selected_frame
->minibuffer_window
;
1838 /*&&& init symbols here &&&*/
1839 Qframep
= intern ("framep");
1840 staticpro (&Qframep
);
1841 Qframe_live_p
= intern ("frame-live-p");
1842 staticpro (&Qframe_live_p
);
1843 Qheight
= intern ("height");
1844 staticpro (&Qheight
);
1845 Qicon
= intern ("icon");
1847 Qminibuffer
= intern ("minibuffer");
1848 staticpro (&Qminibuffer
);
1849 Qmodeline
= intern ("modeline");
1850 staticpro (&Qmodeline
);
1851 Qname
= intern ("name");
1853 Qonly
= intern ("only");
1855 Qunsplittable
= intern ("unsplittable");
1856 staticpro (&Qunsplittable
);
1857 Qmenu_bar_lines
= intern ("menu-bar-lines");
1858 staticpro (&Qmenu_bar_lines
);
1859 Qwidth
= intern ("width");
1860 staticpro (&Qwidth
);
1863 Qvisible
= intern ("visible");
1864 staticpro (&Qvisible
);
1865 Qbuffer_predicate
= intern ("buffer-predicate");
1866 staticpro (&Qbuffer_predicate
);
1868 staticpro (&Vframe_list
);
1870 DEFVAR_LISP ("terminal-frame", &Vterminal_frame
,
1871 "The initial frame-object, which represents Emacs's stdout.");
1873 DEFVAR_LISP ("emacs-iconified", &Vemacs_iconified
,
1874 "Non-nil if all of emacs is iconified and frame updates are not needed.");
1875 Vemacs_iconified
= Qnil
;
1877 DEFVAR_LISP ("default-minibuffer-frame", &Vdefault_minibuffer_frame
,
1878 "Minibufferless frames use this frame's minibuffer.\n\
1880 Emacs cannot create minibufferless frames unless this is set to an\n\
1881 appropriate surrogate.\n\
1883 Emacs consults this variable only when creating minibufferless\n\
1884 frames; once the frame is created, it sticks with its assigned\n\
1885 minibuffer, no matter what this variable is set to. This means that\n\
1886 this variable doesn't necessarily say anything meaningful about the\n\
1887 current set of frames, or where the minibuffer is currently being\n\
1889 Vdefault_minibuffer_frame
= Qnil
;
1891 DEFVAR_LISP ("default-frame-alist", &Vdefault_frame_alist
,
1892 "Alist of default values for frame creation.\n\
1893 These may be set in your init file, like this:\n\
1894 (setq default-frame-alist '((width . 80) (height . 55) (menu-bar-lines . 1))\n\
1895 These override values given in window system configuration data,\n\
1896 including X Windows' defaults database.\n\
1897 For values specific to the first Emacs frame, see `initial-frame-alist'.\n\
1898 For values specific to the separate minibuffer frame, see\n\
1899 `minibuffer-frame-alist'.\n\
1900 The `menu-bar-lines' element of the list controls whether new frames\n\
1901 have menu bars; `menu-bar-mode' works by altering this element.");
1902 Vdefault_frame_alist
= Qnil
;
1904 defsubr (&Sactive_minibuffer_window
);
1906 defsubr (&Sframe_live_p
);
1907 defsubr (&Smake_terminal_frame
);
1908 defsubr (&Shandle_switch_frame
);
1909 defsubr (&Sselect_frame
);
1910 defsubr (&Sselected_frame
);
1911 defsubr (&Swindow_frame
);
1912 defsubr (&Sframe_root_window
);
1913 defsubr (&Sframe_first_window
);
1914 defsubr (&Sframe_selected_window
);
1915 defsubr (&Sset_frame_selected_window
);
1916 defsubr (&Sframe_list
);
1917 defsubr (&Snext_frame
);
1918 defsubr (&Sprevious_frame
);
1919 defsubr (&Sdelete_frame
);
1920 defsubr (&Smouse_position
);
1921 defsubr (&Smouse_pixel_position
);
1922 defsubr (&Sset_mouse_position
);
1923 defsubr (&Sset_mouse_pixel_position
);
1925 defsubr (&Sframe_configuration
);
1926 defsubr (&Srestore_frame_configuration
);
1928 defsubr (&Smake_frame_visible
);
1929 defsubr (&Smake_frame_invisible
);
1930 defsubr (&Siconify_frame
);
1931 defsubr (&Sframe_visible_p
);
1932 defsubr (&Svisible_frame_list
);
1933 defsubr (&Sraise_frame
);
1934 defsubr (&Slower_frame
);
1935 defsubr (&Sredirect_frame_focus
);
1936 defsubr (&Sframe_focus
);
1937 defsubr (&Sframe_parameters
);
1938 defsubr (&Smodify_frame_parameters
);
1939 defsubr (&Sframe_char_height
);
1940 defsubr (&Sframe_char_width
);
1941 defsubr (&Sframe_pixel_height
);
1942 defsubr (&Sframe_pixel_width
);
1943 defsubr (&Sset_frame_height
);
1944 defsubr (&Sset_frame_width
);
1945 defsubr (&Sset_frame_size
);
1946 defsubr (&Sset_frame_position
);
1951 initial_define_lispy_key (global_map
, "switch-frame", "handle-switch-frame");
1952 initial_define_lispy_key (global_map
, "delete-frame", "handle-delete-frame");
1953 initial_define_lispy_key (global_map
, "iconify-frame", "ignore");
1954 initial_define_lispy_key (global_map
, "make-frame-visible", "ignore");
1957 #else /* not MULTI_FRAME */
1959 /* If we're not using multi-frame stuff, we still need to provide some
1960 support functions. */
1962 Lisp_Object Qheight
;
1963 Lisp_Object Qminibuffer
;
1964 Lisp_Object Qmodeline
;
1966 Lisp_Object Qunsplittable
;
1967 Lisp_Object Qmenu_bar_lines
;
1970 Lisp_Object Vterminal_frame
;
1972 /* Unless this function is defined, providing set-frame-height and
1973 set-frame-width doesn't help compatibility any, since they both
1974 want this as their first argument. */
1975 DEFUN ("selected-frame", Fselected_frame
, Sselected_frame
, 0, 0, 0,
1976 /* Don't confuse make-docfile by having two doc strings for this function.
1977 make-docfile does not pay attention to #if, for good reason! */
1981 /* For your possible information, this code is unfolded into the
1982 second WINDOW_FRAME in frame.h. */
1984 XSETFASTINT (tem
, 0);
1988 DEFUN ("window-frame", Fwindow_frame
, Swindow_frame
, 1, 1, 0,
1989 /* Don't confuse make-docfile by having two doc strings for this function.
1990 make-docfile does not pay attention to #if, for good reason! */
1995 /* For your possible information, this code is unfolded into the
1996 second WINDOW_FRAME in frame.h. */
1998 XSETFASTINT (tem
, 0);
2002 DEFUN ("frame-first-window", Fframe_first_window
, Sframe_first_window
, 0, 1, 0,
2009 w
= FRAME_ROOT_WINDOW (selected_frame
);
2011 while (NILP (XWINDOW (w
)->buffer
))
2013 if (! NILP (XWINDOW (w
)->hchild
))
2014 w
= XWINDOW (w
)->hchild
;
2015 else if (! NILP (XWINDOW (w
)->vchild
))
2016 w
= XWINDOW (w
)->vchild
;
2023 DEFUN ("framep", Fframep
, Sframep
, 1, 1, 0,
2024 /* Don't confuse make-docfile by having two doc strings for this function.
2025 make-docfile does not pay attention to #if, for good reason! */
2031 if (FRAME_X_P (object
))
2032 return intern ("pc");
2037 DEFUN ("set-frame-height", Fset_frame_height
, Sset_frame_height
, 2, 3, 0,
2038 /* Don't confuse make-docfile by having two doc strings for this function.
2039 make-docfile does not pay attention to #if, for good reason! */
2041 (frame
, rows
, pretend
)
2042 Lisp_Object frame
, rows
, pretend
;
2044 CHECK_NUMBER (rows
, 0);
2046 change_frame_size (0, XINT (rows
), 0, !NILP (pretend
), 0);
2050 DEFUN ("set-frame-width", Fset_frame_width
, Sset_frame_width
, 2, 3, 0,
2051 /* Don't confuse make-docfile by having two doc strings for this function.
2052 make-docfile does not pay attention to #if, for good reason! */
2054 (frame
, cols
, pretend
)
2055 Lisp_Object frame
, cols
, pretend
;
2057 CHECK_NUMBER (cols
, 0);
2059 change_frame_size (0, 0, XINT (cols
), !NILP (pretend
), 0);
2063 DEFUN ("set-frame-size", Fset_frame_size
, Sset_frame_size
, 3, 3, 0,
2064 /* Don't confuse make-docfile by having two doc strings for this function.
2065 make-docfile does not pay attention to #if, for good reason! */
2068 Lisp_Object frame
, cols
, rows
;
2070 CHECK_NUMBER (cols
, 2);
2071 CHECK_NUMBER (rows
, 1);
2073 change_frame_size (0, XINT (rows
), XINT (cols
), 0, 0);
2078 DEFUN ("frame-height", Fframe_height
, Sframe_height
, 0, 1, 0,
2079 "Return number of lines available for display on FRAME.\n\
2080 If FRAME is omitted, describe the currently selected frame.")
2084 return make_number (FRAME_HEIGHT (selected_frame
));
2087 DEFUN ("frame-width", Fframe_width
, Sframe_width
, 0, 1, 0,
2088 "Return number of columns available for display on FRAME.\n\
2089 If FRAME is omitted, describe the currently selected frame.")
2093 return make_number (FRAME_WIDTH (selected_frame
));
2096 DEFUN ("frame-char-height", Fframe_char_height
, Sframe_char_height
,
2098 /* Don't confuse make-docfile by having two doc strings for this function.
2099 make-docfile does not pay attention to #if, for good reason! */
2104 return make_number (1);
2108 DEFUN ("frame-char-width", Fframe_char_width
, Sframe_char_width
,
2110 /* Don't confuse make-docfile by having two doc strings for this function.
2111 make-docfile does not pay attention to #if, for good reason! */
2116 return make_number (1);
2119 DEFUN ("frame-pixel-height", Fframe_pixel_height
,
2120 Sframe_pixel_height
, 0, 1, 0,
2121 /* Don't confuse make-docfile by having two doc strings for this function.
2122 make-docfile does not pay attention to #if, for good reason! */
2127 return make_number (FRAME_HEIGHT (f
));
2130 DEFUN ("frame-pixel-width", Fframe_pixel_width
,
2131 Sframe_pixel_width
, 0, 1, 0,
2132 /* Don't confuse make-docfile by having two doc strings for this function.
2133 make-docfile does not pay attention to #if, for good reason! */
2138 return make_number (FRAME_WIDTH (f
));
2141 /* These are for backward compatibility with Emacs 18. */
2143 DEFUN ("set-screen-height", Fset_screen_height
, Sset_screen_height
, 1, 2, 0,
2144 "Tell redisplay that the screen has LINES lines.\n\
2145 Optional second arg non-nil means that redisplay should use LINES lines\n\
2146 but that the idea of the actual height of the screen should not be changed.")
2148 Lisp_Object lines
, pretend
;
2150 CHECK_NUMBER (lines
, 0);
2152 change_frame_size (0, XINT (lines
), 0, !NILP (pretend
), 0);
2156 DEFUN ("set-screen-width", Fset_screen_width
, Sset_screen_width
, 1, 2, 0,
2157 "Tell redisplay that the screen has COLS columns.\n\
2158 Optional second arg non-nil means that redisplay should use COLS columns\n\
2159 but that the idea of the actual width of the screen should not be changed.")
2161 Lisp_Object cols
, pretend
;
2163 CHECK_NUMBER (cols
, 0);
2165 change_frame_size (0, 0, XINT (cols
), !NILP (pretend
), 0);
2169 DEFUN ("mouse-position", Fmouse_position
, Smouse_position
, 0, 0, 0,
2170 /* Don't confuse make-docfile by having two doc strings for this function.
2171 make-docfile does not pay attention to #if, for good reason! */
2176 if (mouse_position_hook
)
2179 Lisp_Object lispy_dummy
;
2180 enum scroll_bar_part party_dummy
;
2182 unsigned long long_dummy
;
2184 (*mouse_position_hook
) (&f
, 0,
2185 &lispy_dummy
, &party_dummy
,
2188 return Fcons (Fselected_frame (), Fcons (x
, y
));
2191 return Fcons (Qnil
, Fcons (Qnil
, Qnil
));
2195 store_in_alist (alistptr
, prop
, val
)
2196 Lisp_Object
*alistptr
, val
;
2199 register Lisp_Object tem
;
2201 tem
= Fassq (prop
, *alistptr
);
2203 *alistptr
= Fcons (Fcons (prop
, val
), *alistptr
);
2208 DEFUN ("frame-parameters", Fframe_parameters
, Sframe_parameters
, 0, 1, 0,
2209 /* Don't confuse make-docfile by having two doc strings for this function.
2210 make-docfile does not pay attention to #if, for good reason! */
2218 if (EQ (frame
, Qnil
))
2222 CHECK_FRAME (frame
, 0);
2226 if (!FRAME_LIVE_P (f
))
2233 static char *colornames
[16] =
2235 "black", "blue", "green", "cyan", "red", "magenta", "brown",
2236 "lightgray", "darkgray", "lightblue", "lightgreen", "lightcyan",
2237 "lightred", "lightmagenta", "yellow", "white"
2239 store_in_alist (&alist
, intern ("foreground-color"),
2240 build_string (colornames
[FRAME_FOREGROUND_PIXEL (f
)]));
2241 store_in_alist (&alist
, intern ("background-color"),
2242 build_string (colornames
[FRAME_BACKGROUND_PIXEL (f
)]));
2245 store_in_alist (&alist
, intern ("font"), build_string ("default"));
2246 store_in_alist (&alist
, Qname
, build_string ("emacs"));
2247 store_in_alist (&alist
, Qheight
, make_number (FRAME_HEIGHT (f
)));
2248 store_in_alist (&alist
, Qwidth
, make_number (FRAME_WIDTH (f
)));
2249 store_in_alist (&alist
, Qmodeline
, (FRAME_WANTS_MODELINE_P (f
) ? Qt
: Qnil
));
2250 store_in_alist (&alist
, Qminibuffer
, FRAME_MINIBUF_WINDOW (f
));
2251 store_in_alist (&alist
, Qunsplittable
, (FRAME_NO_SPLIT_P (f
) ? Qt
: Qnil
));
2252 store_in_alist (&alist
, Qmenu_bar_lines
, (FRAME_MENU_BAR_LINES (f
)));
2257 DEFUN ("modify-frame-parameters", Fmodify_frame_parameters
,
2258 Smodify_frame_parameters
, 2, 2, 0,
2259 /* Don't confuse make-docfile by having two doc strings for this function.
2260 make-docfile does not pay attention to #if, for good reason! */
2263 Lisp_Object frame
, alist
;
2266 if (FRAME_X_P (frame
))
2267 IT_set_frame_parameters (XFRAME (frame
), alist
);
2272 DEFUN ("frame-live-p", Fframe_live_p
, Sframe_live_p
, 1, 1, 0,
2273 /* Don't confuse make-docfile by having two doc strings for this function.
2274 make-docfile does not pay attention to #if, for good reason! */
2282 DEFUN ("frame-list", Fframe_list
, Sframe_list
, 0, 0, 0,
2283 /* Don't confuse make-docfile by having two doc strings for this function.
2284 make-docfile does not pay attention to #if, for good reason! */
2288 return Fcons (Fselected_frame (), Qnil
);
2293 Qheight
= intern ("height");
2294 staticpro (&Qheight
);
2295 Qminibuffer
= intern ("minibuffer");
2296 staticpro (&Qminibuffer
);
2297 Qmodeline
= intern ("modeline");
2298 staticpro (&Qmodeline
);
2299 Qname
= intern ("name");
2301 Qunsplittable
= intern ("unsplittable");
2302 staticpro (&Qunsplittable
);
2303 Qmenu_bar_lines
= intern ("menu-bar-lines");
2304 staticpro (&Qmenu_bar_lines
);
2305 Qwidth
= intern ("width");
2306 staticpro (&Qwidth
);
2308 DEFVAR_LISP ("terminal-frame", &Vterminal_frame
,
2309 "The initial frame-object, which represents Emacs's stdout.");
2310 XSETFASTINT (Vterminal_frame
, 0);
2312 defsubr (&Sselected_frame
);
2313 defsubr (&Swindow_frame
);
2314 defsubr (&Sframe_first_window
);
2316 defsubr (&Sframe_char_height
);
2317 defsubr (&Sframe_char_width
);
2318 defsubr (&Sframe_pixel_height
);
2319 defsubr (&Sframe_pixel_width
);
2320 defsubr (&Sset_frame_height
);
2321 defsubr (&Sset_frame_width
);
2322 defsubr (&Sset_frame_size
);
2323 defsubr (&Sset_screen_height
);
2324 defsubr (&Sset_screen_width
);
2325 defsubr (&Sframe_height
);
2326 Ffset (intern ("screen-height"), intern ("frame-height"));
2327 defsubr (&Sframe_width
);
2328 Ffset (intern ("screen-width"), intern ("frame-width"));
2329 defsubr (&Smouse_position
);
2330 defsubr (&Sframe_parameters
);
2331 defsubr (&Smodify_frame_parameters
);
2332 defsubr (&Sframe_live_p
);
2333 defsubr (&Sframe_list
);
2336 /* A comment in dispnew.c says the_only_frame is not protected. */
2337 the_only_frame
.face_alist
= Qnil
;
2338 staticpro (&the_only_frame
.face_alist
);
2339 the_only_frame
.menu_bar_items
= Qnil
;
2340 staticpro (&the_only_frame
.menu_bar_items
);
2341 the_only_frame
.menu_bar_vector
= Qnil
;
2342 staticpro (&the_only_frame
.menu_bar_vector
);
2343 the_only_frame
.menu_bar_items
= menu_bar_items (Qnil
);
2351 #endif /* not MULTI_FRAME */