Last updated 2009-07-25

TextMate Basics Tutorial

Welcome to the TextMate Basics Tutorial. After having setup your TextMate, this Tutorial will show you around the basic features of TextMate. This is a must for everyone who wants to use TextMate seriously.

This Tutorial starts rather unusually with an insight of TextMates Extensibility and Bundle System and also will show off the built-in editing features. I find this “Understanding TextMate” Section is essential for every user.

— Soryu

Notice: Part of this Tutorial is available in Japanese at fraction.jp. 有難う Yuanying!

Content

Understanding TextMate

When you edit a file, TextMate recognizes the file type (in most cases) and provides several specific commands to work with that file.

Let’s assume you are editing an HTML file. TextMate will recognize the following extensions as HTML : html , htm , shtml , xhtml , phtml , php , inc , tmpl , tpl . Furthermore, if your file starts with an HTML DOCTYPE declaration it will be recognized as well.

Based on that the file is syntax-highlighted according to the ‘HTML Language Grammar’ that is defined in the ‘HTML Bundle’.

Let’s take a look what those Bundles are about, shall we?

Bundles

Bundles are Containers for certain functionality, mostly Language-centered. Feel free to open the ‘Bundle Editor’ from within TextMate with ⌃⌥⌘B (Window → Show Bundle Editor) .

I have selected the first Command in the ‘HTML Bundle’. Don’t be scared right off by the funny program source in the text-field to the right.

All the items that are grouped under the “HTML” headline on the left are specific things to HTML . There are Commands that will transform characters or open a window with Documentation for an HTML Tag , Drag Commands that will let you Drag’n’Drop Files (will be inserted as Links) or Images into the HTML Source , Macros and Snippets (expandable, intelligent Text Blocks). Further down there is the ‘HTML Language Grammar’ (that defines how the Syntax is highlighted and provides Semantic info for Commands), several Preferences you can adapt to your needs and different kinds of Templates for various HTML / XHTML versions.

If you select the name of the Bundle you can rearrange how TextMate structures the menu of the Bundle. This menu can be called by selecting the Bundle from Bundles → [Bundle name] or by pressing ⌃⎋ [Control-Escape] (Gear menu in status bar) which opens the right bundle according to the context your caret (Text cursor) is in.

The gear menu gives you a lot of power and control right at your fingertips.

I hope, you are still with me. Let’s take a shallow look at the different things so you get a feeling of the power you have on your hands with these Bundles.

Commands

Commands are shell scripts; little computer programs that invoke other programs to do specific tasks. They are used to transform portions of your document, invoke Documentation, Run files (for programming languages), etc. And because they are usual shell scripts, they have all the power that Mac OSX gives us – Bash, Perl, Python, Ruby, PHP, AppleScript and all those little utilities that make up a UNIX-derivate – grep , wc , etc — You name it!

I can’t got much into detail w/o repeating everything in the manual: Learn more about commands in the official TextMate manual.

Snippets

Snippets are powerful and intelligent Text Blocks.

It can include code to run at the insertion time, variables (like selected text), tab stops/placeholders for missing information (which you can tab through after insertion), and perform transformations on the data which you enter in the placeholders.

— The Manual

Let’s see some quick examples.

Pure Text “Non-Breaking Space”. This is basically the simplest Snippet you can get. It is bound to ⌥⎵ [Option-Space] in HTML Documents. Try it! It just inserts those characters. Text with Placeholders (and default values) <meta name="${1:name}" content="${2:content}" /> “Meta”, Type meta and press ⇥ (Tabulator). This is a very basic Snippet. It will get inserted into your file almost as-is. Notice the ${1:name} and ${2:content} special sequences. Those are placeholders. When you invoke the snippet it will insert <meta name="name" content="content" /> into your file, with the name bit inside placeholder 1 selected. Now you can change that selection by overtyping it (you don’t need to) and press ⇥ (Tabulator) to get to the next Placeholder, which is the value of the content attribute. Type your text, press ⇥ again and you get out of the snippet and can go on editing your file. Does this sound complicated? Try it, it’s easy and you will love it instantly!

