Mercurial > hg > xemacs-beta
comparison src/frame.c @ 5052:92dc90c0bb40
merge
author | Ben Wing <ben@xemacs.org> |
---|---|
date | Sat, 20 Feb 2010 23:56:01 -0600 |
parents | 6f2158fa75ed 07dcc7000bbf |
children | a04cf0fea770 2a462149bd6a |
comparison
equal
deleted
inserted
replaced
5051:c3d372419e09 | 5052:92dc90c0bb40 |
---|---|
1 /* Generic frame functions. | 1 /* Generic frame functions. |
2 Copyright (C) 1989, 1992, 1993, 1994, 1995 Free Software Foundation, Inc. | 2 Copyright (C) 1989, 1992, 1993, 1994, 1995 Free Software Foundation, Inc. |
3 Copyright (C) 1995, 1996, 2002, 2003, 2005 Ben Wing. | 3 Copyright (C) 1995, 1996, 2002, 2003, 2005, 2010 Ben Wing. |
4 Copyright (C) 1995 Sun Microsystems, Inc. | 4 Copyright (C) 1995 Sun Microsystems, Inc. |
5 | 5 |
6 This file is part of XEmacs. | 6 This file is part of XEmacs. |
7 | 7 |
8 XEmacs is free software; you can redistribute it and/or modify it | 8 XEmacs is free software; you can redistribute it and/or modify it |
21 Boston, MA 02111-1307, USA. */ | 21 Boston, MA 02111-1307, USA. */ |
22 | 22 |
23 /* Synched up with: FSF 19.30. */ | 23 /* Synched up with: FSF 19.30. */ |
24 | 24 |
25 /* This file has been Mule-ized. */ | 25 /* This file has been Mule-ized. */ |
26 | |
27 /* About window and frame geometry [ben]: | |
28 | |
29 Here is an ASCII diagram: | |
30 | |
31 +------------------------------------------------------------------------| | |
32 | window-manager decoration | | |
33 | +--------------------------------------------------------------------+ | | |
34 | | menubar | | | |
35 | ###################################################################### | | |
36 | # toolbar # | | |
37 | #--------------------------------------------------------------------# | | |
38 | # | gutter | # | | |
39 | # |--------------------------------------------------------------| # | | |
40 | # | | internal border width | | # | | |
41 | # | | ******************************************************** | | # | | |
42 |w# | | * |s|v* |s* | | #w| | |
43 |i# | | * |c|e* |c* | | #i| | |
44 |n# | | * |r|r* |r* | | #n| | |
45 |d# | | * |o|t* |o* | | #d| | |
46 |o# | | * text area |l|.* text area |l* | | #o| | |
47 |w# | |i* |l| * |l*i| | #w| | |
48 |-# | |n* |b|d* |b*n| | #-| | |
49 |m# | |t* |a|i* |a*t| | #m| | |
50 |a# | |.* |r|v* |r*.| | #a| | |
51 |n# t| | *-------------------------+-|i*----------------------+-* | |t #n| | |
52 |a# o|g|b* scrollbar | |d* scrollbar | *b|g|o #a| | |
53 |g# o|u|o*-------------------------+-|e*----------------------+-*o|u|o #g| | |
54 |e# l|t|r* modeline |r* modeline *r|t|l #e| | |
55 |r# b|t|d********************************************************d|t|b #r| | |
56 | # a|e|e* =..texttexttex....= |s|v* |s*e|e|a # | | |
57 |d# r|r|r*o m=..texttexttextt..=o m|c|e* |c*r|r|r #d| | |
58 |e# | | *u a=.exttexttextte...=u a|r|r* |r* | | #e| | |
59 |c# | |w*t r=....texttexttex..=t r|o|t* |o*w| | #c| | |
60 |o# | |i*s g= etc. =s g|l|.* text area |l*i| | #o| | |
61 |r# | |d*i i= =i i|l| * |l*d| | #r| | |
62 |a# | |t*d n= =d n|b|d* |b*t| | #a| | |
63 |t# | |h*e = inner text area =e |a|i* |a*h| | #t| | |
64 |i# | | * = = |r|v* |r* | | #i| | |
65 |o# | | *---===================---+-|i*----------------------+-* | | #o| | |
66 |n# | | * scrollbar | |d* scrollbar | * | | #n| | |
67 | # | | *-------------------------+-|e*----------------------+-* | | # | | |
68 | # | | * modeline |r* modeline * | | # | | |
69 | # | | ******************************************************** | | # | | |
70 | # | | * minibuffer * | | # | | |
71 | # | | ******************************************************** | | # | | |
72 | # | | internal border width | | # | | |
73 | # |--------------------------------------------------------------| # | | |
74 | # | gutter | # | | |
75 | #--------------------------------------------------------------------# | | |
76 | # toolbar # | | |
77 | ###################################################################### | | |
78 | window manager decoration | | |
79 +------------------------------------------------------------------------+ | |
80 | |
81 # = boundary of client area; * = window boundaries, boundary of paned area | |
82 = = boundary of inner text area; . = inside margin area | |
83 | |
84 Note in particular what happens at the corners, where a "corner box" | |
85 occurs. Top and bottom toolbars take precedence over left and right | |
86 toolbars, extending out horizontally into the corner boxes. Gutters | |
87 work the same way. The corner box where the scrollbars meet, however, | |
88 is assigned to neither scrollbar, and is known as the "dead box"; it is | |
89 an area that must be cleared specially. | |
90 | |
91 THE FRAME | |
92 --------- | |
93 | |
94 The "top-level window area" is the entire area of a top-level window (or | |
95 "frame"). The "client area" (a term from MS Windows) is the area of a | |
96 top-level window that XEmacs draws into and manages with redisplay. | |
97 This includes the toolbar, scrollbars, gutters, dividers, text area, | |
98 modeline and minibuffer. It does not include the menubar, title or | |
99 outer borders. The "non-client area" is the area of a top-level window | |
100 outside of the client area and includes the menubar, title and outer | |
101 borders. Internally, all frame coordinates are relative to the client | |
102 area. | |
103 | |
104 | |
105 THE NON-CLIENT AREA | |
106 ------------------- | |
107 | |
108 Under X, the non-client area is split into two parts: | |
109 | |
110 (1) The outer layer is the window-manager decorations: The title and | |
111 borders. These are controlled by the window manager, a separate process | |
112 that controls the desktop, the location of icons, etc. When a process | |
113 tries to create a window, the window manager intercepts this action and | |
114 "reparents" the window, placing another window around it which contains | |
115 the window decorations, including the title bar, outer borders used for | |
116 resizing, etc. The window manager also implements any actions involving | |
117 the decorations, such as the ability to resize a window by dragging its | |
118 borders, move a window by dragging its title bar, etc. If there is no | |
119 window manager or you kill it, windows will have no decorations (and | |
120 will lose them if they previously had any) and you will not be able to | |
121 move or resize them. | |
122 | |
123 (2) Inside of the window-manager decorations is the "shell", which is | |
124 managed by the toolkit and widget libraries your program is linked with. | |
125 The code in *-x.c uses the Xt toolkit and various possible widget | |
126 libraries built on top of Xt, such as Motif, Athena, the "Lucid" | |
127 widgets, etc. Another possibility is GTK (*-gtk.c), which implements | |
128 both the toolkit and widgets. Under Xt, the "shell" window is an | |
129 EmacsShell widget, containing an EmacsManager widget of the same size, | |
130 which in turn contains a menubar widget and an EmacsFrame widget, inside | |
131 of which is the client area. (The division into EmacsShell and | |
132 EmacsManager is due to the complex and screwy geometry-management system | |
133 in Xt [and X more generally]. The EmacsShell handles negotation with | |
134 the window manager; the place of the EmacsManager widget is normally | |
135 assumed by a widget that manages the geometry of its child widgets, but | |
136 the EmacsManager widget just lets the XEmacs redisplay mechanism do the | |
137 positioning.) | |
138 | |
139 Under Windows, the non-client area is managed by the window system. | |
140 There is no division such as under X. Part of the window-system API | |
141 (USER.DLL) of Win32 includes functions to control the menubars, title, | |
142 etc. and implements the move and resize behavior. There *is* an | |
143 equivalent of the window manager, called the "shell", but it manages | |
144 only the desktop, not the windows themselves. The normal shell under | |
145 Windows is EXPLORER.EXE; if you kill this, you will lose the bar | |
146 containing the "Start" menu and tray and such, but the windows | |
147 themselves will not be affected or lose their decorations. | |
148 | |
149 | |
150 THE CLIENT AREA | |
151 --------------- | |
152 | |
153 Inside of the client area is the toolbars, the gutters (where the buffer | |
154 tabs are displayed), the minibuffer, the internal border width, and one | |
155 or more non-overlapping "windows" (this is old Emacs terminology, from | |
156 before the time when frames existed at all; the standard terminology for | |
157 this would be "pane"). Each window can contain a modeline, horizontal | |
158 and/or vertical scrollbars, and (for non-rightmost windows) a vertical | |
159 divider, surrounding a text area. | |
160 | |
161 The dimensions of the toolbars and gutters are determined by the formula | |
162 (THICKNESS + 2 * BORDER-THICKNESS), where "thickness" is a cover term | |
163 for height or width, as appropriate. The height and width come from | |
164 `default-toolbar-height' and `default-toolbar-width' and the specific | |
165 versions of these (`top-toolbar-height', `left-toolbar-width', etc.). | |
166 The border thickness comes from `default-toolbar-border-height' and | |
167 `default-toolbar-border-width', and the specific versions of these. The | |
168 gutter works exactly equivalently. | |
169 | |
170 Note that for any particular toolbar or gutter, it will only be | |
171 displayed if [a] its visibility specifier (`default-toolbar-visible-p' | |
172 etc.) is non-nil; [b] its thickness (`default-toolbar-height' etc.) is | |
173 greater than 0; [c] its contents (`default-toolbar' etc.) are non-nil. | |
174 | |
175 The position-specific toolbars interact with the default specifications | |
176 as follows: If the value for a position-specific specifier is not | |
177 defined in a particular domain (usually a window), and the position of | |
178 that specifier is set as the default position (using | |
179 `default-toolbar-position'), then the value from the corresponding | |
180 default specifier in that domain will be used. The gutters work the | |
181 same. | |
182 | |
183 | |
184 THE PANED AREA | |
185 -------------- | |
186 | |
187 The area occupied by the "windows" is called the paned area. Note that | |
188 this includes the minibuffer, which is just another window but is | |
189 special-cased in XEmacs. Each window can include a horizontal and/or | |
190 vertical scrollbar, a modeline and a vertical divider to its right, as | |
191 well as the text area. Only non-rightmost windows can include a | |
192 vertical divider. (The minibuffer normally does not include either | |
193 modeline or scrollbars.) | |
194 | |
195 Note that, because the toolbars and gutters are controlled by | |
196 specifiers, and specifiers can have window-specific and buffer-specific | |
197 values, the size of the paned area can change depending on which window | |
198 is selected: In other words, if the selected window or buffer changes, | |
199 the entire paned area for the frame may change. | |
200 | |
201 | |
202 TEXT AREAS, FRINGES, MARGINS | |
203 ---------------------------- | |
204 | |
205 The space occupied by a window can be divided into the text area and the | |
206 fringes. The fringes include the modeline, scrollbars and vertical | |
207 divider on the right side (if any); inside of this is the text area, | |
208 where the text actually occurs. Note that a window may or may not | |
209 contain any of the elements that are part of the fringe -- this is | |
210 controlled by specifiers, e.g. `has-modeline-p', | |
211 `horizontal-scrollbar-visible-p', `vertical-scrollbar-visible-p', | |
212 `vertical-divider-always-visible-p', etc. | |
213 | |
214 In addition, it is possible to set margins in the text area using the | |
215 specifiers `left-margin-width' and `right-margin-width'. When this is | |
216 done, only the "inner text area" (the area inside of the margins) will | |
217 be used for normal display of text; the margins will be used for glyphs | |
218 with a layout policy of `outside-margin' (as set on an extent containing | |
219 the glyph by `set-extent-begin-glyph-layout' or | |
220 `set-extent-end-glyph-layout'). However, the calculation of the text | |
221 area size (e.g. in the function `window-text-area-width') includes the | |
222 margins. Which margin is used depends on whether a glyph has been set | |
223 as the begin-glyph or end-glyph of an extent (`set-extent-begin-glyph' | |
224 etc.), using the left and right margins, respectively. | |
225 | |
226 Technically, the margins outside of the inner text area are known as the | |
227 "outside margins". The "inside margins" are in the inner text area and | |
228 constitute the whitespace between the outside margins and the first or | |
229 last non-whitespace character in a line; their width can vary from line | |
230 to line. Glyphs will be placed in the inside margin if their layout | |
231 policy is `inside-margin' or `whitespace', with `whitespace' glyphs on | |
232 the inside and `inside-margin' glyphs on the outside. Inside-margin | |
233 glyphs can spill over into the outside margin if `use-left-overflow' or | |
234 `use-right-overflow', respectively, is non-nil. | |
235 | |
236 See the Lisp Reference manual, under Annotations, for more details. | |
237 | |
238 | |
239 THE DISPLAYABLE AREA | |
240 -------------------- | |
241 | |
242 The "displayable area" is not so much an actual area as a convenient | |
243 fiction. It is the area used to convert between pixel and character | |
244 dimensions for frames. The character dimensions for a frame (e.g. as | |
245 returned by `frame-width' and `frame-height' and set by | |
246 `set-frame-width' and `set-frame-height') are determined from the | |
247 displayable area by dividing by the pixel size of the default font as | |
248 instantiated in the frame. (For proportional fonts, the "average" width | |
249 is used. Under Windows, this is a built-in property of the fonts. | |
250 Under X, this is based on the width of the lowercase 'n', or if this is | |
251 zero then the width of the default character. [We prefer 'n' to the | |
252 specified default character because many X fonts have a default | |
253 character with a zero or otherwise non-representative width.]) | |
254 | |
255 The displayable area is essentially the "theoretical" paned area of the | |
256 frame excluding the rightmost and bottom-most scrollbars. In this | |
257 context, "theoretical" means that all calculations on based on | |
258 frame-level values for toolbar, gutter and scrollbar thicknesses. | |
259 Because these thicknesses are controlled by specifiers, and specifiers | |
260 can have window-specific and buffer-specific values, these calculations | |
261 may or may not reflect the actual size of the paned area or of the | |
262 scrollbars when any particular window is selected. Note also that the | |
263 "displayable area" may not even be contiguous! In particular, if the | |
264 frame-level value of the horizontal scrollbar height is non-zero, then | |
265 the displayable area includes the paned area above and below the bottom | |
266 horizontal scrollbar but not the scrollbar itself. | |
267 | |
268 As a further twist, the character-dimension calculations are adjusted so | |
269 that the truncation and continuation glyphs (see `truncation-glyph' and | |
270 `continuation-glyph') count as a single character even if they are wider | |
271 than the default font width. (Technically, the character width is | |
272 computed from the displayable-area width by subtracting the maximum of | |
273 the truncation-glyph width, continuation-glyph width and default-font | |
274 width before dividing by the default-font width, and then adding 1 to | |
275 the result.) (The ultimate motivation for this kludge as well as the | |
276 subtraction of the scrollbars, but not the minibuffer or bottom-most | |
277 modeline, is to maintain compatibility with TTY's.) | |
278 | |
279 Despite all these concerns and kludges, however, the "displayable area" | |
280 concept works well in practice and mostly ensures that by default the | |
281 frame will actually fit 79 characters + continuation/truncation glyph. | |
282 | |
283 | |
284 WHICH FUNCTIONS USE WHICH? | |
285 -------------------------- | |
286 | |
287 [1] Top-level window area: | |
288 | |
289 set-frame-position | |
290 `left' and `top' frame properties | |
291 | |
292 [2] Client area: | |
293 | |
294 frame-pixel-*, set-frame-pixel-* | |
295 | |
296 [3] Paned area: | |
297 | |
298 window-pixel-edges | |
299 event-x-pixel, event-y-pixel, event-properties, make-event | |
300 | |
301 [4] Displayable area: | |
302 | |
303 frame-width, frame-height and other all functions specifying frame size | |
304 in characters | |
305 frame-displayable-pixel-* | |
306 | |
307 --ben | |
308 | |
309 */ | |
26 | 310 |
27 #include <config.h> | 311 #include <config.h> |
28 #include "lisp.h" | 312 #include "lisp.h" |
29 | 313 |
30 #include "buffer.h" /* for Vbuffer_alist */ | 314 #include "buffer.h" /* for Vbuffer_alist */ |
118 Lisp_Object Vframe_being_created; | 402 Lisp_Object Vframe_being_created; |
119 Lisp_Object Qframe_being_created; | 403 Lisp_Object Qframe_being_created; |
120 | 404 |
121 static void store_minibuf_frame_prop (struct frame *f, Lisp_Object val); | 405 static void store_minibuf_frame_prop (struct frame *f, Lisp_Object val); |
122 | 406 |
123 typedef enum { | 407 typedef enum |
408 { | |
124 DISPLAYABLE_PIXEL_TO_CHAR, | 409 DISPLAYABLE_PIXEL_TO_CHAR, |
410 CHAR_TO_DISPLAYABLE_PIXEL, | |
125 TOTAL_PIXEL_TO_CHAR, | 411 TOTAL_PIXEL_TO_CHAR, |
126 CHAR_TO_TOTAL_PIXEL, | 412 CHAR_TO_TOTAL_PIXEL, |
127 CHAR_TO_DISPLAYABLE_PIXEL | 413 TOTAL_PIXEL_TO_DISPLAYABLE_PIXEL, |
128 } pixel_to_char_mode_t; | 414 DISPLAYABLE_PIXEL_TO_TOTAL_PIXEL, |
415 } | |
416 pixel_to_char_mode_t; | |
417 | |
418 enum frame_size_type | |
419 { | |
420 SIZE_TOTAL_PIXEL, | |
421 SIZE_DISPLAYABLE_PIXEL, | |
422 SIZE_CHAR_CELL, | |
423 SIZE_FRAME_UNIT, | |
424 }; | |
129 | 425 |
130 static void frame_conversion_internal (struct frame *f, | 426 static void frame_conversion_internal (struct frame *f, |
131 pixel_to_char_mode_t pixel_to_char, | 427 enum frame_size_type source, |
132 int *pixel_width, int *pixel_height, | 428 int source_width, int source_height, |
133 int *char_width, int *char_height, | 429 enum frame_size_type dest, |
134 int real_face); | 430 int *dest_width, int *dest_height); |
431 static void get_frame_char_size (struct frame *f, int *out_width, | |
432 int *out_height); | |
433 static void get_frame_displayable_pixel_size (struct frame *f, int *out_width, | |
434 int *out_height); | |
435 | |
135 static struct display_line title_string_display_line; | 436 static struct display_line title_string_display_line; |
136 /* Used by generate_title_string. Global because they get used so much that | 437 /* Used by generate_title_string. Global because they get used so much that |
137 the dynamic allocation time adds up. */ | 438 the dynamic allocation time adds up. */ |
138 static Ichar_dynarr *title_string_ichar_dynarr; | 439 static Ichar_dynarr *title_string_ichar_dynarr; |
139 | 440 |
656 { | 957 { |
657 reset_face_cachels (XWINDOW (f->minibuffer_window)); | 958 reset_face_cachels (XWINDOW (f->minibuffer_window)); |
658 reset_glyph_cachels (XWINDOW (f->minibuffer_window)); | 959 reset_glyph_cachels (XWINDOW (f->minibuffer_window)); |
659 } | 960 } |
660 | 961 |
661 change_frame_size (f, f->height, f->width, 0); | 962 change_frame_size (f, f->width, f->height, 0); |
662 } | 963 } |
663 | 964 |
664 MAYBE_FRAMEMETH (f, init_frame_2, (f, props)); | 965 MAYBE_FRAMEMETH (f, init_frame_2, (f, props)); |
665 Fset_frame_properties (frame, props); | 966 Fset_frame_properties (frame, props); |
666 MAYBE_FRAMEMETH (f, init_frame_3, (f)); | 967 MAYBE_FRAMEMETH (f, init_frame_3, (f)); |
701 will eventually do. Unfortunately gutter sizing code relies | 1002 will eventually do. Unfortunately gutter sizing code relies |
702 on the frame in question being visible so we can't do this | 1003 on the frame in question being visible so we can't do this |
703 earlier. */ | 1004 earlier. */ |
704 init_frame_gutters (f); | 1005 init_frame_gutters (f); |
705 | 1006 |
706 change_frame_size (f, f->height, f->width, 0); | 1007 change_frame_size (f, f->width, f->height, 0); |
707 } | 1008 } |
708 | 1009 |
709 if (first_frame_on_device) | 1010 if (first_frame_on_device) |
710 { | 1011 { |
711 if (first_frame_on_console) | 1012 if (first_frame_on_console) |
824 } | 1125 } |
825 | 1126 |
826 if (!keep_char_size) | 1127 if (!keep_char_size) |
827 { | 1128 { |
828 int height, width; | 1129 int height, width; |
829 pixel_to_char_size (f, FRAME_PIXWIDTH(f), FRAME_PIXHEIGHT(f), | 1130 pixel_to_frame_unit_size (f, FRAME_PIXWIDTH(f), FRAME_PIXHEIGHT(f), |
830 &width, &height); | 1131 &width, &height); |
831 change_frame_size (f, height, width, 0); | 1132 change_frame_size (f, width, height, 0); |
832 CLEAR_FRAME_SIZE_SLIPPED (f); | 1133 CLEAR_FRAME_SIZE_SLIPPED (f); |
833 } | 1134 } |
834 } | 1135 } |
835 | 1136 |
836 /* | 1137 /* |
2307 | 2608 |
2308 | 2609 |
2309 /***************************************************************************/ | 2610 /***************************************************************************/ |
2310 /* frame properties */ | 2611 /* frame properties */ |
2311 /***************************************************************************/ | 2612 /***************************************************************************/ |
2312 | |
2313 static void internal_set_frame_size (struct frame *f, int cols, int rows, | |
2314 int pretend); | |
2315 | 2613 |
2316 static void | 2614 static void |
2317 store_minibuf_frame_prop (struct frame *f, Lisp_Object val) | 2615 store_minibuf_frame_prop (struct frame *f, Lisp_Object val) |
2318 { | 2616 { |
2319 /* This can call Lisp. */ | 2617 /* This can call Lisp. */ |
2605 | 2903 |
2606 if (EQ (Qname, property)) return f->name; | 2904 if (EQ (Qname, property)) return f->name; |
2607 | 2905 |
2608 if (EQ (Qheight, property) || EQ (Qwidth, property)) | 2906 if (EQ (Qheight, property) || EQ (Qwidth, property)) |
2609 { | 2907 { |
2610 if (window_system_pixelated_geometry (frame)) | 2908 int width, height; |
2611 { | 2909 get_frame_char_size (f, &width, &height); |
2612 int width, height; | 2910 return make_int (EQ (Qheight, property) ? height : width); |
2613 pixel_to_real_char_size (f, FRAME_PIXWIDTH (f), FRAME_PIXHEIGHT (f), | |
2614 &width, &height); | |
2615 return make_int (EQ (Qheight, property) ? height: width); | |
2616 } | |
2617 else | |
2618 return make_int (EQ (Qheight, property) ? | |
2619 FRAME_HEIGHT (f) : | |
2620 FRAME_WIDTH (f)); | |
2621 } | 2911 } |
2622 | 2912 |
2623 /* NOTE: FSF returns Qnil instead of Qt for FRAME_HAS_MINIBUF_P. | 2913 /* NOTE: FSF returns Qnil instead of Qt for FRAME_HAS_MINIBUF_P. |
2624 This is over-the-top bogosity, because it's inconsistent with | 2914 This is over-the-top bogosity, because it's inconsistent with |
2625 the semantics of `minibuffer' when passed to `make-frame'. | 2915 the semantics of `minibuffer' when passed to `make-frame'. |
2707 FRAME_HAS_MINIBUF_P (f) ? Qt : | 2997 FRAME_HAS_MINIBUF_P (f) ? Qt : |
2708 FRAME_MINIBUF_WINDOW (f)), | 2998 FRAME_MINIBUF_WINDOW (f)), |
2709 result); | 2999 result); |
2710 { | 3000 { |
2711 int width, height; | 3001 int width, height; |
2712 | 3002 get_frame_char_size (f, &width, &height); |
2713 if (window_system_pixelated_geometry (frame)) | |
2714 { | |
2715 pixel_to_real_char_size (f, FRAME_PIXWIDTH (f), FRAME_PIXHEIGHT (f), | |
2716 &width, &height); | |
2717 } | |
2718 else | |
2719 { | |
2720 height = FRAME_HEIGHT (f); | |
2721 width = FRAME_WIDTH (f); | |
2722 } | |
2723 result = cons3 (Qwidth , make_int (width), result); | 3003 result = cons3 (Qwidth , make_int (width), result); |
2724 result = cons3 (Qheight, make_int (height), result); | 3004 result = cons3 (Qheight, make_int (height), result); |
2725 } | 3005 } |
2726 | 3006 |
2727 result = cons3 (Qname, f->name, result); | 3007 result = cons3 (Qname, f->name, result); |
2743 Return the height of the displayable area in pixels of FRAME. | 3023 Return the height of the displayable area in pixels of FRAME. |
2744 */ | 3024 */ |
2745 (frame)) | 3025 (frame)) |
2746 { | 3026 { |
2747 struct frame *f = decode_frame (frame); | 3027 struct frame *f = decode_frame (frame); |
2748 int height, pheight; | 3028 int width, height; |
2749 frame = wrap_frame (f); | 3029 |
2750 | 3030 get_frame_displayable_pixel_size (f, &width, &height); |
2751 if (!window_system_pixelated_geometry (frame)) | 3031 return make_int (height); |
2752 { | |
2753 height = FRAME_HEIGHT (f); | |
2754 | |
2755 frame_conversion_internal (f, CHAR_TO_DISPLAYABLE_PIXEL, | |
2756 0, &pheight, 0, &height, 0); | |
2757 } | |
2758 else | |
2759 pheight = FRAME_PIXHEIGHT (f); | |
2760 | |
2761 return make_int (pheight); | |
2762 } | 3032 } |
2763 | 3033 |
2764 DEFUN ("frame-pixel-width", Fframe_pixel_width, 0, 1, 0, /* | 3034 DEFUN ("frame-pixel-width", Fframe_pixel_width, 0, 1, 0, /* |
2765 Return the total width in pixels of FRAME. | 3035 Return the total width in pixels of FRAME. |
2766 */ | 3036 */ |
2773 Return the width of the displayable area in pixels of FRAME. | 3043 Return the width of the displayable area in pixels of FRAME. |
2774 */ | 3044 */ |
2775 (frame)) | 3045 (frame)) |
2776 { | 3046 { |
2777 struct frame *f = decode_frame (frame); | 3047 struct frame *f = decode_frame (frame); |
2778 int width, pwidth; | 3048 int width, height; |
2779 frame = wrap_frame (f); | 3049 |
2780 | 3050 get_frame_displayable_pixel_size (f, &width, &height); |
2781 if (!window_system_pixelated_geometry (frame)) | 3051 return make_int (width); |
2782 { | |
2783 width = FRAME_WIDTH (f); | |
2784 | |
2785 frame_conversion_internal (f, CHAR_TO_DISPLAYABLE_PIXEL, | |
2786 &pwidth, 0, &width, 0, 0); | |
2787 } | |
2788 else | |
2789 pwidth = FRAME_PIXWIDTH (f); | |
2790 | |
2791 return make_int (pwidth); | |
2792 } | 3052 } |
2793 | 3053 |
2794 DEFUN ("frame-name", Fframe_name, 0, 1, 0, /* | 3054 DEFUN ("frame-name", Fframe_name, 0, 1, 0, /* |
2795 Return the name of FRAME (defaulting to the selected frame). | 3055 Return the name of FRAME (defaulting to the selected frame). |
2796 This is not the same as the `title' of the frame. | 3056 This is not the same as the `title' of the frame. |
2812 (frame)) | 3072 (frame)) |
2813 { | 3073 { |
2814 return make_int (decode_frame (frame)->modiff); | 3074 return make_int (decode_frame (frame)->modiff); |
2815 } | 3075 } |
2816 | 3076 |
2817 static void | 3077 void |
2818 internal_set_frame_size (struct frame *f, int cols, int rows, int pretend) | 3078 internal_set_frame_size (struct frame *f, int cols, int rows, int pretend) |
2819 { | 3079 { |
2820 /* This can call Lisp. See mswindows_set_frame_size(). */ | 3080 /* This can call Lisp. See mswindows_set_frame_size(). */ |
2821 /* An explicit size change cancels any pending frame size adjustment */ | 3081 /* An explicit size change cancels any pending frame size adjustment */ |
2822 CLEAR_FRAME_SIZE_SLIPPED (f); | 3082 CLEAR_FRAME_SIZE_SLIPPED (f); |
2823 | 3083 |
2824 if (pretend || !HAS_FRAMEMETH_P (f, set_frame_size)) | 3084 if (pretend || !HAS_FRAMEMETH_P (f, set_frame_size)) |
2825 change_frame_size (f, rows, cols, 0); | 3085 change_frame_size (f, cols, rows, 0); |
2826 else | 3086 else |
2827 FRAMEMETH (f, set_frame_size, (f, cols, rows)); | 3087 FRAMEMETH (f, set_frame_size, (f, cols, rows)); |
2828 } | 3088 } |
2829 | 3089 |
2830 DEFUN ("set-frame-height", Fset_frame_height, 2, 3, 0, /* | 3090 DEFUN ("set-frame-height", Fset_frame_height, 2, 3, 0, /* |
2834 */ | 3094 */ |
2835 (frame, lines, pretend)) | 3095 (frame, lines, pretend)) |
2836 { | 3096 { |
2837 /* This can call Lisp. */ | 3097 /* This can call Lisp. */ |
2838 struct frame *f = decode_frame (frame); | 3098 struct frame *f = decode_frame (frame); |
2839 int height, width; | 3099 int cwidth, cheight; |
2840 frame = wrap_frame (f); | 3100 int guwidth, guheight; |
3101 | |
2841 CHECK_INT (lines); | 3102 CHECK_INT (lines); |
2842 | 3103 get_frame_char_size (f, &cwidth, &cheight); |
2843 if (window_system_pixelated_geometry (frame)) | 3104 cheight = XINT (lines); |
2844 { | 3105 frame_conversion_internal (f, SIZE_CHAR_CELL, cwidth, cheight, |
2845 char_to_real_pixel_size (f, 0, XINT (lines), 0, &height); | 3106 SIZE_FRAME_UNIT, &guwidth, &guheight); |
2846 width = FRAME_PIXWIDTH (f); | 3107 internal_set_frame_size (f, guwidth, guheight, !NILP (pretend)); |
2847 } | 3108 return wrap_frame (f); |
2848 else | |
2849 { | |
2850 height = XINT (lines); | |
2851 width = FRAME_WIDTH (f); | |
2852 } | |
2853 | |
2854 internal_set_frame_size (f, width, height, !NILP (pretend)); | |
2855 return frame; | |
2856 } | 3109 } |
2857 | 3110 |
2858 DEFUN ("set-frame-pixel-height", Fset_frame_pixel_height, 2, 3, 0, /* | 3111 DEFUN ("set-frame-pixel-height", Fset_frame_pixel_height, 2, 3, 0, /* |
2859 Specify that the frame FRAME is a total of HEIGHT pixels tall. | 3112 Specify that the frame FRAME is a total of HEIGHT pixels tall. |
2860 Optional third arg non-nil means that redisplay should be HEIGHT pixels tall | 3113 Optional third arg non-nil means that redisplay should be HEIGHT pixels tall |
2862 */ | 3115 */ |
2863 (frame, height, pretend)) | 3116 (frame, height, pretend)) |
2864 { | 3117 { |
2865 /* This can call Lisp. */ | 3118 /* This can call Lisp. */ |
2866 struct frame *f = decode_frame (frame); | 3119 struct frame *f = decode_frame (frame); |
2867 int pheight, width; | 3120 int pwidth, pheight; |
2868 frame = wrap_frame (f); | 3121 int guwidth, guheight; |
3122 | |
2869 CHECK_INT (height); | 3123 CHECK_INT (height); |
2870 | 3124 pheight = XINT (height); |
2871 if (!window_system_pixelated_geometry (frame)) | 3125 pwidth = FRAME_PIXWIDTH (f); |
2872 { | 3126 frame_conversion_internal (f, SIZE_TOTAL_PIXEL, pwidth, pheight, |
2873 int h = XINT (height); | 3127 SIZE_FRAME_UNIT, &guwidth, &guheight); |
2874 width = FRAME_WIDTH (f); | 3128 internal_set_frame_size (f, guwidth, guheight, !NILP (pretend)); |
2875 | 3129 return wrap_frame (f); |
2876 frame_conversion_internal (f, TOTAL_PIXEL_TO_CHAR, 0, &h, 0, &pheight, 0); | |
2877 } | |
2878 else | |
2879 { | |
2880 width = FRAME_PIXWIDTH (f); | |
2881 pheight = XINT (height); | |
2882 } | |
2883 | |
2884 internal_set_frame_size (f, width, pheight, !NILP (pretend)); | |
2885 return frame; | |
2886 } | 3130 } |
2887 | 3131 |
2888 DEFUN ("set-frame-displayable-pixel-height", Fset_frame_displayable_pixel_height, 2, 3, 0, /* | 3132 DEFUN ("set-frame-displayable-pixel-height", Fset_frame_displayable_pixel_height, 2, 3, 0, /* |
2889 Specify that the displayable area of frame FRAME is HEIGHT pixels tall. | 3133 Specify that the displayable area of frame FRAME is HEIGHT pixels tall. |
2890 Optional third arg non-nil means that redisplay should be HEIGHT pixels tall | 3134 Optional third arg non-nil means that redisplay should be HEIGHT pixels tall |
2892 */ | 3136 */ |
2893 (frame, height, pretend)) | 3137 (frame, height, pretend)) |
2894 { | 3138 { |
2895 /* This can call Lisp. */ | 3139 /* This can call Lisp. */ |
2896 struct frame *f = decode_frame (frame); | 3140 struct frame *f = decode_frame (frame); |
2897 int pheight, width; | 3141 int pwidth, pheight; |
2898 frame = wrap_frame (f); | 3142 int guwidth, guheight; |
3143 | |
2899 CHECK_INT (height); | 3144 CHECK_INT (height); |
2900 | 3145 get_frame_displayable_pixel_size (f, &pwidth, &pheight); |
2901 if (!window_system_pixelated_geometry (frame)) | 3146 pheight = XINT (height); |
2902 { | 3147 frame_conversion_internal (f, SIZE_DISPLAYABLE_PIXEL, pwidth, pheight, |
2903 int h = XINT (height); | 3148 SIZE_FRAME_UNIT, &guwidth, &guheight); |
2904 width = FRAME_WIDTH (f); | 3149 internal_set_frame_size (f, guwidth, guheight, !NILP (pretend)); |
2905 frame_conversion_internal (f, DISPLAYABLE_PIXEL_TO_CHAR, 0, &h, 0, &pheight, 0); | 3150 return wrap_frame (f); |
2906 } | |
2907 else | |
2908 { | |
2909 width = FRAME_PIXWIDTH (f); | |
2910 pheight = XINT (height); | |
2911 } | |
2912 | |
2913 internal_set_frame_size (f, width, pheight, !NILP (pretend)); | |
2914 return frame; | |
2915 } | 3151 } |
2916 | 3152 |
2917 | 3153 |
2918 DEFUN ("set-frame-width", Fset_frame_width, 2, 3, 0, /* | 3154 DEFUN ("set-frame-width", Fset_frame_width, 2, 3, 0, /* |
2919 Specify that the frame FRAME has COLS columns. | 3155 Specify that the frame FRAME has COLS columns. |
2922 */ | 3158 */ |
2923 (frame, cols, pretend)) | 3159 (frame, cols, pretend)) |
2924 { | 3160 { |
2925 /* This can call Lisp. */ | 3161 /* This can call Lisp. */ |
2926 struct frame *f = decode_frame (frame); | 3162 struct frame *f = decode_frame (frame); |
2927 int width, height; | 3163 int cwidth, cheight; |
2928 frame = wrap_frame (f); | 3164 int guwidth, guheight; |
3165 | |
2929 CHECK_INT (cols); | 3166 CHECK_INT (cols); |
2930 | 3167 get_frame_char_size (f, &cwidth, &cheight); |
2931 if (window_system_pixelated_geometry (frame)) | 3168 cwidth = XINT (cols); |
2932 { | 3169 frame_conversion_internal (f, SIZE_CHAR_CELL, cwidth, cheight, |
2933 char_to_real_pixel_size (f, XINT (cols), 0, &width, 0); | 3170 SIZE_FRAME_UNIT, &guwidth, &guheight); |
2934 height = FRAME_PIXHEIGHT (f); | 3171 internal_set_frame_size (f, guwidth, guheight, !NILP (pretend)); |
2935 } | 3172 return wrap_frame (f); |
2936 else | |
2937 { | |
2938 width = XINT (cols); | |
2939 height = FRAME_HEIGHT (f); | |
2940 } | |
2941 | |
2942 internal_set_frame_size (f, width, height, !NILP (pretend)); | |
2943 return frame; | |
2944 } | 3173 } |
2945 | 3174 |
2946 DEFUN ("set-frame-pixel-width", Fset_frame_pixel_width, 2, 3, 0, /* | 3175 DEFUN ("set-frame-pixel-width", Fset_frame_pixel_width, 2, 3, 0, /* |
2947 Specify that the frame FRAME is a total of WIDTH pixels wide. | 3176 Specify that the frame FRAME is a total of WIDTH pixels wide. |
2948 Optional third arg non-nil means that redisplay should be WIDTH wide | 3177 Optional third arg non-nil means that redisplay should be WIDTH wide |
2950 */ | 3179 */ |
2951 (frame, width, pretend)) | 3180 (frame, width, pretend)) |
2952 { | 3181 { |
2953 /* This can call Lisp. */ | 3182 /* This can call Lisp. */ |
2954 struct frame *f = decode_frame (frame); | 3183 struct frame *f = decode_frame (frame); |
2955 int height, pwidth; | 3184 int pwidth, pheight; |
2956 frame = wrap_frame (f); | 3185 int guwidth, guheight; |
3186 | |
2957 CHECK_INT (width); | 3187 CHECK_INT (width); |
2958 | 3188 pwidth = XINT (width); |
2959 if (!window_system_pixelated_geometry (frame)) | 3189 pheight = FRAME_PIXHEIGHT (f); |
2960 { | 3190 frame_conversion_internal (f, SIZE_TOTAL_PIXEL, pwidth, pheight, |
2961 int w = XINT (width); | 3191 SIZE_FRAME_UNIT, &guwidth, &guheight); |
2962 height = FRAME_HEIGHT (f); | 3192 internal_set_frame_size (f, guwidth, guheight, !NILP (pretend)); |
2963 frame_conversion_internal (f, TOTAL_PIXEL_TO_CHAR, &w, 0, &pwidth, 0, 0); | 3193 return wrap_frame (f); |
2964 } | |
2965 else | |
2966 { | |
2967 height = FRAME_PIXHEIGHT (f); | |
2968 pwidth = XINT (width); | |
2969 } | |
2970 | |
2971 internal_set_frame_size (f, pwidth, height, !NILP (pretend)); | |
2972 return frame; | |
2973 } | 3194 } |
2974 | 3195 |
2975 DEFUN ("set-frame-displayable-pixel-width", Fset_frame_displayable_pixel_width, 2, 3, 0, /* | 3196 DEFUN ("set-frame-displayable-pixel-width", Fset_frame_displayable_pixel_width, 2, 3, 0, /* |
2976 Specify that the displayable area of frame FRAME is WIDTH pixels wide. | 3197 Specify that the displayable area of frame FRAME is WIDTH pixels wide. |
2977 Optional third arg non-nil means that redisplay should be WIDTH wide | 3198 Optional third arg non-nil means that redisplay should be WIDTH wide |
2979 */ | 3200 */ |
2980 (frame, width, pretend)) | 3201 (frame, width, pretend)) |
2981 { | 3202 { |
2982 /* This can call Lisp. */ | 3203 /* This can call Lisp. */ |
2983 struct frame *f = decode_frame (frame); | 3204 struct frame *f = decode_frame (frame); |
2984 int height, pwidth; | 3205 int pwidth, pheight; |
2985 frame = wrap_frame (f); | 3206 int guwidth, guheight; |
3207 | |
2986 CHECK_INT (width); | 3208 CHECK_INT (width); |
2987 | 3209 get_frame_displayable_pixel_size (f, &pwidth, &pheight); |
2988 if (!window_system_pixelated_geometry (frame)) | 3210 pwidth = XINT (width); |
2989 { | 3211 frame_conversion_internal (f, SIZE_DISPLAYABLE_PIXEL, pwidth, pheight, |
2990 int w = XINT (width); | 3212 SIZE_FRAME_UNIT, &guwidth, &guheight); |
2991 height = FRAME_HEIGHT (f); | 3213 internal_set_frame_size (f, guwidth, guheight, !NILP (pretend)); |
2992 frame_conversion_internal (f, DISPLAYABLE_PIXEL_TO_CHAR, &w, 0, &pwidth, 0, 0); | 3214 return wrap_frame (f); |
2993 } | |
2994 else | |
2995 { | |
2996 height = FRAME_PIXHEIGHT (f); | |
2997 pwidth = XINT (width); | |
2998 } | |
2999 | |
3000 internal_set_frame_size (f, pwidth, height, !NILP (pretend)); | |
3001 return frame; | |
3002 } | 3215 } |
3003 | 3216 |
3004 DEFUN ("set-frame-size", Fset_frame_size, 3, 4, 0, /* | 3217 DEFUN ("set-frame-size", Fset_frame_size, 3, 4, 0, /* |
3005 Set the size of FRAME to COLS by ROWS, measured in characters. | 3218 Set the size of FRAME to COLS by ROWS, measured in characters. |
3006 Optional fourth arg non-nil means that redisplay should use COLS by ROWS | 3219 Optional fourth arg non-nil means that redisplay should use COLS by ROWS |
3008 */ | 3221 */ |
3009 (frame, cols, rows, pretend)) | 3222 (frame, cols, rows, pretend)) |
3010 { | 3223 { |
3011 /* This can call Lisp. */ | 3224 /* This can call Lisp. */ |
3012 struct frame *f = decode_frame (frame); | 3225 struct frame *f = decode_frame (frame); |
3013 int height, width; | 3226 int guwidth, guheight; |
3014 frame = wrap_frame (f); | 3227 |
3015 CHECK_INT (cols); | 3228 CHECK_INT (cols); |
3016 CHECK_INT (rows); | 3229 CHECK_INT (rows); |
3017 | 3230 frame_conversion_internal (f, SIZE_CHAR_CELL, XINT (cols), XINT (rows), |
3018 if (window_system_pixelated_geometry (frame)) | 3231 SIZE_FRAME_UNIT, &guwidth, &guheight); |
3019 char_to_real_pixel_size (f, XINT (cols), XINT (rows), &width, &height); | 3232 internal_set_frame_size (f, guwidth, guheight, !NILP (pretend)); |
3020 else | 3233 return wrap_frame (f); |
3021 { | |
3022 height = XINT (rows); | |
3023 width = XINT (cols); | |
3024 } | |
3025 | |
3026 internal_set_frame_size (f, width, height, !NILP (pretend)); | |
3027 return frame; | |
3028 } | 3234 } |
3029 | 3235 |
3030 DEFUN ("set-frame-pixel-size", Fset_frame_pixel_size, 3, 4, 0, /* | 3236 DEFUN ("set-frame-pixel-size", Fset_frame_pixel_size, 3, 4, 0, /* |
3031 Set the total size of FRAME to WIDTH by HEIGHT, measured in pixels. | 3237 Set the total size of FRAME to WIDTH by HEIGHT, measured in pixels. |
3032 Optional fourth arg non-nil means that redisplay should use WIDTH by HEIGHT | 3238 Optional fourth arg non-nil means that redisplay should use WIDTH by HEIGHT |
3034 */ | 3240 */ |
3035 (frame, width, height, pretend)) | 3241 (frame, width, height, pretend)) |
3036 { | 3242 { |
3037 /* This can call Lisp. */ | 3243 /* This can call Lisp. */ |
3038 struct frame *f = decode_frame (frame); | 3244 struct frame *f = decode_frame (frame); |
3039 int pheight, pwidth; | 3245 int guwidth, guheight; |
3040 frame = wrap_frame (f); | 3246 |
3041 CHECK_INT (width); | 3247 CHECK_INT (width); |
3042 CHECK_INT (height); | 3248 CHECK_INT (height); |
3043 | 3249 frame_conversion_internal (f, SIZE_TOTAL_PIXEL, XINT (width), XINT (height), |
3044 if (!window_system_pixelated_geometry (frame)) | 3250 SIZE_FRAME_UNIT, &guwidth, &guheight); |
3045 { | 3251 internal_set_frame_size (f, guwidth, guheight, !NILP (pretend)); |
3046 int w = XINT (width); | 3252 return wrap_frame (f); |
3047 int h = XINT (height); | |
3048 frame_conversion_internal (f, TOTAL_PIXEL_TO_CHAR, &w, &h, &pwidth, &pheight, 0); | |
3049 } | |
3050 else | |
3051 { | |
3052 pheight = XINT (height); | |
3053 pwidth = XINT (width); | |
3054 } | |
3055 | |
3056 internal_set_frame_size (f, pwidth, pheight, !NILP (pretend)); | |
3057 return frame; | |
3058 } | 3253 } |
3059 | 3254 |
3060 DEFUN ("set-frame-displayable-pixel-size", Fset_frame_displayable_pixel_size, 3, 4, 0, /* | 3255 DEFUN ("set-frame-displayable-pixel-size", Fset_frame_displayable_pixel_size, 3, 4, 0, /* |
3061 Set the displayable size of FRAME to WIDTH by HEIGHT, measured in pixels. | 3256 Set the displayable size of FRAME to WIDTH by HEIGHT, measured in pixels. |
3062 Optional fourth arg non-nil means that redisplay should use WIDTH by HEIGHT | 3257 Optional fourth arg non-nil means that redisplay should use WIDTH by HEIGHT |
3064 */ | 3259 */ |
3065 (frame, width, height, pretend)) | 3260 (frame, width, height, pretend)) |
3066 { | 3261 { |
3067 /* This can call Lisp. */ | 3262 /* This can call Lisp. */ |
3068 struct frame *f = decode_frame (frame); | 3263 struct frame *f = decode_frame (frame); |
3069 int pheight, pwidth; | 3264 int guwidth, guheight; |
3070 frame = wrap_frame (f); | 3265 |
3071 CHECK_INT (width); | 3266 CHECK_INT (width); |
3072 CHECK_INT (height); | 3267 CHECK_INT (height); |
3073 | 3268 frame_conversion_internal (f, SIZE_DISPLAYABLE_PIXEL, |
3074 if (!window_system_pixelated_geometry (frame)) | 3269 XINT (width), XINT (height), |
3075 { | 3270 SIZE_FRAME_UNIT, &guwidth, &guheight); |
3076 int w = XINT (width); | 3271 internal_set_frame_size (f, guwidth, guheight, !NILP (pretend)); |
3077 int h = XINT (height); | 3272 return wrap_frame (f); |
3078 frame_conversion_internal (f, DISPLAYABLE_PIXEL_TO_CHAR, &w, &h, &pwidth, &pheight, 0); | |
3079 } | |
3080 else | |
3081 { | |
3082 pheight = XINT (height); | |
3083 pwidth = XINT (width); | |
3084 } | |
3085 | |
3086 internal_set_frame_size (f, pwidth, pheight, !NILP (pretend)); | |
3087 return frame; | |
3088 } | 3273 } |
3089 | 3274 |
3090 DEFUN ("set-frame-position", Fset_frame_position, 3, 3, 0, /* | 3275 DEFUN ("set-frame-position", Fset_frame_position, 3, 3, 0, /* |
3091 Set position of FRAME in pixels to XOFFSET by YOFFSET. | 3276 Set position of FRAME in pixels to XOFFSET by YOFFSET. |
3092 This is actually the position of the upper left corner of the frame. | 3277 This is actually the position of the upper left corner of the frame. |
3107 | 3292 |
3108 | 3293 |
3109 /* Frame size conversion functions moved here from EmacsFrame.c | 3294 /* Frame size conversion functions moved here from EmacsFrame.c |
3110 because they're generic and really don't belong in that file. | 3295 because they're generic and really don't belong in that file. |
3111 Function get_default_char_pixel_size() removed because it's | 3296 Function get_default_char_pixel_size() removed because it's |
3112 exactly the same as default_face_height_and_width(). */ | 3297 exactly the same as default_face_width_and_height(). |
3298 | |
3299 Convert between total pixel size, displayable pixel size and | |
3300 character-cell size. Variables are either "in" or "out" | |
3301 depending on the value of PIXEL_TO_CHAR. | |
3302 */ | |
3113 static void | 3303 static void |
3114 frame_conversion_internal (struct frame *f, | 3304 frame_conversion_internal_1 (struct frame *f, |
3115 pixel_to_char_mode_t pixel_to_char, | 3305 pixel_to_char_mode_t pixel_to_char, |
3116 int *pixel_width, int *pixel_height, | 3306 int *total_pixel_width, int *total_pixel_height, |
3117 int *char_width, int *char_height, | 3307 int *disp_pixel_width, int *disp_pixel_height, |
3118 int real_face) | 3308 int *char_width, int *char_height) |
3119 { | 3309 { |
3120 int cpw; | 3310 int cpw, cph; |
3121 int cph; | |
3122 int egw; | 3311 int egw; |
3123 int obw, obh, bdr; | 3312 int obw, obh, bdr; |
3124 Lisp_Object frame, window; | 3313 Lisp_Object frame, window; |
3125 | 3314 |
3126 frame = wrap_frame (f); | 3315 frame = wrap_frame (f); |
3127 if (real_face) | 3316 default_face_width_and_height (frame, &cpw, &cph); |
3128 default_face_height_and_width (frame, &cph, &cpw); | |
3129 else | |
3130 default_face_height_and_width_1 (frame, &cph, &cpw); | |
3131 | 3317 |
3132 window = FRAME_SELECTED_WINDOW (f); | 3318 window = FRAME_SELECTED_WINDOW (f); |
3133 | 3319 |
3320 /* #### It really seems like we should also be subtracting out the | |
3321 theoretical gutter width and height, just like we do for toolbars. | |
3322 There is currently a bug where if you call `set-frame-pixel-width' | |
3323 on MS Windows (at least, possibly also X) things get confused and | |
3324 the top of the root window overlaps the top gutter instead of being | |
3325 below it. This gets fixed next time you resize the frame using the | |
3326 mouse. Possibly this is caused by not handling the gutter height | |
3327 here? */ | |
3134 egw = max (glyph_width (Vcontinuation_glyph, window), | 3328 egw = max (glyph_width (Vcontinuation_glyph, window), |
3135 glyph_width (Vtruncation_glyph, window)); | 3329 glyph_width (Vtruncation_glyph, window)); |
3136 egw = max (egw, cpw); | 3330 egw = max (egw, cpw); |
3137 bdr = 2 * f->internal_border_width; | 3331 bdr = 2 * f->internal_border_width; |
3138 obw = FRAME_SCROLLBAR_WIDTH (f) + FRAME_THEORETICAL_LEFT_TOOLBAR_WIDTH (f) + | 3332 obw = FRAME_SCROLLBAR_WIDTH (f) + FRAME_THEORETICAL_LEFT_TOOLBAR_WIDTH (f) + |
3151 much space. */ | 3345 much space. */ |
3152 switch (pixel_to_char) | 3346 switch (pixel_to_char) |
3153 { | 3347 { |
3154 case DISPLAYABLE_PIXEL_TO_CHAR: | 3348 case DISPLAYABLE_PIXEL_TO_CHAR: |
3155 if (char_width) | 3349 if (char_width) |
3156 *char_width = ROUND_UP (*pixel_width, cpw) / cpw; | 3350 *char_width = ROUND_UP (*disp_pixel_width, cpw) / cpw; |
3157 if (char_height) | 3351 if (char_height) |
3158 *char_height = ROUND_UP (*pixel_height, cph) / cph; | 3352 *char_height = ROUND_UP (*disp_pixel_height, cph) / cph; |
3353 break; | |
3354 case CHAR_TO_DISPLAYABLE_PIXEL: | |
3355 if (disp_pixel_width) | |
3356 *disp_pixel_width = *char_width * cpw; | |
3357 if (disp_pixel_height) | |
3358 *disp_pixel_height = *char_height * cph; | |
3159 break; | 3359 break; |
3160 case TOTAL_PIXEL_TO_CHAR: | 3360 case TOTAL_PIXEL_TO_CHAR: |
3161 /* Convert to chars so that the total frame size is pixel_width x | 3361 /* Convert to chars so that the total frame size is pixel_width x |
3162 pixel_height. */ | 3362 pixel_height. */ |
3163 if (char_width) | 3363 if (char_width) |
3164 *char_width = 1 + ((*pixel_width - egw) - bdr - obw) / cpw; | 3364 *char_width = 1 + ((*total_pixel_width - egw) - bdr - obw) / cpw; |
3165 if (char_height) | 3365 if (char_height) |
3166 *char_height = (*pixel_height - bdr - obh) / cph; | 3366 *char_height = (*total_pixel_height - bdr - obh) / cph; |
3167 break; | 3367 break; |
3168 case CHAR_TO_TOTAL_PIXEL: | 3368 case CHAR_TO_TOTAL_PIXEL: |
3169 if (pixel_width) | 3369 if (total_pixel_width) |
3170 *pixel_width = (*char_width - 1) * cpw + egw + bdr + obw; | 3370 *total_pixel_width = (*char_width - 1) * cpw + egw + bdr + obw; |
3171 if (pixel_height) | 3371 if (total_pixel_height) |
3172 *pixel_height = *char_height * cph + bdr + obh; | 3372 *total_pixel_height = *char_height * cph + bdr + obh; |
3173 break; | 3373 break; |
3174 case CHAR_TO_DISPLAYABLE_PIXEL: | 3374 case TOTAL_PIXEL_TO_DISPLAYABLE_PIXEL: |
3175 if (pixel_width) | 3375 /* Convert to chars so that the total frame size is pixel_width x |
3176 *pixel_width = *char_width * cpw; | 3376 pixel_height. */ |
3177 if (pixel_height) | 3377 if (disp_pixel_width) |
3178 *pixel_height = *char_height * cph; | 3378 *disp_pixel_width = cpw + (*total_pixel_width - egw) - bdr - obw; |
3379 if (disp_pixel_height) | |
3380 *disp_pixel_height = *total_pixel_height - bdr - obh; | |
3179 break; | 3381 break; |
3180 } | 3382 case DISPLAYABLE_PIXEL_TO_TOTAL_PIXEL: |
3181 } | 3383 if (total_pixel_width) |
3182 | 3384 *total_pixel_width = *disp_pixel_width - cpw + egw + bdr + obw; |
3183 /* This takes the size in pixels of the text area, and returns the number | 3385 if (total_pixel_height) |
3386 *total_pixel_height = *disp_pixel_height + bdr + obh; | |
3387 break; | |
3388 } | |
3389 } | |
3390 | |
3391 | |
3392 static enum frame_size_type | |
3393 canonicalize_frame_size_type (enum frame_size_type type, int pixgeom) | |
3394 { | |
3395 if (type == SIZE_FRAME_UNIT) | |
3396 { | |
3397 if (pixgeom) | |
3398 type = SIZE_DISPLAYABLE_PIXEL; | |
3399 else | |
3400 type = SIZE_CHAR_CELL; | |
3401 } | |
3402 return type; | |
3403 } | |
3404 | |
3405 /* Basic frame conversion function. Convert source size to destination | |
3406 size, where either of them can be in total pixels, displayable pixels, | |
3407 frame units or character-cell units. */ | |
3408 | |
3409 static void | |
3410 frame_conversion_internal (struct frame *f, | |
3411 enum frame_size_type source, | |
3412 int source_width, int source_height, | |
3413 enum frame_size_type dest, | |
3414 int *dest_width, int *dest_height) | |
3415 { | |
3416 int pixgeom = window_system_pixelated_geometry (wrap_frame (f)); | |
3417 dest = canonicalize_frame_size_type (dest, pixgeom); | |
3418 source = canonicalize_frame_size_type (source, pixgeom); | |
3419 if (source == dest) | |
3420 { | |
3421 *dest_width = source_width; | |
3422 *dest_height = source_height; | |
3423 } | |
3424 else if (source == SIZE_TOTAL_PIXEL && dest == SIZE_CHAR_CELL) | |
3425 frame_conversion_internal_1 (f, TOTAL_PIXEL_TO_CHAR, | |
3426 &source_width, &source_height, 0, 0, | |
3427 dest_width, dest_height); | |
3428 else if (source == SIZE_DISPLAYABLE_PIXEL && dest == SIZE_CHAR_CELL) | |
3429 frame_conversion_internal_1 (f, DISPLAYABLE_PIXEL_TO_CHAR, 0, 0, | |
3430 &source_width, &source_height, | |
3431 dest_width, dest_height); | |
3432 else if (source == SIZE_TOTAL_PIXEL && dest == SIZE_DISPLAYABLE_PIXEL) | |
3433 frame_conversion_internal_1 (f, TOTAL_PIXEL_TO_DISPLAYABLE_PIXEL, | |
3434 &source_width, &source_height, | |
3435 dest_width, dest_height, 0, 0); | |
3436 else if (dest == SIZE_TOTAL_PIXEL && source == SIZE_CHAR_CELL) | |
3437 frame_conversion_internal_1 (f, CHAR_TO_TOTAL_PIXEL, | |
3438 dest_width, dest_height, 0, 0, | |
3439 &source_width, &source_height); | |
3440 else if (dest == SIZE_DISPLAYABLE_PIXEL && source == SIZE_CHAR_CELL) | |
3441 frame_conversion_internal_1 (f, CHAR_TO_DISPLAYABLE_PIXEL, 0, 0, | |
3442 dest_width, dest_height, | |
3443 &source_width, &source_height); | |
3444 else if (dest == SIZE_TOTAL_PIXEL && source == SIZE_DISPLAYABLE_PIXEL) | |
3445 frame_conversion_internal_1 (f, DISPLAYABLE_PIXEL_TO_TOTAL_PIXEL, | |
3446 dest_width, dest_height, | |
3447 &source_width, &source_height, 0, 0); | |
3448 else | |
3449 { | |
3450 ABORT (); | |
3451 if (dest_width) | |
3452 *dest_width = 0; | |
3453 if (dest_height) | |
3454 *dest_height = 0; | |
3455 } | |
3456 } | |
3457 | |
3458 /* This takes the size in pixels of the client area, and returns the number | |
3184 of characters that will fit there, taking into account the internal | 3459 of characters that will fit there, taking into account the internal |
3185 border width, and the pixel width of the line terminator glyphs (which | 3460 border width, and the pixel width of the line terminator glyphs (which |
3186 always count as one "character" wide, even if they are not the same size | 3461 always count as one "character" wide, even if they are not the same size |
3187 as the default character size of the default font). The frame scrollbar | 3462 as the default character size of the default font). The frame scrollbar |
3188 width and left and right toolbar widths are also subtracted out of the | 3463 width and left and right toolbar widths are also subtracted out of the |
3189 available width. The frame scrollbar height and top and bottom toolbar | 3464 available width. The frame scrollbar height and top and bottom toolbar |
3190 heights are subtracted out of the available height. | 3465 heights are subtracted out of the available height. |
3191 | 3466 |
3192 Therefore the result is not necessarily a multiple of anything in | 3467 Therefore the result is not necessarily a multiple of anything in |
3193 particular. */ | 3468 particular. */ |
3469 | |
3194 void | 3470 void |
3195 pixel_to_char_size (struct frame *f, int pixel_width, int pixel_height, | 3471 pixel_to_char_size (struct frame *f, int pixel_width, int pixel_height, |
3196 int *char_width, int *char_height) | 3472 int *char_width, int *char_height) |
3197 { | 3473 { |
3198 frame_conversion_internal (f, TOTAL_PIXEL_TO_CHAR, | 3474 frame_conversion_internal (f, SIZE_TOTAL_PIXEL, pixel_width, pixel_height, |
3199 &pixel_width, &pixel_height, char_width, | 3475 SIZE_CHAR_CELL, char_width, char_height); |
3200 char_height, 0); | 3476 } |
3201 } | 3477 |
3202 | 3478 /* Given a character size, this returns the minimum pixel size of the |
3203 /* Given a character size, this returns the minimum number of pixels | 3479 client area necessary to display that many characters, taking into |
3204 necessary to display that many characters, taking into account the | 3480 account the internal border width, scrollbar height and width, toolbar |
3205 internal border width, scrollbar height and width, toolbar heights and | 3481 heights and widths and the size of the line terminator glyphs (assuming |
3206 widths and the size of the line terminator glyphs (assuming the line | 3482 the line terminators take up exactly one character position). |
3207 terminators take up exactly one character position). | |
3208 | 3483 |
3209 Therefore the result is not necessarily a multiple of anything in | 3484 Therefore the result is not necessarily a multiple of anything in |
3210 particular. */ | 3485 particular. */ |
3486 | |
3211 void | 3487 void |
3212 char_to_pixel_size (struct frame *f, int char_width, int char_height, | 3488 char_to_pixel_size (struct frame *f, int char_width, int char_height, |
3213 int *pixel_width, int *pixel_height) | 3489 int *pixel_width, int *pixel_height) |
3214 { | 3490 { |
3215 frame_conversion_internal (f, CHAR_TO_TOTAL_PIXEL, | 3491 frame_conversion_internal (f, SIZE_CHAR_CELL, char_width, char_height, |
3216 pixel_width, pixel_height, &char_width, | 3492 SIZE_TOTAL_PIXEL, pixel_width, pixel_height); |
3217 &char_height, 0); | 3493 } |
3218 } | 3494 |
3219 | 3495 /* Versions of the above that operate in "frame units" instead of |
3220 /* Given a pixel size, rounds DOWN to the smallest size in pixels necessary | 3496 characters. frame units are the same as characters except on |
3221 to display the same number of characters as are displayable now. | 3497 MS Windows and MS Printer frames, where they are displayable-area |
3222 */ | 3498 pixels. */ |
3499 | |
3500 void | |
3501 pixel_to_frame_unit_size (struct frame *f, int pixel_width, int pixel_height, | |
3502 int *frame_unit_width, int *frame_unit_height) | |
3503 { | |
3504 frame_conversion_internal (f, SIZE_TOTAL_PIXEL, pixel_width, pixel_height, | |
3505 SIZE_FRAME_UNIT, frame_unit_width, | |
3506 frame_unit_height); | |
3507 } | |
3508 | |
3509 void | |
3510 frame_unit_to_pixel_size (struct frame *f, int frame_unit_width, | |
3511 int frame_unit_height, | |
3512 int *pixel_width, int *pixel_height) | |
3513 { | |
3514 frame_conversion_internal (f, SIZE_FRAME_UNIT, frame_unit_width, | |
3515 frame_unit_height, | |
3516 SIZE_TOTAL_PIXEL, pixel_width, pixel_height); | |
3517 } | |
3518 | |
3223 void | 3519 void |
3224 round_size_to_char (struct frame *f, int in_width, int in_height, | 3520 round_size_to_char (struct frame *f, int in_width, int in_height, |
3225 int *out_width, int *out_height) | 3521 int *out_width, int *out_height) |
3226 { | 3522 { |
3227 int char_width; | 3523 int char_width; |
3228 int char_height; | 3524 int char_height; |
3229 pixel_to_char_size (f, in_width, in_height, &char_width, &char_height); | 3525 pixel_to_char_size (f, in_width, in_height, &char_width, &char_height); |
3230 char_to_pixel_size (f, char_width, char_height, out_width, out_height); | 3526 char_to_pixel_size (f, char_width, char_height, out_width, out_height); |
3231 } | 3527 } |
3232 | 3528 |
3233 /* Versions of the above which always account for real font metrics. | 3529 /* Get the frame size in character cells, recalculating on the fly. |
3234 */ | 3530 #### The logic of this function follows former logic elsewhere, |
3235 void | 3531 which used FRAME_PIXWIDTH() on pixelated-geometry systems but |
3236 pixel_to_real_char_size (struct frame *f, int pixel_width, int pixel_height, | 3532 FRAME_WIDTH() on non-pixelated-geometry systems. Not clear why not |
3237 int *char_width, int *char_height) | 3533 always just use one or the other. |
3238 { | 3534 |
3239 frame_conversion_internal (f, TOTAL_PIXEL_TO_CHAR, | 3535 Why don't we just use FRAME_CHARWIDTH() etc. in get_frame_char_size()? |
3240 &pixel_width, &pixel_height, char_width, | 3536 That wouldn't work because change_frame_size_1() depends on the |
3241 char_height, 1); | 3537 following function to *set* the values of FRAME_CHARWIDTH() etc. |
3242 } | 3538 |
3243 | 3539 But elsewhere I suppose we could use it. |
3244 void | 3540 */ |
3245 char_to_real_pixel_size (struct frame *f, int char_width, int char_height, | 3541 |
3246 int *pixel_width, int *pixel_height) | |
3247 { | |
3248 frame_conversion_internal (f, CHAR_TO_TOTAL_PIXEL, | |
3249 pixel_width, pixel_height, &char_width, | |
3250 &char_height, 1); | |
3251 } | |
3252 | |
3253 void | |
3254 round_size_to_real_char (struct frame *f, int in_width, int in_height, | |
3255 int *out_width, int *out_height) | |
3256 { | |
3257 int char_width; | |
3258 int char_height; | |
3259 pixel_to_real_char_size (f, in_width, in_height, &char_width, &char_height); | |
3260 char_to_real_pixel_size (f, char_width, char_height, out_width, out_height); | |
3261 } | |
3262 | |
3263 /* Change the frame height and/or width. Values may be given as zero to | |
3264 indicate no change is to take place. */ | |
3265 static void | 3542 static void |
3266 change_frame_size_1 (struct frame *f, int newheight, int newwidth) | 3543 get_frame_char_size (struct frame *f, int *out_width, int *out_height) |
3267 { | 3544 { |
3268 Lisp_Object frame; | 3545 if (window_system_pixelated_geometry (wrap_frame (f))) |
3546 pixel_to_char_size (f, FRAME_PIXWIDTH (f), FRAME_PIXHEIGHT (f), | |
3547 out_width, out_height); | |
3548 else | |
3549 { | |
3550 *out_width = FRAME_WIDTH (f); | |
3551 *out_height = FRAME_HEIGHT (f); | |
3552 } | |
3553 } | |
3554 | |
3555 static void | |
3556 get_frame_displayable_pixel_size (struct frame *f, int *out_width, | |
3557 int *out_height) | |
3558 { | |
3559 frame_conversion_internal (f, SIZE_FRAME_UNIT, FRAME_WIDTH (f), | |
3560 FRAME_HEIGHT (f), SIZE_DISPLAYABLE_PIXEL, | |
3561 out_width, out_height); | |
3562 } | |
3563 | |
3564 /* Change the frame height and/or width. Values passed in are in | |
3565 frame units (character cells on X/GTK, displayable-area pixels | |
3566 on MS Windows or generally on pixelated-geometry window systems). */ | |
3567 static void | |
3568 change_frame_size_1 (struct frame *f, int newwidth, int newheight) | |
3569 { | |
3269 int new_pixheight, new_pixwidth; | 3570 int new_pixheight, new_pixwidth; |
3270 int font_height, real_font_height, font_width; | 3571 int real_font_height, real_font_width; |
3271 | 3572 |
3272 /* #### Chuck -- shouldn't we be checking to see if the frame | 3573 /* #### Chuck -- shouldn't we be checking to see if the frame |
3273 is being "changed" to its existing size, and do nothing if so? */ | 3574 is being "changed" to its existing size, and do nothing if so? */ |
3274 /* No, because it would hose toolbar updates. The toolbar | 3575 /* No, because it would hose toolbar updates. The toolbar |
3275 update code relies on this function to cause window `top' and | 3576 update code relies on this function to cause window `top' and |
3276 `left' coordinates to be recomputed even though no frame size | 3577 `left' coordinates to be recomputed even though no frame size |
3277 change occurs. --kyle */ | 3578 change occurs. --kyle */ |
3278 assert (!in_display && !hold_frame_size_changes); | 3579 assert (!in_display && !hold_frame_size_changes); |
3279 | 3580 |
3280 frame = wrap_frame (f); | 3581 /* We no longer allow bogus values passed in. */ |
3281 | 3582 assert (newheight && newwidth); |
3282 default_face_height_and_width (frame, &real_font_height, 0); | 3583 |
3283 default_face_height_and_width_1 (frame, &font_height, &font_width); | 3584 default_face_width_and_height (wrap_frame (f), &real_font_width, |
3585 &real_font_height); | |
3586 | |
3587 frame_conversion_internal (f, SIZE_FRAME_UNIT, newwidth, newheight, | |
3588 SIZE_TOTAL_PIXEL, &new_pixwidth, | |
3589 &new_pixheight); | |
3284 | 3590 |
3285 /* This size-change overrides any pending one for this frame. */ | 3591 /* This size-change overrides any pending one for this frame. */ |
3286 f->size_change_pending = 0; | 3592 f->size_change_pending = 0; |
3287 FRAME_NEW_HEIGHT (f) = 0; | 3593 FRAME_NEW_HEIGHT (f) = 0; |
3288 FRAME_NEW_WIDTH (f) = 0; | 3594 FRAME_NEW_WIDTH (f) = 0; |
3289 | 3595 |
3290 new_pixheight = newheight * font_height; | 3596 /* We need to remove the boundaries of the paned area (see top of file) |
3291 new_pixwidth = (newwidth - 1) * font_width; | 3597 from the total-area pixel size, which is what we have now. |
3292 | 3598 |
3293 /* #### dependency on FRAME_WIN_P should be removed. */ | 3599 #### We should also be subtracting the internal borders. */ |
3294 if (FRAME_WIN_P (f)) | 3600 new_pixheight -= |
3295 { | 3601 (FRAME_REAL_TOP_TOOLBAR_BOUNDS (f) |
3296 new_pixheight += FRAME_SCROLLBAR_HEIGHT (f); | 3602 + FRAME_REAL_BOTTOM_TOOLBAR_BOUNDS (f) |
3297 new_pixwidth += FRAME_SCROLLBAR_WIDTH (f); | 3603 + FRAME_TOP_GUTTER_BOUNDS (f) |
3298 } | 3604 + FRAME_BOTTOM_GUTTER_BOUNDS (f)); |
3299 | 3605 |
3300 /* when frame_conversion_internal() calculated the number of rows/cols | 3606 new_pixwidth -= |
3301 in the frame, the theoretical toolbar sizes were subtracted out. | 3607 (FRAME_REAL_LEFT_TOOLBAR_BOUNDS (f) |
3302 The calculations below adjust for real toolbar height/width in | 3608 + FRAME_REAL_RIGHT_TOOLBAR_BOUNDS (f) |
3303 frame, which may be different from frame spec, taking the above | 3609 + FRAME_LEFT_GUTTER_BOUNDS (f) |
3304 fact into account */ | 3610 + FRAME_RIGHT_GUTTER_BOUNDS (f)); |
3305 new_pixheight += | 3611 |
3306 + FRAME_THEORETICAL_TOP_TOOLBAR_HEIGHT (f) | 3612 XWINDOW (FRAME_ROOT_WINDOW (f))->pixel_top |
3307 + 2 * FRAME_THEORETICAL_TOP_TOOLBAR_BORDER_WIDTH (f) | 3613 = FRAME_TOP_BORDER_END (f) + FRAME_TOP_GUTTER_BOUNDS (f); |
3308 - FRAME_REAL_TOP_TOOLBAR_HEIGHT (f) | 3614 |
3309 - 2 * FRAME_REAL_TOP_TOOLBAR_BORDER_WIDTH (f); | 3615 if (FRAME_HAS_MINIBUF_P (f) |
3310 | 3616 && ! FRAME_MINIBUF_ONLY_P (f)) |
3311 new_pixheight += | 3617 /* Frame has both root and minibuffer. */ |
3312 + FRAME_THEORETICAL_BOTTOM_TOOLBAR_HEIGHT (f) | 3618 { |
3313 + 2 * FRAME_THEORETICAL_BOTTOM_TOOLBAR_BORDER_WIDTH (f) | 3619 /* |
3314 - FRAME_REAL_BOTTOM_TOOLBAR_HEIGHT (f) | 3620 * Leave the minibuffer height the same if the frame has |
3315 - 2 * FRAME_REAL_BOTTOM_TOOLBAR_BORDER_WIDTH (f); | 3621 * been initialized, and the minibuffer height is tall |
3316 | 3622 * enough to display at least one line of text in the default |
3317 new_pixwidth += | 3623 * font, and the old minibuffer height is a multiple of the |
3318 + FRAME_THEORETICAL_LEFT_TOOLBAR_WIDTH (f) | 3624 * default font height. This should cause the minibuffer |
3319 + 2 * FRAME_THEORETICAL_LEFT_TOOLBAR_BORDER_WIDTH (f) | 3625 * height to be recomputed on font changes but not for |
3320 - FRAME_REAL_LEFT_TOOLBAR_WIDTH (f) | 3626 * other frame size changes, which seems reasonable. |
3321 - 2 * FRAME_REAL_LEFT_TOOLBAR_BORDER_WIDTH (f); | 3627 */ |
3322 | 3628 int old_minibuf_height = |
3323 new_pixwidth += | 3629 XWINDOW(FRAME_MINIBUF_WINDOW(f))->pixel_height; |
3324 + FRAME_THEORETICAL_RIGHT_TOOLBAR_WIDTH (f) | 3630 int minibuf_height = |
3325 + 2 * FRAME_THEORETICAL_RIGHT_TOOLBAR_BORDER_WIDTH (f) | 3631 f->init_finished && (old_minibuf_height % real_font_height) == 0 ? |
3326 - FRAME_REAL_RIGHT_TOOLBAR_WIDTH (f) | 3632 max(old_minibuf_height, real_font_height) : |
3327 - 2 * FRAME_REAL_RIGHT_TOOLBAR_BORDER_WIDTH (f); | 3633 real_font_height; |
3328 | 3634 set_window_pixheight (FRAME_ROOT_WINDOW (f), |
3329 /* Adjust the width for the end glyph which may be a different width | 3635 /* - font_height for minibuffer */ |
3330 than the default character width. */ | 3636 new_pixheight - minibuf_height, 0); |
3331 { | 3637 |
3332 int adjustment, trunc_width, cont_width; | 3638 XWINDOW (FRAME_MINIBUF_WINDOW (f))->pixel_top = |
3333 | 3639 FRAME_TOP_BORDER_END (f) + |
3334 trunc_width = glyph_width (Vtruncation_glyph, | 3640 FRAME_TOP_GUTTER_BOUNDS (f) + |
3335 FRAME_SELECTED_WINDOW (f)); | 3641 FRAME_BOTTOM_GUTTER_BOUNDS (f) + |
3336 cont_width = glyph_width (Vcontinuation_glyph, | 3642 new_pixheight - minibuf_height; |
3337 FRAME_SELECTED_WINDOW (f)); | 3643 |
3338 adjustment = max (trunc_width, cont_width); | 3644 set_window_pixheight (FRAME_MINIBUF_WINDOW (f), minibuf_height, 0); |
3339 adjustment = max (adjustment, font_width); | 3645 } |
3340 | 3646 else |
3341 new_pixwidth += adjustment; | 3647 /* Frame has just one top-level window. */ |
3342 } | 3648 set_window_pixheight (FRAME_ROOT_WINDOW (f), new_pixheight, 0); |
3343 | 3649 |
3344 /* If we don't have valid values, exit. */ | 3650 FRAME_HEIGHT (f) = newheight; |
3345 if (!new_pixheight && !new_pixwidth) | 3651 if (FRAME_TTY_P (f)) |
3346 return; | 3652 f->pixheight = newheight; |
3347 | 3653 |
3348 if (new_pixheight) | 3654 XWINDOW (FRAME_ROOT_WINDOW (f))->pixel_left = |
3349 { | 3655 FRAME_LEFT_BORDER_END (f) + FRAME_LEFT_GUTTER_BOUNDS (f); |
3350 /* Adjust for gutters here so that we always get set | 3656 set_window_pixwidth (FRAME_ROOT_WINDOW (f), new_pixwidth, 0); |
3351 properly. */ | 3657 |
3352 new_pixheight -= | 3658 if (FRAME_HAS_MINIBUF_P (f)) |
3353 (FRAME_TOP_GUTTER_BOUNDS (f) | 3659 { |
3354 + FRAME_BOTTOM_GUTTER_BOUNDS (f)); | 3660 XWINDOW (FRAME_MINIBUF_WINDOW (f))->pixel_left = |
3355 | |
3356 XWINDOW (FRAME_ROOT_WINDOW (f))->pixel_top | |
3357 = FRAME_TOP_BORDER_END (f) + FRAME_TOP_GUTTER_BOUNDS (f); | |
3358 | |
3359 if (FRAME_HAS_MINIBUF_P (f) | |
3360 && ! FRAME_MINIBUF_ONLY_P (f)) | |
3361 /* Frame has both root and minibuffer. */ | |
3362 { | |
3363 /* | |
3364 * Leave the minibuffer height the same if the frame has | |
3365 * been initialized, and the minibuffer height is tall | |
3366 * enough to display at least one line of text in the default | |
3367 * font, and the old minibuffer height is a multiple of the | |
3368 * default font height. This should cause the minibuffer | |
3369 * height to be recomputed on font changes but not for | |
3370 * other frame size changes, which seems reasonable. | |
3371 */ | |
3372 int old_minibuf_height = | |
3373 XWINDOW(FRAME_MINIBUF_WINDOW(f))->pixel_height; | |
3374 int minibuf_height = | |
3375 f->init_finished && (old_minibuf_height % real_font_height) == 0 ? | |
3376 max(old_minibuf_height, real_font_height) : | |
3377 real_font_height; | |
3378 set_window_pixheight (FRAME_ROOT_WINDOW (f), | |
3379 /* - font_height for minibuffer */ | |
3380 new_pixheight - minibuf_height, 0); | |
3381 | |
3382 XWINDOW (FRAME_MINIBUF_WINDOW (f))->pixel_top = | |
3383 FRAME_TOP_BORDER_END (f) + | |
3384 FRAME_TOP_GUTTER_BOUNDS (f) + | |
3385 FRAME_BOTTOM_GUTTER_BOUNDS (f) + | |
3386 new_pixheight - minibuf_height; | |
3387 | |
3388 set_window_pixheight (FRAME_MINIBUF_WINDOW (f), minibuf_height, 0); | |
3389 } | |
3390 else | |
3391 /* Frame has just one top-level window. */ | |
3392 set_window_pixheight (FRAME_ROOT_WINDOW (f), new_pixheight, 0); | |
3393 | |
3394 FRAME_HEIGHT (f) = newheight; | |
3395 if (FRAME_TTY_P (f)) | |
3396 f->pixheight = newheight; | |
3397 } | |
3398 | |
3399 if (new_pixwidth) | |
3400 { | |
3401 /* Adjust for gutters here so that we always get set | |
3402 properly. */ | |
3403 new_pixwidth -= | |
3404 (FRAME_LEFT_GUTTER_BOUNDS (f) | |
3405 + FRAME_RIGHT_GUTTER_BOUNDS (f)); | |
3406 | |
3407 XWINDOW (FRAME_ROOT_WINDOW (f))->pixel_left = | |
3408 FRAME_LEFT_BORDER_END (f) + FRAME_LEFT_GUTTER_BOUNDS (f); | 3661 FRAME_LEFT_BORDER_END (f) + FRAME_LEFT_GUTTER_BOUNDS (f); |
3409 set_window_pixwidth (FRAME_ROOT_WINDOW (f), new_pixwidth, 0); | 3662 set_window_pixwidth (FRAME_MINIBUF_WINDOW (f), new_pixwidth, 0); |
3410 | 3663 } |
3411 if (FRAME_HAS_MINIBUF_P (f)) | 3664 |
3412 { | 3665 FRAME_WIDTH (f) = newwidth; |
3413 XWINDOW (FRAME_MINIBUF_WINDOW (f))->pixel_left = | 3666 if (FRAME_TTY_P (f)) |
3414 FRAME_LEFT_BORDER_END (f) + FRAME_LEFT_GUTTER_BOUNDS (f); | 3667 f->pixwidth = newwidth; |
3415 set_window_pixwidth (FRAME_MINIBUF_WINDOW (f), new_pixwidth, 0); | 3668 |
3416 } | 3669 /* #### On MS Windows, this references FRAME_PIXWIDTH() and FRAME_PIXHEIGHT(). |
3417 | 3670 I'm not sure we can count on those values being set. Instead we should |
3418 FRAME_WIDTH (f) = newwidth; | 3671 use the total pixel size we got near the top by calling |
3419 if (FRAME_TTY_P (f)) | 3672 frame_conversion_internal(). We should inline the logic in |
3420 f->pixwidth = newwidth; | 3673 get_frame_char_size() here and change that function so it just looks |
3421 } | 3674 at FRAME_CHARWIDTH() and FRAME_CHARHEIGHT(). */ |
3422 | 3675 get_frame_char_size (f, &FRAME_CHARWIDTH (f), &FRAME_CHARHEIGHT (f)); |
3423 if (window_system_pixelated_geometry (frame)) | |
3424 pixel_to_real_char_size (f, FRAME_PIXWIDTH (f), FRAME_PIXHEIGHT (f), | |
3425 &FRAME_CHARWIDTH (f), &FRAME_CHARHEIGHT (f)); | |
3426 else | |
3427 { | |
3428 FRAME_CHARWIDTH (f) = FRAME_WIDTH (f); | |
3429 FRAME_CHARHEIGHT (f) = FRAME_HEIGHT (f); | |
3430 } | |
3431 | 3676 |
3432 MARK_FRAME_TOOLBARS_CHANGED (f); | 3677 MARK_FRAME_TOOLBARS_CHANGED (f); |
3433 MARK_FRAME_GUTTERS_CHANGED (f); | 3678 MARK_FRAME_GUTTERS_CHANGED (f); |
3434 MARK_FRAME_CHANGED (f); | 3679 MARK_FRAME_CHANGED (f); |
3435 f->echo_area_garbaged = 1; | 3680 f->echo_area_garbaged = 1; |
3436 } | 3681 } |
3437 | 3682 |
3438 void | 3683 void |
3439 change_frame_size (struct frame *f, int newheight, int newwidth, int delay) | 3684 change_frame_size (struct frame *f, int newwidth, int newheight, int delay) |
3440 { | 3685 { |
3441 /* sometimes we get passed a size that's too small (esp. when a | 3686 /* sometimes we get passed a size that's too small (esp. when a |
3442 client widget gets resized, since we have no control over this). | 3687 client widget gets resized, since we have no control over this). |
3443 So deal. */ | 3688 So deal. */ |
3444 check_frame_size (f, &newheight, &newwidth); | 3689 check_frame_size (f, &newwidth, &newheight); |
3445 | 3690 |
3446 /* Unconditionally mark that the frame has changed size. This is | 3691 /* Unconditionally mark that the frame has changed size. This is |
3447 because many things need to know after the | 3692 because many things need to know after the |
3448 fact. f->size_change_pending will get reset below. The most that | 3693 fact. f->size_change_pending will get reset below. The most that |
3449 can happen is that we will cycle through redisplay once more | 3694 can happen is that we will cycle through redisplay once more |
3466 if (FRAME_TTY_P (f)) | 3711 if (FRAME_TTY_P (f)) |
3467 { | 3712 { |
3468 Lisp_Object frmcons; | 3713 Lisp_Object frmcons; |
3469 | 3714 |
3470 DEVICE_FRAME_LOOP (frmcons, XDEVICE (FRAME_DEVICE (f))) | 3715 DEVICE_FRAME_LOOP (frmcons, XDEVICE (FRAME_DEVICE (f))) |
3471 change_frame_size_1 (XFRAME (XCAR (frmcons)), newheight, newwidth); | 3716 change_frame_size_1 (XFRAME (XCAR (frmcons)), newwidth, newheight); |
3472 } | 3717 } |
3473 else | 3718 else |
3474 change_frame_size_1 (f, newheight, newwidth); | 3719 change_frame_size_1 (f, newwidth, newheight); |
3475 } | 3720 } |
3476 | 3721 |
3477 | 3722 |
3478 /* The caller is responsible for freeing the returned string. */ | 3723 /* The caller is responsible for freeing the returned string. */ |
3479 static Ibyte * | 3724 static Ibyte * |