[Top][All Lists]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Nano-devel] updates: possible solution to Tab/Space problem, etc.

From: David L. Ramsey
Subject: [Nano-devel] updates: possible solution to Tab/Space problem, etc.
Date: Thu, 6 May 2004 02:35:29 -0400

I've been working some more on the various patches.

I've gone ahead and committed the restricted mode patch, so now we're on
par with ed and vim in terms of blocking reading of files not specified
on the command line.  I've also committed the patch to work around the
NumLock glitch; it appears that the values generated by the keypad with
NumLock off under xterm and rxvt are standard sequences on the VT100,
VT220, VT320, etc.  (Eterm doesn't have the glitch at all.)  In this
vein, I've also added more documentation on escape sequences; nano
apparently supports enough sequences to cover ANSI, ASCII, VT100, VT220,
and VT320.  I also stuck in DB's tweaks to regexp_init() and removed the
redundant messages, and in the process converted REGEXP_COMPILED from a
flag to a static int in search.c (since it's only used there), freeing
up space for another flag.  Finally, I disabled "Where Is Next" in tiny
mode, since it's a convenience function (most editors have a "Find Next"
option, but most of them also have marking as well, and space is a
priority in tiny mode).

As for what I mentioned before about rewriting the input routines, using
termcap/terminfo is out.  It turns out that that won't solve the main
problem of termcap/terminfo entries missing or misassigning key values,
since it relies on the key values in question.  (For example, putty will
never generate KEY_HOME or KEY_END, but just the escape sequences,
because its terminfo entry in ncurses 5.4 is missing khome and kend
entries.)  As for looking up non-keypad values, almost every terminal
listed is ANSI-compatible enough to support Ctrl-I as Tab, Ctrl-M as
Enter, Ctrl-Q as XON, Ctrl-S as XOFF.  Of course, there's room for
debate on the Backspace front, but they should probably interpret Ctrl-H
as Backspace if they get it for compatibility reasons, since it's also
Backspace on the VT100 and VT220 and derivatives.  I still am planning a
rewrite, but it'll be a bit different; see below for what I'm doing with

On a similar note: for these compatibility reasons, maybe if rebindable
keys are implemented, Ctrl-H, Ctrl-I, and Ctrl-M should be reserved for
Backspace, Tab, and Enter for compatibility reasons, since there aren't
any keypad values for those (KEY_ENTER is Enter on the numeric keypad,
not on the main keyboard).  Besides, Ctrl-H is mapped to KEY_BACKSPACE
on xterm at least, so remapping it to something else may lead to
problems there and possibly elsewhere.  This limitation shouldn't be a
problem for those that want to remap the keys to fit the *ahem* Windows
standard layout, since it follows those (or at least the first two, as
far as I know).  Ctrl-Q and Ctrl-S can be remapped, but there should
probably be a warning that they won't work properly if preserve mode is
used in that case.

I haven't found a way around the problem with syntax highlighting tabs
and spaces problem, but there is another way to visually differentiate
between them.  Specifically, Mike Frysinger's patch from awhile ago
against 1.2.2 does that, and I finally got around to fixing the
refactored version for 1.3.x so that it doesn't use the spacing
characters everywhere display_string() is used.  (Sorry it took me so
long to get to it.)  I also added the commented toggle code back in and
completed it so that it properly toggles the display, now that there's
room for a few more flags.  Of course, since Meta-V is taken by verbatim
input, I had to change the toggle to Meta-P for "Whitespace display"
("conversion" didn't seem right to me, since tabs and spaces aren't
really being converted in the file so much as being displayed
differently).  Comments, especially from those needing a way to tell
tabs and spaces apart and can't get color syntaxes to handle it?

Other updates:

New version of the patch to improve performance when just moving through
the file without changing anything.  This changes the scrolling
functions so that they don't redraw lines that haven't changed on the
screen, and hence not doing unneeded regexec()s if we're in color more,
by using wscrl() to scroll the text up or down and then calling
update_line() to draw just the newly visible lines on the blank areas
created by the scrolling.  It also moves do_(first|last)_line() from
winio.c, since they're movement functions as well, and tweaks them in a
similar way to the movement functions so that they don't do unnecessary
screen updates.  Note that including the scrolling code does bloat the
executable by a few K, but if it results in faster movement (as I
believe it should, as scrolling text that's already there and redrawing
only what's needed should take less time than redundantly redrawing

Synced with CVS, and "smart home" now works at the statusbar prompt as
well as in the edit window.

In this patch, instead of checking for spaces and tabs separately, we
now use isblank() for those cases.  Now isblank() is a GNU extension, so
I added a function is_blank_char() to do the same thing on systems
without it.  The hard part was detecting it reliably, much like the
strcasestr() function.  It turns out that defining _GNU_SOURCE during
compilation makes the tests for both functions work properly. 
Therefore, this patch also only uses nstristr() if strcasestr() isn't
defined.  Defining _GNU_SOURCE during the test programs was tricky;
there is a way to insert literal #define code into the script, but there
are apparently problems with redefinition in some cases.  There is an
autoconf macro to set this automatically and avoid the redefinition
problems, but it's only available in autoconf 2.54 or later.  According
to README.CVS, automake 1.7.x is recommended, and it requires autoconf
2.54 or later to work, so bumping up the minimum requirements to
autoconf 2.54 and automake 1.7 may not be much of a problem.  (Autoconf
2.54 requires automake 1.6c or later to work, but 1.6c is a CVS version,
so if we go by stable versions, we might as well say that nano requires
automake 1.7 or later.  Also, autoconf 2.53 doesn't work properly with
automake 1.6.3 as it is.)  Any objections to this?

I've made a few improvements to this.  It now contains DB's
simplification of do_credits() and an overhaul of the window resizing
code in handle_sigwinch().  The latter finally fixes resizing so that it
(a) doesn't require the apparently ncurses-specific resizeterm() or
wresize() functions, and (b) doesn't corrupt the screen when slang is
used.  I had to borrow ideas and/or short code snippets from Minimum
Profit 3.3.0 and mutt (both GPL v2 or later), respectively.

For (a), I did the rough equivalent of what Minimum Profit does.  Its
SIGWINCH handler ends curses mode via endwin(); goes back into curses
mode via initscr(); reinitializes the terminal state via cbreak(),
keypad(), and the like; and finally calls its own routine to
reinitialize all windows.  Since the manual page for initscr() states
that "portable programs must not call it more than once", and doing so
appears to cause a memory leak since it allocates memory for the screen
structure, this patch doesn't use it.  Instead, it calls endwin() and
refresh() to get out of and back into curses mode, and then calls
window_init() to reinitialize all the windows.  (The previous version of
this patch already restored the terminal state via resetty() and
keypad(), and this version still does.)  This seems to work perfectly
under ncurses, but under slang, it only works if the window is resized
to be smaller.

For (b), I initially tried the approach in (a) until I realized that it
didn't always work, as explained above.  I then tried put mutt with
slang support, which had no problem with resizing due to its calling the
slang-specific functions SLsmg_reset_smg() and SLsmg_init_smg() (I found
out later that the sequence of these two calls is in the slang
documentation as an example of how to properly resize windows) just
before its routine to reinitialize all windows.  The patch uses those
functions followed by window_init() if USE_SLANG is defined.

The patch also includes a workaround for another slang problem: raw()
appears to act just like cbreak() under slang (i.e, it doesn't disable
interpretation of the special control keys such as Ctrl-C and Ctrl-\,
which we need).  The patch now calls the disable_signals() function to
manually turn such interpretation off when slang is used.

My almost-finished attempt at what should be the last rewrite of
low-level input.  I'm trying to get around some limitations in the
current design: (a) the ignored keys are only ignored if Escape wasn't
pressed before them, (b) there's no way to properly ignore certain
escape sequences (e.g. Center [5] on the numeric keypad, which properly
shouldn't generate anything), and (c) there's too much dependence on the
idea of blocking input, which will lead to problems if someone creates
another interface for nano that doesn't have blocking input (e.g. an X11
interface).  Therefore, I'm trying to turn the input routines into
proper state machines that only interpret data passed to them by the
highest-level input routines.  They seem to be working well in the
current version, although the new verbatim input routine is a bit
twisted due to its having to filter out ERR's in the input stream when
an ASCII character sequence is entered (it's the only way to duplicate
the current behavior; e.g. entering verbatim input mode and pressing
Shift-Insert when "213142" is on the primary X clipboard should result
in "[ASCII 213]142" being generated, not "[ERR][ERR][ASCII 213]142"). 
Needed cleanups: Among other things, the functions to reset the state
machines should not be included when NANO_SMALL is defined, since
they're only called after a window resize; the debugging output
statements should be a bit more consistent; and only get_kbinput() and
get_verbatim_kbinput() should require a WINDOW* parameter to get input
since get_(un)?translated_kbinput() and get_ascii_kbinput() should only
be interpreting already-read input.  This is obviously a work in
progress, albeit one close to being finished, and even with all of its
changes, a lot of it uses little-changed chunks of the current input

Attachment: signature.asc
Description: Text document

reply via email to

[Prev in Thread] Current Thread [Next in Thread]