tmux: Remap h, j, k, l to j, k, l, ; in copy-mode - tmux

I want to move in tmux copy mode with jkl; instead of hjkl.
How can I remap those key bindings?
I've tried:
unbind -T copy-mode-vi h;
unbind -T copy-mode-vi j;
unbind -T copy-mode-vi k;
unbind -T copy-mode-vi l;
bind -T copy-mode-vi j send-keys -X move-left;
bind -T copy-mode-vi k send-keys -X move-down;
bind -T copy-mode-vi l send-keys -X move-up;
bind -T copy-mode-vi \; send-keys -X move-right;
but it doesn't work. I suppose move-left, move-down, ... commands are not correct.

You are right about the move- commands being wrong, according to the tmux man page you want:
cursor-down
cursor-left
cursor-right
cursor-up

Related

tmux: Remap h, j, k, l to j, k, l, ; in choose-tree mode

Is it possible to remap hjkl keys in choose-tree mode?
I tried the following:
unbind -T choose-tree h;
unbind -T choose-tree j;
unbind -T choose-tree k;
unbind -T choose-tree l;
bind -T choose-tree j send-keys -X collapse-selected-item;
bind -T choose-tree k send-keys -X select-next-item;
bind -T choose-tree l send-keys -X select-previous-item;
bind -T choose-tree \; send-keys -X expand-selected-item;
But I got an error: table choose-tree doesn't exist.
I also tried replace choose-tree with choose-mode but it also didn't work.
Add this to your config file.
bind-key -T root j if -F "#{==:#{pane_mode},tree-mode}" "send h" "send j"
bind-key -T root k if -F "#{==:#{pane_mode},tree-mode}" "send j" "send k"
bind-key -T root l if -F "#{==:#{pane_mode},tree-mode}" "send k" "send l"
bind-key -T root \; if -F "#{==:#{pane_mode},tree-mode}" "send l" "send \;"
Reference: Is it possible to remap key bindings in choose-tree mode? : tmux

Tmux not recognizing Meta key mapping

I am using neovim and tmux (with tmuxinator) with the ultimate goal of getting https://github.com/christoomey/vim-tmux-navigator setup on my M1 Macbook with iTerm2 or Warp (https://www.warp.dev/)
I have mapped my left option key to be my meta key in my terminal. I would like to use <M-h/j/k/l> in order to navigate between neovim splits and tmux panes. Mapping my left option key to meta and using it with h/j/k/l works as expected in neovim (including neovim in tmux - i.e. i can navigate neovim splits and go from neovim to a tmux terminal pane). However, in a tmux terminal pane it either does nothing in iTerm2 or brings up alternate text (˙∆˚¬ for hjkl to be specific) in Warp.
Below are my configurations which were from https://github.com/christoomey/vim-tmux-navigator and i just updated them to use meta instead of ctrl:
init.vim
let g:tmux_navigator_no_mappings = 1
nnoremap <silent> <M-h> :TmuxNavigateLeft<cr>
nnoremap <silent> <M-j> :TmuxNavigateDown<cr>
nnoremap <silent> <M-k> :TmuxNavigateUp<cr>
nnoremap <silent> <M-l> :TmuxNavigateRight<cr>
nnoremap <silent> <M-\> :TmuxNavigatePrevious<cr>
.tmux.conf
unbind M-h
unbind M-j
unbind M-k
unbind M-l
is_vim="ps -o state= -o comm= -t '#{pane_tty}' \
| grep -iqE '^[^TXZ ]+ +(\\S+\\/)?g?(view|n?vim?x?)(diff)?$'"
bind-key -n 'M-h' if-shell "$is_vim" 'send-keys M-h' 'select-pane -L'
bind-key -n 'M-j' if-shell "$is_vim" 'send-keys M-j' 'select-pane -D'
bind-key -n 'M-k' if-shell "$is_vim" 'send-keys M-k' 'select-pane -U'
bind-key -n 'M-l' if-shell "$is_vim" 'send-keys M-l' 'select-pane -R'
tmux_version='$(tmux -V | sed -En "s/^tmux ([0-9]+(.[0-9]+)?).*/\1/p")'
if-shell -b '[ "$(echo "$tmux_version < 3.0" | bc)" = 1 ]' \
"bind-key -n 'M-\\' if-shell \"$is_vim\" 'send-keys M-\\' 'select-pane -l'"
if-shell -b '[ "$(echo "$tmux_version >= 3.0" | bc)" = 1 ]' \
"bind-key -n 'M-\\' if-shell \"$is_vim\" 'send-keys M-\\\\' 'select-pane -l'"
bind-key -T copy-mode-vi 'M-h' select-pane -L
bind-key -T copy-mode-vi 'M-j' select-pane -D
bind-key -T copy-mode-vi 'M-k' select-pane -U
bind-key -T copy-mode-vi 'M-l' select-pane -R
bind-key -T copy-mode-vi 'M-\' select-pane -l
How can i get this to work? I would be happy to get it working on either terminal.

