tvi: % motion - neatvi - [fork] simple vi-type editor with UTF-8 support
(HTM) git clone git://src.adamsgaard.dk/neatvi
(DIR) Log
(DIR) Files
(DIR) Refs
(DIR) README
---
(DIR) commit 5266f5c8be4e977eaac06ea4a978d13c9b378d28
(DIR) parent 881d54517a9ce3a460cbfbf53c3efc323abd04d4
(HTM) Author: Ali Gholami Rudi <ali@rudi.ir>
Date: Wed, 10 Jun 2015 14:47:38 +0430
vi: % motion
Diffstat:
M mot.c | 29 +++++++++++++++++++++++++++++
M vi.c | 19 ++++++++++++++++---
M vi.h | 1 +
3 files changed, 46 insertions(+), 3 deletions(-)
---
(DIR) diff --git a/mot.c b/mot.c
t@@ -184,3 +184,32 @@ int lbuf_wordend(struct lbuf *lb, int big, int dir, int *row, int *off)
return 1;
return 0;
}
+
+/* move to the matching character */
+int lbuf_pair(struct lbuf *lb, int *row, int *off)
+{
+ int r = *row, o = *off;
+ char *ln = lbuf_get(lb, *row);
+ char *pairs = "()[]{}";
+ int p; /* index for pairs[] */
+ int dep = 1; /* parenthesis depth */
+ if (!ln || !ln[o])
+ return 1;
+ while (!strchr(pairs, ln[o]))
+ if (!ln[++o])
+ return 1;
+ p = strchr(pairs, ln[o]) - pairs;
+ while (!lbuf_next(lb, (p & 1) ? -1 : +1, &r, &o)) {
+ int c = (unsigned char) lbuf_chr(lb, r, o)[0];
+ if (c == pairs[p ^ 1])
+ dep--;
+ if (c == pairs[p])
+ dep++;
+ if (!dep) {
+ *row = r;
+ *off = o;
+ return 0;
+ }
+ }
+ return 1;
+}
(DIR) diff --git a/vi.c b/vi.c
t@@ -279,6 +279,12 @@ static int vi_motionln(int *row, int cmd)
*row = MAX(0, MIN(*row + cnt - 1, lbuf_len(xb) - 1));
break;
}
+ if (c == '%' && (vi_arg1 || vi_arg2)) {
+ if (cnt > 100)
+ return -1;
+ *row = MAX(0, lbuf_len(xb) - 1) * cnt / 100;
+ break;
+ }
vi_back(c);
return 0;
}
t@@ -480,6 +486,10 @@ static int vi_motion(int *row, int *off)
*row = mark_row;
*off = mark_off;
break;
+ case '%':
+ if (lbuf_pair(xb, row, off))
+ return -1;
+ break;
default:
vi_back(mv);
return 0;
t@@ -733,7 +743,7 @@ static int vc_motion(int cmd)
if (r1 == r2 && o1 > o2)
swap(&o1, &o2);
o1 = ren_noeol(lbuf_get(xb, r1), o1);
- if (!lnmode && strchr("fFtTeE", mv))
+ if (!lnmode && strchr("fFtTeE%", mv))
if (o2 < lbuf_eol(xb, r2))
o2 = ren_noeol(lbuf_get(xb, r2), o2) + 1;
if (cmd == 'y')
t@@ -793,8 +803,10 @@ static int vc_put(int cmd)
int lnmode;
char *buf = reg_get(vi_ybuf, &lnmode);
int i;
- if (!buf)
+ if (!buf) {
+ snprintf(vi_msg, sizeof(vi_msg), "yank buffer empty\n");
return 1;
+ }
if (lnmode) {
struct sbuf *sb = sbuf_make();
for (i = 0; i < cnt; i++)
t@@ -982,7 +994,8 @@ static void vi(void)
vi_ybuf = vi_yankbuf();
mv = vi_motion(&nrow, &noff);
if (mv > 0) {
- if (strchr("\'`GHML/?{}[]nN", mv)) {
+ if (strchr("\'`GHML/?{}[]nN", mv) ||
+ (mv == '%' && noff < 0)) {
lbuf_mark(xb, '\'', xrow, xoff);
lbuf_mark(xb, '`', xrow, xoff);
}
(DIR) diff --git a/vi.h b/vi.h
t@@ -30,6 +30,7 @@ int lbuf_paragraphbeg(struct lbuf *lb, int dir, int *row, int *off);
int lbuf_sectionbeg(struct lbuf *lb, int dir, int *row, int *off);
int lbuf_wordbeg(struct lbuf *lb, int big, int dir, int *row, int *off);
int lbuf_wordend(struct lbuf *lb, int big, int dir, int *row, int *off);
+int lbuf_pair(struct lbuf *lb, int *row, int *off);
/* string buffer, variable-sized string */
struct sbuf *sbuf_make(void);