Skip to content

Commit 28d9938

Browse files
refactor(jump): simplify the main jump function
Details: - Instead of always checking if target exists in text, only do so if there was no jump. Additional benefit: the code using the cursor to check if a jump occurred can be replaced by a more direct check. - Rearrange code for a lower LOC and more clarity. Co-authored-by: Evgeni Chasnovski <evgeni.chasnovski@gmail.com>
1 parent 7913069 commit 28d9938

File tree

1 file changed

+18
-34
lines changed

1 file changed

+18
-34
lines changed

lua/mini/jump.lua

Lines changed: 18 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -181,74 +181,58 @@ MiniJump.state = {
181181
MiniJump.jump = function(target, backward, till, n_times)
182182
if H.is_disabled() then return end
183183

184-
-- Ensure to undo "consuming a character" effect if there is no target found
185-
-- Do it here to act on dot-repeat
186-
local has_changed_cursor = false
187-
local undo_no_move = function()
188-
if not has_changed_cursor then vim.cmd('undo!') end
189-
end
190-
if MiniJump._is_expr then vim.schedule(undo_no_move) end
191-
192184
-- Dot-repeat should not change the state, so save it to later restore
193-
local is_dot_repeat = MiniJump._is_expr and not MiniJump._is_expr_init
185+
local is_expr, is_dot_repeat = MiniJump._is_expr, MiniJump._is_expr and not MiniJump._is_expr_init
194186
MiniJump._is_expr, MiniJump._is_expr_init = nil, nil
195187
local state_snapshot = is_dot_repeat and vim.deepcopy(MiniJump.state) or nil
196188

197189
-- Cache inputs for future use
198190
H.update_state(target, backward, till, n_times)
199191

200-
if MiniJump.state.target == nil then
201-
H.message('Can not jump because there is no recent `target`.')
202-
return
203-
end
204-
205-
-- Determine if target is present anywhere in order to correctly enter
206-
-- jumping mode. If not, jumping mode is not possible.
207-
local search_pattern = [[\V]] .. vim.fn.escape(MiniJump.state.target, [[\]])
208-
local target_is_present = vim.fn.search(search_pattern, 'wn') ~= 0
209-
if not target_is_present then return end
192+
if MiniJump.state.target == nil then return H.message('Can not jump because there is no recent `target`.') end
210193

211194
-- Construct search and highlight pattern data
212195
local pattern, hl_pattern, flags = H.make_search_data()
213196

214197
-- Delay highlighting after stopping previous one
198+
-- Update highlighting immediately if any highlighting is already present
215199
local config = H.get_config()
216200
H.timers.highlight:stop()
217-
H.timers.highlight:start(
218-
-- Update highlighting immediately if any highlighting is already present
219-
H.is_highlighting() and 0 or config.delay.highlight,
220-
0,
221-
vim.schedule_wrap(function() H.highlight(hl_pattern) end)
222-
)
201+
local hl = vim.schedule_wrap(function() H.highlight(hl_pattern) end)
202+
H.timers.highlight:start(H.is_highlighting() and 0 or config.delay.highlight, 0, hl)
223203

224204
-- Start idle timer after stopping previous one
225205
H.timers.idle_stop:stop()
226206
H.timers.idle_stop:start(config.delay.idle_stop, 0, vim.schedule_wrap(function() MiniJump.stop_jumping() end))
227207

228208
-- Make jump(s)
229209
H.cache.n_cursor_moved = 0
230-
local init_cursor_data = H.get_cursor_data()
231210
local was_jumping = MiniJump.state.jumping
232211
MiniJump.state.jumping = true
233212
if not was_jumping then H.trigger_event('MiniJumpStart') end
234213
H.trigger_event('MiniJumpJump')
235214

215+
local has_jumped = false
236216
for _ = 1, MiniJump.state.n_times do
237-
vim.fn.search(pattern, flags)
217+
local row = vim.fn.search(pattern, flags)
218+
has_jumped = has_jumped or row > 0
238219
end
239220

240221
-- Open enough folds to show jump
241-
vim.cmd('normal! zv')
222+
if has_jumped then vim.cmd('normal! zv') end
242223

243224
-- Track cursor position to account for movement not caught by `CursorMoved`
244225
H.cache.latest_cursor = H.get_cursor_data()
245-
has_changed_cursor = not vim.deep_equal(H.cache.latest_cursor, init_cursor_data)
246226

247-
-- Restore the state if needed
248-
if is_dot_repeat then
249-
state_snapshot.jumping = true
250-
MiniJump.state = state_snapshot
251-
end
227+
-- Restore the state if needed. It should a jumping state if there was jump
228+
-- or if it is possible to jump in other direction (i.e. target is present).
229+
MiniJump.state = is_dot_repeat and state_snapshot or MiniJump.state
230+
local search_pattern = '\\V' .. vim.fn.escape(MiniJump.state.target, '\\')
231+
MiniJump.state.jumping = has_jumped or vim.fn.search(search_pattern, 'wn') ~= 0
232+
233+
-- Ensure to undo "consume a character" effect in Operator-pending expression
234+
-- mapping if there is no target found. Do it here to also act on dot-repeat.
235+
if is_expr and not has_jumped then vim.schedule(function() vim.cmd('undo!') end) end
252236
end
253237

254238
--- Make smart jump

0 commit comments

Comments
 (0)