1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
|
local vim = assert(vim)
local util = require('warp.util')
local M = {}
local big_line, col_map = (function ()
-- Longest possible line alternating between vowels and (vowels + consanants)
-- which does not have a repeated substring of length 2.
--
-- Size is 5*(26 + 21) + 1
--
-- It can reference up 235 unique columns. That should be enough even for
-- Java.
local big_line =
"tetaoinuserahodilucemafoyiwugepabovikuxeqajozitunesarohidulecamofiyuw"
.. "egapobivukexaqojizutonasirehudelacomifuyewagopibuvekaxoqijuzenotisuri"
.. "hadalocumefeyawogipubevakoxiqujezanicimuhedosorufayoligupebavowixuqej"
.. "azokieaueoaiuaeiouooeeuuiiaat"
local col_map = {}
local i = 0
while i < #big_line do
local sub = big_line:sub(i, i + 1)
if col_map[sub] then
-- Sanity check
error("repeated sequence: '" .. sub .. "'", 2)
end
col_map[sub] = i
i = i + 1
end
return big_line, col_map
end)()
local function char_at(s, i)
local m = (i % #s) + 1
return string.sub(s, m, m)
end
M.strategy = function()
local leftcol = vim.fn.winsaveview().leftcol
local filter
return util.wrap_col_selector({
display = function()
local curpos = vim.api.nvim_win_get_cursor(0)
local line_at = vim.fn.getline(curpos[1])
local current_win = vim.api.nvim_get_current_win();
local wininfo = vim.fn.getwininfo(current_win)[1]
local width = wininfo.width - wininfo.textoff
if vim.o.virtualedit ~= 'all' then
width = math.min(#line_at + 1, width)
end
if vim.o.virtualedit == 'onemore' then
width = width + 1
end
local unfiltered = big_line:sub(leftcol + 1, width)
local line = unfiltered
if filter then
line = ""
local i = 1
while i <= #unfiltered do
local curch = char_at(unfiltered, i - 1)
if curch == filter then
line = line .. char_at(unfiltered, i)
else
line = line .. ' '
end
i = i + 1
end
end
return line
end,
on_char = function(ch)
if not filter then
if ch == '$' or ch == '^' then
vim.cmd("normal! " .. ch)
return false
elseif not ch:match('[a-z]') then
vim.cmd("normal! f" .. ch)
return false
else
filter = ch
return true
end
else
if col_map[filter .. ch] then
vim.cmd("normal! " .. col_map[filter .. ch] .. "|")
end
end
return false
end
})
end
M.run = function ()
print(big_line)
M.strategy().run()
end
return M
|