I think, this will get you started. Explore the other snippets in the Bundle to find some more examples. For more details like running shell code and using regular expression replacement within Snippets check out the Manual.

Macros

Macros are recorded Keystrokes or Command/Snippet invocations. They can be recorded and saved from the Bundles → Macros menu.

In the ‘HTML Bundle’ there is one Macro: “Forward Delete All Whitespace”. It executes a search with a regular expression from the current caret (Text cursor) position which selects all whitespace (Spaces, Tab-characters & New-Line-Characters) until the next non-whitespace character and deletes them. You can invoke it via ⌃⌥⌦ (Control-Option-Delete [Delete = fn-Backspace for Laptop users]).

The Manual has this section about Macros.

Languages

Languages (Language Grammars) are complicated nested rules of Regular Expressions. We can’t even scratch the surface in this Tutorial but you should know about the existence of Scopes.

Scopes are defined by Language Grammars and are considered “Markup for your Language Syntax” – or the context. There is a strong analogy to CSS selectors. Let’s say we have an HTML file. Everywhere in this file we have a scope of text.html . An HTML Tag like <p> will have the scope of meta.tag. ny .html and for the name “p” it has entity.name.tag.html . Those scopes nest and override each other. Why am I bothering you about such details you might say? Those scopes are everywhere. They are the base of the Theming/Syntax Highlighting system. And they define where certain Commands, Snippets and Macros are available (you probably saw the ‘Scope Selector’ text-field way at the bottom of the ‘Bundle Editor’). E.g. you can set a command to only work within an HTML file by setting its scope to text.html .

The Manual says this about Language Grammars and there is the explanation about Scopes as a Blog Entry and the Manual Chapter about Scopes.

Preference Items

Preference Items store several, well, Preferences. Most notable are:

“smartTypingPairs” – They define pairs of characters so that the second character gets automatically inserted when you type the first character. Try it with " (double quote) for example. And try it again while you have some text selected. This saves you time and lets you not forget to insert the closing character of (e.g.) a string.

(double quote) for example. And try it again while you have some text selected. This saves you time and lets you not forget to insert the closing character of (e.g.) a string. “shellVariables” – This lets you define Shell Variables to be available for Commands in certain contexts. This is e.g. used for the “Comment Line / Selection” Command. (More on that later.)

As always, the Manual provides a chapter on Preference Items for further reading.

Templates

Explaining how Templates work and how they are created would be too much for this little Tutorial. To give you the basic idea:

A template consists of a (shell) command which generates the actual new file and generally the template file from which the new file will be generated.

— The Manual

The most important points about templates: You can create a new file from a template. Choose e.g. File → New From Template → HTML → HTML — 4.01 Strict and you will be greeted by a new document with a basic HTML skeleton. You can edit that part via the Bundle Editor when you expand the respective template and edit the index.html entry.

Special Bundles

CAUTION: The “Text” and “Source” Bundles define the basis for most other Bundles. You should not deactivate them!

Conclusion so far

I know this must have been a rough ride until now – but you will thank me at some point for the insight you have gained about the Bundles I think. TextMate is 1000% adaptable and extensible – yes, this number is right. Without those bundles that are mostly written by Users like you and me TextMate would not have 1/10th of its power.

And now for the fun part where we will use all this power.

Harnessing the power

The most vital shortcut in TextMate is ⌃⌘T (Bundles → Select Bundle Item…) . It will show any Command/Snippet/Macro available in the current scope and lets you filter the list.

If you ever wonder where a Command or Snippet was or if one exists for a given purpose, invoke the Select Bundle Item action. Click on the magnifier glass symbol and choose Key equivalent and you can even search for shortcuts!

Some examples (Input → Output):

“remove space” → “Converting / Stripping → Remove Trailing Spaces in Document/Selection — Text”

