]> Sergey Matveev's repositories - nnn.git/commitdiff
Extend plugin mechanism to arbitrary commands
authorArun Prakash Jana <engineerarun@gmail.com>
Thu, 24 Oct 2019 07:09:31 +0000 (12:39 +0530)
committerArun Prakash Jana <engineerarun@gmail.com>
Thu, 24 Oct 2019 07:14:01 +0000 (12:44 +0530)
README.md
plugins/README.md
src/nnn.c

index 04cae24cdbd44f261038f1a9e5203ec65cbc6214..af10e676b8205fe9f82cceb2032f2ab3d7549b6a 100644 (file)
--- a/README.md
+++ b/README.md
@@ -50,7 +50,7 @@ Add to that an awesome [Wiki](https://github.com/jarun/nnn/wiki)!
   - Detailed file information
   - Media information (using plugin)
 - Convenience
-  - Plugins with configurable keybinds
+  - Run plugins (or commands) with configurable keybinds
   - FreeDesktop compliant trash (needs trash-cli)
   - SSHFS mounts (needs sshfs)
   - Cross-dir file/all/range selection
@@ -147,7 +147,7 @@ There is no config file. Associated files are stored under `${XDG_CONFIG_HOME:-$
 | Example `export` | Description |
 | --- | --- |
 | `NNN_BMS='d:~/Documents;D:~/Docs archive/'` | key-bookmark pairs [max 10] |
-| `NNN_PLUG='o:fzy-open;p:mocplay;m:nmount;t:thumb'` | key-plugin pairs (<kbd>:key</kbd> to run) [max 10] |
+| `NNN_PLUG='o:fzy-open;p:mocplay;m:nmount;t:thumb'` | key-plugin pairs (<kbd>:key</kbd> to run) [max 15] |
 | `NNN_USE_EDITOR=1` | open text files in `$VISUAL` (else `$EDITOR`, fallback vi) |
 | `NNN_CONTEXT_COLORS='1234'` | specify per context color [default: '4444' (all blue)] |
 | `NNN_SSHFS_OPTS='sshfs -o reconnect,idmap=user'` | specify SSHFS options |
index 5c166767dd7e273626bdf40c0bef8a024eaef7a3..7986fdb5eba622b75f955c762ac7302ef20df4b0 100644 (file)
@@ -66,6 +66,10 @@ Plugins are installed to `${XDG_CONFIG_HOME:-$HOME/.config}/nnn/plugins`. You ca
 
 With this, plugin `fzy-open` can be run with the keybind <kbd>:o</kbd>, `mocplay` can be run with <kbd>:p</kbd> and so on... The key vs. plugin pairs are shown in the help and config screen. Up to 10 plugins can have such keybinds.
 
+To assign keys to arbitrary commands (non-shell interpreted) and invoke like plugins, add `_` (underscore) before the command. For example:
+
+    export NNN_PLUG='x:_chmod +x;o:fzy-open'
+
 **Method 2:** Use the _pick plugin_ shortcut to visit the plugin directory and execute a plugin. Repeating the same shortcut cancels the operation and puts you back in the original directory.
 
 ## Create your own plugins
@@ -105,7 +109,7 @@ There are many plugins provided by `nnn` which can be used as examples. Here are
     #!/usr/bin/env sh
     git log -p -- "$1"
     ```
-    
+
 - Change to directory in clipboard using helper script
     ```sh
     #!/usr/bin/env sh
@@ -121,13 +125,13 @@ There are many plugins provided by `nnn` which can be used as examples. Here are
 
     nnn_cd "$(dirname $(readlink -fn $1))" 0
     ```
-    
+
 - Change to arbitrary directory without helper script
     ```sh
     #!/usr/bin/env sh
     echo -n "cd to: "
     read dir
-    
+
     echo -n "0$dir" > $NNN_PIPE
     ```
 
index aa4c513ee611905f66593a460af0785e15ae1be4..c5a59c74217c6b01c0e39b053504206b09e0ccb9 100644 (file)
--- a/src/nnn.c
+++ b/src/nnn.c
 #define MSGWAIT '$'
 #define REGEX_MAX 48
 #define BM_MAX 10
-#define PLUGIN_MAX 10
+#define PLUGIN_MAX 15
 #define ENTRY_INCR 64 /* Number of dir 'entry' structures to allocate per shot */
 #define NAMEBUF_INCR 0x800 /* 64 dir entries at once, avg. 32 chars per filename = 64*32B = 2KB */
 #define DESCRIPTOR_LEN 32
@@ -4941,13 +4941,21 @@ nochange:
                                }
 
                                if (sel == SEL_PLUGKEY) {
+                                       uchar flag = F_NORMAL;
+
                                        r = get_input("");
                                        tmp = get_kv_val(plug, NULL, r, PLUGIN_MAX, FALSE);
                                        if (!tmp)
                                                goto nochange;
 
-                                       mkpath(plugindir, tmp, newpath);
-                                       spawn(newpath, (ndents ? dents[cur].name : NULL), path, path, F_NORMAL);
+                                       if (tmp[0] == '_' && tmp[1]) {
+                                               xstrlcpy(newpath, ++tmp, PATH_MAX);
+                                               flag = F_CLI | F_CONFIRM;
+                                       } else
+                                               mkpath(plugindir, tmp, newpath);
+
+                                       spawn(newpath, (ndents ? dents[cur].name : NULL),
+                                             path, path, flag);
 
                                        if (cfg.filtermode)
                                                presel = FILTER;