All,
I recently purchased TextMate and I've been very impressed with it. It was one of the main reasons I just switched to a mac.
I've been wondering about the behavior of the Text | Move Selection | Line Up command. It works exactly as I'd expect when text is actually selected, but when you invoke the command with nothing selected, the behavior is a little bit odd.
When nothing is selected, invoking either "Line Up" or "Line Down" from the Text | Move Selection menu will move the current line up or down, which is exactly what I'd want it to do. The unexpected behavior is that the cursor doesn't remain on the moved line at the original offset; instead, the cursor ends up at the start of the line immediately below the moved line. This makes it difficult to move a given line more than one line up or down.
Could this behavior be changed? For example, in the following five lines of text, imagine the cursor is on the "@" character:
first line second line third @line fourth line fifth line
With nothing selected, I'd like to press control-command-up twice and end up like this:
third @line first line second line fourth line fifth line
with the cursor still in the same place on the "@" symbol. With the current implementation, pressing control-command-up twice first exchanges "second line" and "third line", then exchanges them back, leaving my cursor at the start of "third line":
first line second line @third line fourth line fifth line
I like the way that many features in TextMate operate on the selected text when a selection is active, but fall back to some natural unit of text for the given operation when nothing is selected. To me, the above-described line move operations seem to "line up" with this philosophy.
Thanks, Michael Henry
On 21/5/2006, at 13:40, Michael Henry wrote:
[...] I like the way that many features in TextMate operate on the selected text when a selection is active, but fall back to some natural unit of text for the given operation when nothing is selected. To me, the above-described line move operations seem to "line up" with this philosophy.
FYI the current behavior is not by design, but a side-effect of how the things are implemented internally in TM.
Changing the internals is a to-do item, it’s something which affects many things, so I am not just special-casing this one to get a quick fix, as special casing it has the trade-off of duplicated code, and many other things could just as well be picked to be special-cased, like the increase/decrease indent [1], which is not ideal either.
Allan Odgaard wrote:
On 21/5/2006, at 13:40, Michael Henry wrote:
[...] I like the way that many features in TextMate operate on the selected text when a selection is active, but fall back to some natural unit of text for the given operation when nothing is selected. To me, the above-described line move operations seem to "line up" with this philosophy.
FYI the current behavior is not by design, but a side-effect of how the things are implemented internally in TM.
Changing the internals is a to-do item, it’s something which affects many things, so I am not just special-casing this one to get a quick fix[...]
Thanks for the explanation. I'm happy to wait for the clean fix.
By the way, I had searched the requested features list to see if this behavior were mentioned, and I didn't see it. Is there somewhere I should have looked before posting? If I'd known it was on a TODO list I wouldn't have troubled the list with the question.
Thanks, Michael Henry
On 22/5/2006, at 3:51, Michael Henry wrote:
By the way, I had searched the requested features list to see if this behavior were mentioned, and I didn't see it. Is there somewhere I should have looked before posting?
It has come up here many times in the past, but googling this list seems to give rather poor results.
I do have a searchable ticket tracker [1] but it’s fairly new (although rapidly filling), so it doesn’t give a good picture of the to-do.
If I'd known it was on a TODO list I wouldn't have troubled the list with the question.
Well, the question of what’s not on the to-do is often easier to answer ;)
Michael Henry wrote:
When nothing is selected, invoking either "Line Up" or "Line Down" from the Text | Move Selection menu will move the current line up or down, which is exactly what I'd want it to do. The unexpected behavior is that the cursor doesn't remain on the moved line at the original offset; instead, the cursor ends up at the start of the line immediately below the moved line. This makes it difficult to move a given line more than one line up or down.
While not ideal, one way to get a partial solution to this is to override the "Line Up" and "Line Down" commands using macros.
Sselect "Automation => Start Macro Recording" then
(1) Select "Text => Move Selection => Line Up" (2) Hit your up arrow
and finally select "Automation => Stop Macro Recording". Then use "Automation => Save Scratch Macro..." to save this as, say, "upline" with a blank scope and the same key command as "Text => Move Selection => Line Up". Repeat with obvious modifications for "downline".
This at least eliminates the major pain (cursor not staying on the switched line): you still manage to lose the column position, but for 30 seconds work it's a big improvement.
Cheers, Paul
Paul McCann wrote:
While not ideal, one way to get a partial solution to this is to override the "Line Up" and "Line Down" commands using macros.
Sselect "Automation => Start Macro Recording" then
(1) Select "Text => Move Selection => Line Up" (2) Hit your up arrow
and finally select "Automation => Stop Macro Recording". Then use "Automation => Save Scratch Macro..." to save this as, say, "upline" with a blank scope and the same key command as "Text => Move Selection => Line Up". Repeat with obvious modifications for "downline".
Thanks for the suggestion. I agree that it's a big improvement for the typical use case (moving just a single line), and I may end up with this very work-around until the fix is made in TextMate itself. Before posting, I'd created my own bundle and tried making a command that behaved the way I'd like, but I didn't know enough to get all the behavior correct.
Before purchasing TextMate (and the Macbook Pro to run it on :-)) I'd seen Duane Johnson's MASC hack for simultaneous caret manipulation (see http://blog.inquirylabs.com/my-textmate-bundle/), done solely with an end-user-supplied bundle. The MASC code is a good hack, and it makes for a nice advertisement for the power of TextMate's extensibility. But I didn't look at the actual MASC code before I delved into the bundle editor to hack out my own "move line up" functionality. I started making a command, but I got stalled at the point where I wanted my command to move the caret.
I then studied the MASC bundle to see how he worked his magic. It seems that Duane used snippets to position the caret. He grabs a subset of the buffer, converts it to a snippet, puts in tab-stops (which give the caret positioning he needs), and inserts the snippet into the buffer, replacing the original contents. This is a neat hack, and I may well use it in my attempt to make a complete temporary fix for "move line up".
But I do wonder if there is some other way to position the cursor in the buffer, short of inserting a snippet. Does anyone have a better suggestion for bundle authors who need to process the current buffer and move the caret as a result? Or is the snippet hack the best technique at this time? I'm on a quest to learn how to tailor TextMate, and this seems like a capability I'm going to need in general.
Thanks, Michael Henry