“space tab” → “Convert Spaces to Tabs (Estimating Indent) — Source ⌃⇧⌘T ”

” “html doc” → “Create HTL from Document/Selection — TextMate”

Insider-Tip: Write in ALL CAPS to have the limitation to the current scope switched off. You can search for any item in any bundle that way.

— Soryu

Editing Text

(Please see the TextMate manual about the conventions used for keyboard shortcuts.)

Beside the standard navigation keys there are some handy shortcuts (most of which are working throughout Cocoa/OSX applications and are common to people coming from e.g. emacs).

Caret movement

⌃F , ⌃B Character forward/back

⌃A , ⌃E Line beginning/end

⌃P , ⌃N Line up/down

?? , ⌃V Page up /down

⌘J (Edit → Find → Jump to Selection) Center selection on screen

⌃L Center line with caret on screen

⇧⌘J (Navigation → Go to Middle Visible Line) Go to Middle Visible Line, moves caret

You can also move the window w/o moving the caret. This can be achieved with ⌃⌥⌘←→↑↓ and is a handy way to just move the visible editing area.

Selections

⌃W (Edit → Select → Word) Select current Word

⇧⌘L (Edit → Select → Line) Select current Line

⇧⌘B (Edit → Select → Enclosing Brackets) Select enclosing Smart Typing Pair (see Preference Items). This can be Braces, Brackets, Curly Braces, “<”, “>”, Quotation Marks, etc.

⌃⌘←→ (Text → Move Selection → Column Left/Right) Moves the current Selection character-wise

⌃⌘↑↓ (Text → Move Selection → Line Up/Down) Moves the current Selection line-wise.

⌥⌘A (Text → Edit Each Line in Selection) lets you insert text at the end of each line in the current selection.

⌥F2 will bring up the Context Menu (like right-clicking) so you can easily correct the spelling of the current word or use conversion commands on a selection.

Column Selection

Pressing the ⌥ Key with a selection spanning multiple lines will switch to Column Selection mode. This let’s you edit the text in columns instead of lines which will come in handy in several places.

There is a nice Screencast which demonstrates this feature in conjunction with the Math Bundle and how you can work with it. The Manual has a small section about Column Selections, but please take a look at the Screencast to see what you can really do.

Indents

When using the tab key at the beginning of a line, TextMate will insert as many tabs as estimated correct for that line. If the line already has text, the caret will move to the front of this text.

If the line already has the correct indent (or above) a single tab will be inserted.

— The Manual

If in ‘Soft Tabs Mode’ this will of course insert the specified number of Spaces.

To manually change the indent of a line you can use ⌘[ (Text → Shift Left) and ⌘] (Text → Shift Right) ; also ⌥⇥ and ⌥⇤ (where ⇤ is achieved using ⇧⇥ ).

