comparison src/terminal.c @ 13700:b28d679b1843 v8.0.1722

patch 8.0.1722: cannot specify a minimal size for a terminal window commit https://github.com/vim/vim/commit/498c2562e1bcc72492fe8da8a76504f893e9b5fe Author: Bram Moolenaar <Bram@vim.org> Date: Sun Apr 15 23:45:15 2018 +0200 patch 8.0.1722: cannot specify a minimal size for a terminal window Problem: Cannot specify a minimal size for a terminal window. Solution: Support the "rows*cols" format for 'winsize'.
author Christian Brabandt <cb@256bit.org>
date Mon, 16 Apr 2018 00:00:07 +0200
parents 3b1cfbc70b43
children 7d2039b2ecc8
comparison
equal deleted inserted replaced
13699:6b162e33d63a 13700:b28d679b1843
40 * TODO: 40 * TODO:
41 * - Win32: Make terminal used for :!cmd in the GUI work better. Allow for 41 * - Win32: Make terminal used for :!cmd in the GUI work better. Allow for
42 * redirection. Probably in call to channel_set_pipes(). 42 * redirection. Probably in call to channel_set_pipes().
43 * - Win32: Redirecting output does not work, Test_terminal_redir_file() 43 * - Win32: Redirecting output does not work, Test_terminal_redir_file()
44 * is disabled. 44 * is disabled.
45 * - Copy text in the vterm to the Vim buffer once in a while, so that
46 * completion works.
47 * - When starting terminal window with shell in terminal, then using :gui to 45 * - When starting terminal window with shell in terminal, then using :gui to
48 * switch to GUI, shell stops working. Scrollback seems wrong, command 46 * switch to GUI, shell stops working. Scrollback seems wrong, command
49 * running in shell is still running. 47 * running in shell is still running.
50 * - in GUI vertical split causes problems. Cursor is flickering. (Hirohito
51 * Higashi, 2017 Sep 19)
52 * - after resizing windows overlap. (Boris Staletic, #2164)
53 * - cursor blinks in terminal on widows with a timer. (xtal8, #2142)
54 * - Termdebug does not work when Vim build with mzscheme. gdb hangs.
55 * - After executing a shell command the status line isn't redraw.
56 * - add test for giving error for invalid 'termsize' value.
57 * - support minimal size when 'termsize' is "rows*cols".
58 * - support minimal size when 'termsize' is empty?
59 * - GUI: when using tabs, focus in terminal, click on tab does not work. 48 * - GUI: when using tabs, focus in terminal, click on tab does not work.
49 * - Copy text in the vterm to the Vim buffer once in a while, so that
50 * completion works.
60 * - Redrawing is slow with Athena and Motif. Also other GUI? (Ramel Eshed) 51 * - Redrawing is slow with Athena and Motif. Also other GUI? (Ramel Eshed)
61 * - For the GUI fill termios with default values, perhaps like pangoterm: 52 * - For the GUI fill termios with default values, perhaps like pangoterm:
62 * http://bazaar.launchpad.net/~leonerd/pangoterm/trunk/view/head:/main.c#L134 53 * http://bazaar.launchpad.net/~leonerd/pangoterm/trunk/view/head:/main.c#L134
63 * - When 'encoding' is not utf-8, or the job is using another encoding, setup 54 * - When 'encoding' is not utf-8, or the job is using another encoding, setup
64 * conversions. 55 * conversions.
56 * - Termdebug does not work when Vim build with mzscheme: gdb hangs just after
57 * "run". Everything else works, including communication channel. Not
58 * initializing mzscheme avoid the problem, thus it's not some #ifdef.
65 */ 59 */
66 60
67 #include "vim.h" 61 #include "vim.h"
68 62
69 #if defined(FEAT_TERMINAL) || defined(PROTO) 63 #if defined(FEAT_TERMINAL) || defined(PROTO)
131 char_u *tl_kill; 125 char_u *tl_kill;
132 126
133 /* last known vterm size */ 127 /* last known vterm size */
134 int tl_rows; 128 int tl_rows;
135 int tl_cols; 129 int tl_cols;
136 /* vterm size does not follow window size */
137 int tl_rows_fixed;
138 int tl_cols_fixed;
139 130
140 char_u *tl_title; /* NULL or allocated */ 131 char_u *tl_title; /* NULL or allocated */
141 char_u *tl_status_text; /* NULL or allocated */ 132 char_u *tl_status_text; /* NULL or allocated */
142 133
143 /* Range of screen rows to update. Zero based. */ 134 /* Range of screen rows to update. Zero based. */
206 /************************************** 197 /**************************************
207 * 1. Generic code for all systems. 198 * 1. Generic code for all systems.
208 */ 199 */
209 200
210 /* 201 /*
202 * Parse 'termsize' and set "rows" and "cols" for the terminal size in the
203 * current window.
204 * Sets "rows" and/or "cols" to zero when it should follow the window size.
205 * Return TRUE if the size is the minimum size: "24*80".
206 */
207 static int
208 parse_termsize(win_T *wp, int *rows, int *cols)
209 {
210 int minsize = FALSE;
211
212 *rows = 0;
213 *cols = 0;
214
215 if (*wp->w_p_tms != NUL)
216 {
217 char_u *p = vim_strchr(wp->w_p_tms, 'x');
218
219 /* Syntax of value was already checked when it's set. */
220 if (p == NULL)
221 {
222 minsize = TRUE;
223 p = vim_strchr(wp->w_p_tms, '*');
224 }
225 *rows = atoi((char *)wp->w_p_tms);
226 *cols = atoi((char *)p + 1);
227 }
228 return minsize;
229 }
230
231 /*
211 * Determine the terminal size from 'termsize' and the current window. 232 * Determine the terminal size from 'termsize' and the current window.
212 * Assumes term->tl_rows and term->tl_cols are zero.
213 */ 233 */
214 static void 234 static void
215 set_term_and_win_size(term_T *term) 235 set_term_and_win_size(term_T *term)
216 { 236 {
217 #ifdef FEAT_GUI 237 #ifdef FEAT_GUI
222 term->tl_rows = Rows; 242 term->tl_rows = Rows;
223 term->tl_cols = Columns; 243 term->tl_cols = Columns;
224 return; 244 return;
225 } 245 }
226 #endif 246 #endif
227 if (*curwin->w_p_tms != NUL) 247 if (parse_termsize(curwin, &term->tl_rows, &term->tl_cols))
228 { 248 {
229 char_u *p = vim_strchr(curwin->w_p_tms, 'x') + 1; 249 if (term->tl_rows != 0)
230 250 term->tl_rows = MAX(term->tl_rows, curwin->w_height);
231 term->tl_rows = atoi((char *)curwin->w_p_tms); 251 if (term->tl_cols != 0)
232 term->tl_cols = atoi((char *)p); 252 term->tl_cols = MAX(term->tl_cols, curwin->w_width);
233 } 253 }
234 if (term->tl_rows == 0) 254 if (term->tl_rows == 0)
235 term->tl_rows = curwin->w_height; 255 term->tl_rows = curwin->w_height;
236 else 256 else
237 {
238 win_setheight_win(term->tl_rows, curwin); 257 win_setheight_win(term->tl_rows, curwin);
239 term->tl_rows_fixed = TRUE;
240 }
241 if (term->tl_cols == 0) 258 if (term->tl_cols == 0)
242 term->tl_cols = curwin->w_width; 259 term->tl_cols = curwin->w_width;
243 else 260 else
244 {
245 win_setwidth_win(term->tl_cols, curwin); 261 win_setwidth_win(term->tl_cols, curwin);
246 term->tl_cols_fixed = TRUE;
247 }
248 } 262 }
249 263
250 /* 264 /*
251 * Initialize job options for a terminal job. 265 * Initialize job options for a terminal job.
252 * Caller may overrule some of them. 266 * Caller may overrule some of them.
2851 term_T *term = wp->w_buffer->b_term; 2865 term_T *term = wp->w_buffer->b_term;
2852 VTerm *vterm; 2866 VTerm *vterm;
2853 VTermScreen *screen; 2867 VTermScreen *screen;
2854 VTermState *state; 2868 VTermState *state;
2855 VTermPos pos; 2869 VTermPos pos;
2870 int rows, cols;
2871 int newrows, newcols;
2872 int minsize;
2873 win_T *twp;
2856 2874
2857 if (term == NULL || term->tl_vterm == NULL || term->tl_normal_mode) 2875 if (term == NULL || term->tl_vterm == NULL || term->tl_normal_mode)
2858 return FAIL; 2876 return FAIL;
2859 2877
2860 vterm = term->tl_vterm; 2878 vterm = term->tl_vterm;
2869 2887
2870 /* 2888 /*
2871 * If the window was resized a redraw will be triggered and we get here. 2889 * If the window was resized a redraw will be triggered and we get here.
2872 * Adjust the size of the vterm unless 'termsize' specifies a fixed size. 2890 * Adjust the size of the vterm unless 'termsize' specifies a fixed size.
2873 */ 2891 */
2874 if ((!term->tl_rows_fixed && term->tl_rows != wp->w_height) 2892 minsize = parse_termsize(wp, &rows, &cols);
2875 || (!term->tl_cols_fixed && term->tl_cols != wp->w_width)) 2893
2876 { 2894 newrows = 99999;
2877 int rows = term->tl_rows_fixed ? term->tl_rows : wp->w_height; 2895 newcols = 99999;
2878 int cols = term->tl_cols_fixed ? term->tl_cols : wp->w_width; 2896 FOR_ALL_WINDOWS(twp)
2879 win_T *twp; 2897 {
2880 2898 /* When more than one window shows the same terminal, use the
2881 FOR_ALL_WINDOWS(twp) 2899 * smallest size. */
2882 { 2900 if (twp->w_buffer == term->tl_buffer)
2883 /* When more than one window shows the same terminal, use the 2901 {
2884 * smallest size. */ 2902 newrows = MIN(newrows, twp->w_height);
2885 if (twp->w_buffer == term->tl_buffer) 2903 newcols = MIN(newcols, twp->w_width);
2886 { 2904 }
2887 if (!term->tl_rows_fixed && rows > twp->w_height) 2905 }
2888 rows = twp->w_height; 2906 newrows = rows == 0 ? newrows : minsize ? MAX(rows, newrows) : rows;
2889 if (!term->tl_cols_fixed && cols > twp->w_width) 2907 newcols = cols == 0 ? newcols : minsize ? MAX(cols, newcols) : cols;
2890 cols = twp->w_width; 2908
2891 } 2909 if (term->tl_rows != newrows || term->tl_cols != newcols)
2892 } 2910 {
2911
2893 2912
2894 term->tl_vterm_size_changed = TRUE; 2913 term->tl_vterm_size_changed = TRUE;
2895 vterm_set_size(vterm, rows, cols); 2914 vterm_set_size(vterm, newrows, newcols);
2896 ch_log(term->tl_job->jv_channel, "Resizing terminal to %d lines", 2915 ch_log(term->tl_job->jv_channel, "Resizing terminal to %d lines",
2897 rows); 2916 newrows);
2898 term_report_winsize(term, rows, cols); 2917 term_report_winsize(term, newrows, newcols);
2899 } 2918 }
2900 2919
2901 /* The cursor may have been moved when resizing. */ 2920 /* The cursor may have been moved when resizing. */
2902 vterm_state_get_cursorpos(state, &pos); 2921 vterm_state_get_cursorpos(state, &pos);
2903 position_cursor(wp, &pos); 2922 position_cursor(wp, &pos);