[comp.editors] VI: Positioning the cursor

jurgen@cacilj.UUCP (Jurgen Heymann) (06/12/91)

I am trying to position the cursor on a specific column using a :map macro.
When I enter the command string interactively everything works fine. When I
define it as a :map macro however, the position command is not executed and
the macro execution stops there at the "|". I also tried "\|" but that didn't
help either. What can I do?
I know I could just say "077l" to go to column 77 but that only works when
there are no tabs in that line.

What I really want application-wise is this: Since I have to write
documentation in vi, and I edit passages sometimes, I want to have a command
string that gives me 'full lines' again in a paragraph. Thus I need a command
string that appends the next line to the current ("J") then goes to the right
margin, goes to the beginning of the word there and splits the line at that
point. When you have

    :map ^W J77|bi^M^[

^W would fill up the current line and go to the next.

Any ideas? Thanks

-- Jurgen

-- 
----------------------------------------------------------------
Jurgen Heymann                     CACI Products
jurgen@cacilj.cts.com              3344 N. Torrey Pines Ct
				   La Jolla, CA 92037

stanj@hpnmdla.sr.hp.com (Stan Jaffe) (06/14/91)

How about using the UNIX utility ADJUST?   ADJUST is a simple text formatter
that allows centering, setting margins, justifying text, etc.  You can use
it from VI interactively also.  If you want to take a paragraph of text and
set up the right margin for 72 characters just type:


     {!}adjust -m72

{        moves cursor to the start of the paragraph
!}       writes out the paragraph to an external utility and replaces text
         with the output from that utility.
adjust   the name of the utility
-m72     sets the right margin to 72.  All line wrapping is done automatically.

There are a lot of other nice features in ADJUST.  If you run the above and
find for some reason it didn't turn out as planned, just type u.  (u will
undo the adjust command).

I have mapped this to a key in my .exrc file.  Use control-M for the return
key:

map ^A  {!}adjust -m72 ^M

Good luck,

Stan Jaffe    A.K.A.   stanj@sr.hp.com
HP Santa Rosa, Calif.

		     "Not responsible for any opinions but my own"
------------------------------------------------------------------

wmb@ulysses.att.com (W M Brelsford) (06/14/91)

In article <1501@cacilj.UUCP>, jurgen@cacilj.UUCP (Jurgen Heymann) writes:
> I am trying to position the cursor on a specific column using a :map macro.
> When I enter the command string interactively everything works fine. When I
> define it as a :map macro however, the position command is not executed and
> the macro execution stops there at the "|". I also tried "\|" but that didn't
> help either. What can I do?

"|" needs to be protected with "^V" (Ctrl-V).