⇧⌘[ (Text → Shift Indent Line/Selection) will automatically indent the current line/selection.

Pasting will also automatically indent the pasted text/code. To disable this either use ⌃⌘V (Edit → Paste Without Reindent) temporarily switch it off globally in the Preferences.

Copy/Paste

In addition to the standard Copy/Cut/Paste shortcuts.

⇧⌘V (Edit → Paste Previous) pastes the previously copied item Using this more than once will subsequently insert older items form the Paste History and make them available for the standard ‘Paste’ command as well.

An example: Copy “1” Copy “2” Copy “3” Paste → “3” Paste Previous → “2” Paste Previous → “1” Paste → “1”. ⌥⌘V (Edit → Paste Next) works the other way and pastes the next item in the paste history

⌃⌥⌘V (Edit → Paste from History) brings up a popup menu containing all things copied or cut in this editing session. Once you select an item from this list, the normal “Paste” operation will keep inserting this item until you Copy or Cut something again.

⌃D Forward delete character/selection

⌃K , ⌃Y Kill & Yank Similar to “Cut” and “Paste”, things killed can be yanked. This uses a different buffer than standard Copy/Paste but “Cut” will overwrite this buffer, too. (This is strange OSX default behavior.)

⌃⇧K (Text Bundle → Delete Line) deletes the current line

⌃⇧D (Text Bundle → Duplicate Line) duplicates the current selection or line With a selection, TextMate will duplicate it and insert it after the selected area leaving the duplicated text selected, so you can go on duplicating it again. Without a selection TextMate will duplicate the current line and insert in below, placing the caret on the new line.



Word Completion

⎋ (Edit → Completion → Next Completion)

TextMate has a simple yet effective completion function on ⎋ (escape). It will complete the current word based on matches in the current document. If there are multiple matches, you can cycle through these by pressing ⎋ continuously. It is also possible to cycle backwards using ⇧⎋ .

— The Manual

Find & Replace

There are a lot of keyboard shortcuts for Find and Replace functionality. The Edit → Find Menu tells you about them:

The most notable two are: ⌘E which replaces the search string with the current selection and ⇧⌘E which replaces the replacement string with the current selection (or with nothing if nothing is selected). Using these two shortcuts and a subsequent Replace or Find shortcut you don’t even have to invoke the Find dialog at all.

Incremental Search

Another rather hidden feature is the incremental search. ⌃S or ⌃⇧S incrementally searches forward/backward as you type (the status bar will turn into an input field in that case).

Transposing and Conversions

⌃T (Text → Convert → Transpose) lets you transpose things. Without a selection both characters around the caret will be swapped. With a selection on one line, all characters within the selection will be reversed. Invoking the command on a selection spanning multiple lines will reverse the order of all the lines.

⌃G (Text → Convert → To Opposite Case) with no selection will toggle the case of the character next to the caret and advance the caret. with a selection it will toggle the case of all the characters in the selection (and leave the selection in place).

⌃U (Text → Convert → To Uppercase) will toggle the case of the current word or the current selection to upper case, ⌃⇧U (Text → Convert → To Lowercase) will do the same things for lower case.

⌃⌥U (Text → Convert → To Titlecase) will switch the case of the line or selection to title case. This is intelligent to exclude common short words and is intended to be used on a line containing a title.

Tabs and Spaces

From the Text → Convert Menu (or with a selection from the Context Menu ) you can choose to convert Tabulator characters to Spaces and vice versa. The ⌥⌘I (View → Show Invisibles) Menu item can help you figure out what convention the current file uses and the Tab Menu in the Status line will let you define how TextMate will insert new Tabulator characters you type.

Formatting

TextMate can help you format your text or source in several ways. The ⌥⌘W (View → Soft Wrap) and View → Wrap Column items were discussed in the Setup Tutorial already.

⌃Q (Text → Reformat Paragraph ) will reflow the current paragraph according to the Wrap settings. ⌃⌥Q (Text → Unwrap Paragraph) will do the opposite and reflow the paragraph on a single line.

⌃J (Text → Reformat and Justify ) will do the same as Reformat Paragraph and distribute whitespace between words so that the text is justified. This can be used for quotations, etc.

While this is mainly used for text, there are some bundles that override this shortcut to provide formatting for different things. See this Screencast about how to format comments for C-like languages.

Special Edit Modes

Freehand Editing ⌥⌘E (Edit → Mode → Freehanded Editing) Allows the caret to move past end of line and inside tab characters.

It is also possible to place the caret unrestricted by line endings (and tabs) by holding down ⌥ while placing the caret with the mouse.

— The Manual

Overwrite Mode ⌥⌘O (Edit → Mode → Overwrite Mode) This lets you type over existing text.

Running Shell Commands

⌃R (Execute Line/Selection Inserting Result) will run the the current selection/line as a shell command. Use the ⌥ Modifier to replace the command. Say you want to insert the a calendar: Type cal , press ⌃W to select it and press ⌃R to run the selection: April 2006 S M Tu W Th F S 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 Of course, you still need to know about the shell commands, but this is a very handy way to do certain things without bringing you out of your workflow.

⌥⌘R (Text → Filter through Command…) pops up a dialog where you can enter a shell command. That shell command will ba able to read the Text (Selection or the whole Document) as input from stdin and you have several options to show the output of the shell command. Use this to run shell commands on your selected text. Suppose you have some lines like: Miller, Paul Ashcroft, Rick Clint, Susi Wells, Zac Select them, press ⌥⌘R , type sort and choose “Selection” for ‘Input’ and “Replace Selection” for ‘Output’. The result will be: Ashcroft, Rick Clint, Susi Miller, Paul Wells, Zac Basically the same as using F5 (Text Bundle → “Sort Lines in Document / Selection”) does. Or use cat -n as command in the Dialog and it will produce this: 1 Miller, Paul 2 Ashcroft, Rick 3 Clint, Susi 4 Wells, Zac …which is similar to using Text Bundle → “Add Line Numbers to Document / Selection” .

Basically this is what Commands do, as discussed earlier, just ad hoc.

Common Bundles

Triggering Commands/Snippets/etc. form Bundles can be achieved with the following methods:

“Bundles” Menu Groups by Macros, Snippets and Commands and Bundles

Gear Menu in the status bar ( ⌃⎋ ) Groups by Bundles, Pre-selects the Bundle with the current Language Grammar (defined by the current scope)

) Learning Tab Triggers/Keyboard Shortcuts The Scope system will restrict the available shortcuts to relevant ones As you might already have seen, when there are multiple Items with the same Keyboard Shortcut/Tab Trigger, you will get a menu with those Items. You can then execute them by pressing the respective number to their right or typing their first letter (if this is unambiguous).



