]> Sergey Matveev's repositories - nnn.git/commitdiff
Fix #141, #196
authorArun Prakash Jana <engineerarun@gmail.com>
Fri, 1 Mar 2019 01:16:13 +0000 (06:46 +0530)
committerArun Prakash Jana <engineerarun@gmail.com>
Fri, 1 Mar 2019 01:16:13 +0000 (06:46 +0530)
README.md
nnn.1
src/nnn.c

index 3dbc27f173032720054a902244da9be1e6df67ba..bfba745b528554ccb765eb131573db17d2bdb736 100644 (file)
--- a/README.md
+++ b/README.md
@@ -318,7 +318,9 @@ To copy multiple absolute file paths:
 - press <kbd>^Y</kbd> (or <kbd>Y</kbd>) to enter selection mode. In this mode it's possible to
   - cherry-pick individual files one by one by pressing <kbd>^K</kbd> on each entry (works across directories and contexts); or,
   - navigate to another file in the same directory to select a range of files
-- press <kbd>^Y</kbd> (or <kbd>Y</kbd>) _again_ to copy the paths and exit the selection mode
+- press <kbd>^Y</kbd> again to save the selection and exit selection mode.
+
+Selected files are visually indicated by a `+`.
 
 The files in the list can now be copied (<kbd>P</kbd>), moved (<kbd>V</kbd>) or removed (<kbd>X</kbd>).
 
diff --git a/nnn.1 b/nnn.1
index 8bed5b1bc1850a15d5756912bba9ed4f8ce78eca..8617a4d45510a9d3c2af48adb8ac9a2f967bb0ba 100644 (file)
--- a/nnn.1
+++ b/nnn.1
@@ -265,7 +265,10 @@ In this mode it's possible to
 .br
 (2) navigate to another file in the same directory to select a range of files.
 .Pp
-Pressing \fI^Y\fR again saves the selection to the list and exits the selection mode.
+Press \fI^Y\fR again to save the selection and exit selection mode.
+.Pp
+Selected files are visually indicated by a \fB+\fR.
+.br
 The files in the list can now be copied, moved or removed using respective keyboard shortcuts.
 .Pp
 To list the selected files press \fIy\fR.
index 4e208d6e938868cf1df5cec96ab3f32c989a8462..8951eb7085c6ed9caaf48c42a1133e1c3a09a0d4 100644 (file)
--- a/src/nnn.c
+++ b/src/nnn.c
@@ -184,12 +184,15 @@ disabledbg()
 #define DESCRIPTOR_LEN 32
 #define _ALIGNMENT 0x10 /* 16-byte alignment */
 #define _ALIGNMENT_MASK 0xF
-#define DIR_OR_LINK_TO_DIR 0x1
 #define HOME_LEN_MAX 64
 #define CTX_MAX 4
 #define DOT_FILTER_LEN 7
 #define ASCII_MAX 128
 
+/* Entry flags */
+#define DIR_OR_LINK_TO_DIR 0x1
+#define FILE_COPIED 0x10
+
 /* Macros to define process spawn behaviour as flags */
 #define F_NONE     0x00  /* no flag set */
 #define F_MARKER   0x01  /* draw marker to indicate nnn spawned (e.g. shell) */
@@ -909,6 +912,17 @@ static bool cpsafe(void)
        return TRUE;
 }
 
