Saltar al contenido principal

Configuración Avanzada de Vim

Llegaste al nivel donde Vim se convierte en una herramienta verdaderamente personalizada y poderosa. En este capítulo aprenderás a configurar Vim para que se adapte perfectamente a tu workflow y necesidades específicas.

🛠️ Estructura de Configuración

Organización del .vimrc

" ~/.vimrc - Configuración principal

" ============================================================================
" PLUGINS
" ============================================================================
call plug#begin('~/.vim/plugged')
" Lista de plugins aquí
call plug#end()

" ============================================================================
" CONFIGURACIÓN GENERAL
" ============================================================================
" Configuraciones básicas

" ============================================================================
" INTERFACE Y APARIENCIA
" ============================================================================
" Temas, colores, statusline

" ============================================================================
" MAPEOS Y ATAJOS
" ============================================================================
" Keybindings personalizados

" ============================================================================
" AUTOCOMANDOS
" ============================================================================
" Automatizaciones y hooks

" ============================================================================
" FUNCIONES PERSONALIZADAS
" ============================================================================
" Scripts y funciones propias

Configuración modular

" En ~/.vimrc
runtime! config/*.vim

" Archivos separados:
" ~/.vim/config/plugins.vim
" ~/.vim/config/mappings.vim
" ~/.vim/config/autocmds.vim
" ~/.vim/config/functions.vim

⚙️ Configuraciones Esenciales Avanzadas

Comportamiento del editor

" Configuración avanzada del comportamiento
set hidden " Permitir buffers ocultos
set confirm " Confirmar antes de salir sin guardar
set autowrite " Auto-guardar antes de comandos
set autoread " Auto-recargar archivos modificados externamente
set updatetime=300 " Tiempo de actualización (para plugins)
set timeoutlen=500 " Tiempo para secuencias de teclas
set ttimeoutlen=10 " Tiempo para códigos de terminal

" Historial y undo
set history=1000 " Historial de comandos
set undolevels=1000 " Niveles de undo
set undofile " Undo persistente
set undodir=~/.vim/undo " Directorio para undo files

" Backup y swap
set backup " Habilitar backups
set backupdir=~/.vim/backup " Directorio para backups
set directory=~/.vim/swap " Directorio para swap files
set writebackup " Backup antes de escribir

Búsqueda y substitución avanzada

" Búsqueda inteligente
set ignorecase " Ignorar mayúsculas
set smartcase " Inteligente con mayúsculas
set incsearch " Búsqueda incremental
set hlsearch " Resaltar resultados
set wrapscan " Búsqueda circular
set gdefault " Global por defecto en substitute

" Expresiones regulares más potentes
set magic " Habilitar magic patterns
nnoremap / /\v " Very magic por defecto
vnoremap / /\v
cnoremap %s/ %smagic/
cnoremap \>s/ \>smagic/

Completado avanzado

" Configuración de completado
set completeopt=longest,menuone,preview
set complete=.,w,b,u,t,i,kspell
set pumheight=15 " Altura del menú popup
set shortmess+=c " No mostrar mensajes de completado

" Completado de archivos
set wildmenu " Menú de completado
set wildmode=longest:full,full
set wildignore+=*.pyc,*.o,*.obj,*.swp,*.class
set wildignore+=*/tmp/*,*/node_modules/*,*/build/*
set wildignore+=*.jpg,*.bmp,*.gif,*.png,*.jpeg

🎨 Interface y Apariencia Avanzada

Configuración de ventanas y splits

" Comportamiento de splits
set splitbelow " Nuevos splits horizontales abajo
set splitright " Nuevos splits verticales a la derecha
set equalalways " Igualar ventanas al dividir
set winminheight=0 " Altura mínima de ventana
set winminwidth=0 " Ancho mínimo de ventana

" Redimensionado automático
autocmd VimResized * wincmd =

Statusline personalizada

" Statusline avanzada sin plugins
set laststatus=2 " Siempre mostrar statusline

function! GitBranch()
return system("git rev-parse --abbrev-ref HEAD 2>/dev/null | tr -d '\n'")
endfunction

function! StatuslineGit()
let l:branchname = GitBranch()
return strlen(l:branchname) > 0 ? ' '.l:branchname.' ' : ''
endfunction

set statusline=
set statusline+=%#PmenuSel# " Color
set statusline+=%{StatuslineGit()} " Git branch
set statusline+=%#LineNr# " Color
set statusline+=\ %f " Nombre de archivo
set statusline+=%m " Modificado
set statusline+=%= " Cambiar a la derecha
set statusline+=%#CursorColumn# " Color
set statusline+=\ %y " Tipo de archivo
set statusline+=\ %{&fileencoding?&fileencoding:&encoding}
set statusline+=\ [%{&fileformat}\] " Formato
set statusline+=\ %p%% " Porcentaje
set statusline+=\ %l:%c " Línea:columna

Configuración de colores avanzada

" Configuración de colores
if exists('+termguicolors')
let &t_8f = "\<Esc>[38;2;%lu;%lu;%lum"
let &t_8b = "\<Esc>[48;2;%lu;%lu;%lum"
set termguicolors
endif

" Esquema de colores personalizado
function! MyColorScheme()
highlight Normal ctermbg=NONE guibg=NONE
highlight LineNr ctermfg=grey guifg=grey
highlight CursorLineNr ctermfg=yellow guifg=yellow
highlight Comment ctermfg=green guifg=#50A14F
highlight String ctermfg=cyan guifg=#50A14F
endfunction

autocmd ColorScheme * call MyColorScheme()

🔧 Funciones y Comandos Personalizados

Funciones útiles

" Función para limpiar espacios en blanco
function! CleanWhitespace()
let save_cursor = getpos(".")
let old_query = getreg('/')
silent! %s/\s\+$//e
call setpos('.', save_cursor)
call setreg('/', old_query)
endfunction
command! CleanWhitespace call CleanWhitespace()

" Función para toggle números relativos
function! NumberToggle()
if(&relativenumber == 1)
set norelativenumber
set number
else
set relativenumber
endif
endfunction
command! NumberToggle call NumberToggle()

" Función para crear directorio si no existe
function! s:MkNonExDir(file, buf)
if empty(getbufvar(a:buf, '&buftype')) && a:file!~#'\v^\w+\:\/'
let dir=fnamemodify(a:file, ':h')
if !isdirectory(dir)
call mkdir(dir, 'p')
endif
endif
endfunction
autocmd BufWritePre * :call s:MkNonExDir(expand('<afile>'), +expand('<abuf>'))

" Función para alternar quickfix
function! ToggleQuickFix()
if empty(filter(getwininfo(), 'v:val.quickfix'))
copen
else
cclose
endif
endfunction
command! ToggleQuickFix call ToggleQuickFix()

Comandos personalizados

" Comandos útiles
command! ReloadConfig source $MYVIMRC
command! EditConfig edit $MYVIMRC
command! -nargs=1 -complete=help Help help <args> | only

" Comando para buscar TODO/FIXME
command! Todo vimgrep /TODO\|FIXME\|XXX\|HACK/j **/*.* | copen

