Subject: bug#5615: 23.1.92; [PATCH] term.el: Calculation of window height is bad

From: IRIE Shinsuke <[email-masked]>
Date: Sun, 21 Feb 2010 14:57:46 +0900

When I use term-mode (ansi-term), the bottom row of the terminal
often disappears from the window. For example, if I execute Emacs in
ansi-term with -nw option, the minibuffer is unusable because it becomes
completely hidden. I investigated this problem and found the solution.

In term.el, the number of rows of the terminal window is calculated as:

(1- (window-height))

This expression, however, doesn't always return exact value from lack
of consideration to the header line height and the spacing of each row.
So I tested the better expression instead:

(if (display-graphic-p)
    (let ((e (window-inside-pixel-edges))
          (s (or line-spacing 0)))
      (/ (+ (- (nth 3 e) (cadr e)) s)
         (+ (frame-char-height) s)))
  (window-text-height))

and it seems to work fine. We can test this expression by evaluating
the following code before starting ansi-term:

(add-hook 'term-mode-hook
          (lambda ()
            (fset 'term-window-height
                  #'(lambda ()
                      (if (display-graphic-p)
                          (let ((e (window-inside-pixel-edges))
                                (s (or line-spacing 0)))
                            (/ (+ (- (nth 3 e) (cadr e)) s)
                               (+ (frame-char-height) s)))
                        (window-text-height))))
            (fset 'term-check-size
                  #'(lambda (process)
                      (when (or (/= term-height (term-window-height))
                                (/= term-width (term-window-width)))
                        (term-reset-size (term-window-height) (term-window-width))
                        (set-process-window-size process term-height term-width))))
            (setq term-height (term-window-height))))

or applying the patch I attached.
=== modified file 'lisp/term.el'
*** old/lisp/term.el	2010-02-18 01:32:00 +0000
--- new/lisp/term.el	2010-02-20 18:02:48 +0000
***************
*** 942,947 ****
--- 942,954 ----
  	(window-width)
        (1- (window-width)))))
  
+ (defun term-window-height ()
+   (if (display-graphic-p)
+       (let ((e (window-inside-pixel-edges))
+ 	    (s (or line-spacing 0)))
+ 	(/ (+ (- (nth 3 e) (cadr e)) s)
+ 	   (+ (frame-char-height) s)))
+     (window-text-height)))
  
  (put 'term-mode 'mode-class 'special)
  
***************
*** 1039,1045 ****
    (make-local-variable 'term-height)
    (make-local-variable 'term-width)
    (setq term-width (term-window-width))
!   (setq term-height (1- (window-height)))
    (make-local-variable 'term-terminal-parameter)
    (make-local-variable 'term-saved-cursor)
    (make-local-variable 'term-last-input-start)
--- 1046,1052 ----
    (make-local-variable 'term-height)
    (make-local-variable 'term-width)
    (setq term-width (term-window-width))
!   (setq term-height (term-window-height))
    (make-local-variable 'term-terminal-parameter)
    (make-local-variable 'term-saved-cursor)
    (make-local-variable 'term-last-input-start)
***************
*** 1182,1190 ****
      found))
  
  (defun term-check-size (process)
!   (when (or (/= term-height (1- (window-height)))
  	    (/= term-width (term-window-width)))
!     (term-reset-size (1- (window-height)) (term-window-width))
      (set-process-window-size process term-height term-width)))
  
  (defun term-send-raw-string (chars)
--- 1189,1197 ----
      found))
  
  (defun term-check-size (process)
!   (when (or (/= term-height (term-window-height))
  	    (/= term-width (term-window-width)))
!     (term-reset-size (term-window-height) (term-window-width))
      (set-process-window-size process term-height term-width)))
  
  (defun term-send-raw-string (chars)