From b2bec6638cde0f2f6a64298572bafd0126bcda32 Mon Sep 17 00:00:00 2001 From: Simon Ruderich Date: Thu, 7 Oct 2010 23:16:11 +0200 Subject: vim_mode: Add "0, last yank. --- vim-mode/vim_mode.pl | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) (limited to 'vim-mode/vim_mode.pl') diff --git a/vim-mode/vim_mode.pl b/vim-mode/vim_mode.pl index 134874d..52424ce 100644 --- a/vim-mode/vim_mode.pl +++ b/vim-mode/vim_mode.pl @@ -37,9 +37,10 @@ # * Switch case: ~ # * Repeat change: . # * Repeat ftFT: ; , -# * Registers: "a-"z "" "* "+ "_ (black hole) +# * Registers: "a-"z "" "0 "* "+ "_ (black hole) # Appending to register with "A-"Z # "" is the default yank/delete register. +# "0 contains the last yank (if no register was specified). # The special registers "* "+ contain both irssi's cut-buffer. # * Line-wise shortcuts: dd cc yy # * Shortcuts: s S C D @@ -402,6 +403,7 @@ my $register = '"'; my $registers = { '"' => '', # default register + '0' => '', # yank register '+' => '', # contains irssi's cut buffer '*' => '', # same '_' => '', # black hole register, always empty @@ -525,6 +527,10 @@ sub cmd_operator_y { } else { $registers->{$register} = $string; print "Yanked into $register: ", $registers->{$register} if DEBUG; + if ($register eq '"') { + $registers->{0} = $string; + print "Yanked into 0: ", $registers->{0} if DEBUG; + } } # Always move to the lower position. -- cgit v1.2.3 From 76b1897c629061ae5438da67fa6ad87682427726 Mon Sep 17 00:00:00 2001 From: Simon Ruderich Date: Fri, 8 Oct 2010 01:38:50 +0200 Subject: vim_mode: Use Vim-like char representation. --- vim-mode/vim_mode.pl | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) (limited to 'vim-mode/vim_mode.pl') diff --git a/vim-mode/vim_mode.pl b/vim-mode/vim_mode.pl index 52424ce..a64df1e 100644 --- a/vim-mode/vim_mode.pl +++ b/vim-mode/vim_mode.pl @@ -224,7 +224,7 @@ my $commands # arrow like movement h => { char => 'h', func => \&cmd_h, type => C_NORMAL }, l => { char => 'l', func => \&cmd_l, type => C_NORMAL }, - ' ' => { char => '', func => \&cmd_space, type => C_NORMAL }, + ' ' => { char => '', func => \&cmd_space, type => C_NORMAL }, # history movement j => { char => 'j', func => \&cmd_j, type => C_NORMAL }, k => { char => 'k', func => \&cmd_k, type => C_NORMAL }, @@ -286,28 +286,28 @@ my $commands D => { char => 'D', func => \&cmd_D, type => C_NORMAL, repeatable => 1 }, # scrolling - "\x04" => { char => '', func => \&cmd_ctrl_d, type => C_NORMAL, + "\x04" => { char => '', func => \&cmd_ctrl_d, type => C_NORMAL, repeatable => 1 }, # half screen down - "\x15" => { char => '', func => \&cmd_ctrl_u, type => C_NORMAL, + "\x15" => { char => '', func => \&cmd_ctrl_u, type => C_NORMAL, repeatable => 1 }, # half screen up - "\x06" => { char => '', func => \&cmd_ctrl_f, type => C_NORMAL, + "\x06" => { char => '', func => \&cmd_ctrl_f, type => C_NORMAL, repeatable => 1 }, # screen down - "\x02" => { char => '', func => \&cmd_ctrl_b, type => C_NORMAL, + "\x02" => { char => '', func => \&cmd_ctrl_b, type => C_NORMAL, repeatable => 1 }, # screen up # window switching - "\x17j" => { char => 'j', func => \&cmd_ctrl_wj, type => C_NORMAL }, - "\x17k" => { char => 'k', func => \&cmd_ctrl_wk, type => C_NORMAL }, - "\x1e" => { char => '', func => \&cmd_ctrl_6, type => C_NORMAL }, + "\x17j" => { char => 'j', func => \&cmd_ctrl_wj, type => C_NORMAL }, + "\x17k" => { char => 'k', func => \&cmd_ctrl_wk, type => C_NORMAL }, + "\x1e" => { char => '', func => \&cmd_ctrl_6, type => C_NORMAL }, # misc '~' => { char => '~', func => \&cmd_tilde, type => C_NORMAL, repeatable => 1 }, '"' => { char => '"', func => \&cmd_register, type => C_NEEDSKEY }, '.' => { char => '.', type => C_NORMAL, repeatable => 1 }, ':' => { char => ':', type => C_NORMAL }, - "\n" => { char => '', type => C_NORMAL }, # return + "\n" => { char => '', type => C_NORMAL }, # return # undo 'u' => { char => 'u', func => \&cmd_undo, type => C_NORMAL }, - "\x12" => { char => '', func => \&cmd_redo, type => C_NORMAL }, + "\x12" => { char => '', func => \&cmd_redo, type => C_NORMAL }, }; # All available commands in Ex-Mode. -- cgit v1.2.3 From 8da515880c62744571ac31fa4ccb9e24c0f63e2a Mon Sep 17 00:00:00 2001 From: Simon Ruderich Date: Fri, 8 Oct 2010 01:45:12 +0200 Subject: vim_mode: Fix error in $commands_ex hash. --- vim-mode/vim_mode.pl | 34 +++++++++++++++++----------------- 1 file changed, 17 insertions(+), 17 deletions(-) (limited to 'vim-mode/vim_mode.pl') diff --git a/vim-mode/vim_mode.pl b/vim-mode/vim_mode.pl index a64df1e..8e3a41d 100644 --- a/vim-mode/vim_mode.pl +++ b/vim-mode/vim_mode.pl @@ -313,23 +313,23 @@ my $commands # All available commands in Ex-Mode. my $commands_ex = { - s => { func => \&ex_substitute => type => C_EX }, - bnext => { func => \&ex_bnext => type => C_EX }, - bn => { func => \&ex_bnext => type => C_EX }, - bprev => { func => \&ex_bprev => type => C_EX }, - bp => { func => \&ex_bprev => type => C_EX }, - bdelete => { func => \&ex_bdelete => type => C_EX }, - bd => { func => \&ex_bdelete => type => C_EX }, - buffer => { func => \&ex_buffer => type => C_EX }, - b => { func => \&ex_buffer => type => C_EX }, - registers => { func => \&ex_registers => type => C_EX }, - reg => { func => \&ex_registers => type => C_EX }, - display => { func => \&ex_registers => type => C_EX }, - di => { func => \&ex_registers => type => C_EX }, - buffers => { func => \&ex_buffers => type => C_EX }, - ls => { func => \&ex_buffers => type => C_EX }, - undolist => { func => \&ex_undolist => type => C_EX }, - undol => { func => \&ex_undolist => type => C_EX }, + s => { func => \&ex_substitute, type => C_EX }, + bnext => { func => \&ex_bnext, type => C_EX }, + bn => { func => \&ex_bnext, type => C_EX }, + bprev => { func => \&ex_bprev, type => C_EX }, + bp => { func => \&ex_bprev, type => C_EX }, + bdelete => { func => \&ex_bdelete, type => C_EX }, + bd => { func => \&ex_bdelete, type => C_EX }, + buffer => { func => \&ex_buffer, type => C_EX }, + b => { func => \&ex_buffer, type => C_EX }, + registers => { func => \&ex_registers, type => C_EX }, + reg => { func => \&ex_registers, type => C_EX }, + display => { func => \&ex_registers, type => C_EX }, + di => { func => \&ex_registers, type => C_EX }, + buffers => { func => \&ex_buffers, type => C_EX }, + ls => { func => \&ex_buffers, type => C_EX }, + undolist => { func => \&ex_undolist, type => C_EX }, + undol => { func => \&ex_undolist, type => C_EX }, }; # MAPPINGS -- cgit v1.2.3 From bca1951421952978b11e4c4cf741a83dbd5cfc2a Mon Sep 17 00:00:00 2001 From: Simon Ruderich Date: Fri, 8 Oct 2010 01:50:17 +0200 Subject: vim_mode: Add char to $commands_ex hash. --- vim-mode/vim_mode.pl | 34 +++++++++++++++++----------------- 1 file changed, 17 insertions(+), 17 deletions(-) (limited to 'vim-mode/vim_mode.pl') diff --git a/vim-mode/vim_mode.pl b/vim-mode/vim_mode.pl index 8e3a41d..042fc34 100644 --- a/vim-mode/vim_mode.pl +++ b/vim-mode/vim_mode.pl @@ -313,23 +313,23 @@ my $commands # All available commands in Ex-Mode. my $commands_ex = { - s => { func => \&ex_substitute, type => C_EX }, - bnext => { func => \&ex_bnext, type => C_EX }, - bn => { func => \&ex_bnext, type => C_EX }, - bprev => { func => \&ex_bprev, type => C_EX }, - bp => { func => \&ex_bprev, type => C_EX }, - bdelete => { func => \&ex_bdelete, type => C_EX }, - bd => { func => \&ex_bdelete, type => C_EX }, - buffer => { func => \&ex_buffer, type => C_EX }, - b => { func => \&ex_buffer, type => C_EX }, - registers => { func => \&ex_registers, type => C_EX }, - reg => { func => \&ex_registers, type => C_EX }, - display => { func => \&ex_registers, type => C_EX }, - di => { func => \&ex_registers, type => C_EX }, - buffers => { func => \&ex_buffers, type => C_EX }, - ls => { func => \&ex_buffers, type => C_EX }, - undolist => { func => \&ex_undolist, type => C_EX }, - undol => { func => \&ex_undolist, type => C_EX }, + s => { char => 's', func => \&ex_substitute, type => C_EX }, + bnext => { char => 'bnext', func => \&ex_bnext, type => C_EX }, + bn => { char => 'bn', func => \&ex_bnext, type => C_EX }, + bprev => { char => 'bprev', func => \&ex_bprev, type => C_EX }, + bp => { char => 'bp', func => \&ex_bprev, type => C_EX }, + bdelete => { char => 'bdelete', func => \&ex_bdelete, type => C_EX }, + bd => { char => 'bd', func => \&ex_bdelete, type => C_EX }, + buffer => { char => 'buffer', func => \&ex_buffer, type => C_EX }, + b => { char => 'b', func => \&ex_buffer, type => C_EX }, + registers => { char => 'registers', func => \&ex_registers, type => C_EX }, + reg => { char => 'reg', func => \&ex_registers, type => C_EX }, + display => { char => 'display', func => \&ex_registers, type => C_EX }, + di => { char => 'di', func => \&ex_registers, type => C_EX }, + buffers => { char => 'buffer', func => \&ex_buffers, type => C_EX }, + ls => { char => 'ls', func => \&ex_buffers, type => C_EX }, + undolist => { char => 'undolist', func => \&ex_undolist, type => C_EX }, + undol => { char => 'undol', func => \&ex_undolist, type => C_EX }, }; # MAPPINGS -- cgit v1.2.3 From 8f84f6e57c31085dcf5cc5a987d44debc11860d5 Mon Sep 17 00:00:00 2001 From: Simon Ruderich Date: Fri, 8 Oct 2010 02:23:43 +0200 Subject: vim_mode: Add :map to allow custom mappings. --- vim-mode/vim_mode.pl | 123 ++++++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 121 insertions(+), 2 deletions(-) (limited to 'vim-mode/vim_mode.pl') diff --git a/vim-mode/vim_mode.pl b/vim-mode/vim_mode.pl index 042fc34..e941d07 100644 --- a/vim-mode/vim_mode.pl +++ b/vim-mode/vim_mode.pl @@ -69,6 +69,20 @@ # * Display windows: :ls :buffers # * Display registers: :reg[isters] :di[splay] {args} # * Display undolist: :undol[ist] (mostly used for debugging) +# * Mappings: :map - display custom mappings +# :map {lhs} {rhs} - add mapping +# +# Mappings: +# +# {lhs} is the key combination to be mapped, {rhs} the target. The <> notation +# is used (e.g. is Ctrl-F), case is ignored. Supported <> keys: +# -, , , , . Mapping ex-mode command is +# supported. Only default mappings can be used in {rhs}. +# Examples: +# :map gb :bnext # to map gb to call :bnext +# :map gB :bprev +# :map w W # to remap w to work like W +# # # The following irssi settings are available: # @@ -330,6 +344,7 @@ my $commands_ex ls => { char => 'ls', func => \&ex_buffers, type => C_EX }, undolist => { char => 'undolist', func => \&ex_undolist, type => C_EX }, undol => { char => 'undol', func => \&ex_undolist, type => C_EX }, + map => { char => 'map', func => \&ex_map, type => C_EX }, }; # MAPPINGS @@ -1526,9 +1541,113 @@ sub ex_undolist { _print_undo_buffer(); } +sub ex_map { + my ($arg_str) = @_; + + # :map {lhs} {rhs} + if ($arg_str =~ /^map (\S+) (\S+)$/) { + my $lhs = _parse_mapping($1); + my $rhs = $2; + + if (not defined $lhs) { + return _warn_ex('map', 'invalid {lhs}'); + } + + # Add new mapping. + my $command; + if (index($rhs, ':') == 0) { + $rhs = substr $rhs, 1; + if (not exists $commands_ex->{$rhs}) { + return _warn_ex('map', "$2 not found"); + } else { + $command = $commands_ex->{$rhs}; + } + } else { + $rhs = _parse_mapping($2); + if (not defined $rhs) { + return _warn_ex('map', 'invalid {rhs}'); + } elsif (not exists $commands->{$rhs}) { + return _warn_ex('map', "$2 not found"); + } else { + $command = $commands->{$rhs}; + } + } + add_map($lhs, $command); + + # :map + } elsif ($arg_str eq 'map') { + my $active_window = Irssi::active_win(); + foreach my $key (sort keys %$maps) { + my $map = $maps->{$key}; + my $cmd = $map->{cmd}; + if (defined $map->{char}) { + my $char = _parse_mapping_reverse($map->{char}); + next if $char eq $cmd->{char}; # skip default mappings + + my $cmdc = _parse_mapping_reverse($cmd->{char}); + if ($cmd->{type} == C_EX) { + $cmdc = ":$cmdc"; + } + $active_window->print(sprintf "%-15s %s", $char, $cmdc); + } + } + } else { + _warn_ex('map'); + } +} +sub _parse_mapping { + my ($string) = @_; + + $string =~ s/<([^>]+)>/_parse_mapping_bracket($1)/ge; + if (index($string, '') != -1) { + return undef; + } + return $string; +} +sub _parse_mapping_bracket { + my ($string) = @_; + + $string = lc $string; + + # , get corresponding CTRL char. + if ($string =~ /^c-([a-z])$/i) { + $string = chr(ord($1) - 96); + # and + } elsif ($string =~ /^c-[6^]$/i) { + $string = chr(30); + # + } elsif ($string eq 'space') { + $string = ' '; + # + } elsif ($string eq 'cr') { + $string = "\n"; + # Invalid char, return special string to recognize the error. + } else { + $string = ''; + } + return $string; +} +sub _parse_mapping_reverse { + my ($string) = @_; + + # Convert char to . + $string =~ s/ //g; + $string =~ s/\n//g; + # Convert Ctrl-X to . + $string =~ s/([\x01-\x1A])/""/ge; + # Convert Ctrl-6 and Ctrl-^ to . + $string =~ s/\x1E//g; + + return $string; +} + sub _warn_ex { - my ($command) = @_; - _warn("Error in ex-mode command $command"); + my ($command, $description) = @_; + my $message = "Error in ex-mode command $command"; + if (defined $description) { + $message .= ": $description"; + } + _warn($message); } sub _matching_windows { -- cgit v1.2.3