Skip to content

Commit a44544a

Browse files
committed
Merge branch 'master' into 2941-move-lib-to-explorer
2 parents ff85d80 + 68be6df commit a44544a

File tree

6 files changed

+67
-41
lines changed

6 files changed

+67
-41
lines changed

lua/nvim-tree/actions/finders/find-file.lua

Lines changed: 18 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@ local log = require("nvim-tree.log")
22
local view = require("nvim-tree.view")
33
local utils = require("nvim-tree.utils")
44
local core = require("nvim-tree.core")
5+
6+
local DirectoryNode = require("nvim-tree.node.directory")
57
local Iterator = require("nvim-tree.iterators.node-iterator")
68

79
local M = {}
@@ -59,19 +61,27 @@ function M.fn(path)
5961
local link_match = node.link_to and vim.startswith(path_real, node.link_to .. utils.path_separator)
6062

6163
if abs_match or link_match then
62-
if not node.group_next then
63-
node.open = true
64-
end
65-
if #node.nodes == 0 then
66-
core.get_explorer():expand(node)
67-
if node.group_next and incremented_line then
68-
line = line - 1
64+
local dir = node:as(DirectoryNode)
65+
if dir then
66+
if not dir.group_next then
67+
dir.open = true
68+
end
69+
if #dir.nodes == 0 then
70+
core.get_explorer():expand(dir)
71+
if dir.group_next and incremented_line then
72+
line = line - 1
73+
end
6974
end
7075
end
7176
end
7277
end)
7378
:recursor(function(node)
74-
return node.group_next and { node.group_next } or (node.open and #node.nodes > 0 and node.nodes)
79+
node = node and node:as(DirectoryNode)
80+
if node then
81+
return node.group_next and { node.group_next } or (node.open and #node.nodes > 0 and node.nodes)
82+
else
83+
return nil
84+
end
7585
end)
7686
:iterate()
7787

lua/nvim-tree/actions/moves/item.lua

Lines changed: 12 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -72,7 +72,7 @@ local function move(explorer, where, what, skip_gitignored)
7272
end
7373
end
7474

75-
---@param node Node
75+
---@param node DirectoryNode
7676
local function expand_node(node)
7777
if node:is(DirectoryNode) and not node.open then
7878
---@cast node DirectoryNode
@@ -101,9 +101,9 @@ local function move_next_recursive(explorer, what, skip_gitignored)
101101
if node_init.name ~= ".." then -- root node cannot have a status
102102
valid = status_is_valid(node_init, what, skip_gitignored)
103103
end
104-
if node_init:is(DirectoryNode) and valid and not node_init.open then
105-
---@cast node_init DirectoryNode
106-
node_init:expand_or_collapse(false)
104+
local node_dir = node_init:as(DirectoryNode)
105+
if node_dir and valid and not node_dir.open then
106+
node_dir:expand_or_collapse(false)
107107
end
108108

109109
move(explorer, "next", what, skip_gitignored)
@@ -120,20 +120,15 @@ local function move_next_recursive(explorer, what, skip_gitignored)
120120

121121
-- i is used to limit iterations.
122122
local i = 0
123-
local is_dir = node_cur.nodes ~= nil
124-
while is_dir and i < MAX_DEPTH do
125-
expand_node(node_cur)
123+
local dir_cur = node_cur:as(DirectoryNode)
124+
while dir_cur and i < MAX_DEPTH do
125+
expand_node(dir_cur)
126126

127127
move(explorer, "next", what, skip_gitignored)
128128

129129
-- Save current node.
130130
node_cur = explorer:get_node_at_cursor()
131-
-- Update is_dir.
132-
if node_cur then
133-
is_dir = node_cur.nodes ~= nil
134-
else
135-
is_dir = false
136-
end
131+
dir_cur = node_cur and node_cur:as(DirectoryNode)
137132

138133
i = i + 1
139134
end
@@ -187,8 +182,10 @@ local function move_prev_recursive(explorer, what, skip_gitignored)
187182
end
188183

189184
-- 4.2)
190-
local node_dir = node_cur
191-
expand_node(node_dir)
185+
local node_dir = node_cur:as(DirectoryNode)
186+
if node_dir then
187+
expand_node(node_dir)
188+
end
192189

193190
-- 4.3)
194191
if node_init.name == ".." then -- root node

lua/nvim-tree/actions/node/open-file.lua

Lines changed: 8 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -331,9 +331,9 @@ local function open_in_new_window(filename, mode)
331331

332332
local fname
333333
if M.relative_path then
334-
fname = vim.fn.fnameescape(utils.path_relative(filename, vim.fn.getcwd()))
334+
fname = utils.escape_special_chars(vim.fn.fnameescape(utils.path_relative(filename, vim.fn.getcwd())))
335335
else
336-
fname = vim.fn.fnameescape(filename)
336+
fname = utils.escape_special_chars(vim.fn.fnameescape(filename))
337337
end
338338