" Comando para ver diferencias
command! DiffOrig vert new | set bt=nofile | r ++edit # | 0d_
\ | diffthis | wincmd p | diffthis

" Comando para copiar ruta del archivo
command! CopyPath let @+ = expand('%:p')
command! CopyName let @+ = expand('%:t')

🎯 Mapeos Avanzados

Leader key y prefijos

" Configurar leader key
let mapleader = "\<Space>"
let maplocalleader = ","

" Mapeos con leader
nnoremap <Leader>w :w<CR>
nnoremap <Leader>q :q<CR>
nnoremap <Leader>x :x<CR>
nnoremap <Leader>e :e<Space>
nnoremap <Leader>v :vs<Space>
nnoremap <Leader>s :sp<Space>

" Navegación de buffers
nnoremap <Leader>b :buffers<CR>:buffer<Space>
nnoremap <Leader>n :bnext<CR>
nnoremap <Leader>p :bprevious<CR>
nnoremap <Leader>d :bdelete<CR>

" Utilidades
nnoremap <Leader>h :nohlsearch<CR>
nnoremap <Leader>r :ReloadConfig<CR>
nnoremap <Leader>c :EditConfig<CR>
nnoremap <Leader>t :Todo<CR>

Mapeos para productividad

" Movimiento mejorado
nnoremap j gj
nnoremap k gk
nnoremap gj j
nnoremap gk k

" Selección más intuitiva
vnoremap < <gv
vnoremap > >gv

