#!/usr/bin/env wish set active_transform 0 # Remove empty items at the beginning and the end of a list. proc ltrim {list} { set first [lsearch -not -exact $list {}] set last [lsearch -not -exact [lreverse $list] {}] return [ if {$first == -1} { list } else { lrange $list $first end-$last } ] } # Trim indentation in multiline quoted text. proc undent {msg {whitespaceChars " "}} { set msgLines [split $msg "\n"] set maxLength [string length $msg] set regExp [subst -nocommands {([$whitespaceChars]*)[^$whitespaceChars]}] set indent [ tcl::mathfunc::min {*}[ lmap x $msgLines { if {[regexp $regExp $x match whitespace]} { string length $whitespace } else { lindex $maxLength } } ] ] join [ltrim [lmap x $msgLines {string range $x $indent end}]] "\n" } proc oneline {text} { return [regsub -all \n+ $text " "] } proc wordcount {text} { set lines [expr [llength [split $text \n]] - 1] set words [llength [regexp -all -inline {\S+} $text]] set len [string length $text] lappend out $lines lappend out $words lappend out $len return $out } proc dedent {text} { return [undent $text] } proc markdown_quote {text} { set text [string trim $text] return [string cat "> " [regsub -all \n $text "\n> "]] } proc identity {text} { return $text } lappend transforms [list {None} identity] lappend transforms [list {One line} oneline] lappend transforms [list {Line/Word/Char} wordcount] lappend transforms [list {Dedent} dedent] lappend transforms [list {Markdown Quote} markdown_quote] wm geometry . 750x650 wm title . "Text Tools" wm resizable . false false text .content text .output listbox .transform foreach {elem} $transforms { .transform insert end [lindex $elem 0] } .transform selection set $active_transform grid .transform -row 1 -column 1 -rowspan 2 grid .content -row 1 -column 2 grid .output -row 2 -column 2 focus .content proc update_output {} { global active_transform global transforms set text [.content get 1.0 end] set tf [lindex $transforms $active_transform] set out [[lindex $tf 1] $text] .output replace 1.0 end $out } bind .content update_output bind . exit proc select_transform {args} { global active_transform set active_transform [.transform curselection] update_output } bind .transform select_transform update