Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Speaker Deck
PRO
Sign in
Sign up
for free
Vimprint - A Vim Keystroke Parser
nelstrom
May 28, 2013
Technology
1
730
Vimprint - A Vim Keystroke Parser
nelstrom
May 28, 2013
Tweet
Share
More Decks by nelstrom
See All by nelstrom
nelstrom
9
1.6k
nelstrom
11
24k
nelstrom
1
2.9k
nelstrom
29
4.6k
nelstrom
1
240
nelstrom
1
560
Other Decks in Technology
See All in Technology
ishiayaya
PRO
0
340
clustervr
0
160
ocise
0
170
kenya888
1
130
toshinoritakai
1
210
texmeijin
1
210
saoritakita
0
350
sugimomoto
1
240
hsano
0
130
_kensh
1
170
chaspy
1
150
viva_tweet_x
5
2.7k
Featured
See All Featured
imathis
478
150k
ammeep
656
54k
jonyablonski
14
1.1k
morganepeng
17
1.1k
marcelosomers
220
15k
destraynor
223
47k
sstephenson
144
12k
mongodb
23
3.8k
bkeepers
52
4.1k
yeseniaperezcruz
302
31k
shlominoach
176
7.4k
cherdarchuk
71
260k
Transcript
VIMPRINT A VIM KEYSTROKE PARSER 28th May, 2013 Drew Neil
@nelstrom
VIMPRINT should... visualize keystrokes in realtime
VIMPRINT should... understand all built-in commands
VIMPRINT should... be extensible
VimSpeak Turns spoken English into keystrokes https://github.com/AshleyF/VimSpeak
None
VimSplain Turns keystrokes into plain English https://github.com/pafcu/Vimsplain
Vimulator Turns live keystrokes into plain English https://github.com/thoughtbot/vimulator
None
VimGolf Logs real keystrokes https://github.com/igrigorik/vimgolf
None
vim -w keystrokes are BUFFERED
None
Parslet 1st attempt at parsing Vim keystrokes
None
class Vimprint < Parslet::Parser rule(:start) { match('[iIaAoOsS]').as(:switch) } rule(:typing) {
match('[^\e]').repeat.as(:typing) } rule(:terminate) { match('\e').as(:escape) } rule(:insertion) { start >> typing >> terminate } root(:insertion) end
gv major stumbling block: switch from Normal mode to Visual
mode and select the last selected text
Ragel 2nd attempt at parsing Vim keystrokes
Ragel state machines can not only recognize byte sequences as
regular expression machines do, but can also execute code at arbitrary points in the recognition of a regular language.
%%{ machine vim_print; action return { fret; } action push_insert_mode
{ fcall insert_mode; } escape = 27; input = (any - escape); motion = [hjklbwe0]; switch = [iIaAsSoO]; insert_mode := ( input* escape @return ); normal_mode := ( motion | switch @push_insert_mode )*; }%%
2 IN 1 insert_mode normal_mode '0', 'b', 'e', 'h', 'j'..'l',
'w' 'A', 'I', 'O', 'S', 'a', 'i', 'o', 's' / push_insert_mode 3 27 / return DEF
action H { @head = p } action T {
@tail = p } action EmitMotion { @events << {motion: strokes} } action EmitSwitch { @events << {switch: strokes} } action EmitInput { @events << {input: strokes} } action EmitEscape { @events << {escape: '<Esc>'} } escape = 27 >H@T @EmitEscape; input = (any - escape) >H@T @EmitInput; motion = [hjklbwe0] >H@T @EmitMotion; switch = [iIaAsSoO] >H@T @EmitSwitch;
class VimParser attr_accessor :head, :tail, :data def initialize(listener) @events =
listener %% write data; end def process(input) @data = input.unpack("c*") eof = @data.length stack = [] %% write init; %% write exec; end def strokes @data[@head..@tail].pack('c*') end end
VimParser.new(recorder = []).process("helihello\e") puts recorder {:motion=>"h"} {:motion=>"e"} {:motion=>"l"} {:switch=>"i"} {:input=>"h"}
{:input=>"e"} {:input=>"l"} {:input=>"l"} {:input=>"o"} {:escape=>"<Esc>"} https://gist.github.com/nelstrom/5663083
FATAL FLAWS with parsing keystrokes
FATAL FLAWS no timestamps <leader>{...}
FATAL FLAWS no document context :s/{pattern}/{string}/c
FATAL FLAWS no filetype detection
HALP! https://github.com/nelstrom/vimprint Vimprint Realtime Vim keystroke visualizer