[scinterm] [textadept] Re: [code] [textadept] Sync Curses Cursor for tmux Copy Mode

From: <cavoegele.att.gmail.com>
Date: Mon, 14 Aug 2017 21:20:43 -0700

Hi Mitchell,

On Mon, Aug 14, 2017 at 02:44:55PM -0400, Mitchell wrote:
> Hi Chad,
>
> On Sun, 13 Aug 2017, cavoegele.att.gmail.com wrote:
>
> > Hi Textadept Users!
> >
> > One bit of functionality I miss from Vim is the seamless transition from
> > Vim to tmux copy mode. The tmux cursor starts at the current position of
> > the Vim cursor. In textadept-curses, the tmux cursor always starts at
> > the bottom-left corner of the screen.
> >
> > I dug into this issue a bit and it's caused by Scintilla drawing the
> > caret as a single, inverted-color character and hiding the terminal
> > cursor. Tmux copy mode starts from the position of the terminal cursor.
> > A workaround in the patch below is to move the terminal cursor to the
> > current position of the Scintilla caret after painting is finished. This
> > works for screen and tmux including for split views. However it doesn't
> > work for the command entry cursor.
> >
> > Any chance we can get this patch cleaned up and merged upstream?
> >
> > [snip]
>
> I think Scinterm[1] is a more appropriate place to put this patch, perhaps in the `NoutRefresh()` function[2]. A potential benefit is that since Textadept's command entry is a Scintilla window, the cursor should be updated on paint.
>
> If you want to take a stab at it, go for it. Otherwise I'll see what I can do when I have some time.
>
> Cheers,
> Mitchell
>
> [1]: http://foicica.com/scinterm/
> [2]: http://foicica.com/hg/scinterm/file/938cfedd428a/ScintillaTerm.cxx#l1205

You are a magician! Moving the patch to the scinterm `NoutRefresh()`
function fixed the command entry issue, simplified the code, and will
add the functionality for other ScintillaTerm clients.

One issue however is that textadept redraws all panes on refresh. If the
cursor isn't in the last drawn pane, then the physical cursor ends in
the wrong spot. This can be remedied by explicitly drawing the
`focused_view` again last. I'm not sure this approach is good however.

Thanks again for the quick reply!
Chad

# HG changeset patch
# User Chad Voegele <cavoegele.att.gmail.com>
# Date 1502769381 25200
# Mon Aug 14 20:56:21 2017 -0700
# Branch sync_curses_cursor
# Node ID ed738bb23636209ce05eaac143d6467dee8d79ba
# Parent 938cfedd428af3712dc5429372a5e7f7ba84ae45
Sync physical cursor with Scintilla caret.

diff -r 938cfedd428a -r ed738bb23636 ScintillaTerm.cxx
--- a/ScintillaTerm.cxx Sun Jun 25 16:24:51 2017 -0400
+++ b/ScintillaTerm.cxx Mon Aug 14 20:56:21 2017 -0700
@@ -1218,6 +1218,7 @@
       ac.lb->Select(ac.lb->GetSelection()); // redraw
     else if (ct.inCallTipMode)
       CreateCallTipWindow(PRectangle(0, 0, 0, 0)); // redraw
+ CursorToCurrentPos(w); // for tmux/screen copy mode
   }
   /**
    * Repaints the Scintilla window on the physical screen.
@@ -1398,6 +1399,18 @@
     if (buffer) memcpy(buffer, clipboard.Data(), clipboard.Length() + 1);
     return clipboard.Length() + 1;
   }
+ /**
+ * Move the physical cursor to the current position of the Scintilla caret.
+ * @param window The window to set the cursor.
+ */
+ void CursorToCurrentPos(WINDOW* window) {
+ int current_pos = WndProc(SCI_GETCURRENTPOS, 0, 0);
+ int pointx = WndProc(SCI_POINTXFROMPOSITION, 0, current_pos);
+ int pointy = WndProc(SCI_POINTYFROMPOSITION, 0, current_pos);
+ int begy, begx;
+ getbegyx(window, begy, begx);
+ move(pointy + begy, pointx + begx);
+ }
 };
 
 // Link with C. Documentation in Scintilla.h.

# HG changeset patch
# User Chad Voegele <cavoegele.att.gmail.com>
# Date 1502769083 25200
# Mon Aug 14 20:51:23 2017 -0700
# Branch sync_curses_cursor
# Node ID e7bf2ed95eb929ebd7d055a71f58b690cf68f4f4
# Parent b691095b2f2138bba5c39eda9e940d0f05eb17d2
Additionally noutrefresh focused_view last for cursor sync.

diff -r b691095b2f21 -r e7bf2ed95eb9 src/textadept.c
--- a/src/textadept.c Wed Aug 09 21:31:16 2017 -0400
+++ b/src/textadept.c Mon Aug 14 20:51:23 2017 -0700
@@ -184,6 +184,7 @@
    SS(view, SCI_SETFOCUS, 1, 0))
 #define refresh_all() do { \
   pane_refresh(pane); \
+ scintilla_noutrefresh(focused_view); /* to sync curses cursor with Scintilla */ \
   if (command_entry_focused) scintilla_noutrefresh(command_entry); \
   refresh(); \
 } while (0)

-- 
You are subscribed to code.att.foicica.com.
To change subscription settings, send an e-mail to code+help.att.foicica.com.
To unsubscribe, send an e-mail to code+unsubscribe.att.foicica.com.
Received on Tue 15 Aug 2017 - 00:20:43 EDT

This archive was generated by hypermail 2.2.0 : Tue 15 Aug 2017 - 06:43:32 EDT