Common Bundle Shortcuts

⌘B Build used in programming/markup languages to build/compile/convert the current Project/File Java (“Build with Ant”), LaTeX (“Typeset and View”),…

⌘R used in programming languages to Run the current Project/File AppleScript (Run), HTML/CSS (“Refresh Running Browser(s)”), Perl (“Run”), Python (“Run with PyMate”), Ruby (“Run”), Unix Shell (“Run Script”),…

⌃H Look up current Work/Selection in the Documentation CSS (“Documentation for Property”), HTML (“Documentation for Tag”),…

⌃⇧H Conversions (for Markup languages), Tidy Code HTML (“HTML Tidy”), LaTeX (“Tidy”), Markdown (“Convert Document to HTML”),…

⌃⇧V Validation/Syntax Check CSS, HTML, Perl, PHP, Python, Ruby, XML,…

⌃⇧W Wrap Selection HTML (Wrap on Tag), Java (Wrap in try/catch ), LaTeX (Wrap in Command), etc…

⇧↩ Create a function/method body with previous word as name Obj-C, Ruby,…

⌃↩ Insert a “descriptive” return HTML ( <br/> ), Markdown (hard line break), Source (Escaped newline

),…

⌘↩ Move to end of line and insert a newline

⌘⌥↩ Move to end of line and insert potential end-of-line symbol (; in many sources, . in prose)

⇧⌘↩ As above, but also insert a newline

⌥⌘↩ Insert a new line above the current line

⌅ Insert a newline and start a new “item” (e.g. line comment, bullet point, etc.)

Text Bundle

The Text Bundle contains common functionality for all kinds of Text documents. This includes e.g. Markdown and HTML . Those Bundles won’t work as expected with out the Text Bundle, so don’t disable this one.

Interesting Bundle items here are:

“Add Line Numbers to Document / Selection”

“Current Date — YYYY-MM-DD (isoD)” A snippet with Tab Trigger isoD , will insert e.g. “2006-04-22”

“Join Line With Next” Pressing ⌃⇧J will remove all whitespace after the last character of the current line

“Lorem ipsum (lorem)” Inserts a paragraph of placeholder text

“Open Current URL” When the caret is inside a URL, TextMate will open it when pressing ⌅

“Remove Trailing Spaces in Document / Selection”

“Sort Lines” bound to F5



Source Bundle