" Navegación de ventanas con Ctrl
nnoremap <C-h> <C-w>h
nnoremap <C-j> <C-w>j
nnoremap <C-k> <C-w>k
nnoremap <C-l> <C-w>l

" Redimensionar ventanas
nnoremap <C-Left> :vertical resize -5<CR>
nnoremap <C-Right> :vertical resize +5<CR>
nnoremap <C-Up> :resize -5<CR>
nnoremap <C-Down> :resize +5<CR>

" Mover líneas
vnoremap J :m '>+1<CR>gv=gv
vnoremap K :m '<-2<CR>gv=gv
nnoremap <Leader>j :m .+1<CR>==
nnoremap <Leader>k :m .-2<CR>==

🔄 Autocomandos Avanzados

Eventos útiles

" Grupo de autocomandos para organización
augroup MyAutoCommands
autocmd!

" Volver a la última posición del cursor
autocmd BufReadPost * if line("'\"") > 1 && line("'\"") <= line("$") |
\ execute "normal! g`\"" | endif

" Auto-guardar al perder foco
autocmd FocusLost * :wa

" Mostrar números relativos solo en modo normal
autocmd InsertEnter * :set norelativenumber
autocmd InsertLeave * :set relativenumber

" Resaltar yanked text
autocmd TextYankPost * silent! lua vim.highlight.on_yank()

" Limpiar espacios en blanco al guardar
autocmd BufWritePre *.py,*.js,*.ts,*.vim :call CleanWhitespace()

" Configuración específica por tipo de archivo
autocmd FileType javascript setlocal ts=2 sw=2 expandtab
autocmd FileType python setlocal ts=4 sw=4 expandtab
autocmd FileType vim setlocal ts=2 sw=2 expandtab

augroup END

Eventos para desarrollo

augroup DevelopmentCommands
autocmd!

" Auto-reload vimrc
autocmd BufWritePost .vimrc source %

" Compilar automáticamente
autocmd BufWritePost *.py !python3 -m py_compile %
autocmd BufWritePost *.js !node -c %

" Ejecutar tests
autocmd BufWritePost *_test.py !python3 -m pytest %

augroup END

🚀 Optimización de Performance

Configuración para archivos grandes

" Optimizaciones para archivos grandes
set synmaxcol=200 " Límite de sintaxis por línea
set regexpengine=1 " Motor de regex más rápido
set lazyredraw " No redibujar durante macros

" Deshabilitar características para archivos grandes
autocmd BufReadPre * if getfsize(expand("%")) > 10000000 |
\ syntax off | setlocal noswapfile | endif

Carga lazy de plugins

" Ejemplo de carga condicional
if &compatible
set nocompatible
endif

" Solo cargar plugins si es necesario
if has('vim_starting')
set runtimepath+=~/.vim/plugged/vim-plug
endif

📝 Ejercicios Prácticos

Ejercicio 1: Configuración personalizada

  1. Crea tu propio esquema de mapeos con leader key
  2. Configura una statusline personalizada
  3. Implementa 3 funciones útiles para tu workflow

Ejercicio 2: Autocomandos

  1. Configura auto-guardado para tipos específicos de archivo
  2. Implementa auto-formateo al guardar
  3. Crea un autocomando para cargar templates por tipo de archivo

Ejercicio 3: Optimización

  1. Mide el tiempo de inicio de Vim con :profile
  2. Optimiza tu configuración eliminando plugins innecesarios
  3. Implementa carga condicional de características

🏆 Tips Pro

1. Debugging de configuración

" Verificar qué scripts se cargan
:scriptnames

" Profiling de performance
:profile start profile.log
:profile func *
:profile file *
" ... usar Vim ...
:profile pause
:qa!

2. Versionado de configuración

# Usar Git para tu configuración
cd ~
git init
git add .vimrc .vim/
git commit -m "Initial Vim config"

3. Configuración portable

" Detectar ambiente y adaptar configuración
if has('gui_running')
" Configuración para gVim
elseif has('nvim')
" Configuración para Neovim
else
" Configuración para Vim terminal
endif

4. Testing de configuración

" Función para testar mapeos
function! TestMappings()
redir @a
silent map
redir END
new
put a
endfunction

¡Una configuración bien estructurada y optimizada es la base de un workflow productivo en Vim!