+/* Reset copy indicators */
+static void resetcpind()
+{
+       int r = 0;
+
+       /* Reset copy indicators */
+       for (; r < ndents; ++r)
+               if (dents[r].flags & FILE_COPIED)
+                       dents[r].flags &= ~FILE_COPIED;
+}
+
 /* Initialize curses mode */
 static bool initcurses(void)
 {
@@ -1977,7 +1991,7 @@ static void printent(const struct entry *ent, int sel, uint namecols)
 
 static void printent_long(const struct entry *ent, int sel, uint namecols)
 {
-       char timebuf[18], permbuf[4];
+       char timebuf[18], permbuf[4], cp = ' ';
 
        /* Timestamp */
        strftime(timebuf, 18, "%F %R", localtime(&ent->t));
@@ -1985,6 +1999,10 @@ static void printent_long(const struct entry *ent, int sel, uint namecols)
        /* Permissions */
        snprintf(permbuf, 4, "%d%d%d", (ent->mode >> 6) & 7, (ent->mode >> 3) & 7, ent->mode & 7);
 
+       /* Add copy indicator */
+       if (ent->flags & FILE_COPIED)
+               cp = '+';
+
        /* Trim escape chars from name */
        const char *pname = unescape(ent->name, namecols);
 
@@ -1997,39 +2015,39 @@ static void printent_long(const struct entry *ent, int sel, uint namecols)
        switch (ent->mode & S_IFMT) {
        case S_IFREG:
                if (ent->mode & 0100)
-                       printw(" %-16.16s  0%s %8.8s* %s*\n", timebuf, permbuf,
+                       printw("%c%-16.16s  0%s %8.8s* %s*\n", cp, timebuf, permbuf,
                               coolsize(cfg.blkorder ? ent->blocks << BLK_SHIFT : ent->size), pname);
                else
-                       printw(" %-16.16s  0%s %8.8s  %s\n", timebuf, permbuf,
+                       printw("%c%-16.16s  0%s %8.8s  %s\n", cp, timebuf, permbuf,
                               coolsize(cfg.blkorder ? ent->blocks << BLK_SHIFT : ent->size), pname);
                break;
        case S_IFDIR:
                if (cfg.blkorder)
-                       printw(" %-16.16s  0%s %8.8s/ %s/\n",
-                              timebuf, permbuf, coolsize(ent->blocks << BLK_SHIFT), pname);
+                       printw("%c%-16.16s  0%s %8.8s/ %s/\n",
+                              cp, timebuf, permbuf, coolsize(ent->blocks << BLK_SHIFT), pname);
                else
-                       printw(" %-16.16s  0%s        /  %s/\n", timebuf, permbuf, pname);
+                       printw("%c%-16.16s  0%s        /  %s/\n", cp, timebuf, permbuf, pname);
                break;
        case S_IFLNK:
                if (ent->flags & DIR_OR_LINK_TO_DIR)
-                       printw(" %-16.16s  0%s       @/  %s@\n", timebuf, permbuf, pname);
+                       printw("%c%-16.16s  0%s       @/  %s@\n", cp, timebuf, permbuf, pname);
                else
-                       printw(" %-16.16s  0%s        @  %s@\n", timebuf, permbuf, pname);
+                       printw("%c%-16.16s  0%s        @  %s@\n", cp, timebuf, permbuf, pname);
                break;
        case S_IFSOCK:
-               printw(" %-16.16s  0%s        =  %s=\n", timebuf, permbuf, pname);
+               printw("%c%-16.16s  0%s        =  %s=\n", cp, timebuf, permbuf, pname);
                break;
        case S_IFIFO:
-               printw(" %-16.16s  0%s        |  %s|\n", timebuf, permbuf, pname);
+               printw("%c%-16.16s  0%s        |  %s|\n", cp, timebuf, permbuf, pname);
                break;
        case S_IFBLK:
-               printw(" %-16.16s  0%s        b  %s\n", timebuf, permbuf, pname);
+               printw("%c%-16.16s  0%s        b  %s\n", cp, timebuf, permbuf, pname);
                break;
        case S_IFCHR:
-               printw(" %-16.16s  0%s        c  %s\n", timebuf, permbuf, pname);
+               printw("%c%-16.16s  0%s        c  %s\n", cp, timebuf, permbuf, pname);
                break;
        default:
-               printw(" %-16.16s  0%s %8.8s? %s?\n", timebuf, permbuf,
+               printw("%c%-16.16s  0%s %8.8s? %s?\n", cp, timebuf, permbuf,
                       coolsize(cfg.blkorder ? ent->blocks << BLK_SHIFT : ent->size), pname);
                break;
        }
@@ -2609,6 +2627,7 @@ static int dentfill(char *path, struct entry **dents)
                dentp->mode = sb.st_mode;
                dentp->t = sb.st_mtime;
                dentp->size = sb.st_size;
+               dentp->flags = 0;
 
                if (cfg.blkorder) {
                        if (S_ISDIR(sb.st_mode)) {
@@ -2646,8 +2665,6 @@ static int dentfill(char *path, struct entry **dents)
 
                if (S_ISDIR(sb.st_mode))
                        dentp->flags |= DIR_OR_LINK_TO_DIR;
-               else if (dentp->flags & DIR_OR_LINK_TO_DIR)
-                       dentp->flags &= ~DIR_OR_LINK_TO_DIR;
 
                ++n;
        }
@@ -3463,8 +3480,13 @@ nochange:
                                ++ncp;
                        } else {
                                r = mkpath(path, dents[cur].name, newpath);
-                               /* Keep the copy buf in sync */
-                               copybufpos = 0;
+
+                               if (copybufpos) {
+                                       resetcpind();
+
+                                       /* Keep the copy buf in sync */
+                                       copybufpos = 0;
+                               }
                                appendfpath(newpath, r);
 
                                writecp(newpath, r - 1); /* Truncate NULL from end */
@@ -3472,14 +3494,20 @@ nochange:
                                        spawn(copier, NULL, NULL, NULL, F_NOTRACE);
                        }
 
+                       dents[cur].flags |= FILE_COPIED;
+
                        printmsg(newpath);
                        goto nochange;
                case SEL_COPYMUL:
                        cfg.copymode ^= 1;
                        if (cfg.copymode) {
+                               if (copybufpos) {
+                                       resetcpind();
+                                       writecp(NULL, 0);
+                                       copybufpos = 0;
+                               }
                                g_crc = crc8fast((uchar *)dents, ndents * sizeof(struct entry));
                                copystartid = cur;
-                               copybufpos = 0;
                                ncp = 0;
                                printmsg("selection on");
                                DPRINTF_S("selection on");
@@ -3516,11 +3544,14 @@ nochange:
                        }
 
                        if ((!ncp && copystartid < copyendid) || sel == SEL_COPYALL) {
-                               for (r = copystartid; r <= copyendid; ++r)
+                               for (r = copystartid; r <= copyendid; ++r) {
                                        if (!appendfpath(newpath, mkpath(path,
                                                         dents[r].name, newpath)))
                                                goto nochange;
 
+                                       dents[r].flags |= FILE_COPIED;
+                               }
+
                                mvprintw(LINES - 1, 0, "%d files selected\n",
                                         copyendid - copystartid + 1);
                        }