diff src/normal.c @ 18135:1868ec23360e v8.1.2062

patch 8.1.2062: the mouse code is spread out Commit: https://github.com/vim/vim/commit/b20b9e14ddd8db111e886ad0494e15b955159426 Author: Bram Moolenaar <Bram@vim.org> Date: Sat Sep 21 20:48:04 2019 +0200 patch 8.1.2062: the mouse code is spread out Problem: The mouse code is spread out. Solution: Move all the mouse code to mouse.c. (Yegappan Lakshmanan, closes #4959)
author Bram Moolenaar <Bram@vim.org>
date Sat, 21 Sep 2019 21:00:07 +0200
parents aeabc666a119
children 5e10ee16f4b4
line wrap: on
line diff
--- a/src/normal.c
+++ b/src/normal.c
@@ -30,14 +30,6 @@ static void	set_vcount_ca(cmdarg_T *cap,
 static int	nv_compare(const void *s1, const void *s2);
 static void	op_colon(oparg_T *oap);
 static void	op_function(oparg_T *oap);
-#if defined(FEAT_MOUSE)
-static void	find_start_of_word(pos_T *);
-static void	find_end_of_word(pos_T *);
-static int	get_mouse_class(char_u *p);
-#endif
-static void	prep_redo(int regname, long, int, int, int, int, int);
-static void	clearop(oparg_T *oap);
-static void	clearopbeep(oparg_T *oap);
 static void	unshift_special(cmdarg_T *cap);
 static void	may_clear_cmdline(void);
 #ifdef FEAT_CMDL_INFO
@@ -55,11 +47,6 @@ static void	nv_error(cmdarg_T *cap);
 static void	nv_help(cmdarg_T *cap);
 static void	nv_addsub(cmdarg_T *cap);
 static void	nv_page(cmdarg_T *cap);
-#ifdef FEAT_MOUSE
-static void	nv_mousescroll(cmdarg_T *cap);
-static void	nv_mouse(cmdarg_T *cap);
-#endif
-static void	nv_scroll_line(cmdarg_T *cap);
 static void	nv_zet(cmdarg_T *cap);
 #ifdef FEAT_GUI
 static void	nv_ver_scrollbar(cmdarg_T *cap);
@@ -2201,1010 +2188,6 @@ op_function(oparg_T *oap UNUSED)
 #endif
 }
 
