aboutsummaryrefslogtreecommitdiffstats
path: root/src/window.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/window.c')
-rw-r--r--src/window.c857
1 files changed, 550 insertions, 307 deletions
diff --git a/src/window.c b/src/window.c
index 22e66e4fbf1..0bc09bb5f90 100644
--- a/src/window.c
+++ b/src/window.c
@@ -242,13 +242,13 @@ make_window ()
242 242
243 p = allocate_window (); 243 p = allocate_window ();
244 XSETFASTINT (p->sequence_number, ++sequence_number); 244 XSETFASTINT (p->sequence_number, ++sequence_number);
245 XSETFASTINT (p->left, 0); 245 XSETFASTINT (p->left_col, 0);
246 XSETFASTINT (p->top, 0); 246 XSETFASTINT (p->top_line, 0);
247 XSETFASTINT (p->height, 0); 247 XSETFASTINT (p->total_lines, 0);
248 XSETFASTINT (p->width, 0); 248 XSETFASTINT (p->total_cols, 0);
249 XSETFASTINT (p->hscroll, 0); 249 XSETFASTINT (p->hscroll, 0);
250 XSETFASTINT (p->min_hscroll, 0); 250 XSETFASTINT (p->min_hscroll, 0);
251 p->orig_top = p->orig_height = Qnil; 251 p->orig_top_line = p->orig_total_lines = Qnil;
252 p->start = Fmake_marker (); 252 p->start = Fmake_marker ();
253 p->pointm = Fmake_marker (); 253 p->pointm = Fmake_marker ();
254 XSETFASTINT (p->use_time, 0); 254 XSETFASTINT (p->use_time, 0);
@@ -272,6 +272,13 @@ make_window ()
272 p->frozen_window_start_p = 0; 272 p->frozen_window_start_p = 0;
273 p->height_fixed_p = 0; 273 p->height_fixed_p = 0;
274 p->last_cursor_off_p = p->cursor_off_p = 0; 274 p->last_cursor_off_p = p->cursor_off_p = 0;
275 p->left_margin_cols = Qnil;
276 p->right_margin_cols = Qnil;
277 p->left_fringe_width = Qnil;
278 p->right_fringe_width = Qnil;
279 p->fringes_outside_margins = Qnil;
280 p->scroll_bar_width = Qnil;
281 p->vertical_scroll_bar_type = Qt;
275 282
276 Vwindow_list = Qnil; 283 Vwindow_list = Qnil;
277 return val; 284 return val;
@@ -398,7 +405,7 @@ DEFUN ("window-height", Fwindow_height, Swindow_height, 0, 1, 0,
398 (window) 405 (window)
399 Lisp_Object window; 406 Lisp_Object window;
400{ 407{
401 return decode_window (window)->height; 408 return decode_window (window)->total_lines;
402} 409}
403 410
404DEFUN ("window-width", Fwindow_width, Swindow_width, 0, 1, 0, 411DEFUN ("window-width", Fwindow_width, Swindow_width, 0, 1, 0,
@@ -409,7 +416,7 @@ use (let ((edges (window-edges))) (- (nth 2 edges) (nth 0 edges))). */)
409 (window) 416 (window)
410 Lisp_Object window; 417 Lisp_Object window;
411{ 418{
412 return make_number (window_internal_width (decode_window (window))); 419 return make_number (window_box_text_cols (decode_window (window)));
413} 420}
414 421
415DEFUN ("window-hscroll", Fwindow_hscroll, Swindow_hscroll, 0, 1, 0, 422DEFUN ("window-hscroll", Fwindow_hscroll, Swindow_hscroll, 0, 1, 0,
@@ -482,11 +489,11 @@ and BOTTOM is one more than the bottommost row used by WINDOW
482{ 489{
483 register struct window *w = decode_window (window); 490 register struct window *w = decode_window (window);
484 491
485 return Fcons (w->left, Fcons (w->top, 492 return Fcons (make_number (WINDOW_LEFT_EDGE_COL (w)),
486 Fcons (make_number (WINDOW_RIGHT_EDGE (w)), 493 Fcons (make_number (WINDOW_TOP_EDGE_LINE (w)),
487 Fcons (make_number (XFASTINT (w->top) 494 Fcons (make_number (WINDOW_RIGHT_EDGE_COL (w)),
488 + XFASTINT (w->height)), 495 Fcons (make_number (WINDOW_BOTTOM_EDGE_LINE (w)),
489 Qnil)))); 496 Qnil))));
490} 497}
491 498
492/* Test if the character at column *X, row *Y is within window W. 499/* Test if the character at column *X, row *Y is within window W.
@@ -513,18 +520,16 @@ coordinates_in_window (w, x, y)
513 register struct window *w; 520 register struct window *w;
514 register int *x, *y; 521 register int *x, *y;
515{ 522{
516 /* Let's make this a global enum later, instead of using numbers
517 everywhere. */
518 struct frame *f = XFRAME (WINDOW_FRAME (w)); 523 struct frame *f = XFRAME (WINDOW_FRAME (w));
519 int left_x, right_x, top_y, bottom_y; 524 int left_x, right_x, top_y, bottom_y;
520 enum window_part part; 525 enum window_part part;
521 int ux = CANON_X_UNIT (f); 526 int ux = FRAME_COLUMN_WIDTH (f);
522 int x0 = XFASTINT (w->left) * ux; 527 int x0 = WINDOW_LEFT_EDGE_X (w);
523 int x1 = x0 + XFASTINT (w->width) * ux; 528 int x1 = WINDOW_RIGHT_EDGE_X (w);
524 /* The width of the area where the vertical line can be dragged. 529 /* The width of the area where the vertical line can be dragged.
525 (Between mode lines for instance. */ 530 (Between mode lines for instance. */
526 int grabbable_width = ux; 531 int grabbable_width = ux;
527 int lmargin_width = 0, rmargin_width = 0; 532 int lmargin_width, rmargin_width, text_left, text_right;
528 533
529 if (*x < x0 || *x >= x1) 534 if (*x < x0 || *x >= x1)
530 return ON_NOTHING; 535 return ON_NOTHING;
@@ -534,20 +539,22 @@ coordinates_in_window (w, x, y)
534 if (w->pseudo_window_p) 539 if (w->pseudo_window_p)
535 { 540 {
536 left_x = 0; 541 left_x = 0;
537 right_x = XFASTINT (w->width) * CANON_X_UNIT (f) - 1; 542 right_x = WINDOW_TOTAL_WIDTH (w) - 1;
538 top_y = WINDOW_DISPLAY_TOP_EDGE_PIXEL_Y (w); 543 top_y = WINDOW_TOP_EDGE_Y (w);
539 bottom_y = WINDOW_DISPLAY_BOTTOM_EDGE_PIXEL_Y (w); 544 bottom_y = WINDOW_BOTTOM_EDGE_Y (w);
540 } 545 }
541 else 546 else
542 { 547 {
543 left_x = (WINDOW_DISPLAY_LEFT_EDGE_PIXEL_X (w) 548 left_x = WINDOW_BOX_LEFT_EDGE_X (w);
544 - FRAME_INTERNAL_BORDER_WIDTH_SAFE (f)); 549 right_x = WINDOW_BOX_RIGHT_EDGE_X (w) - 1;
545 right_x = WINDOW_DISPLAY_RIGHT_EDGE_PIXEL_X (w) - 1; 550 top_y = WINDOW_TOP_EDGE_Y (w);
546 top_y = (WINDOW_DISPLAY_TOP_EDGE_PIXEL_Y (w) 551 bottom_y = WINDOW_BOTTOM_EDGE_Y (w);
547 - FRAME_INTERNAL_BORDER_WIDTH_SAFE (f));
548 bottom_y = WINDOW_DISPLAY_BOTTOM_EDGE_PIXEL_Y (w);
549 } 552 }
550 553
554 /* Outside any interesting row? */
555 if (*y < top_y || *y >= bottom_y)
556 return ON_NOTHING;
557
551 /* On the mode line or header line? If it's near the start of 558 /* On the mode line or header line? If it's near the start of
552 the mode or header line of window that's has a horizontal 559 the mode or header line of window that's has a horizontal
553 sibling, say it's on the vertical line. That's to be able 560 sibling, say it's on the vertical line. That's to be able
@@ -558,130 +565,100 @@ coordinates_in_window (w, x, y)
558 && *y >= bottom_y - CURRENT_MODE_LINE_HEIGHT (w) 565 && *y >= bottom_y - CURRENT_MODE_LINE_HEIGHT (w)
559 && *y < bottom_y) 566 && *y < bottom_y)
560 { 567 {
568 part = ON_MODE_LINE;
569
570 header_vertical_border_check:
561 /* We're somewhere on the mode line. We consider the place 571 /* We're somewhere on the mode line. We consider the place
562 between mode lines of horizontally adjacent mode lines 572 between mode lines of horizontally adjacent mode lines
563 as the vertical border. If scroll bars on the left, 573 as the vertical border. If scroll bars on the left,
564 return the right window. */ 574 return the right window. */
565 part = ON_MODE_LINE; 575 if (WINDOW_HAS_VERTICAL_SCROLL_BAR_ON_LEFT (w)
566 576 || WINDOW_RIGHTMOST_P (w))
567 if (FRAME_HAS_VERTICAL_SCROLL_BARS_ON_LEFT (f))
568 { 577 {
569 if (abs (*x - x0) < grabbable_width) 578 if (!WINDOW_LEFTMOST_P (w) && abs (*x - x0) < grabbable_width)
570 part = ON_VERTICAL_BORDER; 579 return ON_VERTICAL_BORDER;
571 } 580 }
572 else if (!WINDOW_RIGHTMOST_P (w) && abs (*x - x1) < grabbable_width) 581 else
573 part = ON_VERTICAL_BORDER;
574 }
575 else if (WINDOW_WANTS_HEADER_LINE_P (w)
576 && *y < top_y + CURRENT_HEADER_LINE_HEIGHT (w)
577 && *y >= top_y)
578 {
579 part = ON_HEADER_LINE;
580
581 if (FRAME_HAS_VERTICAL_SCROLL_BARS_ON_LEFT (f))
582 { 582 {
583 if (abs (*x - x0) < grabbable_width) 583 if (abs (*x - x1) < grabbable_width)
584 part = ON_VERTICAL_BORDER; 584 return ON_VERTICAL_BORDER;
585 } 585 }
586 else if (!WINDOW_RIGHTMOST_P (w) && abs (*x - x1) < grabbable_width) 586
587 part = ON_VERTICAL_BORDER; 587 return part;
588 } 588 }
589 /* Outside anything interesting? */ 589
590 else if (*y < top_y 590 if (WINDOW_WANTS_HEADER_LINE_P (w)
591 || *y >= bottom_y 591 && *y >= top_y
592 || *x < (left_x 592 && *y < top_y + CURRENT_HEADER_LINE_HEIGHT (w))
593 - FRAME_LEFT_FRINGE_WIDTH (f)
594 - FRAME_LEFT_SCROLL_BAR_WIDTH (f) * ux)
595 || *x > (right_x
596 + FRAME_RIGHT_FRINGE_WIDTH (f)
597 + FRAME_RIGHT_SCROLL_BAR_WIDTH (f) * ux))
598 { 593 {
599 part = ON_NOTHING; 594 part = ON_HEADER_LINE;
595 goto header_vertical_border_check;
600 } 596 }
601 else if (FRAME_WINDOW_P (f)) 597
598 /* Outside any interesting column? */
599 if (*x < left_x || *x > right_x)
600 return ON_NOTHING;
601
602 lmargin_width = window_box_width (w, LEFT_MARGIN_AREA);
603 rmargin_width = window_box_width (w, RIGHT_MARGIN_AREA);
604
605 text_left = window_box_left (w, TEXT_AREA);
606 text_right = text_left + window_box_width (w, TEXT_AREA);
607
608 if (FRAME_WINDOW_P (f))
602 { 609 {
603 if (!w->pseudo_window_p 610 if (!w->pseudo_window_p
604 && !FRAME_HAS_VERTICAL_SCROLL_BARS (f) 611 && !WINDOW_HAS_VERTICAL_SCROLL_BAR (w)
605 && !WINDOW_RIGHTMOST_P (w) 612 && !WINDOW_RIGHTMOST_P (w)
606 && (abs (*x - right_x - FRAME_RIGHT_FRINGE_WIDTH (f)) < grabbable_width)) 613 && (abs (*x - right_x) < grabbable_width))
607 { 614 return ON_VERTICAL_BORDER;
608 part = ON_VERTICAL_BORDER;
609 }
610 else if (*x < left_x || *x > right_x)
611 {
612 /* Other lines than the mode line don't include fringes and
613 scroll bars on the left. */
614
615 /* Convert X and Y to window-relative pixel coordinates. */
616 *x -= left_x;
617 *y -= top_y;
618 part = *x < left_x ? ON_LEFT_FRINGE : ON_RIGHT_FRINGE;
619 }
620 else
621 {
622 lmargin_width = window_box_width (w, LEFT_MARGIN_AREA);
623 rmargin_width = window_box_width (w, RIGHT_MARGIN_AREA);
624 /* You can never be on a margin area if its width is zero. */
625 if (lmargin_width
626 && *x <= window_box_right (w, LEFT_MARGIN_AREA))
627 part = ON_LEFT_MARGIN;
628 else if (rmargin_width
629 && *x >= window_box_left (w, RIGHT_MARGIN_AREA))
630 part = ON_RIGHT_MARGIN;
631 else
632 {
633 part = ON_TEXT;
634 *x -= left_x;
635 *y -= top_y;
636 }
637 }
638 } 615 }
639 else 616 else
640 { 617 {
641 /* Need to say "*x > right_x" rather than >=, since on character 618 /* Need to say "*x > right_x" rather than >=, since on character
642 terminals, the vertical line's x coordinate is right_x. */ 619 terminals, the vertical line's x coordinate is right_x. */
643 if (*x < left_x || *x > right_x) 620 if (!w->pseudo_window_p
644 { 621 && !WINDOW_RIGHTMOST_P (w)
645 /* Other lines than the mode line don't include fringes and 622 && *x > right_x - ux)
646 scroll bars on the left. */
647
648 /* Convert X and Y to window-relative pixel coordinates. */
649 *x -= left_x;
650 *y -= top_y;
651 part = *x < left_x ? ON_LEFT_FRINGE : ON_RIGHT_FRINGE;
652 }
653 /* Here, too, "*x > right_x" is because of character terminals. */
654 else if (!w->pseudo_window_p
655 && !WINDOW_RIGHTMOST_P (w)
656 && *x > right_x - ux)
657 { 623 {
658 /* On the border on the right side of the window? Assume that 624 /* On the border on the right side of the window? Assume that
659 this area begins at RIGHT_X minus a canonical char width. */ 625 this area begins at RIGHT_X minus a canonical char width. */
660 part = ON_VERTICAL_BORDER; 626 return ON_VERTICAL_BORDER;
661 }
662 else
663 {
664 lmargin_width = window_box_width (w, LEFT_MARGIN_AREA);
665 rmargin_width = window_box_width (w, RIGHT_MARGIN_AREA);
666 /* You can never be on a margin area if its width is zero.
667 This is especially important for character terminals. */
668 if (lmargin_width
669 && *x <= window_box_right (w, LEFT_MARGIN_AREA))
670 part = ON_LEFT_MARGIN;
671 else if (rmargin_width
672 && *x >= window_box_left (w, RIGHT_MARGIN_AREA))
673 part = ON_RIGHT_MARGIN;
674 else
675 {
676 part = ON_TEXT;
677 /* Convert X and Y to window-relative pixel coordinates. */
678 *x -= left_x;
679 *y -= top_y;
680 }
681 } 627 }
682 } 628 }
683 629
684 return part; 630 if (*x < text_left)
631 {
632 if (lmargin_width > 0
633 && (WINDOW_HAS_FRINGES_OUTSIDE_MARGINS (w)
634 ? (*x >= left_x + WINDOW_LEFT_FRINGE_WIDTH (w))
635 : (*x < left_x + lmargin_width)))
636 return ON_LEFT_MARGIN;
637
638 /* Convert X and Y to window-relative pixel coordinates. */
639 *x -= left_x;
640 *y -= top_y;
641 return ON_LEFT_FRINGE;
642 }
643
644 if (*x >= text_right)
645 {
646 if (rmargin_width > 0
647 && (WINDOW_HAS_FRINGES_OUTSIDE_MARGINS (w)
648 ? (*x < right_x - WINDOW_RIGHT_FRINGE_WIDTH (w))
649 : (*x >= right_x - rmargin_width)))
650 return ON_RIGHT_MARGIN;
651
652 /* Convert X and Y to window-relative pixel coordinates. */
653 *x -= left_x + WINDOW_LEFT_FRINGE_WIDTH (w);
654 *y -= top_y;
655 return ON_RIGHT_FRINGE;
656 }
657
658 /* Everything special ruled out - must be on text area */
659 *x -= left_x + WINDOW_LEFT_FRINGE_WIDTH (w);
660 *y -= top_y;
661 return ON_TEXT;
685} 662}
686 663
687 664
@@ -718,8 +695,8 @@ If they are in the windows's left or right marginal areas, `left-margin'\n\
718 ly = Fcdr (coordinates); 695 ly = Fcdr (coordinates);
719 CHECK_NUMBER_OR_FLOAT (lx); 696 CHECK_NUMBER_OR_FLOAT (lx);
720 CHECK_NUMBER_OR_FLOAT (ly); 697 CHECK_NUMBER_OR_FLOAT (ly);
721 x = PIXEL_X_FROM_CANON_X (f, lx); 698 x = FRAME_PIXEL_X_FROM_CANON_X (f, lx);
722 y = PIXEL_Y_FROM_CANON_Y (f, ly); 699 y = FRAME_PIXEL_Y_FROM_CANON_Y (f, ly);
723 700
724 switch (coordinates_in_window (w, &x, &y)) 701 switch (coordinates_in_window (w, &x, &y))
725 { 702 {
@@ -729,8 +706,8 @@ If they are in the windows's left or right marginal areas, `left-margin'\n\
729 case ON_TEXT: 706 case ON_TEXT:
730 /* X and Y are now window relative pixel coordinates. Convert 707 /* X and Y are now window relative pixel coordinates. Convert
731 them to canonical char units before returning them. */ 708 them to canonical char units before returning them. */
732 return Fcons (CANON_X_FROM_PIXEL_X (f, x), 709 return Fcons (FRAME_CANON_X_FROM_PIXEL_X (f, x),
733 CANON_Y_FROM_PIXEL_Y (f, y)); 710 FRAME_CANON_Y_FROM_PIXEL_Y (f, y));
734 711
735 case ON_MODE_LINE: 712 case ON_MODE_LINE:
736 return Qmode_line; 713 return Qmode_line;
@@ -797,8 +774,12 @@ check_window_containing (w, user_data)
797 774
798 775
799/* Find the window containing frame-relative pixel position X/Y and 776/* Find the window containing frame-relative pixel position X/Y and
800 return it as a Lisp_Object. If X, Y is on one of the window's 777 return it as a Lisp_Object.
801 special `window_part' elements, set *PART to the id of that element. 778
779 If X, Y is on one of the window's special `window_part' elements,
780 set *PART to the id of that element, and return X and Y converted
781 to window relative coordinates in WX and WY.
782
802 If there is no window under X, Y return nil and leave *PART 783 If there is no window under X, Y return nil and leave *PART
803 unmodified. TOOL_BAR_P non-zero means detect tool-bar windows. 784 unmodified. TOOL_BAR_P non-zero means detect tool-bar windows.
804 785
@@ -812,10 +793,11 @@ check_window_containing (w, user_data)
812 case. */ 793 case. */
813 794
814Lisp_Object 795Lisp_Object
815window_from_coordinates (f, x, y, part, tool_bar_p) 796window_from_coordinates (f, x, y, part, wx, wy, tool_bar_p)
816 struct frame *f; 797 struct frame *f;
817 int x, y; 798 int x, y;
818 enum window_part *part; 799 enum window_part *part;
800 int *wx, *wy;
819 int tool_bar_p; 801 int tool_bar_p;
820{ 802{
821 Lisp_Object window; 803 Lisp_Object window;
@@ -834,7 +816,7 @@ window_from_coordinates (f, x, y, part, tool_bar_p)
834 if (NILP (window) 816 if (NILP (window)
835 && tool_bar_p 817 && tool_bar_p
836 && WINDOWP (f->tool_bar_window) 818 && WINDOWP (f->tool_bar_window)
837 && XINT (XWINDOW (f->tool_bar_window)->height) > 0 819 && WINDOW_TOTAL_LINES (XWINDOW (f->tool_bar_window)) > 0
838 && (coordinates_in_window (XWINDOW (f->tool_bar_window), &x, &y) 820 && (coordinates_in_window (XWINDOW (f->tool_bar_window), &x, &y)
839 != ON_NOTHING)) 821 != ON_NOTHING))
840 { 822 {
@@ -842,6 +824,9 @@ window_from_coordinates (f, x, y, part, tool_bar_p)
842 window = f->tool_bar_window; 824 window = f->tool_bar_window;
843 } 825 }
844 826
827 if (wx) *wx = x;
828 if (wy) *wy = y;
829
845 return window; 830 return window;
846} 831}
847 832
@@ -865,9 +850,9 @@ column 0. */)
865 CHECK_NUMBER_OR_FLOAT (y); 850 CHECK_NUMBER_OR_FLOAT (y);
866 851
867 return window_from_coordinates (f, 852 return window_from_coordinates (f,
868 PIXEL_X_FROM_CANON_X (f, x), 853 FRAME_PIXEL_X_FROM_CANON_X (f, x),
869 PIXEL_Y_FROM_CANON_Y (f, y), 854 FRAME_PIXEL_Y_FROM_CANON_Y (f, y),
870 0, 0); 855 0, 0, 0, 0);
871} 856}
872 857
873DEFUN ("window-point", Fwindow_point, Swindow_point, 0, 1, 0, 858DEFUN ("window-point", Fwindow_point, Swindow_point, 0, 1, 0,
@@ -1167,10 +1152,10 @@ replace_window (old, replacement)
1167 if (EQ (old, FRAME_ROOT_WINDOW (XFRAME (o->frame)))) 1152 if (EQ (old, FRAME_ROOT_WINDOW (XFRAME (o->frame))))
1168 FRAME_ROOT_WINDOW (XFRAME (o->frame)) = replacement; 1153 FRAME_ROOT_WINDOW (XFRAME (o->frame)) = replacement;
1169 1154
1170 p->left = o->left; 1155 p->left_col = o->left_col;
1171 p->top = o->top; 1156 p->top_line = o->top_line;
1172 p->width = o->width; 1157 p->total_cols = o->total_cols;
1173 p->height = o->height; 1158 p->total_lines = o->total_lines;
1174 p->desired_matrix = p->current_matrix = 0; 1159 p->desired_matrix = p->current_matrix = 0;
1175 p->vscroll = 0; 1160 p->vscroll = 0;
1176 bzero (&p->cursor, sizeof (p->cursor)); 1161 bzero (&p->cursor, sizeof (p->cursor));
@@ -1184,7 +1169,7 @@ replace_window (old, replacement)
1184 XSETFASTINT (p->window_end_pos, 0); 1169 XSETFASTINT (p->window_end_pos, 0);
1185 p->window_end_valid = Qnil; 1170 p->window_end_valid = Qnil;
1186 p->frozen_window_start_p = 0; 1171 p->frozen_window_start_p = 0;
1187 p->orig_top = p->orig_height = Qnil; 1172 p->orig_top_line = p->orig_total_lines = Qnil;
1188 1173
1189 p->next = tem = o->next; 1174 p->next = tem = o->next;
1190 if (!NILP (tem)) 1175 if (!NILP (tem))
@@ -1343,18 +1328,18 @@ delete_window (window)
1343 set_window_{height,width} will re-position the sibling's 1328 set_window_{height,width} will re-position the sibling's
1344 children. */ 1329 children. */
1345 sib = p->next; 1330 sib = p->next;
1346 XWINDOW (sib)->top = p->top; 1331 XWINDOW (sib)->top_line = p->top_line;
1347 XWINDOW (sib)->left = p->left; 1332 XWINDOW (sib)->left_col = p->left_col;
1348 } 1333 }
1349 1334
1350 /* Stretch that sibling. */ 1335 /* Stretch that sibling. */
1351 if (!NILP (par->vchild)) 1336 if (!NILP (par->vchild))
1352 set_window_height (sib, 1337 set_window_height (sib,
1353 XFASTINT (XWINDOW (sib)->height) + XFASTINT (p->height), 1338 XFASTINT (XWINDOW (sib)->total_lines) + XFASTINT (p->total_lines),
1354 1); 1339 1);
1355 if (!NILP (par->hchild)) 1340 if (!NILP (par->hchild))
1356 set_window_width (sib, 1341 set_window_width (sib,
1357 XFASTINT (XWINDOW (sib)->width) + XFASTINT (p->width), 1342 XFASTINT (XWINDOW (sib)->total_cols) + XFASTINT (p->total_cols),
1358 1); 1343 1);
1359 1344
1360 /* If parent now has only one child, 1345 /* If parent now has only one child,
@@ -1890,7 +1875,7 @@ window_loop (type, obj, mini, frames)
1890 display there. */ 1875 display there. */
1891 Lisp_Object buffer; 1876 Lisp_Object buffer;
1892 buffer = Fother_buffer (obj, Qnil, w->frame); 1877 buffer = Fother_buffer (obj, Qnil, w->frame);
1893 Fset_window_buffer (window, buffer); 1878 Fset_window_buffer (window, buffer, Qnil);
1894 if (EQ (window, selected_window)) 1879 if (EQ (window, selected_window))
1895 Fset_buffer (w->buffer); 1880 Fset_buffer (w->buffer);
1896 } 1881 }
@@ -1910,8 +1895,8 @@ window_loop (type, obj, mini, frames)
1910 else 1895 else
1911 { 1896 {
1912 struct window *b = XWINDOW (best_window); 1897 struct window *b = XWINDOW (best_window);
1913 if (XFASTINT (w->height) * XFASTINT (w->width) 1898 if (XFASTINT (w->total_lines) * XFASTINT (w->total_cols)
1914 > XFASTINT (b->height) * XFASTINT (b->width)) 1899 > XFASTINT (b->total_lines) * XFASTINT (b->total_cols))
1915 best_window = window; 1900 best_window = window;
1916 } 1901 }
1917 } 1902 }
@@ -1954,7 +1939,7 @@ window_loop (type, obj, mini, frames)
1954 { 1939 {
1955 /* Otherwise show a different buffer in the window. */ 1940 /* Otherwise show a different buffer in the window. */
1956 w->dedicated = Qnil; 1941 w->dedicated = Qnil;
1957 Fset_window_buffer (window, buffer); 1942 Fset_window_buffer (window, buffer, Qnil);
1958 if (EQ (window, selected_window)) 1943 if (EQ (window, selected_window))
1959 Fset_buffer (w->buffer); 1944 Fset_buffer (w->buffer);
1960 } 1945 }
@@ -2059,7 +2044,7 @@ value is reasonable when this function is called. */)
2059 w = XWINDOW (window); 2044 w = XWINDOW (window);
2060 2045
2061 startpos = marker_position (w->start); 2046 startpos = marker_position (w->start);
2062 top = XFASTINT (w->top) - FRAME_TOP_MARGIN (XFRAME (WINDOW_FRAME (w))); 2047 top = WINDOW_TOP_EDGE_LINE (w) - FRAME_TOP_MARGIN (XFRAME (WINDOW_FRAME (w)));
2063 2048
2064 if (MINI_WINDOW_P (w) && top > 0) 2049 if (MINI_WINDOW_P (w) && top > 0)
2065 error ("Can't expand minibuffer to full frame"); 2050 error ("Can't expand minibuffer to full frame");
@@ -2071,7 +2056,7 @@ value is reasonable when this function is called. */)
2071 on the frame. But don't try to do this if the window start is 2056 on the frame. But don't try to do this if the window start is
2072 outside the visible portion (as might happen when the display is 2057 outside the visible portion (as might happen when the display is
2073 not current, due to typeahead). */ 2058 not current, due to typeahead). */
2074 new_top = XFASTINT (w->top) - FRAME_TOP_MARGIN (XFRAME (WINDOW_FRAME (w))); 2059 new_top = WINDOW_TOP_EDGE_LINE (w) - FRAME_TOP_MARGIN (XFRAME (WINDOW_FRAME (w)));
2075 if (new_top != top 2060 if (new_top != top
2076 && startpos >= BUF_BEGV (XBUFFER (w->buffer)) 2061 && startpos >= BUF_BEGV (XBUFFER (w->buffer))
2077 && startpos <= BUF_ZV (XBUFFER (w->buffer))) 2062 && startpos <= BUF_ZV (XBUFFER (w->buffer)))
@@ -2426,7 +2411,7 @@ window_min_size (w, width_p, ignore_fixed_p, fixed)
2426 *fixed = fixed_p; 2411 *fixed = fixed_p;
2427 2412
2428 if (fixed_p) 2413 if (fixed_p)
2429 size = width_p ? XFASTINT (w->width) : XFASTINT (w->height); 2414 size = width_p ? XFASTINT (w->total_cols) : XFASTINT (w->total_lines);
2430 else 2415 else
2431 size = window_min_size_1 (w, width_p); 2416 size = window_min_size_1 (w, width_p);
2432 2417
@@ -2434,6 +2419,43 @@ window_min_size (w, width_p, ignore_fixed_p, fixed)
2434} 2419}
2435 2420
2436 2421
2422/* Adjust the margins of window W if text area is too small.
2423 Return 1 if window width is ok after adjustment; 0 if window
2424 is still too narrow. */
2425
2426static int
2427adjust_window_margins (w)
2428 struct window *w;
2429{
2430 int box_cols = (WINDOW_TOTAL_COLS (w)
2431 - WINDOW_FRINGE_COLS (w)
2432 - WINDOW_SCROLL_BAR_COLS (w));
2433 int margin_cols = (WINDOW_LEFT_MARGIN_COLS (w)
2434 + WINDOW_RIGHT_MARGIN_COLS (w));
2435
2436 if (box_cols - margin_cols >= MIN_SAFE_WINDOW_WIDTH)
2437 return 1;
2438
2439 if (margin_cols < 0 || box_cols < MIN_SAFE_WINDOW_WIDTH)
2440 return 0;
2441
2442 /* Window's text area is too narrow, but reducing the window
2443 margins will fix that. */
2444 margin_cols = box_cols - MIN_SAFE_WINDOW_WIDTH;
2445 if (WINDOW_RIGHT_MARGIN_COLS (w) > 0)
2446 {
2447 if (WINDOW_LEFT_MARGIN_COLS (w) > 0)
2448 w->left_margin_cols = w->right_margin_cols
2449 = make_number (margin_cols/2);
2450 else
2451 w->right_margin_cols = make_number (margin_cols);
2452 }
2453 else
2454 w->left_margin_cols = make_number (margin_cols);
2455 return 1;
2456}
2457
2458
2437/* Set WINDOW's height or width to SIZE. WIDTH_P non-zero means set 2459/* Set WINDOW's height or width to SIZE. WIDTH_P non-zero means set
2438 WINDOW's width. Resize WINDOW's children, if any, so that they 2460 WINDOW's width. Resize WINDOW's children, if any, so that they
2439 keep their proportionate size relative to WINDOW. Propagate 2461 keep their proportionate size relative to WINDOW. Propagate
@@ -2451,8 +2473,10 @@ size_window (window, size, width_p, nodelete_p)
2451 struct window *w = XWINDOW (window); 2473 struct window *w = XWINDOW (window);
2452 struct window *c; 2474 struct window *c;
2453 Lisp_Object child, *forward, *sideward; 2475 Lisp_Object child, *forward, *sideward;
2454 int old_size, min_size; 2476 int old_size, min_size, safe_min_size;
2455 2477
2478 /* We test nodelete_p != 2 and nodelete_p != 1 below, so it
2479 seems like it's too soon to do this here. ++KFS. */
2456 if (nodelete_p == 2) 2480 if (nodelete_p == 2)
2457 nodelete_p = 0; 2481 nodelete_p = 0;
2458 2482
@@ -2464,13 +2488,19 @@ size_window (window, size, width_p, nodelete_p)
2464 Preserve it as long as that is at all possible. */ 2488 Preserve it as long as that is at all possible. */
2465 if (width_p) 2489 if (width_p)
2466 { 2490 {
2467 old_size = XINT (w->width); 2491 old_size = WINDOW_TOTAL_COLS (w);
2468 min_size = window_min_width; 2492 min_size = window_min_width;
2493 /* Ensure that there is room for the scroll bar and fringes!
2494 We may reduce display margins though. */
2495 safe_min_size = (MIN_SAFE_WINDOW_WIDTH
2496 + WINDOW_FRINGE_COLS (w)
2497 + WINDOW_SCROLL_BAR_COLS (w));
2469 } 2498 }
2470 else 2499 else
2471 { 2500 {
2472 old_size = XINT (w->height); 2501 old_size = XINT (w->total_lines);
2473 min_size = window_min_height; 2502 min_size = window_min_height;
2503 safe_min_size = MIN_SAFE_WINDOW_HEIGHT;
2474 } 2504 }
2475 2505
2476 if (old_size < min_size && nodelete_p != 2) 2506 if (old_size < min_size && nodelete_p != 2)
@@ -2481,9 +2511,8 @@ size_window (window, size, width_p, nodelete_p)
2481 { 2511 {
2482 if (!MINI_WINDOW_P (w) && !NILP (w->too_small_ok)) 2512 if (!MINI_WINDOW_P (w) && !NILP (w->too_small_ok))
2483 min_size = width_p ? MIN_SAFE_WINDOW_WIDTH : MIN_SAFE_WINDOW_HEIGHT; 2513 min_size = width_p ? MIN_SAFE_WINDOW_WIDTH : MIN_SAFE_WINDOW_HEIGHT;
2484 else 2514 if (min_size < safe_min_size)
2485 min_size = width_p ? window_min_width : window_min_height; 2515 min_size = safe_min_size;
2486
2487 if (size < min_size) 2516 if (size < min_size)
2488 { 2517 {
2489 delete_window (window); 2518 delete_window (window);
@@ -2501,14 +2530,15 @@ size_window (window, size, width_p, nodelete_p)
2501 { 2530 {
2502 sideward = &w->vchild; 2531 sideward = &w->vchild;
2503 forward = &w->hchild; 2532 forward = &w->hchild;
2504 w->width = make_number (size); 2533 w->total_cols = make_number (size);
2534 adjust_window_margins (w);
2505 } 2535 }
2506 else 2536 else
2507 { 2537 {
2508 sideward = &w->hchild; 2538 sideward = &w->hchild;
2509 forward = &w->vchild; 2539 forward = &w->vchild;
2510 w->height = make_number (size); 2540 w->total_lines = make_number (size);
2511 w->orig_height = Qnil; 2541 w->orig_total_lines = Qnil;
2512 } 2542 }
2513 2543
2514 if (!NILP (*sideward)) 2544 if (!NILP (*sideward))
@@ -2517,9 +2547,9 @@ size_window (window, size, width_p, nodelete_p)
2517 { 2547 {
2518 c = XWINDOW (child); 2548 c = XWINDOW (child);
2519 if (width_p) 2549 if (width_p)
2520 c->left = w->left; 2550 c->left_col = w->left_col;
2521 else 2551 else
2522 c->top = w->top; 2552 c->top_line = w->top_line;
2523 size_window (child, size, width_p, nodelete_p); 2553 size_window (child, size, width_p, nodelete_p);
2524 } 2554 }
2525 } 2555 }
@@ -2537,7 +2567,7 @@ size_window (window, size, width_p, nodelete_p)
2537 int child_size; 2567 int child_size;
2538 2568
2539 c = XWINDOW (child); 2569 c = XWINDOW (child);
2540 child_size = width_p ? XINT (c->width) : XINT (c->height); 2570 child_size = width_p ? XINT (c->total_cols) : XINT (c->total_lines);
2541 total += child_size; 2571 total += child_size;
2542 2572
2543 if (window_fixed_size_p (c, width_p, 0)) 2573 if (window_fixed_size_p (c, width_p, 0))
@@ -2559,22 +2589,22 @@ size_window (window, size, width_p, nodelete_p)
2559 extra = (size - total) - n * each; 2589 extra = (size - total) - n * each;
2560 2590
2561 /* Compute new children heights and edge positions. */ 2591 /* Compute new children heights and edge positions. */
2562 first_pos = width_p ? XINT (w->left) : XINT (w->top); 2592 first_pos = width_p ? XINT (w->left_col) : XINT (w->top_line);
2563 last_pos = first_pos; 2593 last_pos = first_pos;
2564 for (child = *forward; !NILP (child); child = c->next) 2594 for (child = *forward; !NILP (child); child = c->next)
2565 { 2595 {
2566 int new_size, old_size; 2596 int new_size, old_size;
2567 2597
2568 c = XWINDOW (child); 2598 c = XWINDOW (child);
2569 old_size = width_p ? XFASTINT (c->width) : XFASTINT (c->height); 2599 old_size = width_p ? XFASTINT (c->total_cols) : XFASTINT (c->total_lines);
2570 new_size = old_size; 2600 new_size = old_size;
2571 2601
2572 /* The top or left edge position of this child equals the 2602 /* The top or left edge position of this child equals the
2573 bottom or right edge of its predecessor. */ 2603 bottom or right edge of its predecessor. */
2574 if (width_p) 2604 if (width_p)
2575 c->left = make_number (last_pos); 2605 c->left_col = make_number (last_pos);
2576 else 2606 else
2577 c->top = make_number (last_pos); 2607 c->top_line = make_number (last_pos);
2578 2608
2579 /* If this child can be resized, do it. */ 2609 /* If this child can be resized, do it. */
2580 if (resize_fixed_p || !window_fixed_size_p (c, width_p, 0)) 2610 if (resize_fixed_p || !window_fixed_size_p (c, width_p, 0))
@@ -2602,7 +2632,7 @@ size_window (window, size, width_p, nodelete_p)
2602 { 2632 {
2603 int child_size; 2633 int child_size;
2604 c = XWINDOW (child); 2634 c = XWINDOW (child);
2605 child_size = width_p ? XINT (c->width) : XINT (c->height); 2635 child_size = width_p ? XINT (c->total_cols) : XINT (c->total_lines);
2606 size_window (child, child_size, width_p, 2); 2636 size_window (child, child_size, width_p, 2);
2607 } 2637 }
2608 } 2638 }
@@ -2646,13 +2676,13 @@ change_window_heights (window, n)
2646{ 2676{
2647 struct window *w = XWINDOW (window); 2677 struct window *w = XWINDOW (window);
2648 2678
2649 XSETFASTINT (w->top, XFASTINT (w->top) + n); 2679 XSETFASTINT (w->top_line, XFASTINT (w->top_line) + n);
2650 XSETFASTINT (w->height, XFASTINT (w->height) - n); 2680 XSETFASTINT (w->total_lines, XFASTINT (w->total_lines) - n);
2651 2681
2652 if (INTEGERP (w->orig_top)) 2682 if (INTEGERP (w->orig_top_line))
2653 XSETFASTINT (w->orig_top, XFASTINT (w->orig_top) + n); 2683 XSETFASTINT (w->orig_top_line, XFASTINT (w->orig_top_line) + n);
2654 if (INTEGERP (w->orig_height)) 2684 if (INTEGERP (w->orig_total_lines))
2655 XSETFASTINT (w->orig_height, XFASTINT (w->orig_height) - n); 2685 XSETFASTINT (w->orig_total_lines, XFASTINT (w->orig_total_lines) - n);
2656 2686
2657 /* Handle just the top child in a vertical split. */ 2687 /* Handle just the top child in a vertical split. */
2658 if (!NILP (w->vchild)) 2688 if (!NILP (w->vchild))
@@ -2680,12 +2710,14 @@ Fset_window_buffer_unwind (obuf)
2680 2710
2681/* Make WINDOW display BUFFER as its contents. RUN_HOOKS_P non-zero 2711/* Make WINDOW display BUFFER as its contents. RUN_HOOKS_P non-zero
2682 means it's allowed to run hooks. See make_frame for a case where 2712 means it's allowed to run hooks. See make_frame for a case where
2683 it's not allowed. */ 2713 it's not allowed. KEEP_MARGINS_P non-zero means that the current
2714 margins, fringes, and scroll-bar settings of the window are not
2715 reset from the buffer's local settings. */
2684 2716
2685void 2717void
2686set_window_buffer (window, buffer, run_hooks_p) 2718set_window_buffer (window, buffer, run_hooks_p, keep_margins_p)
2687 Lisp_Object window, buffer; 2719 Lisp_Object window, buffer;
2688 int run_hooks_p; 2720 int run_hooks_p, keep_margins_p;
2689{ 2721{
2690 struct window *w = XWINDOW (window); 2722 struct window *w = XWINDOW (window);
2691 struct buffer *b = XBUFFER (buffer); 2723 struct buffer *b = XBUFFER (buffer);
@@ -2730,8 +2762,25 @@ set_window_buffer (window, buffer, run_hooks_p)
2730 Fset_buffer (buffer); 2762 Fset_buffer (buffer);
2731 } 2763 }
2732 2764
2733 /* Set left and right marginal area width from buffer. */ 2765 if (!keep_margins_p)
2734 Fset_window_margins (window, b->left_margin_width, b->right_margin_width); 2766 {
2767 /* Set left and right marginal area width etc. from buffer. */
2768
2769 /* This may call adjust_window_margins three times, so
2770 temporarily disable window margins. */
2771 w->left_margin_cols = w->right_margin_cols = Qnil;
2772
2773 Fset_window_fringes (window,
2774 b->left_fringe_width, b->right_fringe_width,
2775 b->fringes_outside_margins);
2776
2777 Fset_window_scroll_bars (window,
2778 b->scroll_bar_width,
2779 b->vertical_scroll_bar_type, Qnil);
2780
2781 Fset_window_margins (window,
2782 b->left_margin_cols, b->right_margin_cols);
2783 }
2735 2784
2736 if (run_hooks_p) 2785 if (run_hooks_p)
2737 { 2786 {
@@ -2748,10 +2797,14 @@ set_window_buffer (window, buffer, run_hooks_p)
2748} 2797}
2749 2798
2750 2799
2751DEFUN ("set-window-buffer", Fset_window_buffer, Sset_window_buffer, 2, 2, 0, 2800DEFUN ("set-window-buffer", Fset_window_buffer, Sset_window_buffer, 2, 3, 0,
2752 doc: /* Make WINDOW display BUFFER as its contents. 2801 doc: /* Make WINDOW display BUFFER as its contents.
2753BUFFER can be a buffer or buffer name. */) 2802BUFFER can be a buffer or buffer name.
2754 (window, buffer) 2803Optional third arg KEEP_MARGINS non-nil means that WINDOW's current
2804display margins, fringe widths, and scroll bar settings are maintained;
2805the default is to reset these from BUFFER's local settings or the frame
2806defaults. */)
2807 (window, buffer, keep_margins)
2755 register Lisp_Object window, buffer; 2808 register Lisp_Object window, buffer;
2756{ 2809{
2757 register Lisp_Object tem; 2810 register Lisp_Object tem;
@@ -2777,7 +2830,7 @@ BUFFER can be a buffer or buffer name. */)
2777 unshow_buffer (w); 2830 unshow_buffer (w);
2778 } 2831 }
2779 2832
2780 set_window_buffer (window, buffer, 1); 2833 set_window_buffer (window, buffer, 1, !NILP (keep_margins));
2781 return Qnil; 2834 return Qnil;
2782} 2835}
2783 2836
@@ -3047,7 +3100,7 @@ displayed. */)
3047 if (pop_up_frames || last_nonminibuf_frame == 0) 3100 if (pop_up_frames || last_nonminibuf_frame == 0)
3048 { 3101 {
3049 window = Fframe_selected_window (call0 (Vpop_up_frame_function)); 3102 window = Fframe_selected_window (call0 (Vpop_up_frame_function));
3050 Fset_window_buffer (window, buffer); 3103 Fset_window_buffer (window, buffer, Qnil);
3051 return display_buffer_1 (window); 3104 return display_buffer_1 (window);
3052 } 3105 }
3053 3106
@@ -3136,14 +3189,14 @@ displayed. */)
3136 if (!NILP (other) 3189 if (!NILP (other)
3137 && !NILP (Veven_window_heights) 3190 && !NILP (Veven_window_heights)
3138 /* Check that OTHER and WINDOW are vertically arrayed. */ 3191 /* Check that OTHER and WINDOW are vertically arrayed. */
3139 && !EQ (XWINDOW (other)->top, XWINDOW (window)->top) 3192 && !EQ (XWINDOW (other)->top_line, XWINDOW (window)->top_line)
3140 && (XFASTINT (XWINDOW (other)->height) 3193 && (XFASTINT (XWINDOW (other)->total_lines)
3141 > XFASTINT (XWINDOW (window)->height))) 3194 > XFASTINT (XWINDOW (window)->total_lines)))
3142 { 3195 {
3143 int total = (XFASTINT (XWINDOW (other)->height) 3196 int total = (XFASTINT (XWINDOW (other)->total_lines)
3144 + XFASTINT (XWINDOW (window)->height)); 3197 + XFASTINT (XWINDOW (window)->total_lines));
3145 enlarge_window (upper, 3198 enlarge_window (upper,
3146 total / 2 - XFASTINT (XWINDOW (upper)->height), 3199 total / 2 - XFASTINT (XWINDOW (upper)->total_lines),
3147 0, 0); 3200 0, 0);
3148 } 3201 }
3149 } 3202 }
@@ -3151,7 +3204,7 @@ displayed. */)
3151 else 3204 else
3152 window = Fget_lru_window (Qnil); 3205 window = Fget_lru_window (Qnil);
3153 3206
3154 Fset_window_buffer (window, buffer); 3207 Fset_window_buffer (window, buffer, Qnil);
3155 return display_buffer_1 (window); 3208 return display_buffer_1 (window);
3156} 3209}
3157 3210
@@ -3282,9 +3335,9 @@ SIZE includes that window's scroll bar, or the divider column to its right. */)
3282 the usable space in columns by two. 3335 the usable space in columns by two.
3283 We round up, since the left-hand window may include 3336 We round up, since the left-hand window may include
3284 a dividing line, while the right-hand may not. */ 3337 a dividing line, while the right-hand may not. */
3285 size_int = (XFASTINT (o->width) + 1) >> 1; 3338 size_int = (XFASTINT (o->total_cols) + 1) >> 1;
3286 else 3339 else
3287 size_int = XFASTINT (o->height) >> 1; 3340 size_int = XFASTINT (o->total_lines) >> 1;
3288 } 3341 }
3289 else 3342 else
3290 { 3343 {
@@ -3303,9 +3356,9 @@ SIZE includes that window's scroll bar, or the divider column to its right. */)
3303 { 3356 {
3304 if (size_int < window_min_height) 3357 if (size_int < window_min_height)
3305 error ("Window height %d too small (after splitting)", size_int); 3358 error ("Window height %d too small (after splitting)", size_int);
3306 if (size_int + window_min_height > XFASTINT (o->height)) 3359 if (size_int + window_min_height > XFASTINT (o->total_lines))
3307 error ("Window height %d too small (after splitting)", 3360 error ("Window height %d too small (after splitting)",
3308 XFASTINT (o->height) - size_int); 3361 XFASTINT (o->total_lines) - size_int);
3309 if (NILP (o->parent) 3362 if (NILP (o->parent)
3310 || NILP (XWINDOW (o->parent)->vchild)) 3363 || NILP (XWINDOW (o->parent)->vchild))
3311 { 3364 {
@@ -3319,9 +3372,9 @@ SIZE includes that window's scroll bar, or the divider column to its right. */)
3319 if (size_int < window_min_width) 3372 if (size_int < window_min_width)
3320 error ("Window width %d too small (after splitting)", size_int); 3373 error ("Window width %d too small (after splitting)", size_int);
3321 3374
3322 if (size_int + window_min_width > XFASTINT (o->width)) 3375 if (size_int + window_min_width > XFASTINT (o->total_cols))
3323 error ("Window width %d too small (after splitting)", 3376 error ("Window width %d too small (after splitting)",
3324 XFASTINT (o->width) - size_int); 3377 XFASTINT (o->total_cols) - size_int);
3325 if (NILP (o->parent) 3378 if (NILP (o->parent)
3326 || NILP (XWINDOW (o->parent)->hchild)) 3379 || NILP (XWINDOW (o->parent)->hchild))
3327 { 3380 {
@@ -3351,28 +3404,41 @@ SIZE includes that window's scroll bar, or the divider column to its right. */)
3351 p->window_end_valid = Qnil; 3404 p->window_end_valid = Qnil;
3352 bzero (&p->last_cursor, sizeof p->last_cursor); 3405 bzero (&p->last_cursor, sizeof p->last_cursor);
3353 3406
3407 /* Duplicate special geometry settings. */
3408
3409 p->left_margin_cols = o->left_margin_cols;
3410 p->right_margin_cols = o->right_margin_cols;
3411 p->left_fringe_width = o->left_fringe_width;
3412 p->right_fringe_width = o->right_fringe_width;
3413 p->fringes_outside_margins = o->fringes_outside_margins;
3414 p->scroll_bar_width = o->scroll_bar_width;
3415 p->vertical_scroll_bar_type = o->vertical_scroll_bar_type;
3416
3354 /* Apportion the available frame space among the two new windows */ 3417 /* Apportion the available frame space among the two new windows */
3355 3418
3356 if (!NILP (horflag)) 3419 if (!NILP (horflag))
3357 { 3420 {
3358 p->height = o->height; 3421 p->total_lines = o->total_lines;
3359 p->top = o->top; 3422 p->top_line = o->top_line;
3360 XSETFASTINT (p->width, XFASTINT (o->width) - size_int); 3423 XSETFASTINT (p->total_cols, XFASTINT (o->total_cols) - size_int);
3361 XSETFASTINT (o->width, size_int); 3424 XSETFASTINT (o->total_cols, size_int);
3362 XSETFASTINT (p->left, XFASTINT (o->left) + size_int); 3425 XSETFASTINT (p->left_col, XFASTINT (o->left_col) + size_int);
3426 adjust_window_margins (p);
3427 adjust_window_margins (o);
3363 } 3428 }
3364 else 3429 else
3365 { 3430 {
3366 p->left = o->left; 3431 p->left_col = o->left_col;
3367 p->width = o->width; 3432 p->total_cols = o->total_cols;
3368 XSETFASTINT (p->height, XFASTINT (o->height) - size_int); 3433 XSETFASTINT (p->total_lines, XFASTINT (o->total_lines) - size_int);
3369 XSETFASTINT (o->height, size_int); 3434 XSETFASTINT (o->total_lines, size_int);
3370 XSETFASTINT (p->top, XFASTINT (o->top) + size_int); 3435 XSETFASTINT (p->top_line, XFASTINT (o->top_line) + size_int);
3371 } 3436 }
3372 3437
3373 /* Adjust glyph matrices. */ 3438 /* Adjust glyph matrices. */
3374 adjust_glyphs (fo); 3439 adjust_glyphs (fo);
3375 Fset_window_buffer (new, o->buffer); 3440
3441 Fset_window_buffer (new, o->buffer, Qt);
3376 return new; 3442 return new;
3377} 3443}
3378 3444
@@ -3423,7 +3489,7 @@ window_height (window)
3423 Lisp_Object window; 3489 Lisp_Object window;
3424{ 3490{
3425 register struct window *p = XWINDOW (window); 3491 register struct window *p = XWINDOW (window);
3426 return XFASTINT (p->height); 3492 return WINDOW_TOTAL_LINES (p);
3427} 3493}
3428 3494
3429int 3495int
@@ -3431,15 +3497,15 @@ window_width (window)
3431 Lisp_Object window; 3497 Lisp_Object window;
3432{ 3498{
3433 register struct window *p = XWINDOW (window); 3499 register struct window *p = XWINDOW (window);
3434 return XFASTINT (p->width); 3500 return WINDOW_TOTAL_COLS (p);
3435} 3501}
3436 3502
3437 3503
3438#define CURBEG(w) \ 3504#define CURBEG(w) \
3439 *(widthflag ? &(XWINDOW (w)->left) : &(XWINDOW (w)->top)) 3505 *(widthflag ? &(XWINDOW (w)->left_col) : &(XWINDOW (w)->top_line))
3440 3506
3441#define CURSIZE(w) \ 3507#define CURSIZE(w) \
3442 *(widthflag ? &(XWINDOW (w)->width) : &(XWINDOW (w)->height)) 3508 *(widthflag ? &(XWINDOW (w)->total_cols) : &(XWINDOW (w)->total_lines))
3443 3509
3444 3510
3445/* Enlarge WINDOW by DELTA. WIDTHFLAG non-zero means 3511/* Enlarge WINDOW by DELTA. WIDTHFLAG non-zero means
@@ -3770,15 +3836,15 @@ shrink_window_lowest_first (w, height)
3770 windows_or_buffers_changed++; 3836 windows_or_buffers_changed++;
3771 FRAME_WINDOW_SIZES_CHANGED (XFRAME (WINDOW_FRAME (w))) = 1; 3837 FRAME_WINDOW_SIZES_CHANGED (XFRAME (WINDOW_FRAME (w))) = 1;
3772 3838
3773 old_height = XFASTINT (w->height); 3839 old_height = XFASTINT (w->total_lines);
3774 XSETFASTINT (w->height, height); 3840 XSETFASTINT (w->total_lines, height);
3775 3841
3776 if (!NILP (w->hchild)) 3842 if (!NILP (w->hchild))
3777 { 3843 {
3778 for (child = w->hchild; !NILP (child); child = c->next) 3844 for (child = w->hchild; !NILP (child); child = c->next)
3779 { 3845 {
3780 c = XWINDOW (child); 3846 c = XWINDOW (child);
3781 c->top = w->top; 3847 c->top_line = w->top_line;
3782 shrink_window_lowest_first (c, height); 3848 shrink_window_lowest_first (c, height);
3783 } 3849 }
3784 } 3850 }
@@ -3802,23 +3868,23 @@ shrink_window_lowest_first (w, height)
3802 int this_one; 3868 int this_one;
3803 3869
3804 c = XWINDOW (child); 3870 c = XWINDOW (child);
3805 this_one = XFASTINT (c->height) - MIN_SAFE_WINDOW_HEIGHT; 3871 this_one = XFASTINT (c->total_lines) - MIN_SAFE_WINDOW_HEIGHT;
3806 3872
3807 if (this_one > delta) 3873 if (this_one > delta)
3808 this_one = delta; 3874 this_one = delta;
3809 3875
3810 shrink_window_lowest_first (c, XFASTINT (c->height) - this_one); 3876 shrink_window_lowest_first (c, XFASTINT (c->total_lines) - this_one);
3811 delta -= this_one; 3877 delta -= this_one;
3812 } 3878 }
3813 3879
3814 /* Compute new positions. */ 3880 /* Compute new positions. */
3815 last_top = XINT (w->top); 3881 last_top = XINT (w->top_line);
3816 for (child = w->vchild; !NILP (child); child = c->next) 3882 for (child = w->vchild; !NILP (child); child = c->next)
3817 { 3883 {
3818 c = XWINDOW (child); 3884 c = XWINDOW (child);
3819 c->top = make_number (last_top); 3885 c->top_line = make_number (last_top);
3820 shrink_window_lowest_first (c, XFASTINT (c->height)); 3886 shrink_window_lowest_first (c, XFASTINT (c->total_lines));
3821 last_top += XFASTINT (c->height); 3887 last_top += XFASTINT (c->total_lines);
3822 } 3888 }
3823 } 3889 }
3824} 3890}
@@ -3827,15 +3893,15 @@ shrink_window_lowest_first (w, height)
3827/* Save, restore, or check positions and sizes in the window tree 3893/* Save, restore, or check positions and sizes in the window tree
3828 rooted at W. ACTION says what to do. 3894 rooted at W. ACTION says what to do.
3829 3895
3830 If ACTION is CHECK_ORIG_SIZES, check if orig_top and orig_height 3896 If ACTION is CHECK_ORIG_SIZES, check if orig_top_line and
3831 members are valid for all windows in the window tree. Value is 3897 orig_total_lines members are valid for all windows in the window
3832 non-zero if they are valid. 3898 tree. Value is non-zero if they are valid.
3833 3899
3834 If ACTION is SAVE_ORIG_SIZES, save members top and height in 3900 If ACTION is SAVE_ORIG_SIZES, save members top and height in
3835 orig_top and orig_height for all windows in the tree. 3901 orig_top_line and orig_total_lines for all windows in the tree.
3836 3902
3837 If ACTION is RESTORE_ORIG_SIZES, restore top and height from 3903 If ACTION is RESTORE_ORIG_SIZES, restore top and height from values
3838 values stored in orig_top and orig_height for all windows. */ 3904 stored in orig_top_line and orig_total_lines for all windows. */
3839 3905
3840static int 3906static int
3841save_restore_orig_size (w, action) 3907save_restore_orig_size (w, action)
@@ -3860,22 +3926,22 @@ save_restore_orig_size (w, action)
3860 switch (action) 3926 switch (action)
3861 { 3927 {
3862 case CHECK_ORIG_SIZES: 3928 case CHECK_ORIG_SIZES:
3863 if (!INTEGERP (w->orig_top) || !INTEGERP (w->orig_height)) 3929 if (!INTEGERP (w->orig_top_line) || !INTEGERP (w->orig_total_lines))
3864 return 0; 3930 return 0;
3865 break; 3931 break;
3866 3932
3867 case SAVE_ORIG_SIZES: 3933 case SAVE_ORIG_SIZES:
3868 w->orig_top = w->top; 3934 w->orig_top_line = w->top_line;
3869 w->orig_height = w->height; 3935 w->orig_total_lines = w->total_lines;
3870 XSETFASTINT (w->last_modified, 0); 3936 XSETFASTINT (w->last_modified, 0);
3871 XSETFASTINT (w->last_overlay_modified, 0); 3937 XSETFASTINT (w->last_overlay_modified, 0);
3872 break; 3938 break;
3873 3939
3874 case RESTORE_ORIG_SIZES: 3940 case RESTORE_ORIG_SIZES:
3875 xassert (INTEGERP (w->orig_top) && INTEGERP (w->orig_height)); 3941 xassert (INTEGERP (w->orig_top_line) && INTEGERP (w->orig_total_lines));
3876 w->top = w->orig_top; 3942 w->top_line = w->orig_top_line;
3877 w->height = w->orig_height; 3943 w->total_lines = w->orig_total_lines;
3878 w->orig_height = w->orig_top = Qnil; 3944 w->orig_total_lines = w->orig_top_line = Qnil;
3879 XSETFASTINT (w->last_modified, 0); 3945 XSETFASTINT (w->last_modified, 0);
3880 XSETFASTINT (w->last_overlay_modified, 0); 3946 XSETFASTINT (w->last_overlay_modified, 0);
3881 break; 3947 break;
@@ -3915,10 +3981,10 @@ grow_mini_window (w, delta)
3915 if (delta) 3981 if (delta)
3916 { 3982 {
3917 int min_height = window_min_size (root, 0, 0, 0); 3983 int min_height = window_min_size (root, 0, 0, 0);
3918 if (XFASTINT (root->height) - delta < min_height) 3984 if (XFASTINT (root->total_lines) - delta < min_height)
3919 /* Note that the root window may already be smaller than 3985 /* Note that the root window may already be smaller than
3920 min_height. */ 3986 min_height. */
3921 delta = max (0, XFASTINT (root->height) - min_height); 3987 delta = max (0, XFASTINT (root->total_lines) - min_height);
3922 } 3988 }
3923 3989
3924 if (delta) 3990 if (delta)
@@ -3928,11 +3994,11 @@ grow_mini_window (w, delta)
3928 save_restore_orig_size (root, SAVE_ORIG_SIZES); 3994 save_restore_orig_size (root, SAVE_ORIG_SIZES);
3929 3995
3930 /* Shrink other windows. */ 3996 /* Shrink other windows. */
3931 shrink_window_lowest_first (root, XFASTINT (root->height) - delta); 3997 shrink_window_lowest_first (root, XFASTINT (root->total_lines) - delta);
3932 3998
3933 /* Grow the mini-window. */ 3999 /* Grow the mini-window. */
3934 w->top = make_number (XFASTINT (root->top) + XFASTINT (root->height)); 4000 w->top_line = make_number (XFASTINT (root->top_line) + XFASTINT (root->total_lines));
3935 w->height = make_number (XFASTINT (w->height) + delta); 4001 w->total_lines = make_number (XFASTINT (w->total_lines) + delta);
3936 XSETFASTINT (w->last_modified, 0); 4002 XSETFASTINT (w->last_modified, 0);
3937 XSETFASTINT (w->last_overlay_modified, 0); 4003 XSETFASTINT (w->last_overlay_modified, 0);
3938 4004
@@ -3960,13 +4026,13 @@ shrink_mini_window (w)
3960 FRAME_WINDOW_SIZES_CHANGED (f) = 1; 4026 FRAME_WINDOW_SIZES_CHANGED (f) = 1;
3961 windows_or_buffers_changed = 1; 4027 windows_or_buffers_changed = 1;
3962 } 4028 }
3963 else if (XFASTINT (w->height) > 1) 4029 else if (XFASTINT (w->total_lines) > 1)
3964 { 4030 {
3965 /* Distribute the additional lines of the mini-window 4031 /* Distribute the additional lines of the mini-window
3966 among the other windows. */ 4032 among the other windows. */
3967 Lisp_Object window; 4033 Lisp_Object window;
3968 XSETWINDOW (window, w); 4034 XSETWINDOW (window, w);
3969 enlarge_window (window, 1 - XFASTINT (w->height), 0, 0); 4035 enlarge_window (window, 1 - XFASTINT (w->total_lines), 0, 0);
3970 } 4036 }
3971} 4037}
3972 4038
@@ -4001,7 +4067,7 @@ int
4001window_internal_height (w) 4067window_internal_height (w)
4002 struct window *w; 4068 struct window *w;
4003{ 4069{
4004 int ht = XFASTINT (w->height); 4070 int ht = XFASTINT (w->total_lines);
4005 4071
4006 if (!MINI_WINDOW_P (w)) 4072 if (!MINI_WINDOW_P (w))
4007 { 4073 {
@@ -4026,24 +4092,27 @@ window_internal_height (w)
4026 separating W from the sibling to its right. */ 4092 separating W from the sibling to its right. */
4027 4093
4028int 4094int
4029window_internal_width (w) 4095window_box_text_cols (w)
4030 struct window *w; 4096 struct window *w;
4031{ 4097{
4032 struct frame *f = XFRAME (WINDOW_FRAME (w)); 4098 struct frame *f = XFRAME (WINDOW_FRAME (w));
4033 int width = XINT (w->width); 4099 int width = XINT (w->total_cols);
4034 4100
4035 if (FRAME_HAS_VERTICAL_SCROLL_BARS (f)) 4101 if (WINDOW_HAS_VERTICAL_SCROLL_BAR (w))
4036 /* Scroll bars occupy a few columns. */ 4102 /* Scroll bars occupy a few columns. */
4037 width -= FRAME_SCROLL_BAR_COLS (f); 4103 width -= WINDOW_CONFIG_SCROLL_BAR_COLS (w);
4038 else if (!WINDOW_RIGHTMOST_P (w) && !WINDOW_FULL_WIDTH_P (w)) 4104 else if (!FRAME_WINDOW_P (f)
4105 && !WINDOW_RIGHTMOST_P (w) && !WINDOW_FULL_WIDTH_P (w))
4039 /* The column of `|' characters separating side-by-side windows 4106 /* The column of `|' characters separating side-by-side windows
4040 occupies one column only. */ 4107 occupies one column only. */
4041 width -= 1; 4108 width -= 1;
4042 4109
4043 /* On window-systems, areas to the left and right of the window
4044 are used as fringes. */
4045 if (FRAME_WINDOW_P (f)) 4110 if (FRAME_WINDOW_P (f))
4046 width -= FRAME_FRINGE_COLS (f); 4111 /* On window-systems, fringes and display margins cannot be
4112 used for normal text. */
4113 width -= (WINDOW_FRINGE_COLS (w)
4114 + WINDOW_LEFT_MARGIN_COLS (w)
4115 + WINDOW_RIGHT_MARGIN_COLS (w));
4047 4116
4048 return width; 4117 return width;
4049} 4118}
@@ -4148,7 +4217,7 @@ window_scroll_pixel_based (window, n, whole, noerror)
4148 if (whole) 4217 if (whole)
4149 { 4218 {
4150 int screen_full = (window_box_height (w) 4219 int screen_full = (window_box_height (w)
4151 - next_screen_context_lines * CANON_Y_UNIT (it.f)); 4220 - next_screen_context_lines * FRAME_LINE_HEIGHT (it.f));
4152 int dy = n * screen_full; 4221 int dy = n * screen_full;
4153 4222
4154 /* Note that move_it_vertically always moves the iterator to the 4223 /* Note that move_it_vertically always moves the iterator to the
@@ -4245,8 +4314,8 @@ window_scroll_pixel_based (window, n, whole, noerror)
4245 { 4314 {
4246 /* Move PT out of scroll margins. */ 4315 /* Move PT out of scroll margins. */
4247 this_scroll_margin = max (0, scroll_margin); 4316 this_scroll_margin = max (0, scroll_margin);
4248 this_scroll_margin = min (this_scroll_margin, XFASTINT (w->height) / 4); 4317 this_scroll_margin = min (this_scroll_margin, XFASTINT (w->total_lines) / 4);
4249 this_scroll_margin *= CANON_Y_UNIT (it.f); 4318 this_scroll_margin *= FRAME_LINE_HEIGHT (it.f);
4250 4319
4251 if (n > 0) 4320 if (n > 0)
4252 { 4321 {
@@ -4323,7 +4392,7 @@ window_scroll_line_based (window, n, whole, noerror)
4323 4392
4324 posit = *compute_motion (startpos, 0, 0, 0, 4393 posit = *compute_motion (startpos, 0, 0, 0,
4325 PT, ht, 0, 4394 PT, ht, 0,
4326 window_internal_width (w), XINT (w->hscroll), 4395 window_box_text_cols (w), XINT (w->hscroll),
4327 0, w); 4396 0, w);
4328 original_vpos = posit.vpos; 4397 original_vpos = posit.vpos;
4329 4398
@@ -4360,8 +4429,8 @@ window_scroll_line_based (window, n, whole, noerror)
4360 if (this_scroll_margin < 0) 4429 if (this_scroll_margin < 0)
4361 this_scroll_margin = 0; 4430 this_scroll_margin = 0;
4362 4431
4363 if (XINT (w->height) < 4 * scroll_margin) 4432 if (XINT (w->total_lines) < 4 * scroll_margin)
4364 this_scroll_margin = XINT (w->height) / 4; 4433 this_scroll_margin = XINT (w->total_lines) / 4;
4365 4434
4366 set_marker_restricted_both (w->start, w->buffer, pos, pos_byte); 4435 set_marker_restricted_both (w->start, w->buffer, pos, pos_byte);
4367 w->start_at_line_beg = bolp; 4436 w->start_at_line_beg = bolp;
@@ -4611,7 +4680,7 @@ by this function. */)
4611 struct window *w = XWINDOW (selected_window); 4680 struct window *w = XWINDOW (selected_window);
4612 4681
4613 if (NILP (arg)) 4682 if (NILP (arg))
4614 XSETFASTINT (arg, window_internal_width (w) - 2); 4683 XSETFASTINT (arg, window_box_text_cols (w) - 2);
4615 else 4684 else
4616 arg = Fprefix_numeric_value (arg); 4685 arg = Fprefix_numeric_value (arg);
4617 4686
@@ -4641,7 +4710,7 @@ by this function. */)
4641 struct window *w = XWINDOW (selected_window); 4710 struct window *w = XWINDOW (selected_window);
4642 4711
4643 if (NILP (arg)) 4712 if (NILP (arg))
4644 XSETFASTINT (arg, window_internal_width (w) - 2); 4713 XSETFASTINT (arg, window_box_text_cols (w) - 2);
4645 else 4714 else
4646 arg = Fprefix_numeric_value (arg); 4715 arg = Fprefix_numeric_value (arg);
4647 4716
@@ -4715,7 +4784,7 @@ displayed_window_lines (w)
4715 /* Add in empty lines at the bottom of the window. */ 4784 /* Add in empty lines at the bottom of the window. */
4716 if (bottom_y < height) 4785 if (bottom_y < height)
4717 { 4786 {
4718 int uy = CANON_Y_UNIT (it.f); 4787 int uy = FRAME_LINE_HEIGHT (it.f);
4719 it.vpos += (height - bottom_y + uy - 1) / uy; 4788 it.vpos += (height - bottom_y + uy - 1) / uy;
4720 } 4789 }
4721 4790
@@ -4807,7 +4876,7 @@ and redisplay normally--don't erase and redraw the frame. */)
4807 /* If we can't move down NLINES lines because we hit 4876 /* If we can't move down NLINES lines because we hit
4808 the end of the buffer, count in some empty lines. */ 4877 the end of the buffer, count in some empty lines. */
4809 if (it.vpos < nlines) 4878 if (it.vpos < nlines)
4810 y1 += (nlines - it.vpos) * CANON_Y_UNIT (it.f); 4879 y1 += (nlines - it.vpos) * FRAME_LINE_HEIGHT (it.f);
4811 4880
4812 h = window_box_height (w) - (y1 - y0); 4881 h = window_box_height (w) - (y1 - y0);
4813 4882
@@ -4865,7 +4934,7 @@ partial-height lines in the text display area. */)
4865{ 4934{
4866 struct window *w = decode_window (window); 4935 struct window *w = decode_window (window);
4867 int pixel_height = window_box_height (w); 4936 int pixel_height = window_box_height (w);
4868 int line_height = pixel_height / CANON_Y_UNIT (XFRAME (w->frame)); 4937 int line_height = pixel_height / FRAME_LINE_HEIGHT (XFRAME (w->frame));
4869 return make_number (line_height); 4938 return make_number (line_height);
4870} 4939}
4871 4940
@@ -4924,7 +4993,7 @@ struct save_window_data
4924 { 4993 {
4925 EMACS_INT size_from_Lisp_Vector_struct; 4994 EMACS_INT size_from_Lisp_Vector_struct;
4926 struct Lisp_Vector *next_from_Lisp_Vector_struct; 4995 struct Lisp_Vector *next_from_Lisp_Vector_struct;
4927 Lisp_Object frame_width, frame_height, frame_menu_bar_lines; 4996 Lisp_Object frame_cols, frame_lines, frame_menu_bar_lines;
4928 Lisp_Object frame_tool_bar_lines; 4997 Lisp_Object frame_tool_bar_lines;
4929 Lisp_Object selected_frame; 4998 Lisp_Object selected_frame;
4930 Lisp_Object current_window; 4999 Lisp_Object current_window;
@@ -4950,14 +5019,18 @@ struct saved_window
4950 5019
4951 Lisp_Object window; 5020 Lisp_Object window;
4952 Lisp_Object buffer, start, pointm, mark; 5021 Lisp_Object buffer, start, pointm, mark;
4953 Lisp_Object left, top, width, height, hscroll, min_hscroll; 5022 Lisp_Object left_col, top_line, total_cols, total_lines;
5023 Lisp_Object hscroll, min_hscroll;
4954 Lisp_Object parent, prev; 5024 Lisp_Object parent, prev;
4955 Lisp_Object start_at_line_beg; 5025 Lisp_Object start_at_line_beg;
4956 Lisp_Object display_table; 5026 Lisp_Object display_table;
4957 Lisp_Object orig_top, orig_height; 5027 Lisp_Object orig_top_line, orig_total_lines;
5028 Lisp_Object left_margin_cols, right_margin_cols;
5029 Lisp_Object left_fringe_width, right_fringe_width, fringes_outside_margins;
5030 Lisp_Object scroll_bar_width, vertical_scroll_bar_type;
4958}; 5031};
4959 5032
4960#define SAVED_WINDOW_VECTOR_SIZE 17 /* Arg to Fmake_vector */ 5033#define SAVED_WINDOW_VECTOR_SIZE 24 /* Arg to Fmake_vector */
4961 5034
4962#define SAVED_WINDOW_N(swv,n) \ 5035#define SAVED_WINDOW_N(swv,n) \
4963 ((struct saved_window *) (XVECTOR ((swv)->contents[(n)]))) 5036 ((struct saved_window *) (XVECTOR ((swv)->contents[(n)])))
@@ -5041,8 +5114,8 @@ the return value is nil. Otherwise the value is t. */)
5041 made, we change the frame to the size specified in the 5114 made, we change the frame to the size specified in the
5042 configuration, restore the configuration, and then resize it 5115 configuration, restore the configuration, and then resize it
5043 back. We keep track of the prevailing height in these variables. */ 5116 back. We keep track of the prevailing height in these variables. */
5044 int previous_frame_height = FRAME_HEIGHT (f); 5117 int previous_frame_lines = FRAME_LINES (f);
5045 int previous_frame_width = FRAME_WIDTH (f); 5118 int previous_frame_cols = FRAME_COLS (f);
5046 int previous_frame_menu_bar_lines = FRAME_MENU_BAR_LINES (f); 5119 int previous_frame_menu_bar_lines = FRAME_MENU_BAR_LINES (f);
5047 int previous_frame_tool_bar_lines = FRAME_TOOL_BAR_LINES (f); 5120 int previous_frame_tool_bar_lines = FRAME_TOOL_BAR_LINES (f);
5048 5121
@@ -5050,10 +5123,10 @@ the return value is nil. Otherwise the value is t. */)
5050 if it runs during this. */ 5123 if it runs during this. */
5051 BLOCK_INPUT; 5124 BLOCK_INPUT;
5052 5125
5053 if (XFASTINT (data->frame_height) != previous_frame_height 5126 if (XFASTINT (data->frame_lines) != previous_frame_lines
5054 || XFASTINT (data->frame_width) != previous_frame_width) 5127 || XFASTINT (data->frame_cols) != previous_frame_cols)
5055 change_frame_size (f, XFASTINT (data->frame_height), 5128 change_frame_size (f, XFASTINT (data->frame_lines),
5056 XFASTINT (data->frame_width), 0, 0, 0); 5129 XFASTINT (data->frame_cols), 0, 0, 0);
5057#if defined (HAVE_WINDOW_SYSTEM) || defined (MSDOS) 5130#if defined (HAVE_WINDOW_SYSTEM) || defined (MSDOS)
5058 if (XFASTINT (data->frame_menu_bar_lines) 5131 if (XFASTINT (data->frame_menu_bar_lines)
5059 != previous_frame_menu_bar_lines) 5132 != previous_frame_menu_bar_lines)
@@ -5128,7 +5201,7 @@ the return value is nil. Otherwise the value is t. */)
5128 w->prev = Qnil; 5201 w->prev = Qnil;
5129 if (!NILP (w->parent)) 5202 if (!NILP (w->parent))
5130 { 5203 {
5131 if (EQ (p->width, XWINDOW (w->parent)->width)) 5204 if (EQ (p->total_cols, XWINDOW (w->parent)->total_cols))
5132 { 5205 {
5133 XWINDOW (w->parent)->vchild = p->window; 5206 XWINDOW (w->parent)->vchild = p->window;
5134 XWINDOW (w->parent)->hchild = Qnil; 5207 XWINDOW (w->parent)->hchild = Qnil;
@@ -5143,17 +5216,24 @@ the return value is nil. Otherwise the value is t. */)
5143 5216
5144 /* If we squirreled away the buffer in the window's height, 5217 /* If we squirreled away the buffer in the window's height,
5145 restore it now. */ 5218 restore it now. */
5146 if (BUFFERP (w->height)) 5219 if (BUFFERP (w->total_lines))
5147 w->buffer = w->height; 5220 w->buffer = w->total_lines;
5148 w->left = p->left; 5221 w->left_col = p->left_col;
5149 w->top = p->top; 5222 w->top_line = p->top_line;
5150 w->width = p->width; 5223 w->total_cols = p->total_cols;
5151 w->height = p->height; 5224 w->total_lines = p->total_lines;
5152 w->hscroll = p->hscroll; 5225 w->hscroll = p->hscroll;
5153 w->min_hscroll = p->min_hscroll; 5226 w->min_hscroll = p->min_hscroll;
5154 w->display_table = p->display_table; 5227 w->display_table = p->display_table;
5155 w->orig_top = p->orig_top; 5228 w->orig_top_line = p->orig_top_line;
5156 w->orig_height = p->orig_height; 5229 w->orig_total_lines = p->orig_total_lines;
5230 w->left_margin_cols = p->left_margin_cols;
5231 w->right_margin_cols = p->right_margin_cols;
5232 w->left_fringe_width = p->left_fringe_width;
5233 w->right_fringe_width = p->right_fringe_width;
5234 w->fringes_outside_margins = p->fringes_outside_margins;
5235 w->scroll_bar_width = p->scroll_bar_width;
5236 w->vertical_scroll_bar_type = p->vertical_scroll_bar_type;
5157 XSETFASTINT (w->last_modified, 0); 5237 XSETFASTINT (w->last_modified, 0);
5158 XSETFASTINT (w->last_overlay_modified, 0); 5238 XSETFASTINT (w->last_overlay_modified, 0);
5159 5239
@@ -5235,9 +5315,9 @@ the return value is nil. Otherwise the value is t. */)
5235#endif 5315#endif
5236 5316
5237 /* Set the screen height to the value it had before this function. */ 5317 /* Set the screen height to the value it had before this function. */
5238 if (previous_frame_height != FRAME_HEIGHT (f) 5318 if (previous_frame_lines != FRAME_LINES (f)
5239 || previous_frame_width != FRAME_WIDTH (f)) 5319 || previous_frame_cols != FRAME_COLS (f))
5240 change_frame_size (f, previous_frame_height, previous_frame_width, 5320 change_frame_size (f, previous_frame_lines, previous_frame_cols,
5241 0, 0, 0); 5321 0, 0, 0);
5242#if defined (HAVE_WINDOW_SYSTEM) || defined (MSDOS) 5322#if defined (HAVE_WINDOW_SYSTEM) || defined (MSDOS)
5243 if (previous_frame_menu_bar_lines != FRAME_MENU_BAR_LINES (f)) 5323 if (previous_frame_menu_bar_lines != FRAME_MENU_BAR_LINES (f))
@@ -5308,7 +5388,7 @@ delete_all_subwindows (w)
5308 if (!NILP (w->hchild)) 5388 if (!NILP (w->hchild))
5309 delete_all_subwindows (XWINDOW (w->hchild)); 5389 delete_all_subwindows (XWINDOW (w->hchild));
5310 5390
5311 w->height = w->buffer; /* See Fset_window_configuration for excuse. */ 5391 w->total_lines = w->buffer; /* See Fset_window_configuration for excuse. */
5312 5392
5313 if (!NILP (w->buffer)) 5393 if (!NILP (w->buffer))
5314 unshow_buffer (w); 5394 unshow_buffer (w);
@@ -5406,15 +5486,22 @@ save_window_save (window, vector, i)
5406 XSETFASTINT (w->temslot, i++); 5486 XSETFASTINT (w->temslot, i++);
5407 p->window = window; 5487 p->window = window;
5408 p->buffer = w->buffer; 5488 p->buffer = w->buffer;
5409 p->left = w->left; 5489 p->left_col = w->left_col;
5410 p->top = w->top; 5490 p->top_line = w->top_line;
5411 p->width = w->width; 5491 p->total_cols = w->total_cols;
5412 p->height = w->height; 5492 p->total_lines = w->total_lines;
5413 p->hscroll = w->hscroll; 5493 p->hscroll = w->hscroll;
5414 p->min_hscroll = w->min_hscroll; 5494 p->min_hscroll = w->min_hscroll;
5415 p->display_table = w->display_table; 5495 p->display_table = w->display_table;
5416 p->orig_top = w->orig_top; 5496 p->orig_top_line = w->orig_top_line;
5417 p->orig_height = w->orig_height; 5497 p->orig_total_lines = w->orig_total_lines;
5498 p->left_margin_cols = w->left_margin_cols;
5499 p->right_margin_cols = w->right_margin_cols;
5500 p->left_fringe_width = w->left_fringe_width;
5501 p->right_fringe_width = w->right_fringe_width;
5502 p->fringes_outside_margins = w->fringes_outside_margins;
5503 p->scroll_bar_width = w->scroll_bar_width;
5504 p->vertical_scroll_bar_type = w->vertical_scroll_bar_type;
5418 if (!NILP (w->buffer)) 5505 if (!NILP (w->buffer))
5419 { 5506 {
5420 /* Save w's value of point in the window configuration. 5507 /* Save w's value of point in the window configuration.
@@ -5492,8 +5579,8 @@ redirection (see `redirect-frame-focus'). */)
5492 vec = allocate_other_vector (VECSIZE (struct save_window_data)); 5579 vec = allocate_other_vector (VECSIZE (struct save_window_data));
5493 data = (struct save_window_data *)vec; 5580 data = (struct save_window_data *)vec;
5494 5581
5495 XSETFASTINT (data->frame_width, FRAME_WIDTH (f)); 5582 XSETFASTINT (data->frame_cols, FRAME_COLS (f));
5496 XSETFASTINT (data->frame_height, FRAME_HEIGHT (f)); 5583 XSETFASTINT (data->frame_lines, FRAME_LINES (f));
5497 XSETFASTINT (data->frame_menu_bar_lines, FRAME_MENU_BAR_LINES (f)); 5584 XSETFASTINT (data->frame_menu_bar_lines, FRAME_MENU_BAR_LINES (f));
5498 XSETFASTINT (data->frame_tool_bar_lines, FRAME_TOOL_BAR_LINES (f)); 5585 XSETFASTINT (data->frame_tool_bar_lines, FRAME_TOOL_BAR_LINES (f));
5499 data->selected_frame = selected_frame; 5586 data->selected_frame = selected_frame;
@@ -5554,6 +5641,10 @@ A nil width parameter means no margin. */)
5554{ 5641{
5555 struct window *w = decode_window (window); 5642 struct window *w = decode_window (window);
5556 5643
5644 /* TODO: It doesn't make sense to use FLOATs here, since
5645 the rest of the code assumes they are integers.
5646 So don't allow floats! ++KFS */
5647
5557 if (!NILP (left)) 5648 if (!NILP (left))
5558 CHECK_NUMBER_OR_FLOAT (left); 5649 CHECK_NUMBER_OR_FLOAT (left);
5559 if (!NILP (right)) 5650 if (!NILP (right))
@@ -5573,11 +5664,18 @@ A nil width parameter means no margin. */)
5573 if (INTEGERP (right) && XFASTINT (right) == 0) 5664 if (INTEGERP (right) && XFASTINT (right) == 0)
5574 right = Qnil; 5665 right = Qnil;
5575 5666
5576 w->left_margin_width = left; 5667 if (!EQ (w->left_margin_cols, left)
5577 w->right_margin_width = right; 5668 || !EQ (w->right_margin_cols, right))
5669 {
5670 w->left_margin_cols = left;
5671 w->right_margin_cols = right;
5672
5673 adjust_window_margins (w);
5674
5675 ++windows_or_buffers_changed;
5676 adjust_glyphs (XFRAME (WINDOW_FRAME (w)));
5677 }
5578 5678
5579 ++windows_or_buffers_changed;
5580 adjust_glyphs (XFRAME (WINDOW_FRAME (w)));
5581 return Qnil; 5679 return Qnil;
5582} 5680}
5583 5681
@@ -5593,7 +5691,134 @@ as nil. */)
5593 Lisp_Object window; 5691 Lisp_Object window;
5594{ 5692{
5595 struct window *w = decode_window (window); 5693 struct window *w = decode_window (window);
5596 return Fcons (w->left_margin_width, w->right_margin_width); 5694 return Fcons (w->left_margin_cols, w->right_margin_cols);
5695}
5696
5697
5698
5699/***********************************************************************
5700 Fringes
5701 ***********************************************************************/
5702
5703DEFUN ("set-window-fringes", Fset_window_fringes, Sset_window_fringes,
5704 2, 4, 0,
5705 doc: /* Set width of fringes of window WINDOW.
5706
5707If window is nil, set fringes of the currently selected window.
5708Second parameter LEFT-WIDTH specifies the number of pixels to reserve
5709for the left fringe. Third parameter RIGHT-WIDTH does the same for
5710the right fringe. Fourth parameter OUTSIDE-MARGINS non-nil specifies
5711that fringes are drawn outside of the display margins; by default, fringes
5712are drawn between display marginal areas and the text area.
5713A nil width parameter means to use the frame's corresponding fringe width. */)
5714 (window, left, right, outside_margins)
5715 Lisp_Object window, left, right, outside_margins;
5716{
5717 struct window *w = decode_window (window);
5718
5719 if (!NILP (left))
5720 CHECK_NUMBER (left);
5721 if (!NILP (right))
5722 CHECK_NUMBER (right);
5723
5724 if (!EQ (w->left_fringe_width, left)
5725 || !EQ (w->right_fringe_width, right)
5726 || !EQ (w->fringes_outside_margins, outside_margins))
5727 {
5728 w->left_fringe_width = left;
5729 w->right_fringe_width = right;
5730 w->fringes_outside_margins = outside_margins;
5731
5732 adjust_window_margins (w);
5733
5734 clear_glyph_matrix (w->current_matrix);
5735 w->window_end_valid = Qnil;
5736
5737 ++windows_or_buffers_changed;
5738 adjust_glyphs (XFRAME (WINDOW_FRAME (w)));
5739 }
5740
5741 return Qnil;
5742}
5743
5744
5745DEFUN ("window-fringes", Fwindow_fringes, Swindow_fringes,
5746 0, 1, 0,
5747 doc: /* Get width of fringes of window WINDOW.
5748If WINDOW is omitted or nil, use the currently selected window.
5749Value is a list of the form (LEFT-WIDTH RIGHT-WIDTH OUTSIDE-MARGINS).
5750If a window specific fringe width is not set, its width will be returned
5751as nil. */)
5752 (window)
5753 Lisp_Object window;
5754{
5755 struct window *w = decode_window (window);
5756 return Fcons (make_number (WINDOW_LEFT_FRINGE_WIDTH (w)),
5757 Fcons (make_number (WINDOW_RIGHT_FRINGE_WIDTH (w)),
5758 Fcons ((WINDOW_HAS_FRINGES_OUTSIDE_MARGINS (w) ?
5759 Qt : Qnil), Qnil)));
5760}
5761
5762
5763
5764/***********************************************************************
5765 Scroll bars
5766 ***********************************************************************/
5767
5768DEFUN ("set-window-scroll-bars", Fset_window_scroll_bars, Sset_window_scroll_bars,
5769 2, 4, 0,
5770 doc: /* Set width and type of scroll bars of window WINDOW.
5771If window is nil, set scroll bars of the currently selected window.
5772Second parameter WIDTH specifies the pixel width for the scroll bar;
5773this is automatically adjusted to a multiple of the frame column width.
5774Third parameter VERTICAL-TYPE specifies the type of the vertical scroll
5775bar: left, right, or nil.
5776A width of nil and type of t means to use the frame's corresponding value. */)
5777 (window, width, vertical_type, horisontal_type)
5778 Lisp_Object window, width, vertical_type, horisontal_type;
5779{
5780 struct window *w = decode_window (window);
5781
5782 if (!NILP (width))
5783 CHECK_NUMBER (width);
5784
5785 if (XINT (width) == 0)
5786 vertical_type = Qnil;
5787
5788 if (!EQ (w->scroll_bar_width, width)
5789 || !EQ (w->vertical_scroll_bar_type, vertical_type))
5790 {
5791 w->scroll_bar_width = width;
5792 w->vertical_scroll_bar_type = vertical_type;
5793
5794 adjust_window_margins (w);
5795
5796 clear_glyph_matrix (w->current_matrix);
5797 w->window_end_valid = Qnil;
5798
5799 ++windows_or_buffers_changed;
5800 adjust_glyphs (XFRAME (WINDOW_FRAME (w)));
5801 }
5802
5803 return Qnil;
5804}
5805
5806
5807DEFUN ("window-scroll-bars", Fwindow_scroll_bars, Swindow_scroll_bars,
5808 0, 1, 0,
5809 doc: /* Get width and type of scroll bars of window WINDOW.
5810If WINDOW is omitted or nil, use the currently selected window.
5811Value is a list of the form (WIDTH COLS VERTICAL-TYPE HORISONTAL-TYPE). */)
5812 (window)
5813 Lisp_Object window;
5814{
5815 struct window *w = decode_window (window);
5816 return Fcons (make_number ((WINDOW_CONFIG_SCROLL_BAR_WIDTH (w)
5817 ? WINDOW_CONFIG_SCROLL_BAR_WIDTH (w)
5818 : WINDOW_SCROLL_BAR_AREA_WIDTH (w))),
5819 Fcons (make_number (WINDOW_SCROLL_BAR_COLS (w)),
5820 Fcons (w->vertical_scroll_bar_type,
5821 Fcons (Qnil, Qnil))));
5597} 5822}
5598 5823
5599 5824
@@ -5621,7 +5846,7 @@ Value is a multiple of the canonical character height of WINDOW. */)
5621 f = XFRAME (w->frame); 5846 f = XFRAME (w->frame);
5622 5847
5623 if (FRAME_WINDOW_P (f)) 5848 if (FRAME_WINDOW_P (f))
5624 result = CANON_Y_FROM_PIXEL_Y (f, -w->vscroll); 5849 result = FRAME_CANON_Y_FROM_PIXEL_Y (f, -w->vscroll);
5625 else 5850 else
5626 result = make_number (0); 5851 result = make_number (0);
5627 return result; 5852 return result;
@@ -5652,7 +5877,7 @@ multiple of the canonical character height of WINDOW. */)
5652 { 5877 {
5653 int old_dy = w->vscroll; 5878 int old_dy = w->vscroll;
5654 5879
5655 w->vscroll = - CANON_Y_UNIT (f) * XFLOATINT (vscroll); 5880 w->vscroll = - FRAME_LINE_HEIGHT (f) * XFLOATINT (vscroll);
5656 w->vscroll = min (w->vscroll, 0); 5881 w->vscroll = min (w->vscroll, 0);
5657 5882
5658 /* Adjust glyph matrix of the frame if the virtual display 5883 /* Adjust glyph matrix of the frame if the virtual display
@@ -5771,9 +5996,9 @@ compare_window_configurations (c1, c2, ignore_positions)
5771 sw1 = XVECTOR (d1->saved_windows); 5996 sw1 = XVECTOR (d1->saved_windows);
5772 sw2 = XVECTOR (d2->saved_windows); 5997 sw2 = XVECTOR (d2->saved_windows);
5773 5998
5774 if (! EQ (d1->frame_width, d2->frame_width)) 5999 if (! EQ (d1->frame_cols, d2->frame_cols))
5775 return 0; 6000 return 0;
5776 if (! EQ (d1->frame_height, d2->frame_height)) 6001 if (! EQ (d1->frame_lines, d2->frame_lines))
5777 return 0; 6002 return 0;
5778 if (! EQ (d1->frame_menu_bar_lines, d2->frame_menu_bar_lines)) 6003 if (! EQ (d1->frame_menu_bar_lines, d2->frame_menu_bar_lines))
5779 return 0; 6004 return 0;
@@ -5825,13 +6050,13 @@ compare_window_configurations (c1, c2, ignore_positions)
5825 /* Verify that the corresponding windows do match. */ 6050 /* Verify that the corresponding windows do match. */
5826 if (! EQ (p1->buffer, p2->buffer)) 6051 if (! EQ (p1->buffer, p2->buffer))
5827 return 0; 6052 return 0;
5828 if (! EQ (p1->left, p2->left)) 6053 if (! EQ (p1->left_col, p2->left_col))
5829 return 0; 6054 return 0;
5830 if (! EQ (p1->top, p2->top)) 6055 if (! EQ (p1->top_line, p2->top_line))
5831 return 0; 6056 return 0;
5832 if (! EQ (p1->width, p2->width)) 6057 if (! EQ (p1->total_cols, p2->total_cols))
5833 return 0; 6058 return 0;
5834 if (! EQ (p1->height, p2->height)) 6059 if (! EQ (p1->total_lines, p2->total_lines))
5835 return 0; 6060 return 0;
5836 if (! EQ (p1->display_table, p2->display_table)) 6061 if (! EQ (p1->display_table, p2->display_table))
5837 return 0; 6062 return 0;
@@ -5854,6 +6079,20 @@ compare_window_configurations (c1, c2, ignore_positions)
5854 if (NILP (Fequal (p1->mark, p2->mark))) 6079 if (NILP (Fequal (p1->mark, p2->mark)))
5855 return 0; 6080 return 0;
5856 } 6081 }
6082 if (! EQ (p1->left_margin_cols, p2->left_margin_cols))
6083 return 0;
6084 if (! EQ (p1->right_margin_cols, p2->right_margin_cols))
6085 return 0;
6086 if (! EQ (p1->left_fringe_width, p2->left_fringe_width))
6087 return 0;
6088 if (! EQ (p1->right_fringe_width, p2->right_fringe_width))
6089 return 0;
6090 if (! EQ (p1->fringes_outside_margins, p2->fringes_outside_margins))
6091 return 0;
6092 if (! EQ (p1->scroll_bar_width, p2->scroll_bar_width))
6093 return 0;
6094 if (! EQ (p1->vertical_scroll_bar_type, p2->vertical_scroll_bar_type))
6095 return 0;
5857 } 6096 }
5858 6097
5859 return 1; 6098 return 1;
@@ -6152,6 +6391,10 @@ This variable automatically becomes buffer-local when set. */);
6152 defsubr (&Ssave_window_excursion); 6391 defsubr (&Ssave_window_excursion);
6153 defsubr (&Sset_window_margins); 6392 defsubr (&Sset_window_margins);
6154 defsubr (&Swindow_margins); 6393 defsubr (&Swindow_margins);
6394 defsubr (&Sset_window_fringes);
6395 defsubr (&Swindow_fringes);
6396 defsubr (&Sset_window_scroll_bars);
6397 defsubr (&Swindow_scroll_bars);
6155 defsubr (&Swindow_vscroll); 6398 defsubr (&Swindow_vscroll);
6156 defsubr (&Sset_window_vscroll); 6399 defsubr (&Sset_window_vscroll);
6157 defsubr (&Scompare_window_configurations); 6400 defsubr (&Scompare_window_configurations);