339339
local command
@@ -370,36 +370,35 @@ end
370370
---@param mode string
371371
---@param filename string
372372
function M.fn(mode, filename)
373-
local fname = utils.escape_special_chars(filename)
374373
if type(mode) ~= "string" then
375374
mode = ""
376375
end
377376

378377
if mode == "tabnew" then
379-
return open_file_in_tab(fname)
378+
return open_file_in_tab(filename)
380379
end
381380

382381
if mode == "drop" then
383-
return drop(fname)
382+
return drop(filename)
384383
end
385384

386385
if mode == "tab_drop" then
387-
return tab_drop(fname)
386+
return tab_drop(filename)
388387
end
389388

390389
if mode == "edit_in_place" then
391-
return edit_in_current_buf(fname)
390+
return edit_in_current_buf(filename)
392391
end
393392

394-
local buf_loaded = is_already_loaded(fname)
393+
local buf_loaded = is_already_loaded(filename)
395394

396395
local found_win = utils.get_win_buf_from_path(filename)
397396
if found_win and (mode == "preview" or mode == "preview_no_picker") then
398397
return
399398
end
400399

401400
if not found_win then
402-
open_in_new_window(fname, mode)
401+
open_in_new_window(filename, mode)
403402
else
404403
vim.api.nvim_set_current_win(found_win)
405404
vim.bo.bufhidden = ""

lua/nvim-tree/lib.lua

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -65,7 +65,7 @@ end
6565
---@param items_short string[]
6666
---@param items_long string[]
6767
---@param kind string|nil
68-
---@param callback fun(item_short: string)
68+
---@param callback fun(item_short: string|nil)
6969
function M.prompt(prompt_input, prompt_select, items_short, items_long, kind, callback)
7070
local function format_item(short)
7171
for i, s in ipairs(items_short) do

lua/nvim-tree/node/init.lua

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,10 +2,6 @@ local git = require("nvim-tree.git")
22

33
local Class = require("nvim-tree.class")
44

5-
---TODO #2886
6-
---TODO remove all @cast
7-
---TODO remove all references to directory fields:
8-
95
---Abstract Node class.
106
---Uses the abstract factory pattern to instantiate child instances.
117
---@class (exact) Node: Class

lua/nvim-tree/utils.lua

Lines changed: 28 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,17 @@ function M.path_basename(path)
5959
return path:sub(i + 1, #path)
6060
end
6161

62+
--- Check if there are parentheses before brackets, it causes problems for windows.
63+
--- Refer to issue #2862 and #2961 for more details.
64+
local function has_parentheses_and_brackets(path)
65+
local _, i_parentheses = path:find("(", 1, true)
66+
local _, i_brackets = path:find("[", 1, true)
67+
if i_parentheses and i_brackets then
68+
return true
69+
end
70+
return false
71+
end
72+
6273
--- Get a path relative to another path.
6374
---@param path string
6475
---@param relative_to string|nil
@@ -68,13 +79,18 @@ function M.path_relative(path, relative_to)
6879
return path
6980
end
7081

71-
local _, r = path:find(M.path_add_trailing(relative_to), 1, true)
72-
local p = path
82+
local norm_path = path
83+
if M.is_windows and has_parentheses_and_brackets(path) then
84+
norm_path = path:gsub("/", "\\")
85+
end
86+
87+
local _, r = norm_path:find(M.path_add_trailing(relative_to), 1, true)
88+
local p = norm_path
7389
if r then
7490
-- take the relative path starting after '/'
7591
-- if somehow given a completely matching path,
7692
-- returns ""
77-
p = path:sub(r + 1)
93+
p = norm_path:sub(r + 1)
7894
end
7995
return p
8096
end
@@ -272,14 +288,22 @@ function M.canonical_path(path)
272288
return path
273289
end
274290

291+
--- Escapes special characters in string for windows, refer to issue #2862 and #2961 for more details.
292+
local function escape_special_char_for_windows(path)
293+
if has_parentheses_and_brackets(path) then
294+
return path:gsub("\\", "/"):gsub("/ ", "\\ ")
295+
end
296+
return path:gsub("%(", "\\("):gsub("%)", "\\)")
297+
end
298+
275299
--- Escapes special characters in string if windows else returns unmodified string.
276300
---@param path string
277301
---@return string|nil
278302
function M.escape_special_chars(path)
279303
if path == nil then
280304
return path
281305
end
282-
return M.is_windows and path:gsub("\\", "/") or path
306+
return M.is_windows and escape_special_char_for_windows(path) or path
283307
end
284308

285309
--- Create empty sub-tables if not present

0 commit comments

Comments
 (0)