-#if defined(FEAT_MOUSE) || defined(PROTO)
-/*
- * Do the appropriate action for the current mouse click in the current mode.
- * Not used for Command-line mode.
- *
- * Normal and Visual Mode:
- * event	 modi-	position      visual	   change   action
- *		 fier	cursor			   window
- * left press	  -	yes	    end		    yes
- * left press	  C	yes	    end		    yes	    "^]" (2)
- * left press	  S	yes	end (popup: extend) yes	    "*" (2)
- * left drag	  -	yes	start if moved	    no
- * left relse	  -	yes	start if moved	    no
- * middle press	  -	yes	 if not active	    no	    put register
- * middle press	  -	yes	 if active	    no	    yank and put
- * right press	  -	yes	start or extend	    yes
- * right press	  S	yes	no change	    yes	    "#" (2)
- * right drag	  -	yes	extend		    no
- * right relse	  -	yes	extend		    no
- *
- * Insert or Replace Mode:
- * event	 modi-	position      visual	   change   action
- *		 fier	cursor			   window
- * left press	  -	yes	(cannot be active)  yes
- * left press	  C	yes	(cannot be active)  yes	    "CTRL-O^]" (2)
- * left press	  S	yes	(cannot be active)  yes	    "CTRL-O*" (2)
- * left drag	  -	yes	start or extend (1) no	    CTRL-O (1)
- * left relse	  -	yes	start or extend (1) no	    CTRL-O (1)
- * middle press	  -	no	(cannot be active)  no	    put register
- * right press	  -	yes	start or extend	    yes	    CTRL-O
- * right press	  S	yes	(cannot be active)  yes	    "CTRL-O#" (2)
- *
- * (1) only if mouse pointer moved since press
- * (2) only if click is in same buffer
- *
- * Return TRUE if start_arrow() should be called for edit mode.
- */
-    int
-do_mouse(
-    oparg_T	*oap,		/* operator argument, can be NULL */
-    int		c,		/* K_LEFTMOUSE, etc */
-    int		dir,		/* Direction to 'put' if necessary */
-    long	count,
-    int		fixindent)	/* PUT_FIXINDENT if fixing indent necessary */
-{
-    static int	do_always = FALSE;	/* ignore 'mouse' setting next time */
-    static int	got_click = FALSE;	/* got a click some time back */
-
-    int		which_button;	/* MOUSE_LEFT, _MIDDLE or _RIGHT */
-    int		is_click;	/* If FALSE it's a drag or release event */
-    int		is_drag;	/* If TRUE it's a drag event */
-    int		jump_flags = 0;	/* flags for jump_to_mouse() */
-    pos_T	start_visual;
-    int		moved;		/* Has cursor moved? */
-    int		in_status_line;	/* mouse in status line */
-    static int	in_tab_line = FALSE; /* mouse clicked in tab line */
-    int		in_sep_line;	/* mouse in vertical separator line */
-    int		c1, c2;
-#if defined(FEAT_FOLDING)
-    pos_T	save_cursor;
-#endif
-    win_T	*old_curwin = curwin;
-    static pos_T orig_cursor;
-    colnr_T	leftcol, rightcol;
-    pos_T	end_visual;
-    int		diff;
-    int		old_active = VIsual_active;
-    int		old_mode = VIsual_mode;
-    int		regname;
-
-#if defined(FEAT_FOLDING)
-    save_cursor = curwin->w_cursor;
-#endif
-
-    /*
-     * When GUI is active, always recognize mouse events, otherwise:
-     * - Ignore mouse event in normal mode if 'mouse' doesn't include 'n'.
-     * - Ignore mouse event in visual mode if 'mouse' doesn't include 'v'.
-     * - For command line and insert mode 'mouse' is checked before calling
-     *	 do_mouse().
-     */
-    if (do_always)
-	do_always = FALSE;
-    else
-#ifdef FEAT_GUI
-	if (!gui.in_use)
-#endif
-	{
-	    if (VIsual_active)
-	    {
-		if (!mouse_has(MOUSE_VISUAL))
-		    return FALSE;
-	    }
-	    else if (State == NORMAL && !mouse_has(MOUSE_NORMAL))
-		return FALSE;
-	}
-
-    for (;;)
-    {
-	which_button = get_mouse_button(KEY2TERMCAP1(c), &is_click, &is_drag);
-	if (is_drag)
-	{
-	    /* If the next character is the same mouse event then use that
-	     * one. Speeds up dragging the status line. */
-	    if (vpeekc() != NUL)
-	    {
-		int nc;
-		int save_mouse_row = mouse_row;
-		int save_mouse_col = mouse_col;
-
-		/* Need to get the character, peeking doesn't get the actual
-		 * one. */
-		nc = safe_vgetc();
-		if (c == nc)
-		    continue;
-		vungetc(nc);
-		mouse_row = save_mouse_row;
-		mouse_col = save_mouse_col;
-	    }
-	}
-	break;
-    }
-
-    if (c == K_MOUSEMOVE)
-    {
-	// Mouse moved without a button pressed.
-#ifdef FEAT_BEVAL_TERM
-	ui_may_remove_balloon();
-	if (p_bevalterm)
-	{
-	    profile_setlimit(p_bdlay, &bevalexpr_due);
-	    bevalexpr_due_set = TRUE;
-	}
-#endif
-#ifdef FEAT_TEXT_PROP
-	popup_handle_mouse_moved();
-#endif
-	return FALSE;
-    }
-
-#ifdef FEAT_MOUSESHAPE
-    /* May have stopped dragging the status or separator line.  The pointer is
-     * most likely still on the status or separator line. */
-    if (!is_drag && drag_status_line)
-    {
-	drag_status_line = FALSE;
-	update_mouseshape(SHAPE_IDX_STATUS);
-    }
-    if (!is_drag && drag_sep_line)
-    {
-	drag_sep_line = FALSE;
-	update_mouseshape(SHAPE_IDX_VSEP);
-    }
-#endif
-
-    /*
-     * Ignore drag and release events if we didn't get a click.
-     */
-    if (is_click)
-	got_click = TRUE;
-    else
-    {
-	if (!got_click)			/* didn't get click, ignore */
-	    return FALSE;
-	if (!is_drag)			/* release, reset got_click */
-	{
-	    got_click = FALSE;
-	    if (in_tab_line)
-	    {
-		in_tab_line = FALSE;
-		return FALSE;
-	    }
-	}
-    }
-
-    /*
-     * CTRL right mouse button does CTRL-T
-     */
-    if (is_click && (mod_mask & MOD_MASK_CTRL) && which_button == MOUSE_RIGHT)
-    {
-	if (State & INSERT)
-	    stuffcharReadbuff(Ctrl_O);
-	if (count > 1)
-	    stuffnumReadbuff(count);
-	stuffcharReadbuff(Ctrl_T);
-	got_click = FALSE;		/* ignore drag&release now */
-	return FALSE;
-    }
-
-    /*
-     * CTRL only works with left mouse button
-     */
-    if ((mod_mask & MOD_MASK_CTRL) && which_button != MOUSE_LEFT)
-	return FALSE;
-
-    /*
-     * When a modifier is down, ignore drag and release events, as well as
-     * multiple clicks and the middle mouse button.
-     * Accept shift-leftmouse drags when 'mousemodel' is "popup.*".
-     */
-    if ((mod_mask & (MOD_MASK_SHIFT | MOD_MASK_CTRL | MOD_MASK_ALT
-							     | MOD_MASK_META))
-	    && (!is_click
-		|| (mod_mask & MOD_MASK_MULTI_CLICK)
-		|| which_button == MOUSE_MIDDLE)
-	    && !((mod_mask & (MOD_MASK_SHIFT|MOD_MASK_ALT))
-		&& mouse_model_popup()
-		&& which_button == MOUSE_LEFT)
-	    && !((mod_mask & MOD_MASK_ALT)
-		&& !mouse_model_popup()
-		&& which_button == MOUSE_RIGHT)
-	    )
-	return FALSE;
-
-    /*
-     * If the button press was used as the movement command for an operator
-     * (eg "d<MOUSE>"), or it is the middle button that is held down, ignore
-     * drag/release events.
-     */
-    if (!is_click && which_button == MOUSE_MIDDLE)
-	return FALSE;
-
-    if (oap != NULL)
-	regname = oap->regname;
-    else
-	regname = 0;
-
-    /*
-     * Middle mouse button does a 'put' of the selected text
-     */
-    if (which_button == MOUSE_MIDDLE)
-    {
-	if (State == NORMAL)
-	{
-	    /*
-	     * If an operator was pending, we don't know what the user wanted
-	     * to do. Go back to normal mode: Clear the operator and beep().
-	     */
-	    if (oap != NULL && oap->op_type != OP_NOP)
-	    {
-		clearopbeep(oap);
-		return FALSE;
-	    }
-
-	    /*
-	     * If visual was active, yank the highlighted text and put it
-	     * before the mouse pointer position.
-	     * In Select mode replace the highlighted text with the clipboard.
-	     */
-	    if (VIsual_active)
-	    {
-		if (VIsual_select)
-		{
-		    stuffcharReadbuff(Ctrl_G);
-		    stuffReadbuff((char_u *)"\"+p");
-		}
-		else
-		{
-		    stuffcharReadbuff('y');
-		    stuffcharReadbuff(K_MIDDLEMOUSE);
-		}
-		do_always = TRUE;	/* ignore 'mouse' setting next time */
-		return FALSE;
-	    }
-	    /*
-	     * The rest is below jump_to_mouse()
-	     */
-	}
-
-	else if ((State & INSERT) == 0)
-	    return FALSE;
-
-	/*
-	 * Middle click in insert mode doesn't move the mouse, just insert the
-	 * contents of a register.  '.' register is special, can't insert that
-	 * with do_put().
-	 * Also paste at the cursor if the current mode isn't in 'mouse' (only
-	 * happens for the GUI).
-	 */
-	if ((State & INSERT) || !mouse_has(MOUSE_NORMAL))
-	{
-	    if (regname == '.')
-		insert_reg(regname, TRUE);
-	    else
-	    {
-#ifdef FEAT_CLIPBOARD
-		if (clip_star.available && regname == 0)
-		    regname = '*';
-#endif
-		if ((State & REPLACE_FLAG) && !yank_register_mline(regname))
-		    insert_reg(regname, TRUE);
-		else
-		{
-		    do_put(regname, BACKWARD, 1L, fixindent | PUT_CURSEND);
-
-		    /* Repeat it with CTRL-R CTRL-O r or CTRL-R CTRL-P r */
-		    AppendCharToRedobuff(Ctrl_R);
-		    AppendCharToRedobuff(fixindent ? Ctrl_P : Ctrl_O);
-		    AppendCharToRedobuff(regname == 0 ? '"' : regname);
-		}
-	    }
-	    return FALSE;
-	}
-    }
-
-    /* When dragging or button-up stay in the same window. */
-    if (!is_click)
-	jump_flags |= MOUSE_FOCUS | MOUSE_DID_MOVE;
-
-    start_visual.lnum = 0;
-
-    /* Check for clicking in the tab page line. */
-    if (mouse_row == 0 && firstwin->w_winrow > 0)
-    {
-	if (is_drag)
-	{
-	    if (in_tab_line)
-	    {
-		c1 = TabPageIdxs[mouse_col];
-		tabpage_move(c1 <= 0 ? 9999 : c1 < tabpage_index(curtab)
-								? c1 - 1 : c1);
-	    }
-	    return FALSE;
-	}
-
-	/* click in a tab selects that tab page */
-	if (is_click
-# ifdef FEAT_CMDWIN
-		&& cmdwin_type == 0
-# endif
-		&& mouse_col < Columns)
-	{
-	    in_tab_line = TRUE;
-	    c1 = TabPageIdxs[mouse_col];
-	    if (c1 >= 0)
-	    {
-		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();
-		}
-	    }
-	    else
-	    {
-		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);
-	    }
-	}
-	return TRUE;
-    }
-    else if (is_drag && in_tab_line)
-    {
-	c1 = TabPageIdxs[mouse_col];
-	tabpage_move(c1 <= 0 ? 9999 : c1 - 1);
-	return FALSE;
-    }
-
-    /*
-     * When 'mousemodel' is "popup" or "popup_setpos", translate mouse events:
-     * right button up   -> pop-up menu
-     * shift-left button -> right button
-     * alt-left button   -> alt-right button
-     */
-    if (mouse_model_popup())
-    {
-	if (which_button == MOUSE_RIGHT
-			    && !(mod_mask & (MOD_MASK_SHIFT | MOD_MASK_CTRL)))
-	{
-#if defined(FEAT_GUI_MOTIF) || defined(FEAT_GUI_GTK) \
-	    || defined(FEAT_GUI_ATHENA) || defined(FEAT_GUI_MSWIN) \
-	    || defined(FEAT_GUI_MAC) || defined(FEAT_GUI_PHOTON) \
-	    || defined(FEAT_TERM_POPUP_MENU)
-# ifdef FEAT_GUI
-	    if (gui.in_use)
-	    {
-#  if defined(FEAT_GUI_MOTIF) || defined(FEAT_GUI_GTK) \
-			  || defined(FEAT_GUI_PHOTON) || defined(FEAT_GUI_MAC)
-		if (!is_click)
-		    /* Ignore right button release events, only shows the popup
-		     * menu on the button down event. */
-		    return FALSE;
-#  endif
-#  if defined(FEAT_GUI_ATHENA) || defined(FEAT_GUI_MSWIN)
-		if (is_click || is_drag)
-		    /* Ignore right button down and drag mouse events.  Windows
-		     * only shows the popup menu on the button up event. */
-		    return FALSE;
-#  endif
-	    }
-# endif
-# if defined(FEAT_GUI) && defined(FEAT_TERM_POPUP_MENU)
-	    else
-# endif
-# if defined(FEAT_TERM_POPUP_MENU)
-	    if (!is_click)
-		/* Ignore right button release events, only shows the popup
-		 * menu on the button down event. */
-		return FALSE;
-#endif
-
-	    jump_flags = 0;
-	    if (STRCMP(p_mousem, "popup_setpos") == 0)
-	    {
-		/* First set the cursor position before showing the popup
-		 * menu. */
-		if (VIsual_active)
-		{
-		    pos_T    m_pos;
-
-		    /*
-		     * set MOUSE_MAY_STOP_VIS if we are outside the
-		     * selection or the current window (might have false
-		     * negative here)
-		     */
-		    if (mouse_row < curwin->w_winrow
-			 || mouse_row
-				  > (curwin->w_winrow + curwin->w_height))
-			jump_flags = MOUSE_MAY_STOP_VIS;
-		    else if (get_fpos_of_mouse(&m_pos) != IN_BUFFER)
-			jump_flags = MOUSE_MAY_STOP_VIS;
-		    else
-		    {
-			if ((LT_POS(curwin->w_cursor, VIsual)
-				    && (LT_POS(m_pos, curwin->w_cursor)
-					|| LT_POS(VIsual, m_pos)))
-				|| (LT_POS(VIsual, curwin->w_cursor)
-				    && (LT_POS(m_pos, VIsual)
-				      || LT_POS(curwin->w_cursor, m_pos))))
-			{
-			    jump_flags = MOUSE_MAY_STOP_VIS;
-			}
-			else if (VIsual_mode == Ctrl_V)
-			{
-			    getvcols(curwin, &curwin->w_cursor, &VIsual,
-						     &leftcol, &rightcol);
-			    getvcol(curwin, &m_pos, NULL, &m_pos.col, NULL);
-			    if (m_pos.col < leftcol || m_pos.col > rightcol)
-				jump_flags = MOUSE_MAY_STOP_VIS;
-			}
-		    }
-		}
-		else
-		    jump_flags = MOUSE_MAY_STOP_VIS;
-	    }
-	    if (jump_flags)
-	    {
-		jump_flags = jump_to_mouse(jump_flags, NULL, which_button);
-		update_curbuf(VIsual_active ? INVERTED : VALID);
-		setcursor();
-		out_flush();    /* Update before showing popup menu */
-	    }
-# ifdef FEAT_MENU
-	    show_popupmenu();
-	    got_click = FALSE;	/* ignore release events */
-# endif
-	    return (jump_flags & CURSOR_MOVED) != 0;
-#else
-	    return FALSE;
-#endif
-	}
-	if (which_button == MOUSE_LEFT
-				&& (mod_mask & (MOD_MASK_SHIFT|MOD_MASK_ALT)))
-	{
-	    which_button = MOUSE_RIGHT;
-	    mod_mask &= ~MOD_MASK_SHIFT;
-	}
-    }
-
-    if ((State & (NORMAL | INSERT))
-			    && !(mod_mask & (MOD_MASK_SHIFT | MOD_MASK_CTRL)))
-    {
-	if (which_button == MOUSE_LEFT)
-	{
-	    if (is_click)
-	    {
-		/* stop Visual mode for a left click in a window, but not when
-		 * on a status line */
-		if (VIsual_active)
-		    jump_flags |= MOUSE_MAY_STOP_VIS;
-	    }
-	    else if (mouse_has(MOUSE_VISUAL))
-		jump_flags |= MOUSE_MAY_VIS;
-	}
-	else if (which_button == MOUSE_RIGHT)
-	{
-	    if (is_click && VIsual_active)
-	    {
-		/*
-		 * Remember the start and end of visual before moving the
-		 * cursor.
-		 */
-		if (LT_POS(curwin->w_cursor, VIsual))
-		{
-		    start_visual = curwin->w_cursor;
-		    end_visual = VIsual;
-		}
-		else
-		{
-		    start_visual = VIsual;
-		    end_visual = curwin->w_cursor;
-		}
-	    }
-	    jump_flags |= MOUSE_FOCUS;
-	    if (mouse_has(MOUSE_VISUAL))
-		jump_flags |= MOUSE_MAY_VIS;
-	}
-    }
-
-    /*
-     * If an operator is pending, ignore all drags and releases until the
-     * next mouse click.
-     */
-    if (!is_drag && oap != NULL && oap->op_type != OP_NOP)
-    {
-	got_click = FALSE;
-	oap->motion_type = MCHAR;
-    }
-
-    /* When releasing the button let jump_to_mouse() know. */
-    if (!is_click && !is_drag)
-	jump_flags |= MOUSE_RELEASED;
-
-    /*
-     * JUMP!
-     */
-    jump_flags = jump_to_mouse(jump_flags,
-			oap == NULL ? NULL : &(oap->inclusive), which_button);
-
-#ifdef FEAT_MENU
-    /* A click in the window toolbar has no side effects. */
-    if (jump_flags & MOUSE_WINBAR)
-	return FALSE;
-#endif
-    moved = (jump_flags & CURSOR_MOVED);
-    in_status_line = (jump_flags & IN_STATUS_LINE);
-    in_sep_line = (jump_flags & IN_SEP_LINE);
-
-#ifdef FEAT_NETBEANS_INTG
-    if (isNetbeansBuffer(curbuf)
-			    && !(jump_flags & (IN_STATUS_LINE | IN_SEP_LINE)))
-    {
-	int key = KEY2TERMCAP1(c);
-
-	if (key == (int)KE_LEFTRELEASE || key == (int)KE_MIDDLERELEASE
-					       || key == (int)KE_RIGHTRELEASE)
-	    netbeans_button_release(which_button);
-    }
-#endif
-
-    /* When jumping to another window, clear a pending operator.  That's a bit
-     * friendlier than beeping and not jumping to that window. */
-    if (curwin != old_curwin && oap != NULL && oap->op_type != OP_NOP)
-	clearop(oap);
-
-#ifdef FEAT_FOLDING
-    if (mod_mask == 0
-	    && !is_drag
-	    && (jump_flags & (MOUSE_FOLD_CLOSE | MOUSE_FOLD_OPEN))
-	    && which_button == MOUSE_LEFT)
-    {
-	/* open or close a fold at this line */
-	if (jump_flags & MOUSE_FOLD_OPEN)
-	    openFold(curwin->w_cursor.lnum, 1L);
-	else
-	    closeFold(curwin->w_cursor.lnum, 1L);
-	/* don't move the cursor if still in the same window */
-	if (curwin == old_curwin)
-	    curwin->w_cursor = save_cursor;
-    }
-#endif
-
-#if defined(FEAT_CLIPBOARD) && defined(FEAT_CMDWIN)
-    if ((jump_flags & IN_OTHER_WIN) && !VIsual_active && clip_star.available)
-    {
-	clip_modeless(which_button, is_click, is_drag);
-	return FALSE;
-    }
-#endif
-
-    /* Set global flag that we are extending the Visual area with mouse
-     * dragging; temporarily minimize 'scrolloff'. */
-    if (VIsual_active && is_drag && get_scrolloff_value())
-    {
-	/* In the very first line, allow scrolling one line */
-	if (mouse_row == 0)
-	    mouse_dragging = 2;
-	else
-	    mouse_dragging = 1;
-    }
-
-    /* When dragging the mouse above the window, scroll down. */
-    if (is_drag && mouse_row < 0 && !in_status_line)
-    {
-	scroll_redraw(FALSE, 1L);
-	mouse_row = 0;
-    }
-
-    if (start_visual.lnum)		/* right click in visual mode */
-    {
-       /* When ALT is pressed make Visual mode blockwise. */
-       if (mod_mask & MOD_MASK_ALT)
-	   VIsual_mode = Ctrl_V;
-
-	/*
-	 * In Visual-block mode, divide the area in four, pick up the corner
-	 * that is in the quarter that the cursor is in.
-	 */
-	if (VIsual_mode == Ctrl_V)
-	{
-	    getvcols(curwin, &start_visual, &end_visual, &leftcol, &rightcol);
-	    if (curwin->w_curswant > (leftcol + rightcol) / 2)
-		end_visual.col = leftcol;
-	    else
-		end_visual.col = rightcol;
-	    if (curwin->w_cursor.lnum >=
-				    (start_visual.lnum + end_visual.lnum) / 2)
-		end_visual.lnum = start_visual.lnum;
-
-	    /* move VIsual to the right column */
-	    start_visual = curwin->w_cursor;	    /* save the cursor pos */
-	    curwin->w_cursor = end_visual;
-	    coladvance(end_visual.col);
-	    VIsual = curwin->w_cursor;
-	    curwin->w_cursor = start_visual;	    /* restore the cursor */
-	}
-	else
-	{
-	    /*
-	     * If the click is before the start of visual, change the start.
-	     * If the click is after the end of visual, change the end.  If
-	     * the click is inside the visual, change the closest side.
-	     */
-	    if (LT_POS(curwin->w_cursor, start_visual))
-		VIsual = end_visual;
-	    else if (LT_POS(end_visual, curwin->w_cursor))
-		VIsual = start_visual;
-	    else
-	    {
-		/* In the same line, compare column number */
-		if (end_visual.lnum == start_visual.lnum)
-		{
-		    if (curwin->w_cursor.col - start_visual.col >
-				    end_visual.col - curwin->w_cursor.col)
-			VIsual = start_visual;
-		    else
-			VIsual = end_visual;
-		}
-
-		/* In different lines, compare line number */
-		else
-		{
-		    diff = (curwin->w_cursor.lnum - start_visual.lnum) -
-				(end_visual.lnum - curwin->w_cursor.lnum);
-
-		    if (diff > 0)		/* closest to end */
-			VIsual = start_visual;
-		    else if (diff < 0)	/* closest to start */
-			VIsual = end_visual;
-		    else			/* in the middle line */
-		    {
-			if (curwin->w_cursor.col <
-					(start_visual.col + end_visual.col) / 2)
-			    VIsual = end_visual;
-			else
-			    VIsual = start_visual;
-		    }
-		}
-	    }
-	}
-    }
-    /*
-     * If Visual mode started in insert mode, execute "CTRL-O"
-     */
-    else if ((State & INSERT) && VIsual_active)
-	stuffcharReadbuff(Ctrl_O);
-
-    /*
-     * Middle mouse click: Put text before cursor.
-     */
-    if (which_button == MOUSE_MIDDLE)
-    {
-#ifdef FEAT_CLIPBOARD
-	if (clip_star.available && regname == 0)
-	    regname = '*';
-#endif
-	if (yank_register_mline(regname))
-	{
-	    if (mouse_past_bottom)
-		dir = FORWARD;
-	}
-	else if (mouse_past_eol)
-	    dir = FORWARD;
-
-	if (fixindent)
-	{
-	    c1 = (dir == BACKWARD) ? '[' : ']';
-	    c2 = 'p';
-	}
-	else
-	{
-	    c1 = (dir == FORWARD) ? 'p' : 'P';
-	    c2 = NUL;
-	}
-	prep_redo(regname, count, NUL, c1, NUL, c2, NUL);
-
-	/*
-	 * Remember where the paste started, so in edit() Insstart can be set
-	 * to this position
-	 */
-	if (restart_edit != 0)
-	    where_paste_started = curwin->w_cursor;
-	do_put(regname, dir, count, fixindent | PUT_CURSEND);
-    }
-
-#if defined(FEAT_QUICKFIX)
-    /*
-     * Ctrl-Mouse click or double click in a quickfix window jumps to the
-     * error under the mouse pointer.
-     */
-    else if (((mod_mask & MOD_MASK_CTRL)
-		|| (mod_mask & MOD_MASK_MULTI_CLICK) == MOD_MASK_2CLICK)
-	    && bt_quickfix(curbuf))
-    {
-	if (curwin->w_llist_ref == NULL)	/* quickfix window */
-	    do_cmdline_cmd((char_u *)".cc");
-	else					/* location list window */
-	    do_cmdline_cmd((char_u *)".ll");
-	got_click = FALSE;		/* ignore drag&release now */
-    }
-#endif
-
-    /*
-     * Ctrl-Mouse click (or double click in a help window) jumps to the tag
-     * under the mouse pointer.
-     */
-    else if ((mod_mask & MOD_MASK_CTRL) || (curbuf->b_help
-		     && (mod_mask & MOD_MASK_MULTI_CLICK) == MOD_MASK_2CLICK))
-    {
-	if (State & INSERT)
-	    stuffcharReadbuff(Ctrl_O);
-	stuffcharReadbuff(Ctrl_RSB);
-	got_click = FALSE;		/* ignore drag&release now */
-    }
-
-    /*
-     * Shift-Mouse click searches for the next occurrence of the word under
-     * the mouse pointer
-     */
-    else if ((mod_mask & MOD_MASK_SHIFT))
-    {
-	if ((State & INSERT) || (VIsual_active && VIsual_select))
-	    stuffcharReadbuff(Ctrl_O);
-	if (which_button == MOUSE_LEFT)
-	    stuffcharReadbuff('*');
-	else	/* MOUSE_RIGHT */
-	    stuffcharReadbuff('#');
-    }
-
-    /* Handle double clicks, unless on status line */
-    else if (in_status_line)
-    {
-#ifdef FEAT_MOUSESHAPE
-	if ((is_drag || is_click) && !drag_status_line)
-	{
-	    drag_status_line = TRUE;
-	    update_mouseshape(-1);
-	}
-#endif
-    }
-    else if (in_sep_line)
-    {
-#ifdef FEAT_MOUSESHAPE
-	if ((is_drag || is_click) && !drag_sep_line)
-	{
-	    drag_sep_line = TRUE;
-	    update_mouseshape(-1);
-	}
-#endif
-    }
-    else if ((mod_mask & MOD_MASK_MULTI_CLICK) && (State & (NORMAL | INSERT))
-	     && mouse_has(MOUSE_VISUAL))
-    {
-	if (is_click || !VIsual_active)
-	{
-	    if (VIsual_active)
-		orig_cursor = VIsual;
-	    else
-	    {
-		check_visual_highlight();
-		VIsual = curwin->w_cursor;
-		orig_cursor = VIsual;
-		VIsual_active = TRUE;
-		VIsual_reselect = TRUE;
-		/* start Select mode if 'selectmode' contains "mouse" */
-		may_start_select('o');
-		setmouse();
-	    }
-	    if ((mod_mask & MOD_MASK_MULTI_CLICK) == MOD_MASK_2CLICK)
-	    {
-		/* Double click with ALT pressed makes it blockwise. */
-		if (mod_mask & MOD_MASK_ALT)
-		    VIsual_mode = Ctrl_V;
-		else
-		    VIsual_mode = 'v';
-	    }
-	    else if ((mod_mask & MOD_MASK_MULTI_CLICK) == MOD_MASK_3CLICK)
-		VIsual_mode = 'V';
-	    else if ((mod_mask & MOD_MASK_MULTI_CLICK) == MOD_MASK_4CLICK)
-		VIsual_mode = Ctrl_V;
-#ifdef FEAT_CLIPBOARD
-	    /* Make sure the clipboard gets updated.  Needed because start and
-	     * end may still be the same, and the selection needs to be owned */
-	    clip_star.vmode = NUL;
-#endif
-	}
-	/*
-	 * A double click selects a word or a block.
-	 */
-	if ((mod_mask & MOD_MASK_MULTI_CLICK) == MOD_MASK_2CLICK)
-	{
-	    pos_T	*pos = NULL;
-	    int		gc;
-
-	    if (is_click)
-	    {
-		/* If the character under the cursor (skipping white space) is
-		 * not a word character, try finding a match and select a (),
-		 * {}, [], #if/#endif, etc. block. */
-		end_visual = curwin->w_cursor;
-		while (gc = gchar_pos(&end_visual), VIM_ISWHITE(gc))
-		    inc(&end_visual);
-		if (oap != NULL)
-		    oap->motion_type = MCHAR;
-		if (oap != NULL
-			&& VIsual_mode == 'v'
-			&& !vim_iswordc(gchar_pos(&end_visual))
-			&& EQUAL_POS(curwin->w_cursor, VIsual)
-			&& (pos = findmatch(oap, NUL)) != NULL)
-		{
-		    curwin->w_cursor = *pos;
-		    if (oap->motion_type == MLINE)
-			VIsual_mode = 'V';
-		    else if (*p_sel == 'e')
-		    {
-			if (LT_POS(curwin->w_cursor, VIsual))
-			    ++VIsual.col;
-			else
-			    ++curwin->w_cursor.col;
-		    }
-		}
-	    }
-
-	    if (pos == NULL && (is_click || is_drag))
-	    {
-		/* When not found a match or when dragging: extend to include
-		 * a word. */
-		if (LT_POS(curwin->w_cursor, orig_cursor))
-		{
-		    find_start_of_word(&curwin->w_cursor);
-		    find_end_of_word(&VIsual);
-		}
-		else
-		{
-		    find_start_of_word(&VIsual);
-		    if (*p_sel == 'e' && *ml_get_cursor() != NUL)
-			curwin->w_cursor.col +=
-					 (*mb_ptr2len)(ml_get_cursor());
-		    find_end_of_word(&curwin->w_cursor);
-		}
-	    }
-	    curwin->w_set_curswant = TRUE;
-	}
-	if (is_click)
-	    redraw_curbuf_later(INVERTED);	/* update the inversion */
-    }
-    else if (VIsual_active && !old_active)
-    {
-	if (mod_mask & MOD_MASK_ALT)
-	    VIsual_mode = Ctrl_V;
-	else
-	    VIsual_mode = 'v';
-    }
-
-    /* If Visual mode changed show it later. */
-    if ((!VIsual_active && old_active && mode_displayed)
-	    || (VIsual_active && p_smd && msg_silent == 0
-				 && (!old_active || VIsual_mode != old_mode)))
-	redraw_cmdline = TRUE;
-
-    return moved;
-}
-
-/*
- * Move "pos" back to the start of the word it's in.
- */
-    static void
-find_start_of_word(pos_T *pos)
-{
-    char_u	*line;
-    int		cclass;
-    int		col;
-
-    line = ml_get(pos->lnum);
-    cclass = get_mouse_class(line + pos->col);
-
-    while (pos->col > 0)
-    {
-	col = pos->col - 1;
-	col -= (*mb_head_off)(line, line + col);
-	if (get_mouse_class(line + col) != cclass)
-	    break;
-	pos->col = col;
-    }
-}
-
-/*
- * Move "pos" forward to the end of the word it's in.
- * When 'selection' is "exclusive", the position is just after the word.
- */
-    static void
-find_end_of_word(pos_T *pos)
-{
-    char_u	*line;
-    int		cclass;
-    int		col;
-
-    line = ml_get(pos->lnum);
-    if (*p_sel == 'e' && pos->col > 0)
-    {
-	--pos->col;
-	pos->col -= (*mb_head_off)(line, line + pos->col);
-    }
-    cclass = get_mouse_class(line + pos->col);
-    while (line[pos->col] != NUL)
-    {
-	col = pos->col + (*mb_ptr2len)(line + pos->col);
-	if (get_mouse_class(line + col) != cclass)
-	{
-	    if (*p_sel == 'e')
-		pos->col = col;
-	    break;
-	}
-	pos->col = col;
-    }
-}
-
-/*
- * Get class of a character for selection: same class means same word.
- * 0: blank
- * 1: punctuation groups
- * 2: normal word character
- * >2: multi-byte word character.
- */
-    static int
-get_mouse_class(char_u *p)
-{
-    int		c;
-
-    if (has_mbyte && MB_BYTE2LEN(p[0]) > 1)
-	return mb_get_class(p);
-
-    c = *p;
-    if (c == ' ' || c == '\t')
-	return 0;
-
-    if (vim_iswordc(c))
-	return 2;
-
-    /*
-     * There are a few special cases where we want certain combinations of
-     * characters to be considered as a single word.  These are things like
-     * "->", "/ *", "*=", "+=", "&=", "<=", ">=", "!=" etc.  Otherwise, each
-     * character is in its own class.
-     */
-    if (c != NUL && vim_strchr((char_u *)"-+*/%<>&|^!=", c) != NULL)
-	return 1;
-    return c;
-}
-#endif /* FEAT_MOUSE */
-
 /*
  * Check if  highlighting for visual mode is possible, give a warning message
  * if not.
@@ -3531,7 +2514,7 @@ prep_redo_cmd(cmdarg_T *cap)
  * Prepare for redo of any command.
  * Note that only the last argument can be a multi-byte char.
  */
