-
Notifications
You must be signed in to change notification settings - Fork 2
/
Copy pathtext-objects.kak
147 lines (133 loc) · 5.53 KB
/
text-objects.kak
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
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
# extended behaviors for pairs
map global object '(' '<esc>: text-object-block (<ret>' -docstring 'prev parenthesis block'
map global object ')' '<esc>: text-object-block )<ret>' -docstring 'next parenthesis block'
map global object '{' '<esc>: text-object-block {<ret>' -docstring 'prev braces block'
map global object '}' '<esc>: text-object-block }<ret>' -docstring 'next braces block'
map global object '[' '<esc>: text-object-block [<ret>' -docstring 'prev brackets block'
map global object ']' '<esc>: text-object-block ]<ret>' -docstring 'next brackets block'
map global object '<lt>' '<esc>: text-object-block <lt><ret>' -docstring 'prev angle block'
map global object '<gt>' '<esc>: text-object-block <gt><ret>' -docstring 'next angle block'
# additional text objects
map global object 'x' '<esc>: text-object-line<ret>' -docstring 'line'
map global object 't' '<esc>: text-object-tag<ret>' -docstring 'tag'
map global object 'f' '<esc>: text-object-buffer<ret>' -docstring 'buffer'
map global object '<tab>' '<esc>: text-object-indented-paragraph<ret>' -docstring 'indented paragraph'
# depends on occivink/kakoune-vertical-selection
map global object 'v' '<esc>: text-object-vertical<ret>' -docstring 'vertical selection'
# alias to avoid shift
map global object 'd' '"' -docstring 'double quote string'
map global object 'o' 'B' -docstring 'braces'
# see issue #9
# first normal behavior, then fallback if it fails
define-command -hidden text-object-block -params 1 %@
evaluate-commands %sh!
# there may be clever way to do this, but I don't want to be clever in shell
case "$1" in
'(') t=')';dir='<a-/>'; ;;
'{') t='}';dir='<a-/>'; ;;
'[') t=']';dir='<a-/>'; ;;
'<') t='>';dir='<a-/>'; ;;
')') t='(';dir='/'; ;;
'}') t='{';dir='/'; ;;
']') t='[';dir='/'; ;;
'>') t='<';dir='/'; ;;
esac
# $t is used instead of $1 to provide more 'intuitive' prev / next blocks when nested
echo "try %| exec $kak_opt_objects_last_mode '$t' | catch %| exec $dir \Q '$t' \E <ret> ; exec $kak_opt_objects_last_mode '$t' |"
!
@
# this line object may seem to repeat builtins,
# it is mostly here to improve the orthogonality of kakoune design
define-command -hidden text-object-line %{
evaluate-commands %sh{
case "$kak_opt_objects_last_mode" in
# around
'<a-a>') k='x' ;;
'[') k='<a-h>' ;;
']') k='<a-l>L' ;;
'{') k='Gh' ;;
'}') k='GlL' ;;
# inside
'<a-i>') k='x_' ;;
'<a-[>') k='<a-h>_' ;;
'<a-]>') k='<a-l>' ;;
'<a-{>') k='Gi' ;;
'<a-}>') k='Gl' ;;
esac
[ -n "$k" ] && echo "execute-keys <esc> $k"
}
}
# this buffer object may seem to repeat builtins,
# it is mostly here to improve the orthogonality of kakoune design
define-command -hidden text-object-buffer %{
evaluate-commands %sh{
case "$kak_opt_objects_last_mode" in
# around
'<a-a>') k='\%' ;;
'[') k='<a-:><a-\;>\;Gk' ;;
']') k='<a-:>\;Ge' ;;
'{') k='<a-:><a-\;>Gk' ;;
'}') k='<a-:>Ge' ;;
# inside
'<a-i>') k='\%_' ;;
'<a-[>') k='<a-:><a-\;>\;Gk_' ;;
'<a-]>') k='<a-:>\;Ge_' ;;
'<a-{>') k='<a-:><a-\;>Gk_' ;;
'<a-}>') k='<a-:>Ge_' ;;
esac
[ -n "$k" ] && echo "execute-keys <esc> $k"
}
}
# work in progress - very brittle for now
define-command -hidden text-object-tag %{
evaluate-commands %sh{
case "$kak_opt_objects_last_mode" in
'<a-a>') k='<esc><a-f><lt>2f<gt>' ;;
'<a-i>') k='<a-i>c<gt>,<lt><ret>' ;;
esac
[ -n "$k" ] && echo "execute-keys $k"
}
}
# thanks occivink
define-command -hidden text-object-indented-paragraph %{
execute-keys -draft -save-regs '' '<a-i>pZ'
execute-keys '<a-i>i<a-z>i'
}
# depends on occivink/kakoune-vertical-selection
define-command -hidden text-object-vertical %{
try %{
evaluate-commands %sh{
case "$kak_opt_objects_last_mode" in
'<a-i>') k='<esc>:<space>vertical-selection-up-and-down<ret>' ;;
'<a-a>') k='<a-i>w<esc>:<space>vertical-selection-up-and-down<ret>' ;;
'[') k='<esc>:<space>vertical-selection-up<ret>' ;;
']') k='<esc>:<space>vertical-selection-down<ret>' ;;
'{') k='<a-i>w<esc>:<space>vertical-selection-up<ret>' ;;
'}') k='<a-i>w<esc>:<space>vertical-selection-down<ret>' ;;
esac
[ -n "$k" ] && echo "execute-keys $k"
}
} catch %{
fail "no selections remaining"
}
}
# helpers
# hack to know in which "submode" we are
# gGvV are not used in the context of this plugin
declare-option -hidden str objects_last_mode
hook global NormalKey (g|G|v|V|<a-i>|<a-a>|\[|\]|\{|\}|<a-\[>|<a-\]>|<a-\{>|<a-\}>) %{
set-option global objects_last_mode %val{hook_param}
}
# selectors user-mode, see README for usage
declare-user-mode selectors
map global selectors 'a' '*%s<ret>' -docstring 'select all'
map global selectors 'i' '<a-i>' -docstring 'select inside object <a-i>'
map global selectors 'o' '<a-a>' -docstring 'select outside object <a-a>'
map global selectors 'j' '<a-[>' -docstring 'select inner object start <a-[>'
map global selectors 'k' '<a-]>' -docstring 'select inner object end <a-]>'
map global selectors 'J' '<a-{>' -docstring 'extend inner object start <a-{>'
map global selectors 'K' '<a-}>' -docstring 'extend inner object end <a-}>'
map global selectors 'h' '[' -docstring 'select object start ['
map global selectors 'l' ']' -docstring 'select object end ]'
map global selectors 'H' '{' -docstring 'extend object start {'
map global selectors 'L' '}' -docstring 'extend object end }'