package require BWidget proc tree'mark {w x y label} { set text [[winfo parent $w] itemcget $label -text] $w create text $x $y -text $text -tag marked set ::g(x) $x set ::g(y) $y } proc tree'motion {w x y label} { $w move marked [expr $x-$::g(x)] [expr $y-$::g(y)] set ::g(x) $x set ::g(y) $y } proc tree'release {w x y label} { $w delete marked if [regexp n:(.+) [$w gettags [$w find closest $x $y]] -> target] { if {$label ne $target} { set tree [winfo parent $w] catch { $tree move $target $label 0 $tree opentree $target } } } }#----- testing demo:
pack [Tree .t] .t insert 0 root node1 -text hello .t insert 0 root node2 -text world .t insert 0 root node3 -text again .t insert 0 node2 node4 -text fourth .t bindText <1> {+ tree'mark %W %x %y} .t bindText <B1-Motion> {tree'motion %W %x %y} .t bindText <ButtonRelease-1> {tree'release %W %x %y}
MPJ Nice. The only problem I saw was that you can not move a node to the top level.
CJB I created new procs for this.
#Allows only children of non-root nodes to move. proc tree'release'child {w x y label} { $w delete marked if [regexp n:(.+) [$w gettags [$w find closest $x $y]] -> target] { if {$label ne $target} { set tree [winfo parent $w] if {[::Tree::parent $tree $label] ne "root"} { catch { $tree move $target $label 0 $tree opentree $target } } } } } #Allows nodes to move back to the root. proc tree'release'root {w x y label} { $w delete marked set tree [winfo parent $w] if [regexp n:(.+) [$w gettags [$w find closest $x $y]] -> target] { if {$label ne $target} { catch { $tree move $target $label 0 $tree opentree $target } } } else { $tree move root $label 0 } } #Allows nodes to move between children of root. #Each child of the root contains only leaves. #Children of the root cannot move. proc tree'release'leaf {w x y label} { $w delete marked if [regexp n:(.+) [$w gettags [$w find closest $x $y]] -> target] { if {$label ne $target} { set tree [winfo parent $w] if {[::Tree::parent $tree $label] ne "root" && [::Tree::parent $tree $target] eq "root"} { catch { $tree move $target $label 0 $tree opentree $target } } } } }