-    static void
+    void
 prep_redo(
     int	    regname,
     long    num,
@@ -3590,7 +2573,7 @@ checkclearopq(oparg_T *oap)
     return TRUE;
 }
 
-    static void
+    void
 clearop(oparg_T *oap)
 {
     oap->op_type = OP_NOP;
@@ -3599,7 +2582,7 @@ clearop(oparg_T *oap)
     oap->use_reg_one = FALSE;
 }
 
-    static void
+    void
 clearopbeep(oparg_T *oap)
 {
     clearop(oap);
@@ -4513,113 +3496,11 @@ nv_screengo(oparg_T *oap, int dir, long 
     return retval;
 }
 
-#ifdef FEAT_MOUSE
-/*
- * Mouse scroll wheel: Default action is to scroll three lines, or one page
- * when Shift or Ctrl is used.
- * K_MOUSEUP (cap->arg == 1) or K_MOUSEDOWN (cap->arg == 0) or
- * K_MOUSELEFT (cap->arg == -1) or K_MOUSERIGHT (cap->arg == -2)
- */
-    static void
-nv_mousescroll(cmdarg_T *cap)
-{
-    win_T *old_curwin = curwin, *wp;
-
-    if (mouse_row >= 0 && mouse_col >= 0)
-    {
-	int row, col;
-
-	row = mouse_row;
-	col = mouse_col;
-
-	/* find the window at the pointer coordinates */
-	wp = mouse_find_win(&row, &col, FIND_POPUP);
-	if (wp == NULL)
-	    return;
-#ifdef FEAT_TEXT_PROP
-	if (WIN_IS_POPUP(wp) && !wp->w_has_scrollbar)
-	    return;
-#endif
-	curwin = wp;
-	curbuf = curwin->w_buffer;
-    }
-
-    if (cap->arg == MSCR_UP || cap->arg == MSCR_DOWN)
-    {
-# ifdef FEAT_TERMINAL
-	if (term_use_loop())
-	    /* This window is a terminal window, send the mouse event there.
-	     * Set "typed" to FALSE to avoid an endless loop. */
-	    send_keys_to_term(curbuf->b_term, cap->cmdchar, FALSE);
-	else
-# endif
-	if (mod_mask & (MOD_MASK_SHIFT | MOD_MASK_CTRL))
-	{
-	    (void)onepage(cap->arg ? FORWARD : BACKWARD, 1L);
-	}
-	else
-	{
-	    // Don't scroll more than half the window height.
-	    if (curwin->w_height < 6)
-	    {
-		cap->count1 = curwin->w_height / 2;
-		if (cap->count1 == 0)
-		    cap->count1 = 1;
-	    }
-	    else
-		cap->count1 = 3;
-	    cap->count0 = cap->count1;
-	    nv_scroll_line(cap);
-	}
-#ifdef FEAT_TEXT_PROP
-	if (WIN_IS_POPUP(curwin))
-	    popup_set_firstline(curwin);
-#endif
-    }
-# ifdef FEAT_GUI
-    else
-    {
-	/* Horizontal scroll - only allowed when 'wrap' is disabled */
-	if (!curwin->w_p_wrap)
-	{
-	    int val, step = 6;
-
-	    if (mod_mask & (MOD_MASK_SHIFT | MOD_MASK_CTRL))
-		step = curwin->w_width;
-	    val = curwin->w_leftcol + (cap->arg == MSCR_RIGHT ? -step : +step);
-	    if (val < 0)
-		val = 0;
-
-	    gui_do_horiz_scroll(val, TRUE);
-	}
-    }
-# endif
-# ifdef FEAT_SYN_HL
-    if (curwin != old_curwin && curwin->w_p_cul)
-	redraw_for_cursorline(curwin);
-# endif
-
-    curwin->w_redr_status = TRUE;
-
-    curwin = old_curwin;
-    curbuf = curwin->w_buffer;
-}
-
-/*
- * Mouse clicks and drags.
- */
-    static void
-nv_mouse(cmdarg_T *cap)
-{
-    (void)do_mouse(cap->oap, cap->cmdchar, BACKWARD, cap->count1, 0);
-}
-#endif
-
 /*
  * Handle CTRL-E and CTRL-Y commands: scroll a line up or down.
  * cap->arg must be TRUE for CTRL-E.
  */
-    static void
+    void
 nv_scroll_line(cmdarg_T *cap)
 {
     if (!checkclearop(cap->oap))
@@ -7572,9 +6453,7 @@ nv_visual(cmdarg_T *cap)
 	    if (!cap->arg)
 		/* start Select mode when 'selectmode' contains "cmd" */
 		may_start_select('c');
-#ifdef FEAT_MOUSE
 	    setmouse();
-#endif
 	    if (p_smd && msg_silent == 0)
 		redraw_cmdline = TRUE;	    /* show visual mode later */
 	    /*
@@ -7687,9 +6566,7 @@ n_start_visual_mode(int c)
     foldAdjustVisual();
 #endif
 
-#ifdef FEAT_MOUSE
     setmouse();
-#endif
 #ifdef FEAT_CONCEAL
     /* Check for redraw after changing the state. */
     conceal_check_cursor_line();
@@ -7854,9 +6731,7 @@ nv_g_cmd(cmdarg_T *cap)
 		VIsual_select = TRUE;
 	    else
 		may_start_select('c');
-#ifdef FEAT_MOUSE
 	    setmouse();
-#endif
 #ifdef FEAT_CLIPBOARD
 	    /* Make sure the clipboard gets updated.  Needed because start and
 	     * end are still the same, and the selection needs to be owned */