Skip to content

Commit

Permalink
attempt 2
Browse files Browse the repository at this point in the history
  • Loading branch information
jamestrew committed Jan 31, 2022
1 parent ed715ef commit 1cd81e4
Show file tree
Hide file tree
Showing 4 changed files with 102 additions and 46 deletions.
56 changes: 31 additions & 25 deletions lua/telescope/_extensions/file_browser/actions.lua
Original file line number Diff line number Diff line change
Expand Up @@ -57,15 +57,17 @@ local os_sep = Path.path.sep
fb_actions.create = function(prompt_bufnr)
local current_picker = action_state.get_current_picker(prompt_bufnr)
local finder = current_picker.finder
local file = fb_utils.get_valid_path("Insert the file name: ", finder.path .. os_sep)
local quiet = finder.quiet
local file = fb_utils.get_valid_path("Insert the file name: ", finder.path .. os_sep, { quiet = quiet })
-- local success
if file then
if not fb_utils.is_dir(file.filename) then
file:touch { parents = true }
else
Path:new(file.filename:sub(1, -2)):mkdir { parents = true }
end
current_picker:refresh(finder, { reset_prompt = true, multi = current_picker._multi })
fb_utils.tele_notify(string.format("\n%s created!", file.filename))
fb_utils.action_cmp_msg(string.format("%s created!", file.filename), quiet)
end
end

Expand Down Expand Up @@ -152,6 +154,7 @@ fb_actions.rename = function(prompt_bufnr)
local current_picker = action_state.get_current_picker(prompt_bufnr)
local selections = fb_utils.get_selected_files(prompt_bufnr, false)
local parent_dir = Path:new(current_picker.finder.path):parent()
local quiet = current_picker.finder.quiet

if not vim.tbl_isempty(selections) then
batch_rename(prompt_bufnr, selections)
Expand All @@ -168,7 +171,7 @@ fb_actions.rename = function(prompt_bufnr)
return
end