..(macro to join two text lines, then split before column 77):
>	:map ^W J77|bi^M^[

A minor modification:

	:map ^W J77^V|BBf r^M

insures that no trailing blanks are left on the split line.

Bill Brelsford
AT&T, Basking Ridge NJ
wmb@joplin.att.com

dattier@vpnet.chi.il.us (David W. Tamkin) (06/15/91)

wmb@ulysses.att.com (W M Brelsford) wrote in <14977@ulysses.att.com>:

| "|" needs to be protected with "^V" (Ctrl-V).

It needs to be protected with a fully entered ^V, which means typing ctrl-V
twice when you enter the :map command (either during a session or into your
.exrc) so that one ^V sticks.

| ..(macro to join two text lines, then split before column 77):
| >	:map ^W J77|bi^M^[
| 
| A minor modification:
| 
| 	:map ^W J77^V|BBf r^M

                J77^V|Bhr^M

will do the same thing a little more efficiently.  It will keep every line
down to seventy-four or fewer columns.  Note that it none of the three does
what the orignal poster seems to want if the two joined lines together take
up seventy-four or fewer columns.

David Tamkin  PO Box 7002  Des Plaines IL  60018-7002  dattier@vpnet.chi.il.us
GEnie:D.W.TAMKIN  CIS:73720,1570  MCIMail:426-1818  708 518 6769  312 693 0591

asylvain@felix.UUCP (Alvin "the Chipmunk" Sylvain) (06/15/91)

Written in article <1501@cacilj.UUCP>
    by jurgen@cacilj.UUCP (Jurgen Heymann):

> I am trying to position the cursor on a specific column using a :map macro.
> When I enter the command string interactively everything works fine. When I
> define it as a :map macro however, the position command is not executed and
> the macro execution stops there at the "|". I also tried "\|" but that didn't
> help either. What can I do?
> I know I could just say "077l" to go to column 77 but that only works when
> there are no tabs in that line.

I ran into that problem too, trying to do a similar application and ran
into the same reason to use "|".  I was able to find out at least why it
won't work.  We have _some_ documentation down here, if you know who to bug.

It turns out that the ":" brings you to "ex" mode, which you probably
aready knew.

What you probably did not know is that the "|" character is a command
separator for "ex".  This means, from the "ex" colon, you could enter,
say:

   :.,.+3d|s/fred/charlie/|s/bill/ted/|wq

which will delete four lines, including the current, then on the line
that becomes current, change "fred" to "charlie", "bill" to "ted", then
write the file out and quit.

Your best example of a use for this is outside the editor.  You may have
an EXINIT environment variable defined:

    EXINIT="set ai|set sw=8|set nomagic"
    export EXINIT    # for /bin/sh users, other shells slightly different

This performs all three "set" commands at "vi" or "ex" initialization.

"ex" refuses to allow you to "quote" it's command separator, or at least
our version does.  I have found absolutely no way to get around that.

There is a slower solution to your application.  You could pipe the line
into "expand" to convert the tabs to spaces, then "077l" will work just
fine.  Then, if you want to, you can repipe the line into "unexpand" to
get the tabs back.  I haven't tried it, but that might be one of very few
solutions to your problem.  Something like this:

    :map K !!expand^M077l{whatever else you want to do}!!unexpand^M

The reason this is slow is because it must spawn a subshell for both
"expand" and "unexpand".  You can speed it up somewhat if you can live
with the tabs permanently removed, saving one subshell.  Alternately,
just remember to run "unexpand" on the entire file when you're thru.

Give it a try.  I can't think of anything better.
--
Alvin ===== asylvain@felix.UUCP ===== hplabs!felix!asylvain ===== 
"hplabs!felix!asylvain"@uunet.uu.net
(I always try to respond to mail, if possible.  If you don't hear back 
from me, try changing "hplabs" to "ccicpg," "spsd," or "lawnet.")
DISCLAIMER: It's all in fun, folks, no flames intended.  Any similarity
between my opinion and that of my employer is purely coincidental and
sufficient reason to change my opinion, although I'll still be right.

asylvain@felix.UUCP (Alvin "the Chipmunk" Sylvain) (06/16/91)

Written in article <14977@ulysses.att.com>
    by wmb@ulysses.att.com (W M Brelsford):

: In article <1501@cacilj.UUCP>, jurgen@cacilj.UUCP (Jurgen Heymann) writes:
: > I am trying to position the cursor on a specific column using a :map macro.
: > When I enter the command string interactively everything works fine. When I
: > define it as a :map macro however, the position command is not executed and
: > the macro execution stops there at the "|". I also tried "\|" but that didn't
: > help either. What can I do?
: 
: "|" needs to be protected with "^V" (Ctrl-V).
: 
: ..(macro to join two text lines, then split before column 77):
: >	:map ^W J77|bi^M^[
: 
: A minor modification:
: 
: 	:map ^W J77^V|BBf r^M
: 
: insures that no trailing blanks are left on the split line.

At the risk of calling forth an old Usenet cliche ...

"Bzzzzzt!  We're sorry, but that's the wrong answer!"

I know.  I tried it in posting this article.  Control V does *not* quote
the "pipe" character (at least not on an Ultix VAX).
--
Alvin ===== asylvain@felix.UUCP ===== hplabs!felix!asylvain ===== 
"hplabs!felix!asylvain"@uunet.uu.net
(I always try to respond to mail, if possible.  If you don't hear back 
from me, try changing "hplabs" to "ccicpg," "spsd," or "lawnet.")
DISCLAIMER: It's all in fun, folks, no flames intended.  Any similarity
between my opinion and that of my employer is purely coincidental and
sufficient reason to change my opinion, although I'll still be right.

asylvain@felix.UUCP (Alvin "the Chipmunk" Sylvain) (06/17/91)

Let me make a correction here.  I remembered seeing a post some time ago
about mapping TAB into ^T so you could use the TAB key to do a Shift-In
instead of insert ^I.  In order to do that successfully, you had to
enter ^V THREE TIMES before the TAB.  Therefore, I thot, what the hell,
let's try it with "|".

Written in article <165175@felix.UUCP>
    by asylvain@felix.UUCP (Alvin "the Chipmunk" Sylvain):

> Written in article <14977@ulysses.att.com>
>     by wmb@ulysses.att.com (W M Brelsford):
> 
> : In article <1501@cacilj.UUCP>, jurgen@cacilj.UUCP (Jurgen Heymann) writes:
> : > I am trying to position the cursor on a specific column using a
> : > :map macro.
> : 
> : "|" needs to be protected with "^V" (Ctrl-V).
>
> At the risk of calling forth an old Usenet cliche ...
> 
> "Bzzzzzt!  We're sorry, but that's the wrong answer!"
> 
> I know.  I tried it in posting this article.  Control V does *not* quote
> the "pipe" character (at least not on an Ultrix VAX).

OK, I did a tad more research, and I think I may have stumbled on the 
solution here.  What needs to be done is to "quote" the quote character, 
which will then successfully quote the command separator.  To-wit:

Type  :map K 72^V^V|?[- ]^V^Ma^V^MJ

Translation:

    :map K      in "ex" mode, map the letter K
    72          position 72 (regardless of quantity of tabs)
    ^V^V        press control V TWICE
    |           "vi"'s column command (but "ex"'s command separator)
    ?           search backward for ...
    [- ]        ... the first hyphen or space (to split both words
                         and hyphenated words, such as mother-
                         in-law.)
    ^V^M        press control V, then RETURN, to end the search string
    a           enter append mode, so you can add ...
    ^V^M        ... a carriage return, quoted of course with ^V.
    J           Join the next line to the end of the new next line.

I've checked this out, and it works beautifully!  No need to call
"expand" or "adjust" or "fmt" or any other external routine!

Success at last!!!  Nothing like trying to wring 20th century features 
out of a 19th century product!
--
Alvin ===== asylvain@felix.UUCP ===== hplabs!felix!asylvain ===== 
"hplabs!felix!asylvain"@uunet.uu.net
(I always try to respond to mail, if possible.  If you don't hear back 
from me, try changing "hplabs" to "ccicpg," "spsd," or "lawnet.")
DISCLAIMER: It's all in fun, folks, no flames intended.  Any similarity
between my opinion and that of my employer is purely coincidental and
sufficient reason to change my opinion, although I'll still be right.

dattier@vpnet.chi.il.us (David W. Tamkin) (06/18/91)

asylvain@felix.UUCP (Alvin "the Chipmunk" Sylvain) wrote in <165192@felix.UUCP>:

|     a           enter append mode, so you can add ...
|     ^V^M        ... a carriage return, quoted of course with ^V.
|     J           Join the next line to the end of the new next line.

You must have some really strange vi.  After a^V^M you should still be in
append mode and the J should be taken as additional text to add.  It
shouldn't work as a join command unless you have ^V^[ in the mapping to
return to command mode.

In my own macro for it, I don't bother with hyphens but look only for spaces.
That allows me to use this:

:map whateverkeyyouwant 77^V^V|F r^V^M

The space doesn't seem to need quoting.

David Tamkin  PO Box 7002  Des Plaines IL  60018-7002  dattier@vpnet.chi.il.us
GEnie:D.W.TAMKIN  CIS:73720,1570  MCIMail:426-1818  708 518 6769  312 693 0591

"Parker Lewis Can't Lose" mailing list:
 flamingo-request@esd.sgi.com (reflector)    flamingo-request@mcs.com (digest)

asylvain@felix.UUCP (Alvin "the Chipmunk" Sylvain) (06/20/91)

Written in article <1991Jun18.000454.6342@vpnet.chi.il.us>
    by dattier@vpnet.chi.il.us (David W. Tamkin):

> asylvain@felix.UUCP (Alvin "the Chipmunk" Sylvain) wrote in <165192@felix.UUCP>:
> |     a           enter append mode, so you can add ...
> |     ^V^M        ... a carriage return, quoted of course with ^V.
> |     J           Join the next line to the end of the new next line.
> 
> You must have some really strange vi.  After a^V^M you should still be in
> append mode and the J should be taken as additional text to add.  It
> shouldn't work as a join command unless you have ^V^[ in the mapping to
> return to command mode.

You're absolutely right, of course.  You need an ESCape to leave append
mode and return to "beep" mode.  That should have been "^V^M^[".  I was
so excited at having discovered a solution to a problem that had been 
nagging me for a long time, I got careless.

> In my own macro for it, I don't bother with hyphens but look only for spaces.
> That allows me to use this:
> 
> :map whateverkeyyouwant 77^V^V|F r^V^M
> 
> The space doesn't seem to need quoting.

This is true.  The space won't need quoting.

I write lots of stuff with hyphens and slashes etc., so I have a partic-
ular need for those kinds of word breaks.  Therefore, instead of "F ", I
have "?[- /]^V^M".  Instead of replacing the space with a CR, I just add
the CR after what may be a space, a hyphen, or a slash.  This will prop-
erly word break mother-in-
law, input/
output, as well as normal space separated words.

I use "nroff" to break between syllables.  I don't use it often, because 
of the subshell overhead, but occasionally it gives the nicest-looking 
result.