[1] [2] Google Speaker Series: introducing Open Source Developer Bram Moolenaar
Unfortunately, it uses an ugly, proprietary scripting language. If a good alternative to vim popped up that used, say, Ruby as its scripting language I would jump ship in an instant.
:help options
Vim has a number of internal variables and switches which can be set to achieve special effects.
:set...
You can get the current value of an option and store it in a variable:
let old_indentexpr = &indentexpr let &indentexpr = ''
:help expr-option
option *expr-option* *E112* *E113* ------ &option option value, local value if possible &g:option global option value &l:option local option value
Predefined Vim variables: *vim-variable* *v:var*
v:fname_new The name of the new version of the file. Only valid while
evaluating 'diffexpr'.
*v:fname_diff* *fname_diff-variable*
v:fname_diff The name of the diff (patch) file. Only valid while
evaluating 'patchexpr'.
*v:folddashes* *folddashes-variable*
v:folddashes Used for 'foldtext': dashes representing foldlevel of a closed
fold.
Read-only. |fold-foldtext|
...
*v:this_session* *this_session-variable*
v:this_session Full filename of the last loaded or saved session file. See
|:mksession|. It is allowed to set this variable. When no
session file has been saved, this variable is empty.
"this_session" also works, for backwards compatibility.
*v:throwpoint* *throwpoint-variable*
v:throwpoint The point where the exception most recently caught and not
finished was thrown. Not set when commands are typed. See
also |v:exception| and |throw-variables|.
Example: >
:try
: throw "oops"
:catch /.*/
: echo "Exception from" v:throwpoint
:endtry
< Output: "Exception from test.vim, line 2"
*v:version* *version-variable*
v:version Version number of Vim: Major version number times 100 plus
minor version number. Version 5.0 is 500. Version 5.1 (5.01)
is 501. Read-only. "version" also works, for backwards
compatibility.
Use |has()| to check if a certain patch was included, e.g.: >
if has("patch123")
< Note that patch numbers are specific to the version, thus both
version 5.0 and 5.1 may have a patch 123, but these are
completely different.
There are nine types of registers: *registers* *E354*
1. The unnamed register ""
2. 10 numbered registers "0 to "9
3. The small delete register "-
4. 26 named registers "a to "z or "A to "Z
5. four read-only registers ":, "., "% and "#
6. the expression register "=
7. The selection and drop registers "*, "+ and "~
8. The black hole register "_
9. Last search pattern register "/
4. Named registers "a to "z or "A to "Z *quote_alpha* *quotea*
Vim fills these registers only when you say so. Specify them as lowercase
letters to replace their previous contents or as uppercase letters to append
to their previous contents.
5. Read-only registers ":, "., "% and "#
These are '%', '#', ':' and '.'. You can use them only with the "p", "P",
and ":put" commands and with CTRL-R. {not in Vi}
*quote_.* *quote.* *E29*
". Contains the last inserted text (the same as what is inserted
with the insert mode commands CTRL-A and CTRL-@). Note: this
doesn't work with CTRL-R on the command-line. It works a bit
differently, like inserting the text instead of putting it
('textwidth' and other options affect what is inserted).
*quote_%* *quote%*
"% Contains the name of the current file.
*quote_#* *quote#*
"# Contains the name of the alternate file.
*quote_:* *quote:* *E30*
": Contains the most recent executed command-line. Example: Use
"@:" to repeat the previous command-line command.
The command-line is only stored in this register when at least
one character of it was typed. Thus it remains unchanged if
the command was completely from a mapping.
{not available when compiled without the |+cmdline_hist|
feature}
...
8. Black hole register "_ *quote_*
When writing to this register, nothing happens. This can be used to delete
text without affecting the normal registers. When reading from this register,
nothing is returned. {not in Vi}
9. Last search pattern register "/ *quote_/* *quote/*
Contains the most recent search-pattern. This is used for "n" and 'hlsearch'.
It is writable with ":let", you can change it to have 'hlsearch' highlight
other matches without actually searching. You can't yank or delete into this
register. {not in Vi}
*@/*
You can write to a register with a ":let" command |:let-@|. Example: >
:let @/ = "the"
register *expr-register*
--------
@r contents of register 'r'
The result is the contents of the named register, as a single string.
Newlines are inserted where required. To get the contents of the unnamed
register use @" or @@. The '=' register can not be used here. See
|registers| for an explanation of the available registers.
:let @{reg-name} = {expr1} *:let-register* *:let-@*
Write the result of the expression {expr1} in register
{reg-name}. {reg-name} must be a single letter, and
must be the name of a writable register (see
|registers|). "@@" can be used for the unnamed
register, "@/" for the search pattern.
If the result of {expr1} ends in a <CR> or <NL>, the
register will be linewise, otherwise it will be set to
characterwise.
This can be used to clear the last search pattern: >
:let @/ = ""
< This is different from searching for an empty string,
that would match everywhere.
fnamemodify
:echo fnamemodify("main.c", ":p:h")
http://www.vim.org/scripts/index.php
http://www.vim.org/scripts/script.php?script_id=95 winmanager - A windows style IDE for Vim 6.0 : vim online
http://www.vim.org/scripts/script.php?script_id=273 taglist.vim - Source code browser (supports C/C++, java, perl, python, tcl, sql, php, etc) : vim online
http://www.geocities.com/yegappan/taglist/ Vim Taglist plugin
This is for general usage tips (not script-writing tips).
http://vim.sourceforge.net/tips/tip.php?tip_id=305 Tip #305 - Best of VIM Tips (VIM's best Features) : vim online [To do: {{{1}}}]
:history : list of all your commands :reg
Go to beginning of word and type:
g~e
gg : Beginning
G : End
<C-O> : retrace your movements in file (old)
<C-I> : retrace your movements in file (new)
:ju(mps)
:help jump-motions
( [count] sentences backward. |exclusive| motion.
) [count] sentences forward. |exclusive| motion.
{ [count] paragraphs backward. |exclusive| motion.
} [count] paragraphs forward. |exclusive| motion.
------------------------------------------------------------------------------
# Markers
`< , `> -- jump to beginning/end of (visual) selection
'. : jump to last modification line (SUPER)
`. : jump to exact spot in last modification line
(changing the viewpoint/interacting with the "scroll bars")
'$' indicates EOL
'^I' indicates tabspace
To visualize non-printing control characters hidden in a file, do
':set list'
':set nolist' #toggles back to normal mode
':set invlist' #toggles
This is a series of commands that can only be used while in Visual mode or
after an operator. The commands that start with "a" select "a"n object
including white space, the commands starting with "i" select an "inner" object
without white space, or just the white space. Thus the "inner" commands
always select less text than the "a" commands.
These commands are {not in Vi}.
These commands are not available when the |+textobjects| feature has been
disabled at compile time.
aw "a word", select [count] words (see |word|).
Leading or trailing white space is included, but not
counted.
iw "inner word", select [count] words (see |word|).
aW "a WORD", select [count] WORDs (see |WORD|).
Leading or trailing white space is included, but not
counted.
iW "inner WORD", select [count] WORDs (see |WORD|).
as "a sentence", select [count] sentences
is "inner sentence", select [count] sentences (see
|sentence|).
When used in Visual mode it is made characterwise.
*v_ap* *ap*
ap "a paragraph", select [count] paragraphs (see
|paragraph|).
Exception: a blank line (only containing white space)
is also a paragraph boundary.
When used in Visual mode it is made linewise.
*v_ip* *ip*
ip "inner paragraph", select [count] paragraphs (see
|paragraph|).
Exception: a blank line (only containing white space)
is also a paragraph boundary.
When used in Visual mode it is made linewise.
a] *v_a]* *v_a[* *a]* *a[*
a[ "a [] block", select [count] '[' ']' blocks. This
goes backwards to the [count] unclosed '[', and finds
the matching ']'. The enclosed text is selected,
including the '[' and ']'.
When used in Visual mode it is made characterwise.
a) *v_a)* *a)* *a(*
a( *v_ab* *v_a(* *ab*
ab "a block", select [count] blocks, from "[count] [(" to
the matching ')', including the '(' and ')' (see
|[(|). Does not include white space outside of the
parenthesis.
...
http://vim.sourceforge.net/scripts/script.php?script_id=453 HTML.zip - HTML/XHTML editing macros and menus. (haven't tried)
surround.vim pluginPrerequisite: Understand text-objects!
http://vim.sourceforge.net/scripts/script.php?script_id=1697
Old text Command New text ~
"Hello *world!" ds" Hello world!
[123+4*56]/2 cs]) (123+456)/2
"Look ma, I'm *HTML!" cs"<q> <q>Look ma, I'm HTML!</q>
if *x>3 { ysW( if ( x>3 ) {
my $str = *whee!; vlllls' my $str = 'whee!';
Delete surroundings is *ds*. The next character given determines the target
to delete. The exact nature of the target are explained in
|surround-targets| but essentially it is the last character of a
|text-object|. This mapping deletes the difference between the "inner"
object and "an" object. This is easiest to understand with some examples:
Old text Command New text ~
"Hello *world!" ds" Hello world!
(123+4*56)/2 ds) 123+456/2
<div>Yo!*</div> dst Yo!
Change surroundings is *cs*. It takes two arguments, a target like with
|ds|, and a replacement. Details about the second argument can be found
below in |surround-replacements|. Once again, examples are in order.
Old text Command New text ~
"Hello *world!" cs"' 'Hello world!'
"Hello *world!" cs"<q> <q>Hello world!</q>
(123+4*56)/2 cs)] [123+456]/2
(123+4*56)/2 cs)[ [ 123+456 ]/2
<div>Yo!*</div> cst<p> <p>Yo!</p>
(A t is a pair of HTML or XML tags. See |tag-blocks| for details. Remember
that you can specify a numerical argument if you want to get to a tag other
than the innermost one.)
*ys* takes an valid Vim motion or text object as the first object, and wraps
it using the second argument as with |cs|. (Unfortunately there's no good
mnemonic for "ys").
Old text Command New text ~
Hello w*orld! ysiw) Hello (world)!
As a special case, *yss* operates on the current line, ignoring leading
whitespace.
Old text Command New text ~
Hello w*orld! yssB {Hello world!}
There is also *yS* and *ySS* which indent the surrounded text and place it
on a line of its own.
In visual mode, a simple "s" with an argument wraps the selection. This is
referred to as the *vs* mapping, although ordinarily there will be
additional keystrokes between the v and s. In linewise visual mode, the
surroundings are placed on separate lines. In blockwise visual mode, each
line is surrounded.
viss" : Surround current sentence in "..."
vips) : Surround current paragraph with (...) (delimiters on separate lines)
vipS) : Surround current paragraph with (...) (delimiters on separate lines) and indent the whole paragraph
An "S" in visual mode (*vS*) behaves similarly but always places the
surroundings on separate lines. Additionally, the surrounded text is
indented. In blockwise visual mode, using "S" instead of "s" instead skips
trailing whitespace.
You can even easily create your own custom replacements (without modifying the plugin script itself)!
:echo char2nr("p"))
112
" Customizations for surround plugin
" Ruby
" Use v or # to get a variable interpolation (inside of a string)}
" ysiw# Wrap the token under the cursor in #{}
" v...s# Wrap the selection in #{}
let g:surround_113 = "#{\r}" " v
let g:surround_35 = "#{\r}" " #
" Select text in an ERb file with visual mode and then press s- or s=
" Or yss- to do entire line.
let g:surround_45 = "<% \r %>" " -
let g:surround_61 = "<%= \r %>" " =
" PHP
" Use p to get php tags
autocmd FileType php let b:surround_112 = "<?php \r ?>" " p
http://vim.sourceforge.net/tips/tip.php?tip_id=1495 Tip #1495 - Wrap a Visual hilight in an arbitrary HTML tag : vim online
Tip 346http://vim.sourceforge.net/tips/tip.php?tip_id=346
" Tag Select/Wrapper
" These mappings and TagSelection function will allow you to place " an XML tag around either the current word, or the current selected " text
" Use nmap, not nnoremap, since we do want to use an existing mapping
nmap ,,, viw,,,
vnoremap ,,, <Esc>:call TagSelection()<CR>
function! TagSelection()
let tag = input("Tag name (include attributes)? ")
if strlen(tag) == 0
return
endif
" Save b register
let saveB = @b
" <C-R> seems to automatically reindent the line for some filetypes
" this will disable it until we have applied our changes
let saveIndent = &indentexpr
let curl = line(".")
let curc = col(".")
let &indentexpr = ''
" If the visual selection is over multiple lines, then place the
" data between the tags on newlines:
" <tag>
" data
" </tag>
let newline = ''
if getline("'>") != getline("'<")
let newline = "\n"
let curl = line("'>")
endif
" Strip off all but the first word in the tag for the end tag
let @b = newline . substitute( tag, '^[ \t"]*\(\<\S*\>\).*', '<\/\1>\e', "" )
let curc = curc + strlen(@b)
exec "normal `>a\<C-R>b"
let @b = substitute( tag, '^[ \t"]*\(\<.*\)', '<\1>\e', "" ) . newline
let curc = curc + strlen(@b)
exec "normal `<i\<C-R>b"
" Now format the area
exec "normal `<V'>j="
" Restore b register
let @b = saveB
let &indentexpr = saveIndent
call cursor(curl, curc)
endfunction
^M and ^[Press Ctrl-V to get the ^ character, and then (while still holding Ctrl) press Ctrl-whatever.
If you have a buffer with color codes in it like this:
^[[1m^[[32ms^[[0m^[[0m^[[1m^[[
, then you could remove those characters with something like this %s/Ctrl-V Ctrl-[[\d*m//g.
(Alias: Substitution) [Regular expressions / Applications of (category)]
For more help, check the documentation:
:help pattern-overview
From the vim documentation (change.txt.gz or :help substitute)):
When the {string} starts with "\=" it is evaluated as an expression, see
|sub-replace-expression|. Otherwise these characters in {string} have a
special meaning:
magic nomagic action ~
& \& replaced with the whole matched pattern *s/\&*
\& & replaced with &
\0 replaced with the whole matched pattern *\0* *s/\0*
\1 replaced with the matched pattern in the first
pair of () *s/\1*
\2 replaced with the matched pattern in the first
pair of () *s/\2*
.. .. *s/\3*
\9 replaced with the matched pattern in the ninth
pair of () *s/\9*
~ \~ replaced with the {string} of the previous
substitute *s~*
\~ ~ replaced with ~ *s/\~*
\u next character made uppercase *s/\u*
\U following characters made uppercase, until \E *s/\U*
\l next character made lowercase *s/\l*
\L following characters made lowercase, until \E *s/\L*
\e end of \u, \U, \l and \L (NOTE: not <Esc>!) *s/\e*
\E end of \u, \U, \l and \L *s/\E*
<CR> split line in two at this point
(Type the <CR> as CTRL-V <Enter>) *s<CR>*
\r idem *s/\r*
\<CR> insert a carriage-return (CTRL-M)
(Type the <CR> as CTRL-V <Enter>) *s/\<CR>*
\n insert a <NL> (<NUL> in the file)
(does NOT break the line) *s/\n*
\b insert a <BS> *s/\b*
\t insert a <Tab> *s/\t*
\\ insert a single backslash *s/\\*
\x where x is any character not mentioned above:
Reserved for future expansion
^
:%s/^Heading/==Heading/g
[^^]
Find and replace all : characters, except the ones that occur at the beginning of the line
:%s/[^^]://g
.\{-} is the non-greedy version of .*. So simply replace .* with .\{-}.
Example: Trying to match words starting with "e" and ending in "t", like "element":
/e.*t is greedy and matches all of this:
an E element, only child of its parent/e.\{-}t is non-greedy and generates two, shorter matches in this example:
an E element, only child of its parentReference:
Overview of multi items. */multi* *E61* *E62*
More explanation and examples below, follow the links. *E64*
multi ~
'magic' 'nomagic' matches of the preceding atom ~
|/star| * \* 0 or more as many as possible
|/\+| \+ \+ 1 or more as many as possible (*)
|/\=| \= \= 0 or 1 as many as possible (*)
|/\?| \? \? 0 or 1 as many as possible (*)
|/\{| \{n,m} \{n,m} n to m as many as possible (*)
\{n} \{n} n exactly (*)
\{n,} \{n,} at least n as many as possible (*)
\{,m} \{,m} 0 to m as many as possible (*)
\{} \{} 0 or more as many as possible (same as *) (*)
|/\{-| \{-n,m} \{-n,m} n to m as few as possible (*)
\{-n} \{-n} n exactly (*)
\{-n,} \{-n,} at least n as few as possible (*)
\{-,m} \{-,m} 0 to m as few as possible (*)
\{-} \{-} 0 or more as few as possible (*)
It involves a bit of hackery, unfortunately. I'd like to be able to just press : , press Up to browse in my command history back to my previous search, and then edit the (plain old, read-only) search command to turn it into a substitution command.
Unfortunately, the searches are stored in a separate command history from other commands (so press /<Up> is different from :<Up>).
So this is my workaround:
:execute "%s/" . @/ . "/\"/g"
You can use /<Up> to preview and edit the last search pattern before you commit to using it. I use that to strip off the \< and \> from the search pattern that get added for me if I do a [keyword]/[tag] search (using * or #).
Why would I ever need this? How about when it shows some weird Unicode character on the screen that I can't even type. Maybe I can just select it with my mouse to copy and paste it, but that doesn't always work, like when the character is stored properly but not displayed properly. Also, in Windows gvim, how do you paste onto the command line? (I don't know if it's possible.)
Example:
?\<â▪▪input\> (3 characters instead of 1; squares in place of 2 of the real characters)?\<“input\> (so even if I could paste that back into the command buffer to create a substitute command, it probably wouldn't work properly...)So that's when I use it...
:%s/<[^>]*>//cg
:%s#<td>\(.*\)</td>#<td>\r \1\r </td>#cg
Let's say you started with this:
SELECT
year,
make,
model,
and you're goal is to prefix each column name with a table name, to turn it into this:
SELECT
vehicles.year,
vehicles.make,
vehicles.model,
You could match all word characters ([0-9A-Za-z_]) that are followed by commas and do a replacement on that match:
:%s/\(\w*\),/vehicles.\1/cg
Or, if you prefer to use whitespace as your matching basis, you can append your new text at the end of the whitesace at the beginning of the line, like this:
:%s/^\(\s\+\)/\1vehicles./cg
When to prefer one method over the other? Well, one advantage of the first method is that it only matches lines with a comma on them, so you might be able to get away with doing the command on the whole file (%).
The second method, on the other hand, will match every line that has whitespace at the beginning of the line, which could be most of the lines in the file! So with the second one, you might have to restrict the command to only operate on a range, like this (after first selecting the lines containing the column names):
:'<,'>s/^\(\s\+\)/\1vehicles./cg
:%s/:to => '\(.*\)', :from => '\(.*\)'/:from => '\2', :to => '\1'/cg
From:
transition :to => 'address', :from => 'in_progress'
to:
transition :from => 'in_progress', :to => 'address'
:%s/^[ 0-9]\+[0-9]\+ //g :%s/^[ 0-9]\+[0-9]\+\n/\r/cg
Will change something like this:
144 Rake::XForge::Release.new(MetaProject::Project::XForge::RubyForge.new(ProjectName)) do |release| 145 release.user_name = ENV['RUBYFORGE_USER'] 146 release.password = ENV['RUBYFORGE_PASSWORD'] 147 release.files = release_files.to_a 149 release.release_changes = '' 150 release.release_notes = '' 151 end 152 end
into this:
Rake::XForge::Release.new(MetaProject::Project::XForge::RubyForge.new(ProjectName)) do |release|
release.user_name = ENV['RUBYFORGE_USER']
release.password = ENV['RUBYFORGE_PASSWORD']
release.files = release_files.to_a
release.release_changes = ''
release.release_notes = ''
end
:'<,'>s#[^^]:#:#g # Match any ':' that's *not* at the beginning of the line (because those we legitimately *want* to be [indent] characters; replace with ":"
(These examples/solutions all assume we have copy and pasted from a rendered web page in Firefox and that the target wiki is MediaWiki)
How to turn this:
*
any element
E
an element of type E
into MediaWiki wiki text:
;* :any element ;E :an element of type E
Here's how:
Select region to change. :'<,'>s/^\(\S\)/;\1/g " Match all lines that start with a non-whitespace character, and prefix that character with ';' (definition item) :'<,'>s/^\s\+/:/g " Match every line that starts with 1 or more whitespace characters. Replace those characters with a ':' character (definition)
http://www.vim.org/scripts/script.php?script_id=861
Neat idea, but... I don't think it's what I want, as it makes you do all your editing through vim (?) and probably stores information in flat files rather than a DB.
http://bbs.archlinux.org/viewtopic.php?pid=133601
Type :set to see what encoding and fileencoding are set to...
You probably have added some Unicode characters that can't be converted to Latin1?
Anyway, setting :set fileencoding=utf8 and then trying to save again usually works for me.