local new_path = fb_utils.get_valid_path("Insert a new name: ", old_path:absolute())
local new_path = fb_utils.get_valid_path("Insert a new name: ", old_path:absolute(), { quiet = quiet })
if new_path then
-- rename changes old_name in place
local old_name = old_path:absolute()
Expand All @@ -184,7 +187,7 @@ fb_actions.rename = function(prompt_bufnr)
current_picker._multi:drop(entry)
end
current_picker:refresh(current_picker.finder)
fb_utils.tele_notify(string.format("\n%s renamed to %s!", old_name, new_path.filename))
fb_utils.action_cmp_msg(string.format("%s renamed to %s!", old_name, new_path.filename), quiet)
end
end
end
Expand Down Expand Up @@ -215,7 +218,7 @@ fb_actions.move = function(prompt_bufnr)
file:rename {
new_name = new_path.filename,
}
fb_utils.tele_notify(string.format("%s has been moved!", filename))
fb_utils.action_cmp_msg(string.format("%s has been moved!", filename), finder.quiet, #selections)
end
end

Expand All @@ -229,6 +232,7 @@ end
fb_actions.copy = function(prompt_bufnr)
local current_picker = action_state.get_current_picker(prompt_bufnr)
local finder = current_picker.finder
local quiet = finder.quiet
if finder.files ~= nil and finder.files == false then
fb_utils.tele_notify("Copying files in folder browser mode not supported.", log_levels.WARN)
return
Expand All @@ -252,15 +256,19 @@ fb_actions.copy = function(prompt_bufnr)
if file:parent():absolute() == finder.path then
local absolute_path = file:absolute()
fb_utils.tele_notify "Copying existing file or folder within original directory."
destination = fb_utils.get_valid_path("Please provide a new file or folder name: ", absolute_path)
destination = fb_utils.get_valid_path(
"Please provide a new file or folder name: ",
absolute_path,
{ quiet = quiet }
)
end
if destination then
file:copy {
destination = destination,
recursive = true,
parents = true,
}
fb_utils.tele_notify(string.format("%s has been copied!", filename))
fb_utils.action_cmp_msg(string.format("%s has been copied!", filename), quiet, #selections)
end
end

Expand All @@ -272,6 +280,7 @@ end
---@param prompt_bufnr number: The prompt bufnr
fb_actions.remove = function(prompt_bufnr)
local current_picker = action_state.get_current_picker(prompt_bufnr)
local quiet = current_picker.finder.quiet
local selections = fb_utils.get_selected_files(prompt_bufnr, true)
if vim.tbl_isempty(selections) then
fb_utils.tele_notify "Nothing currently selected to be removed."
Expand All @@ -282,30 +291,27 @@ fb_actions.remove = function(prompt_bufnr)
return sel:absolute()
end, selections)

fb_utils.tele_notify "Following files/folders are going to be deleted:"
-- BUG: printing below completely messes with the y/n 'Operation aborted' & '.. has been removed!' printing
fb_utils.tele_notify "Following files/folders will be remove:"
for _, file in ipairs(filenames) do
fb_utils.tele_notify(" - " .. file)
end

vim.ui.input({ prompt = "[telescope] Remove selected files [y/N]: " }, function(input)
if input and input:lower() == "y" then
vim.notify "\n"
for _, p in ipairs(selections) do
local is_dir = p:is_dir()
p:rm { recursive = is_dir }
-- clean up opened buffers
if not is_dir then
fb_utils.delete_buf(p:absolute())
else
fb_utils.delete_dir_buf(p:absolute())
end
fb_utils.tele_notify(string.format("%s has been removed!", p:absolute()))
local ans = fb_utils.get_answer_yes("Remove selected files", false, { quiet = quiet })
if ans then
for _, p in ipairs(selections) do
local is_dir = p:is_dir()
p:rm { recursive = is_dir }
-- clean up opened buffers
if not is_dir then
fb_utils.delete_buf(p:absolute())
else
fb_utils.delete_dir_buf(p:absolute())
end
current_picker:refresh(current_picker.finder)
else
fb_utils.tele_notify "\nRemoving files aborted!"
fb_utils.action_cmp_msg(string.format("%s has been removed!", p:absolute()), quiet, #selections)
end
end)
current_picker:refresh(current_picker.finder)
end
end

--- Toggle hidden files or folders for |fb_picker.file_browser|.
Expand Down
17 changes: 11 additions & 6 deletions lua/telescope/_extensions/file_browser/finders.lua
Original file line number Diff line number Diff line change
Expand Up @@ -110,15 +110,19 @@ end

--- Returns a finder that combines |fb_finders.browse_files| and |fb_finders.browse_folders| into a unified finder.
---@param opts table: options to pass to the picker
---@field path string: root dir to file_browse from (default: vim.loop.cwd())
---@field cwd string: root dir (default: vim.loop.cwd())
---@field cwd_to_path bool: folder browser follows `path` of file browser
---@field files boolean: start in file (true) or folder (false) browser (default: true)
---@field path string: dir to browse files from from, `vim.fn.expanded` automatically (default: vim.loop.cwd())
---@field cwd string: dir to browse folders from, `vim.fn.expanded` automatically (default: vim.loop.cwd())
---@field cwd_to_path boolean: whether folder browser is launched from `path` rather than `cwd` (default: false)
---@field grouped boolean: group initial sorting by directories and then files; uses plenary.scandir (default: false)
---@field depth number: file tree depth to display (default: 1)
---@field dir_icon string: change the icon for a directory. (default: )
---@field files boolean: start in file (true) or folder (false) browser (default: true)
---@field add_dirs boolean: whether the file browser shows folders (default: true)
---@field depth number: file tree depth to display, `false` for unlimited depth (default: 1)
---@field dir_icon string: change the icon for a directory (default: )
---@field hidden boolean: determines whether to show hidden files or not (default: false)
---@field respect_gitignore boolean: induces slow-down w/ plenary finder (default: false, true if `fd` available)
---@field browse_files function: custom override for the file browser (default: |fb_finders.browse_files|)
---@field browse_folders function: custom override for the folder browser (default: |fb_finders.browse_folders|)
---@field quiet bool: suppress action completion messages (default: false)
fb_finders.finder = function(opts)
opts = opts or {}
-- cache entries such that multi selections are maintained across {file, folder}_browsers
Expand All @@ -134,6 +138,7 @@ fb_finders.finder = function(opts)
respect_gitignore = vim.F.if_nil(opts.respect_gitignore, has_fd),
files = vim.F.if_nil(opts.files, true), -- file or folders mode
grouped = vim.F.if_nil(opts.grouped, false),
quiet = vim.F.if_nil(opts.quiet, false),
-- ensure we forward make_entry opts adequately
entry_maker = vim.F.if_nil(opts.entry_maker, function(local_opts)
return fb_make_entry(vim.tbl_extend("force", opts, local_opts))
Expand Down
2 changes: 2 additions & 0 deletions lua/telescope/_extensions/file_browser/picker.lua
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ local fb_picker = {}
---@field respect_gitignore boolean: induces slow-down w/ plenary finder (default: false, true if `fd` available)
---@field browse_files function: custom override for the file browser (default: |fb_finders.browse_files|)
---@field browse_folders function: custom override for the folder browser (default: |fb_finders.browse_folders|)
---@field quiet bool: suppress action completion messages (default: false)
fb_picker.file_browser = function(opts)
opts = opts or {}

Expand All @@ -63,6 +64,7 @@ fb_picker.file_browser = function(opts)
opts.cwd = opts.cwd and vim.fn.expand(opts.cwd) or cwd
opts.path = opts.path and vim.fn.expand(opts.path) or opts.cwd
opts.files = vim.F.if_nil(opts.files, true)
opts.quiet = vim.F.if_nil(opts.quiet, false)
pickers.new(opts, {
prompt_title = opts.files and "File Browser" or "Folder Browser",
results_title = opts.files and Path:new(opts.path):make_relative(cwd) .. os_sep or "Results",
Expand Down
73 changes: 58 additions & 15 deletions lua/telescope/_extensions/file_browser/utils.lua
Original file line number Diff line number Diff line change
Expand Up @@ -156,37 +156,80 @@ end

-- Move this and above functions into telescope core?
fb_utils.tele_notify = function(msg, log_level, opts)
while msg:match "^\n" do
msg = msg:sub(2, #msg)
vim.notify "\n"
end
opts = opts or {}
opts.title = "telescope"
vim.notify(add_tele_prefix(msg), log_level, opts)
while msg:match "\n$" do
msg = msg:sub(1, #msg - 1)
vim.notify "\n"
end
end

fb_utils.get_valid_path = function(prompt, default, check_exist)
check_exist = vim.F.if_nil(check_exist, true)
---@param opts table: options to pass to the path getter
---@field check_exist boolean: check if path already exists
---@field quiet boolean: suppress 'Operation aborted' message
fb_utils.get_valid_path = function(prompt, default, opts)
opts = opts or {}
opts.check_exist = vim.F.if_nil(opts.check_exist, true)
opts.quiet = vim.F.if_nil(opts.quiet, false)

local path
vim.ui.input({ prompt = add_tele_prefix(prompt), default = default }, function(input)
input = input and input:match "^%s*(.-)%s*$" or nil
if not input then
fb_utils.tele_notify("\nOperation aborted!", vim.log.levels.WARN)
if not input and not opts.quiet then
-- BUG: if default is completely deleted, msg prints on the same line
fb_utils.tele_notify("Operation aborted!", vim.log.levels.WARN)
return
elseif input == "" then
fb_utils.tele_notify("\nPlease provide valid path input!", vim.log.levels.WARN)
fb_utils.clear_cmd()
fb_utils.tele_notify("Please provide valid path input!", vim.log.levels.WARN)
return
end

path = Path:new(input)
if check_exist and path:exists() then
fb_utils.tele_notify(string.format("\n%s already exists! Skipping.", path.filename), vim.log.levels.WARN)
if opts.check_exist and path:exists() then
fb_utils.clear_cmd()
fb_utils.tele_notify(string.format("%s already exists! Skipping.", path.filename), vim.log.levels.WARN)
path = nil
end
end)
return path
end

---@param opts table: options to pass to the path getter
---@field quiet boolean: suppress 'Operation aborted' message
fb_utils.get_answer_yes = function(prompt, default_yes, opts)
opts = opts or {}
opts.quiet = vim.F.if_nil(opts.quiet, false)
default_yes = vim.F.if_nil(default_yes, true)
prompt = add_tele_prefix(prompt) .. (default_yes and " [Y/n]:" or " [y/N]:")

local answer
vim.ui.input({ prompt = prompt, default = " " }, function(input)
input = input and input:match "^%s*(.-)%s*$" or nil
answer = input and input:lower() == "y"
if not input and not opts.quiet then
fb_utils.tele_notify("Operation aborted!", vim.log.levels.WARN)
elseif not answer then
fb_utils.clear_cmd()
fb_utils.tele_notify("Operation aborted!", vim.log.levels.WARN)
end
end)
return answer
end

fb_utils.clear_cmd = function()
-- barely works and not even always
-- also tried `echon ''`
vim.api.nvim_command "norm :esc<CR>"
end

fb_utils.action_cmp_msg = function(msg, quiet, count)
quiet = vim.F.if_nil(quiet, false)
count = vim.F.if_nil(count, 1)

if not quiet then
if count == 1 then -- don't clear for multi file move/remove
fb_utils.clear_cmd()
end
fb_utils.tele_notify(msg)
end
end

return fb_utils

0 comments on commit 1cd81e4

Please sign in to comment.