The Source Bundle defines the base of all programming language bundles, so don’t disable it.

It contains several very useful command like:

“Comment Line / Selection” This Command is very powerful. It is adaptable via Preference Items for every language. You can define comment start/end characters, make comments single or multi-line, whether they should indent the source code, etc.

“Toggle Single / Double String quotes” As the name implies you can switch the quotes of a string, e.g. in Ruby: "code" , 'code' , Q{code} . Activated via ⌃⇧' .

, , . Activated via . “Align assignments” Activated via ⌘⌥] this Command will beautify your code from this: x = 1 abc = 2 long_var = "foo" to that: x = 1 abc = 2 long_var = "foo" (It also works for arrays and hashes).

Diff Bundle

The Diff Bundle contains several commands to compare files and make diffs/patches. All those functions have a common shortcut ⌃⇧⌘D and work without restriction in all kinds of files.

Math bundle

The Math Bundle provides some functionality to calculate numbers inline. Just type an equation like 3+4/5 on a new line (or select it) and press ⌃⇧C to bring up the menu containing the available Commands. Select “Evaluate Line” and it will insert the result of your expression.

Also see this Screencast that shows how to use the Math Bundle and Column selections.

Subversion Bundle

Subversion Support is provided via this Bundle. Just checkout a directory or file from a Subversion repository, open it in TextMate and you can use this Bundle. All Subversion Commands use the same shortcut ⌃⇧A .

TextMate Bundle

The TextMate Bundle provides some function to help you with TextMate in general.

“Show Keyboard Shortcuts” This will output a list of all Commands, Snippets and Macros for the Bundles in use (not for built-in functionality). There is even a helper on the net that will compile your own TextMate reference card.

“Show Scope” You learned about the ‘Scope System’ (remember the Languages section?). This command shows the current Scope of the caret as a tooltip. You can use this to specify a scope for your Commands or to adapt the “Fonts & Colors” (in the Preferences) and make you own theme.

“Search the TextMate Mailing List” Pretty Self-explaining: This will popup a window where you can enter a search term and show the results in an HTML window.

“Install ‘Edit in TextMate’…” See the Setup Tutorial. This is an extremely useful helper to edit text in any Cocoa Applications using TextMate (or FireFox).



TODO Bundle

The “Show TODO List” command will scan your current document or documents in your project for lines containing certain tags. You will be presented with a row of “Tabs” that are counting matches while the search is going on. Once the search finishes a list for each of the tags and their context is shown. Each entry can be clicked to jump to that line in that file.

— ‘Help’ Command from the TODO Bundle

Navigation

Bookmarks

Use Bookmarks to mark places in your document. ⌥⌘B (View → Gutter → Bookmarks) will show them in the gutter (the gray panel to the left of the editable area, containing line numbers etc.) You can create a bookmark with ⌘F2 (Navigation → Add Bookmark) . This will put a star (★) in the bookmark column of the gutter for that line. You can then cycle through your bookmarks in that file with F2 (Navigation → Next Bookmark) and ⇧F2 (Navigation → Previous Bookmark) .

Text/Code Folding

When working in a language which has start/end markers for blocks, like { … }, do … end, … , and similar, TextMate can spot these blocks and will show up/down arrows in the gutter for the start/end marker. When these arrows are present, it is possible to fold the block into a single line either by using the mouse and clicking on the up/down arrow, or pressing the F1 key. This will make the arrow in the gutter point to the right, and indicate that the entire block got folded by placing an ellipsis marker at the end of the line. An example where the two sub-blocks of the constructor has been folded can be seen below.

—The Manual

So, F1 View → Fold Current Block and View → Toggle Foldings at Level will fold/unfold your code at the current block or a certain level. Imagine an HTML file that consists of a number of divs in the body. Just press ⌥⌘2 to fold them all and you can concentrate on other things or edit them one after the other.

Structure

For languages for which it is supported, the rightmost pop-up in the status bar shows the current “symbol” (often the function prototype or heading above the caret).

— The Manual