aboutsummaryrefslogtreecommitdiff
path: root/src/nvim/mouse.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/nvim/mouse.c')
-rw-r--r--src/nvim/mouse.c140
1 files changed, 75 insertions, 65 deletions
diff --git a/src/nvim/mouse.c b/src/nvim/mouse.c
index 8fe3864424..506a428243 100644
--- a/src/nvim/mouse.c
+++ b/src/nvim/mouse.c
@@ -15,14 +15,15 @@
#include "nvim/eval/typval.h"
#include "nvim/ex_docmd.h"
#include "nvim/fold.h"
-#include "nvim/func_attr.h"
#include "nvim/getchar.h"
#include "nvim/globals.h"
#include "nvim/grid.h"
+#include "nvim/grid_defs.h"
#include "nvim/keycodes.h"
#include "nvim/macros_defs.h"
-#include "nvim/mark.h"
+#include "nvim/mark_defs.h"
#include "nvim/mbyte.h"
+#include "nvim/mbyte_defs.h"
#include "nvim/memline.h"
#include "nvim/memory.h"
#include "nvim/menu.h"
@@ -38,7 +39,9 @@
#include "nvim/pos_defs.h"
#include "nvim/search.h"
#include "nvim/state.h"
+#include "nvim/state_defs.h"
#include "nvim/statusline.h"
+#include "nvim/statusline_defs.h"
#include "nvim/strings.h"
#include "nvim/types_defs.h"
#include "nvim/ui.h"
@@ -133,6 +136,26 @@ static void move_tab_to_mouse(void)
tabpage_move(tabnr);
}
}
+/// Close the current or specified tab page.
+///
+/// @param c1 tabpage number, or 999 for the current tabpage
+static void mouse_tab_close(int c1)
+{
+ tabpage_T *tp;
+
+ if (c1 == 999) {
+ tp = curtab;
+ } else {
+ tp = find_tabpage(c1);
+ }
+ if (tp == curtab) {
+ if (first_tabpage->tp_next != NULL) {
+ tabpage_close(false);
+ }
+ } else if (tp != NULL) {
+ tabpage_close_other(tp, false);
+ }
+}
static bool got_click = false; // got a click some time back
@@ -189,7 +212,7 @@ static void call_click_def_func(StlClickDefinition *click_defs, int col, int whi
}
};
typval_T rettv;
- (void)call_vim_function(click_defs[col].func, ARRAY_SIZE(argv), argv, &rettv);
+ call_vim_function(click_defs[col].func, ARRAY_SIZE(argv), argv, &rettv);
tv_clear(&rettv);
// Make sure next click does not register as drag when callback absorbs the release event.
got_click = false;
@@ -231,7 +254,7 @@ static int get_fpos_of_mouse(pos_T *mpos)
return IN_STATUS_LINE;
}
- if (winrow == -1 && wp->w_winbar_height != 0) {
+ if (winrow < 0 && winrow + wp->w_winbar_height >= 0) {
return MOUSE_WINBAR;
}
@@ -484,43 +507,32 @@ bool do_mouse(oparg_T *oap, int c, int dir, int count, bool fixindent)
if (is_click && cmdwin_type == 0 && mouse_col < Columns) {
in_tab_line = true;
c1 = tab_page_click_defs[mouse_col].tabnr;
+
switch (tab_page_click_defs[mouse_col].type) {
case kStlClickDisabled:
break;
- case kStlClickTabClose: {
- tabpage_T *tp;
-
- // Close the current or specified tab page.
- if (c1 == 999) {
- tp = curtab;
- } else {
- tp = find_tabpage(c1);
- }
- if (tp == curtab) {
- if (first_tabpage->tp_next != NULL) {
- tabpage_close(false);
- }
- } else if (tp != NULL) {
- tabpage_close_other(tp, false);
- }
- break;
- }
case kStlClickTabSwitch:
- if ((mod_mask & MOD_MASK_MULTI_CLICK) == MOD_MASK_2CLICK) {
- // double click opens new page
- end_visual_mode();
- tabpage_new();
- tabpage_move(c1 == 0 ? 9999 : c1 - 1);
- } else {
- // Go to specified tab page, or next one if not clicking
- // on a label.
- goto_tabpage(c1);
-
- // It's like clicking on the status line of a window.
- if (curwin != old_curwin) {
+ if (which_button != MOUSE_MIDDLE) {
+ if ((mod_mask & MOD_MASK_MULTI_CLICK) == MOD_MASK_2CLICK) {
+ // double click opens new page
end_visual_mode();
+ tabpage_new();
+ tabpage_move(c1 == 0 ? 9999 : c1 - 1);
+ } else {
+ // Go to specified tab page, or next one if not clicking
+ // on a label.
+ goto_tabpage(c1);
+
+ // It's like clicking on the status line of a window.
+ if (curwin != old_curwin) {
+ end_visual_mode();
+ }
}
+ break;
}
+ FALLTHROUGH;
+ case kStlClickTabClose:
+ mouse_tab_close(c1);
break;
case kStlClickFuncRun:
call_click_def_func(tab_page_click_defs, mouse_col, which_button);
@@ -1012,7 +1024,7 @@ void do_mousescroll(cmdarg_T *cap)
// Vertical scrolling
if ((State & MODE_NORMAL) && shift_or_ctrl) {
// whole page up or down
- (void)onepage(cap->arg ? FORWARD : BACKWARD, 1);
+ onepage(cap->arg ? FORWARD : BACKWARD, 1);
} else {
if (shift_or_ctrl) {
// whole page up or down
@@ -1032,7 +1044,7 @@ void do_mousescroll(cmdarg_T *cap)
if (leftcol < 0) {
leftcol = 0;
}
- (void)do_mousescroll_horiz(leftcol);
+ do_mousescroll_horiz(leftcol);
}
}
@@ -1251,7 +1263,7 @@ retnomove:
bool below_window = grid == DEFAULT_GRID_HANDLE && row + wp->w_winbar_height >= wp->w_height;
on_status_line = below_window && row + wp->w_winbar_height - wp->w_height + 1 == 1;
on_sep_line = grid == DEFAULT_GRID_HANDLE && col >= wp->w_width && col - wp->w_width + 1 == 1;
- on_winbar = row == -1 && wp->w_winbar_height != 0;
+ on_winbar = row < 0 && row + wp->w_winbar_height >= 0;
on_statuscol = !below_window && !on_status_line && !on_sep_line && !on_winbar
&& *wp->w_p_stc != NUL
&& (wp->w_p_rl
@@ -1323,18 +1335,18 @@ retnomove:
&& !sep_line_offset
&& (wp->w_p_rl
? col < wp->w_width_inner - fdc
- : col >= fdc + (cmdwin_type == 0 && wp == curwin ? 0 : 1))
+ : col >= fdc + (wp != cmdwin_win ? 0 : 1))
&& (flags & MOUSE_MAY_STOP_VIS)))) {
end_visual_mode();
redraw_curbuf_later(UPD_INVERTED); // delete the inversion
}
- if (cmdwin_type != 0 && wp != curwin) {
+ if (cmdwin_type != 0 && wp != cmdwin_win) {
// A click outside the command-line window: Use modeless
// selection if possible. Allow dragging the status lines.
sep_line_offset = 0;
row = 0;
col += wp->w_wincol;
- wp = curwin;
+ wp = cmdwin_win;
}
// Only change window focus when not clicking on or dragging the
// status line. Do change focus when releasing the mouse button
@@ -1418,7 +1430,7 @@ retnomove:
break;
}
first = false;
- (void)hasFolding(curwin->w_topline, &curwin->w_topline, NULL);
+ hasFolding(curwin->w_topline, &curwin->w_topline, NULL);
if (curwin->w_topfill < win_get_fill(curwin, curwin->w_topline)) {
curwin->w_topfill++;
} else {
@@ -1568,9 +1580,6 @@ void nv_mousescroll(cmdarg_T *cap)
// Call the common mouse scroll function shared with other modes.
do_mousescroll(cap);
- if (curwin != old_curwin && curwin->w_p_cul) {
- redraw_for_cursorline(curwin);
- }
curwin->w_redr_status = true;
curwin = old_curwin;
curbuf = curwin->w_buffer;
@@ -1579,7 +1588,7 @@ void nv_mousescroll(cmdarg_T *cap)
/// Mouse clicks and drags.
void nv_mouse(cmdarg_T *cap)
{
- (void)do_mouse(cap->oap, cap->cmdchar, BACKWARD, cap->count1, 0);
+ do_mouse(cap->oap, cap->cmdchar, BACKWARD, cap->count1, 0);
}
/// Compute the position in the buffer line from the posn on the screen in
@@ -1628,7 +1637,7 @@ bool mouse_comp_pos(win_T *win, int *rowp, int *colp, linenr_T *lnump)
break; // Position is in this buffer line.
}
- (void)hasFoldingWin(win, lnum, NULL, &lnum, true, NULL);
+ hasFoldingWin(win, lnum, NULL, &lnum, true, NULL);
if (lnum == win->w_buffer->b_ml.ml_line_count) {
retval = true;
@@ -1722,7 +1731,7 @@ static win_T *mouse_find_grid_win(int *gridp, int *rowp, int *colp)
} else if (*gridp > 1) {
win_T *wp = get_win_by_grid_handle(*gridp);
if (wp && wp->w_grid_alloc.chars
- && !(wp->w_floating && !wp->w_float_config.focusable)) {
+ && !(wp->w_floating && !wp->w_config.focusable)) {
*rowp = MIN(*rowp - wp->w_grid.row_offset, wp->w_grid.rows - 1);
*colp = MIN(*colp - wp->w_grid.col_offset, wp->w_grid.cols - 1);
return wp;
@@ -1753,22 +1762,23 @@ colnr_T vcol2col(win_T *wp, linenr_T lnum, colnr_T vcol, colnr_T *coladdp)
{
// try to advance to the specified column
char *line = ml_get_buf(wp->w_buffer, lnum);
- chartabsize_T cts;
- init_chartabsize_arg(&cts, wp, lnum, 0, line, line);
- while (cts.cts_vcol < vcol && *cts.cts_ptr != NUL) {
- int size = win_lbr_chartabsize(&cts, NULL);
- if (cts.cts_vcol + size > vcol) {
+ CharsizeArg csarg;
+ CSType cstype = init_charsize_arg(&csarg, wp, lnum, line);
+ StrCharInfo ci = utf_ptr2StrCharInfo(line);
+ int cur_vcol = 0;
+ while (cur_vcol < vcol && *ci.ptr != NUL) {
+ int next_vcol = cur_vcol + win_charsize(cstype, cur_vcol, ci.ptr, ci.chr.value, &csarg).width;
+ if (next_vcol > vcol) {
break;
}
- cts.cts_vcol += size;
- MB_PTR_ADV(cts.cts_ptr);
+ cur_vcol = next_vcol;
+ ci = utfc_next(ci);
}
- clear_chartabsize_arg(&cts);
if (coladdp != NULL) {
- *coladdp = vcol - cts.cts_vcol;
+ *coladdp = vcol - cur_vcol;
}
- return (colnr_T)(cts.cts_ptr - line);
+ return (colnr_T)(ci.ptr - line);
}
/// Set UI mouse depending on current mode and 'mouse'.
@@ -1850,13 +1860,13 @@ static void mouse_check_grid(colnr_T *vcolp, int *flagsp)
int click_col = mouse_col;
// XXX: this doesn't change click_grid if it is 1, even with multigrid
- win_T *wp = mouse_find_win(&click_grid, &click_row, &click_col);
- // Only use vcols[] after the window was redrawn. Mainly matters
- // for tests, a user would not click before redrawing.
- if (wp == NULL || wp->w_redr_type != 0) {
+ if (mouse_find_win(&click_grid, &click_row, &click_col) != curwin
+ // Only use vcols[] after the window was redrawn. Mainly matters
+ // for tests, a user would not click before redrawing.
+ || curwin->w_redr_type != 0) {
return;
}
- ScreenGrid *gp = &wp->w_grid;
+ ScreenGrid *gp = &curwin->w_grid;
int start_row = 0;
int start_col = 0;
grid_adjust(&gp, &start_row, &start_col);
@@ -1892,12 +1902,12 @@ static void mouse_check_grid(colnr_T *vcolp, int *flagsp)
if (eol_vcol < 0) {
// Empty line or whole line before w_leftcol,
// with columns before buffer text
- eol_vcol = wp->w_leftcol - 1;
+ eol_vcol = curwin->w_leftcol - 1;
}
*vcolp = eol_vcol + (int)(off - off_r);
} else {
// Empty line or whole line before w_leftcol
- *vcolp = click_col - start_col + wp->w_leftcol;
+ *vcolp = click_col - start_col + curwin->w_leftcol;
}
} else if (col_from_screen >= 0) {
// Use the virtual column from vcols[], it is accurate also after
@@ -1941,7 +1951,7 @@ void f_getmousepos(typval_T *argvars, typval_T *rettv, EvalFuncData fptr)
winrow = row + 1 + wp->w_winrow_off; // Adjust by 1 for top border
wincol = col + 1 + wp->w_wincol_off; // Adjust by 1 for left border
if (row >= 0 && row < wp->w_height && col >= 0 && col < wp->w_width) {
- (void)mouse_comp_pos(wp, &row, &col, &lnum);
+ mouse_comp_pos(wp, &row, &col, &lnum);
col = vcol2col(wp, lnum, col, &coladd);
column = col + 1;
}