Hi!

Personally I don't like this mode, I think it will be much better just
to add condition to {beginning,end}-of-buffer to push mark only if it's
not pushed already.

The only thing I didn't implement is region highlighting because I am
still not familiar with mg's code.

Here's the diff:

Index: basic.c
===================================================================
RCS file: /cvs/src/usr.bin/mg/basic.c,v
retrieving revision 1.48
diff -u -p -u -p -r1.48 basic.c
--- basic.c     3 Jun 2019 16:26:30 -0000       1.48
+++ basic.c     8 Jun 2019 14:21:17 -0000
@@ -116,6 +116,23 @@ forwchar(int f, int n)
        return (TRUE);
 }
 
+static int     transient_mark = 1;
+static int     mark_active = 1;
+
+/*
+ * Toggle transient marking
+ */
+int
+transientmarktoggle(int f, int n)
+{
+       if (f & FFARG)
+               transient_mark = mark_active = n > 0;
+       else
+               transient_mark = mark_active = !transient_mark;
+       ewprintf("Transient marking %sabled", transient_mark ? "en" : "dis");
+       return (TRUE);
+}
+
 /*
  * Go to the beginning of the buffer. Setting WFFULL is conservative,
  * but almost always the case. A universal argument of higher than 9
@@ -124,7 +141,8 @@ forwchar(int f, int n)
 int
 gotobob(int f, int n)
 {
-       (void) setmark(f, n);
+       if (!(mark_active && curwp->w_markp))
+               (void) setmark(f, n);
        curwp->w_dotp = bfirstlp(curbp);
        curwp->w_doto = 0;
        curwp->w_rflag |= WFFULL;
@@ -150,7 +168,8 @@ gotoeob(int f, int n)
        int              ln;
        struct line     *lp;
 
-       (void) setmark(f, n);
+       if (!(mark_active && curwp->w_markp))
+               (void) setmark(f, n);
        curwp->w_dotp = blastlp(curbp);
        curwp->w_doto = llength(curwp->w_dotp);
        curwp->w_dotline = curwp->w_bufp->b_lines;
@@ -478,8 +497,15 @@ isetmark(void)
 int
 setmark(int f, int n)
 {
-       isetmark();
-       ewprintf("Mark set");
+       if (curwp->w_markp == curwp->w_dotp &&
+           curwp->w_marko == curwp->w_doto &&
+           curwp->w_markline == curwp->w_dotline) {
+               mark_active = !transient_mark | !(transient_mark & mark_active);
+               ewprintf("Mark %sactivated", mark_active ? "" : "de");
+       } else {
+               isetmark();
+               ewprintf("Mark set");
+       }
        return (TRUE);
 }
 
@@ -491,6 +517,7 @@ clearmark(int f, int n)
        if (!curwp->w_markp)
                return (FALSE);
 
+       mark_active = transient_mark;
        curwp->w_markp = NULL;
        curwp->w_marko = 0;
        curwp->w_markline = 0;
Index: def.h
===================================================================
RCS file: /cvs/src/usr.bin/mg/def.h,v
retrieving revision 1.157
diff -u -p -u -p -r1.157 def.h
--- def.h       13 Dec 2018 14:59:16 -0000      1.157
+++ def.h       8 Jun 2019 14:21:17 -0000
@@ -508,6 +508,7 @@ int          gotobol(int, int);
 int             backchar(int, int);
 int             gotoeol(int, int);
 int             forwchar(int, int);
+int             transientmarktoggle(int, int);
 int             gotobob(int, int);
 int             gotoeob(int, int);
 int             forwline(int, int);
Index: funmap.c
===================================================================
RCS file: /cvs/src/usr.bin/mg/funmap.c,v
retrieving revision 1.55
diff -u -p -u -p -r1.55 funmap.c
--- funmap.c    13 Dec 2018 14:59:16 -0000      1.55
+++ funmap.c    8 Jun 2019 14:21:18 -0000
@@ -202,6 +202,7 @@ static struct funmap functnames[] = {
        {poptobuffer, "switch-to-buffer-other-window",},
        {togglereadonly, "toggle-read-only" },
        {togglereadonlyall, "toggle-read-only-all" },
+       {transientmarktoggle, "transient-mark-mode"},
        {twiddle, "transpose-chars",},
        {transposepara, "transpose-paragraphs",},
        {transposeword, "transpose-words",},
Index: mg.1
===================================================================
RCS file: /cvs/src/usr.bin/mg/mg.1,v
retrieving revision 1.114
diff -u -p -u -p -r1.114 mg.1
--- mg.1        6 Jun 2019 18:17:34 -0000       1.114
+++ mg.1        8 Jun 2019 14:21:18 -0000
@@ -1,7 +1,7 @@
 .\"    $OpenBSD: mg.1,v 1.114 2019/06/06 18:17:34 jmc Exp $
 .\" This file is in the public domain.
 .\"
-.Dd $Mdocdate: June 6 2019 $
+.Dd $Mdocdate: June 8 2019 $
 .Dt MG 1
 .Os
 .Sh NAME
@@ -408,6 +408,8 @@ Move cursor to the top of the buffer.
 A numeric argument
 .Va n
 will move n/10th of the way from the top.
+Set mark at previous position if transient marking is disabled
+and mark is not set.
 .It beginning-of-line
 Move cursor to the beginning of the line.
 .It blink-and-insert
@@ -532,6 +534,8 @@ Move cursor to the end of the buffer.
 A numeric argument
 .Va n
 will move n/10th of the way from the end.
+Set mark at previous position if transient marking is disabled
+and mark is not set.
 .It end-of-line
 Move cursor to the end of the line.
 .It enlarge-window
@@ -864,6 +868,8 @@ Prompt the user for a fill column.
 Used by auto-fill-mode.
 .It set-mark-command
 Sets the mark in the current window to the current dot location.
+Repetitive invokation in sequence temporarily turns transient
+marking on/off.
 .It set-prefix-string
 Sets the prefix string to be used by the 'prefix-region' command.
 .It shell-command
@@ -894,6 +900,8 @@ Toggle the read-only flag on the current
 Toggle the read-only flag on all non-ephemeral buffers.
 A simple toggle that switches a global read-only flag either on
 or off.
+.It transient-mark-mode
+Toggle transient marking where active region is highlighted.
 .It transpose-chars
 Transpose the two characters in front of and under dot,
 then move forward one character.
Index: region.c
===================================================================
RCS file: /cvs/src/usr.bin/mg/region.c,v
retrieving revision 1.37
diff -u -p -u -p -r1.37 region.c
--- region.c    9 Sep 2016 06:05:51 -0000       1.37
+++ region.c    8 Jun 2019 14:21:18 -0000
@@ -405,6 +405,7 @@ markbuffer(int f, int n)
 {
        if (gotoeob(f,n) == FALSE)
                return (FALSE);
+       (void) clearmark(f, n);
        if (gotobob(f,n) == FALSE)
                return (FALSE);
        return (TRUE);

Reply via email to