diff --git a/doc/nvim-tree-lua.txt b/doc/nvim-tree-lua.txt index 436baf35..eda8f846 100644 --- a/doc/nvim-tree-lua.txt +++ b/doc/nvim-tree-lua.txt @@ -1203,8 +1203,10 @@ exists. - create - remove - trash + - rename_node `(node: table, modifier?: string vim.fn.fnamemodify argument)` - rename - rename_sub + - rename_basename - cut - paste - clear_clipboard @@ -1337,6 +1339,7 @@ DEFAULT MAPPINGS *nvim-tree-default-mappings `D` trash trash a file via |trash| option `r` rename rename a file `` full_rename rename a file and omit the filename on input +`e` rename_basename rename a file with filename-modifiers ':t:r' without changing extension `x` cut add/remove file/directory to cut clipboard `c` copy add/remove file/directory to copy clipboard `p` paste paste from clipboard; cut clipboard has precedence over copy; will prompt for confirmation @@ -1388,6 +1391,7 @@ DEFAULT MAPPINGS *nvim-tree-default-mappings { key = "D", action = "trash" }, { key = "r", action = "rename" }, { key = "", action = "full_rename" }, + { key = "e", action = "rename_basename" }, { key = "x", action = "cut" }, { key = "c", action = "copy" }, { key = "p", action = "paste" }, diff --git a/lua/nvim-tree/actions/dispatch.lua b/lua/nvim-tree/actions/dispatch.lua index e28fdb5c..a3781f80 100644 --- a/lua/nvim-tree/actions/dispatch.lua +++ b/lua/nvim-tree/actions/dispatch.lua @@ -22,11 +22,12 @@ local Actions = { copy = require("nvim-tree.actions.fs.copy-paste").copy, create = require("nvim-tree.actions.fs.create-file").fn, cut = require("nvim-tree.actions.fs.copy-paste").cut, - full_rename = require("nvim-tree.actions.fs.rename-file").fn(true), + full_rename = require("nvim-tree.actions.fs.rename-file").fn ":p", paste = require("nvim-tree.actions.fs.copy-paste").paste, trash = require("nvim-tree.actions.fs.trash").fn, remove = require("nvim-tree.actions.fs.remove-file").fn, - rename = require("nvim-tree.actions.fs.rename-file").fn(false), + rename = require("nvim-tree.actions.fs.rename-file").fn ":t", + rename_basename = require("nvim-tree.actions.fs.rename-file").fn ":t:r", -- Movements in tree close_node = require("nvim-tree.actions.moves.parent").fn(true), diff --git a/lua/nvim-tree/actions/fs/rename-file.lua b/lua/nvim-tree/actions/fs/rename-file.lua index d37e35b5..443858ec 100644 --- a/lua/nvim-tree/actions/fs/rename-file.lua +++ b/lua/nvim-tree/actions/fs/rename-file.lua @@ -5,6 +5,12 @@ local notify = require "nvim-tree.notify" local M = {} +local ALLOWED_MODIFIERS = { + [":p"] = true, + [":t"] = true, + [":t:r"] = true, +} + local function err_fmt(from, to, reason) return string.format("Cannot rename %s -> %s: %s", from, to, reason) end @@ -25,17 +31,45 @@ function M.rename(node, to) events._dispatch_node_renamed(node.absolute_path, to) end -function M.fn(with_sub) - return function(node) +function M.fn(default_modifier) + default_modifier = default_modifier or ":t" + + return function(node, modifier) + if type(node) ~= "table" then + node = lib.get_node_at_cursor() + end + + if type(modifier) ~= "string" then + modifier = default_modifier + end + + -- support for only specific modifiers have been implemented + if not ALLOWED_MODIFIERS[modifier] then + return notify.warn( + "Modifier " .. vim.inspect(modifier) .. " is not in allowed list : " .. table.concat(ALLOWED_MODIFIERS, ",") + ) + end + node = lib.get_last_group_node(node) if node.name == ".." then return end local namelen = node.name:len() - local abs_path = with_sub and node.absolute_path:sub(0, namelen * -1 - 1) or node.absolute_path + local directory = node.absolute_path:sub(0, namelen * -1 - 1) + local default_path + local prepend = "" + local append = "" + default_path = vim.fn.fnamemodify(node.absolute_path, modifier) + if modifier:sub(0, 2) == ":t" then + prepend = directory + end + if modifier == ":t:r" then + local extension = vim.fn.fnamemodify(node.name, ":e") + append = extension:len() == 0 and "" or "." .. extension + end - local input_opts = { prompt = "Rename to ", default = abs_path, completion = "file" } + local input_opts = { prompt = "Rename to ", default = default_path, completion = "file" } vim.ui.input(input_opts, function(new_file_path) utils.clear_prompt() @@ -43,7 +77,7 @@ function M.fn(with_sub) return end - M.rename(node, new_file_path) + M.rename(node, prepend .. new_file_path .. append) if M.enable_reload then require("nvim-tree.actions.reloaders.reloaders").reload_explorer() end diff --git a/lua/nvim-tree/actions/init.lua b/lua/nvim-tree/actions/init.lua index 5764249c..b1f12c9a 100644 --- a/lua/nvim-tree/actions/init.lua +++ b/lua/nvim-tree/actions/init.lua @@ -131,6 +131,11 @@ local DEFAULT_MAPPINGS = { action = "full_rename", desc = "rename a file and omit the filename on input", }, + { + key = "e", + action = "rename_basename", + desc = "rename a file with filename-modifiers ':t:r' without changing extension", + }, { key = "x", action = "cut", diff --git a/lua/nvim-tree/api.lua b/lua/nvim-tree/api.lua index 92c14dc4..515d9ffd 100644 --- a/lua/nvim-tree/api.lua +++ b/lua/nvim-tree/api.lua @@ -9,9 +9,9 @@ local Api = { } local function inject_node(f) - return function(node) + return function(node, ...) node = node or require("nvim-tree.lib").get_node_at_cursor() - f(node) + f(node, ...) end end @@ -47,8 +47,10 @@ Api.tree.toggle_help = require("nvim-tree.actions.tree-modifiers.toggles").help Api.fs.create = inject_node(require("nvim-tree.actions.fs.create-file").fn) Api.fs.remove = inject_node(require("nvim-tree.actions.fs.remove-file").fn) Api.fs.trash = inject_node(require("nvim-tree.actions.fs.trash").fn) -Api.fs.rename = inject_node(require("nvim-tree.actions.fs.rename-file").fn(false)) -Api.fs.rename_sub = inject_node(require("nvim-tree.actions.fs.rename-file").fn(true)) +Api.fs.rename_node = inject_node(require("nvim-tree.actions.fs.rename-file").fn ":t") +Api.fs.rename = inject_node(require("nvim-tree.actions.fs.rename-file").fn ":t") +Api.fs.rename_sub = inject_node(require("nvim-tree.actions.fs.rename-file").fn ":p") +Api.fs.rename_basename = inject_node(require("nvim-tree.actions.fs.rename-file").fn ":t:r") Api.fs.cut = inject_node(require("nvim-tree.actions.fs.copy-paste").cut) Api.fs.paste = inject_node(require("nvim-tree.actions.fs.copy-paste").paste) Api.fs.clear_clipboard = require("nvim-tree.actions.fs.copy-paste").clear_clipboard