Why doesn't incremental history search work in zsh?

I'm trying to get rid of Oh-my-zsh and currently my biggest challenge is getting incremental history search working. I've acked and grepped my way through the code and there's no clues in site. I get this error :
No such widget 'histrory-beginning-search-backward'
EDIT:
I've tried this with the absolute least possible code, it still doesn't work. here's the reduced test case:
# key bindings
bindkey -v
function zle-line-init zle-keymap-select {
RPS1="${${KEYMAP/vicmd/NORMAL}/(main|viins)/INSERT}"
RPS2=$RPS1
zle reset-prompt
}
zle -N zle-line-init
zle -N zle-keymap-select
bindkey -M vicmd '^R' histrory-beginning-search-backward
bindkey -M viins '^R' histrory-beginning-search-backward
Here's my config, taken from the zsh config wizzard, my current zshrc and oh-my-zsh:
autoload zkbd
# The following lines were added by compinstall
zstyle ':completion:*' completer _expand _complete _ignored _correct _approximate
zstyle ':completion:*' matcher-list 'm:{a-zA-Z}={A-Za-z}' 'r:|[._-]=* r:|=*' 'l:|=* r:|=*'zstyle ':completion:*' verbose true
zstyle :compinstall filename '/home/jonathan/.zshrc'
zstyle ':completion:*' list-colors ''
zstyle ':completion::complete:*' use-cache 1
zstyle ':completion::complete:*' cache-path $HOME/.cache/zsh
#load colorstuff
autoload -Uz compinit
autoload -U colors && colors
compinit
# End of lines added by compinstall
# Lines configured by zsh-newuser-install
HISTFILE=~/.histfile
HISTSIZE=1000
SAVEHIST=1000
setopt extendedglob
unsetopt beep nomatch notify
# End of lines configured by zsh-newuser-install
setopt completealiases
# Ignore boring stuff
zstyle ':completion:*:*:*:users' ignored-patterns \
adm amanda apache at avahi avahi-autoipd beaglidx bin cacti canna \
clamav daemon dbus distcache dnsmasq dovecot fax ftp games gdm \
gkrellmd gopher hacluster haldaemon halt hsqldb ident junkbust kdm \
ldap lp mail mailman mailnull man messagebus mldonkey mysql nagios \
named netdump news nfsnobody nobody nscd ntp nut nx obsrun openvpn \
operator pcap polkitd postfix postgres privoxy pulse pvm quagga radvd \
rpc rpcuser rpm rtkit scard shutdown squid sshd statd svn sync tftp \
usbmux uucp vcsa wwwrun xfs '_*'
zstyle ':completion:*:functions' ignored-patterns '_*'
# Completion dots
expand-or-complete-with-dots() {
echo -n "\e[31m......\e[0m"
zle expand-or-complete
zle redisplay
}
zle -N expand-or-complete-with-dots
bindkey "^I" expand-or-complete-with-dots
# Prompt stuff *truncated*
# key bindings
bindkey -v
function zle-line-init zle-keymap-select {
RPS1="${${KEYMAP/vicmd/NORMAL}/(main|viins)/INSERT}"
RPS2=$RPS1
zle reset-prompt
}
zle -N zle-line-init
zle -N zle-keymap-select
bindkey -M vicmd '^R' histrory-beginning-search-backward
bindkey -M viins '^R' histrory-beginning-search-backward
function run-again {
zle up-history
zle accept-line
}
zle -N run-again
bindkey -M viins '^W' run-again
bindkey -M vicmd '^W' run-again
bindkey -M viins ' ' magic-space # [Space] - do history expansion
bindkey '^[[1;5C' forward-word # [Ctrl-RightArrow] - move forward one word
bindkey '^[[1;5D' backward-word # [Ctrl-LeftArrow] - move backward one word
if [[ "${terminfo[kcbt]}" != "" ]]; then
bindkey -M viins "${terminfo[kcbt]}" reverse-menu-complete # [Shift-Tab] - move through the completion menu backwards
fi
dirstackfile="$HOME/.cache/zsh/dirs"
if [[ -f dirstackfile ]] && [[ $#dirstack -eq 0 ]]; then
dirstack=( ${(f)"$(< $dirstackfile)"} )
[[ -d $dirstack[1] ]] && builtin cd $dirstack[1]
fi
chpwd() {
print -l $PWD ${(u)dirstack} > $dirstackfile
}
dirstacksize=20
setopt autopushd pushdsilent pushdtohome
# remove duplicate entries
setopt pushdignoredups
#revert plus and minus operators.
setopt pushdminus
#PATH info truncated
What am I doing wrong?
Whoops... I had a typo, now I feel dumb. I had it as histrory, when it should be history..

XMLStarlet - Adding RSS feed items

Been using an example I found here (https://stackoverflow.com/a/14397390/3168446) and I just noticed it's not adding items correctly. The following example is actually adding items outside of the channel-tag. Anyone know the correct way to make this work?
feed.xml:
<?xml version="1.0" encoding="utf-8"?>
<rss xmlns:atom="http://www.w3.org/2005/Atom" version="2.0">
<channel>
<title>My RSS Feed</title>
<description>This is my RSS Feed</description>
</channel>
</rss>
shell script:
#!/bin/sh
TITLE="My RSS entry"
LINK="http://example.com/entry4711"
DATE="`date`"
DESC="Good news"
GUID="http://example.com/entry4711"
xmlstarlet ed -L -a "//channel" -t elem -n item -v "" \
-s "//item[1]" -t elem -n title -v "$TITLE" \
-s "//item[1]" -t elem -n link -v "$LINK" \
-s "//item[1]" -t elem -n pubDate -v "$DATE" \
-s "//item[1]" -t elem -n description -v "$DESC" \
-s "//item[1]" -t elem -n guid -v "$GUID" \
-d "//item[position()>10]" feed.xml ;
windows command line example:
xml ed -L -a "//channel" -t elem -n item -v "" -s "//item[1]" -t elem -n title -v "My RSS entry" -s "//item[1]" -t elem -n link -v "http://example.com/entry4711" -s "//item[1]" -t elem -n pubDate -v "Sat, 26 Jul 2014 01:14:30 +0200" -s "//item[1]" -t elem -n description -v "Good news" -s "//item[1]" -t elem -n guid -v "http://example.com/entry4711" -d "//item[position()>10]" feed.xml
output feed.xml:
<?xml version="1.0" encoding="utf-8"?>
<rss xmlns:atom="http://www.w3.org/2005/Atom" version="2.0">
<channel>
<title>My RSS Feed</title>
<description>This is my RSS Feed</description>
</channel>
<item>
<title>My RSS entry</title>
<link>http://example.com/entry4711</link>
<pubDate>Sat, 26 Jul 2014 01:14:30 +0200</pubDate>
<description>Good news</description>
<guid>http://example.com/entry4711</guid>
</item>
</rss>
As you see in the output the item is added outside of the channel-tag so the feed won't validate.
Wasn't actually that hard after a good night sleep.
The reason every item is added outside of the channel tag is because I used;
xml ed -L -a "//channel"
Solution is to use a tag in the feed-template that is not used within the items you're adding. I'm using the generator-tag.
Example feed.xml with added generator-tag:
<?xml version="1.0" encoding="utf-8"?>
<rss xmlns:atom="http://www.w3.org/2005/Atom" version="2.0">
<channel>
<title>My RSS Feed</title>
<description>This is my RSS Feed</description>
<link>http://example.com/entry4711</link>
<generator>your-rss-generator</generator>
</channel>
</rss>
Shell script where I replace //channel with //generator:
#!/bin/sh
TITLE="My RSS entry"
LINK="http://example.com/entry4711"
DATE="`date`"
DESC="Good news"
GUID="http://example.com/entry4711"
xmlstarlet ed -L -a "//generator" -t elem -n item -v "" \
-s "//item[1]" -t elem -n title -v "$TITLE" \
-s "//item[1]" -t elem -n link -v "$LINK" \
-s "//item[1]" -t elem -n pubDate -v "$DATE" \
-s "//item[1]" -t elem -n description -v "$DESC" \
-s "//item[1]" -t elem -n guid -v "$GUID" \
-d "//item[position()>10]" feed.xml ;
Windows command line where I replace //channel with //generator:
xml ed -L -a "//generator" -t elem -n item -v "" -s "//item[1]" -t elem -n title -v "My RSS entry" -s "//item[1]" -t elem -n link -v "http://example.com/entry4711" -s "//item[1]" -t elem -n pubDate -v "Sat, 26 Jul 2014 01:14:30 +0200" -s "//item[1]" -t elem -n description -v "Good news" -s "//item[1]" -t elem -n guid -v "http://example.com/entry4711" -d "//item[position()>10]" feed.xml
This will make every new item go within the channel-tag.

xmlstarlet to insert tags

I am using the command:
xmlstarlet ed --omit-decl --subnode "/boinc" --type elem -n app -v "" project_00.xml > project_01.xml
However, I would like to insert two more tags into that one:
<app>
<name>name</name>
<nikname>nikname</nikname>
</app>
In my project_00.xml, I already have others tag app and it is causing conflicts.
The problem with this command:
xmlstarlet ed --subnode "/boinc" --type elem -n app -v "" project_00.xml| xmlstarlet ed --subnode //app --type elem -n name -v "newApp"| xmlstarlet ed --subnode //app --type elem -n user_friendly_name -v "New.App" > project_01.xml
is that it created this.:
<app name="wilson">
<name>wilson</name>
<user_friendly_name>Mr.Wilson</user_friendly_name>
<name>newApp</name>
<user_friendly_name>New.App</user_friendly_name>
</app>
<app>
<name>newApp</name>
<user_friendly_name>New.App</user_friendly_name>
</app>
Does know the exactly command?
I tried this command but it replicated the to all app tags
xmlstarlet ed -s "/boinc" -t elem -n app -v "" -s "/boinc/app" -t elem -n name -v "name" -s "/boinc/app" -t elem -n user_friendly_name -v "New.App" project_00.xml > project_01.xml
Basically, you need an XPath expression to match the node you just inserted; since --subnode always puts new children in last place you can use /boinc/app[last()]:
xmlstarlet ed \
--subnode /boinc --type elem -n app -v '' \
--subnode '/boinc/app[last()]' --type elem -n name -v newApp \
--subnode '/boinc/app[last()]' --type elem -n user_friendly_name -v New.App \
project_00.xml > project_01.xml

Resources