Version 0 of auto-indent

Updated 2006-02-12 09:51:58 by suchenwi

if 0 {Richard Suchenwirth 2006-02-12 - Here's ten lines of code that I really like. If you intend to indent your source code (like good coders should), on most editors you'd have to sprinkle in spaces or tabs for that effect. Emacs at least takes care of bracing levels and auto-indents accordingly. I'm not reinventing Emacs here (which would take more than 10 loc anyway), but the following command, bound to <Return> in a text widget, does

  • determine the whitespace prefix of the current line
  • insert the prefix on the next line
  • if the current line ended in "{", indents one layer more
  • and creates the matching "}" line after the insert point.

I have scheduled events with after so that they happen after the <Return> has been inserted. This code goes into e: a tiny editor plugin for eTcl, but obviously does not depend on it. }

 proc e'indent w {
    set lineno [expr {int([$w index insert])}]
    set line [$w get $lineno.0 $lineno.end]
    regexp {^(\s*)} $line -> prefix
    after 1 [list $w insert insert $prefix]
    if {[string index $line end] eq "\{"} {
        after 2 [list $w insert insert [string repeat " " 4]]
        after 3 [list $w insert insert+1c $prefix\}\n]
    }
 }

#-- Testing demo:

 pack [text .t]
 bind .t <Return> {e'indent %W}
 focus -force .t

 bind . <Escape> {exec wish $argv0 &; exit}
 bind . <F1> {console show}

if 0 {Known problem: if the insert cursor is at the very end of the text, "insert+1c" delivers the same position as "insert", leading to wrong indentation on open-brace. I haven't found a good solution for that. But it rarely happens when editing existing text, and in an empty text widget, just type one newline and <Up> to avoid this problem.


Category Editors | Arts and crafts of Tcl-Tk programming }