summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog4
-rw-r--r--Src/Zle/iwidgets.list1
-rw-r--r--Src/Zle/zle_misc.c14
-rw-r--r--Src/Zle/zle_move.c18
-rw-r--r--Src/Zle/zle_refresh.c2
-rw-r--r--Src/Zle/zle_vi.c48
6 files changed, 74 insertions, 13 deletions
diff --git a/ChangeLog b/ChangeLog
index fc9f8e5fa..7391f300c 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,9 @@
2014-11-17 Oliver Kiddle <opk@zsh.org>
+ * 33635: Src/Zle/iwidgets.list, Src/Zle/zle_misc.c,
+ Src/Zle/zle_move.c, Src/Zle/zle_refresh.c, Src/Zle/zle_vi.c:
+ adapt region to function as vim style visual selection mode
+
* 33700: Doc/Zsh/zle.yo, Src/Zle/iwidgets.list,
Src/Zle/zle_misc.c, Src/Zle/zle_utils.c: new widget
for put in vim style visual selection mode
diff --git a/Src/Zle/iwidgets.list b/Src/Zle/iwidgets.list
index 070116f5f..23e5783f9 100644
--- a/Src/Zle/iwidgets.list
+++ b/Src/Zle/iwidgets.list
@@ -184,6 +184,7 @@
"vi-yank", viyank, ZLE_LASTCOL
"vi-yank-eol", viyankeol, 0
"vi-yank-whole-line", viyankwholeline, 0
+"visual-mode", visualmode, ZLE_MENUCMP | ZLE_KEEPSUFFIX | ZLE_LASTCOL
"what-cursor-position", whatcursorposition, ZLE_MENUCMP | ZLE_KEEPSUFFIX | ZLE_LASTCOL
"where-is", whereis, ZLE_MENUCMP | ZLE_KEEPSUFFIX | ZLE_LASTCOL
"which-command", processcmd, ZLE_MENUCMP | ZLE_KEEPSUFFIX | ZLE_LASTCOL
diff --git a/Src/Zle/zle_misc.c b/Src/Zle/zle_misc.c
index 3e6d1aaac..5996c485d 100644
--- a/Src/Zle/zle_misc.c
+++ b/Src/Zle/zle_misc.c
@@ -446,9 +446,12 @@ killregion(UNUSED(char **args))
if (mark > zlell)
mark = zlell;
if (mark > zlecs)
- forekill(mark - zlecs, CUT_RAW);
- else
+ forekill(mark - zlecs + invicmdmode(), CUT_RAW);
+ else {
+ if (invicmdmode())
+ INCCS();
backkill(zlecs - mark, CUT_FRONT|CUT_RAW);
+ }
return 0;
}
@@ -465,9 +468,9 @@ copyregionaskill(char **args)
if (mark > zlell)
mark = zlell;
if (mark > zlecs)
- cut(zlecs, mark - zlecs, 0);
+ cut(zlecs, mark - zlecs + invicmdmode(), 0);
else
- cut(mark, zlecs - mark, CUT_FRONT);
+ cut(mark, zlecs - mark + invicmdmode(), CUT_FRONT);
}
return 0;
}
@@ -1016,7 +1019,8 @@ quoteregion(UNUSED(char **args))
mark = zlecs;
zlecs = tmp;
}
- str = (ZLE_STRING_T)hcalloc((len = mark - zlecs) * ZLE_CHAR_SIZE);
+ str = (ZLE_STRING_T)hcalloc((len = mark - zlecs + invicmdmode()) *
+ ZLE_CHAR_SIZE);
ZS_memcpy(str, zleline + zlecs, len);
foredel(len, CUT_RAW);
str = makequote(str, &len);
diff --git a/Src/Zle/zle_move.c b/Src/Zle/zle_move.c
index 35e419369..7b6420c06 100644
--- a/Src/Zle/zle_move.c
+++ b/Src/Zle/zle_move.c
@@ -509,6 +509,24 @@ exchangepointandmark(UNUSED(char **args))
/**/
int
+visualmode(UNUSED(char **args))
+{
+ switch (region_active) {
+ case 1:
+ region_active = 0;
+ break;
+ case 0:
+ mark = zlecs;
+ /* fall through */
+ case 2:
+ region_active = 1;
+ break;
+ }
+ return 0;
+}
+
+/**/
+int
vigotocolumn(UNUSED(char **args))
{
int x, y, n = zmult;
diff --git a/Src/Zle/zle_refresh.c b/Src/Zle/zle_refresh.c
index 684ac13a2..ebc6b494c 100644
--- a/Src/Zle/zle_refresh.c
+++ b/Src/Zle/zle_refresh.c
@@ -1037,6 +1037,8 @@ zrefresh(void)
region_highlights[0].start = mark;
region_highlights[0].end = zlecs;
}
+ if (invicmdmode())
+ INCPOS(region_highlights[0].end);
} else {
region_highlights[0].start = region_highlights[0].end = -1;
}
diff --git a/Src/Zle/zle_vi.c b/Src/Zle/zle_vi.c
index c3a9e75aa..02877deee 100644
--- a/Src/Zle/zle_vi.c
+++ b/Src/Zle/zle_vi.c
@@ -162,9 +162,14 @@ static int
getvirange(int wf)
{
int pos = zlecs, mpos = mark, ret = 0;
+ int visual = region_active; /* don't trust movement cmd not to change it */
int mult1 = zmult, hist1 = histline;
Thingy k2;
+ if (visual) {
+ pos = mark;
+ } else {
+
virangeflag = 1;
wordflag = wf;
mark = -1;
@@ -239,6 +244,7 @@ getvirange(int wf)
* and use the mark. */
if (mark != -1)
pos = mark;
+ }
mark = mpos;
/* Get the range the right way round. zlecs is placed at the *
@@ -250,6 +256,11 @@ getvirange(int wf)
pos = tmp;
}
+ if (visual && invicmdmode()) {
+ region_active = 0;
+ INCPOS(pos);
+ }
+
/* Was it a line-oriented move? If so, the command will have set *
* the vilinerange flag. In this case, entire lines are taken, *
* rather than just the sequence of characters delimited by pos *
@@ -377,6 +388,10 @@ videletechar(char **args)
int n = zmult;
startvichange(-1);
+
+ if (region_active)
+ return killregion(args);
+
/* handle negative argument */
if (n < 0) {
int ret;
@@ -430,12 +445,16 @@ visubstitute(UNUSED(char **args))
/* it is an error to be on the end of line */
if (zlecs == zlell || zleline[zlecs] == '\n')
return 1;
- /* Put argument into the acceptable range -- it is not an error to *
- * specify a greater count than the number of available characters. */
- if (n > findeol() - zlecs)
- n = findeol() - zlecs;
- /* do the substitution */
- forekill(n, CUT_RAW);
+ if (region_active) {
+ killregion(zlenoargs);
+ } else {
+ /* Put argument into the acceptable range -- it is not an error to *
+ * specify a greater count than the number of available characters. */
+ if (n > findeol() - zlecs)
+ n = findeol() - zlecs;
+ /* do the substitution */
+ forekill(n, CUT_RAW);
+ }
startvitext(1);
return 0;
}
@@ -770,6 +789,10 @@ vibackwarddeletechar(char **args)
if (invicmdmode())
startvichange(-1);
+
+ if (region_active)
+ return killregion(args);
+
/* handle negative argument */
if (n < 0) {
int ret;
@@ -811,12 +834,21 @@ vijoin(UNUSED(char **args))
{
int x, pos;
int n = zmult;
+ int visual = region_active;
startvichange(-1);
if (n < 1)
return 1;
- if ((x = findeol()) == zlell)
+ if (visual && zlecs > mark) {
+ exchangepointandmark(zlenoargs);
+ x = findeol();
+ if (x >= mark) {
+ exchangepointandmark(zlenoargs);
+ return 1;
+ }
+ } else if ((x = findeol()) == zlell || (visual && x >= mark))
return 1;
+
while (n) {
zlecs = x + 1;
pos = zlecs;
@@ -834,7 +866,7 @@ vijoin(UNUSED(char **args))
}
spaceinline(1);
zleline[zlecs] = ZWC(' ');
- if (--n < 2 || (x = findeol()) == zlell)
+ if ((!visual && --n < 2) || (x = findeol()) == zlell || (visual && x >= mark))
return 0;
}
return 0;