home *** CD-ROM | disk | FTP | other *** search
- # SpecTcl, by S. A. Uhler
- # Copyright (c) 1994-1995 Sun Microsystems, Inc.
- #
- # See the file "license.txt" for information on usage and redistribution
- # of this file, and for a DISCLAIMER OF ALL WARRANTIES.
- #
- # utility routines for extracting table structures
-
- ### This has been replaced by the "blt_table location" extension
- # procedure to generate a binary search
- # name: The name of the procedure to generate
- # list: A list of numbers that indicate the size of each bucket
- # (must have at least 1 element)
- # start: The index of the first bucket
- # level: Used internally for indenting the code
- # result: A string to be "eval'd" to generate the procedure
-
- proc gen_bsearch {name list {start 0} {level 0}} {
-
- if {!$level} {
- append result "# procedure automatically generated by gen_bsearch\n"
- append result "# Calling sequence: $name <integer>\n"
- append result "# returns bucket number given by:\n"
- append result "# $list\n\n"
- append result "proc $name x \{\n"
- }
-
- set len [llength $list]
- set pivot [expr [llength $list] / 2]
- set indent [format "%*s" [expr ($level + 1) * 2] ""]
-
- append result $indent "if \{\$x < [lindex $list $pivot] \} \{\n"
-
- if {$pivot == 0} {
- # append result "puts stderr \"$name \$x -> $start\"\n"
- append result "$indent return $start\n"
- } else {
- append result [gen_bsearch $name \
- [lrange $list 0 [expr $pivot - 1]] \
- $start \
- [expr $level + 1]]
- }
- append result "$indent\} else \{\n"
- incr pivot
- if {$len == $pivot } {
- # append result "puts stderr \"$name \$x -> [expr $start + $pivot]\"\n"
- append result "$indent return [expr $start + $pivot]\n"
- } else {
- append result [gen_bsearch $name \
- [lrange $list $pivot end] \
- [expr $start + $pivot] \
- [expr $level + 1]]
- }
- append result "$indent\}\n"
-
- if {!$level} {
- append result \}\n
- }
- return $result
- }
-
- # insert a row or column into the table
- # Table: The parent table to do the inserting in
- # What is "row" or "column"
- # index must be even!
- # count must be even
-
- proc table_insert {table what index {count 2}} {
- global P _Message
- dputs $table $what $index
- undo_log create_grid $table $what $index
- foreach item [blt_table slaves $table -exclude *@*] {
- blt_get $item info
- set start $info(-$what)
- set end [expr $start + $info(-${what}span) -1]
- if {$end < $index} {
- continue ;# before insertion - skip
- }
- if {$start >= $index} { ;# move entire widget
- incr info(-$what) $count
- } else { ;# shift span
- incr info(-${what}span) $count
- }
- eval [blt_set $table $item info]
- }
- resize_insert $table $what $index
- return 1
- }
-
- # delete a row or column - only delete empty rows or columns
- # table: parent of the table to operate on
- # what: "row" or "col"
- # index: table index - MUST be even
- # count: How many to delete - MUST be even
- # return value: TRUE if successful, false if widget would be deleted
-
- proc table_delete {table what index {count 2}} {
- global _Message
-
- # check for widget that would be deleted, gather info for the rest
-
- dputs $table $what $index
- foreach item [blt_table slaves $table -exclude *@*] {
- blt_get $item info
- set start $info(-$what)
- set end [expr $start + $info(-${what}span) -1]
- if {$start == $index && $end == $index} { ;# has widget!
- dputs "No place for $item, aborting"
- return 0
- }
- if {$end < $index} {
- continue
- }
- if {$start > $index} { ;# move entire widget
- incr info(-$what) -$count
- } else { ;# shift span
- incr info(-${what}span) -$count
- }
- set eval($item) [blt_set $table $item info]
- }
-
- # OK, now shift everything
-
- foreach item [array names eval] {
- eval $eval($item)
- }
- update_table $table "deleting $what $index"
- resize_delete $table $what $index
- return 1
- }
-
- # manage structures for efficient item highlighting
- # handle = hightlight_setup <table> [<overlap>]
- # highlight_adjust <handle> <add|del> <widget> (later)
- # highlight_delete <handle>
- # highlight <handle> <row> <col> <how> [<frame>]
-
- # table_setup
- # table: name of table to do highlighting for
- # overlap: number of pixels to overlap grid
- # result:
- # The name of an array is returned containing:
- # array(<window>) x y width height
- # For each window in the table, return coords relative to parent
- # in a form suitable for use with the placer
- # array(owner:<row>,<col>) <window>
- # for every slot occupied by a window, return the window name
- # array(all:<row>,<col>) x y wide high
- # for every slot occupied by a window, return coords spanning
- # all slots it occupies, in a form suitable for use with placer
- # array(slot:<row>,<col> x y wide high
- # for every slot, return coords suitable for use with placer
-
- proc table_setup {table {overlap 0}} {
- set handle geom:$table ;# Everyone depends upon this naming convention
- global $handle
- upvar #0 $handle data
-
- # temporary
-
- set old_rows 0; set old_columns 0
- catch {set old_rows $data(rows)}
- catch {set old_columns $data(columns)}
-
- # reset array, except indeces marked "saved..."
-
- # set save [array get data save*]
- catch {unset data}
- # array set data $save
-
- set data(HighLightHandle) 1 ;# for error checking
- set data(table) $table ;# identify it
-
- # extract the table row and column info
-
- blt_table arrange $table
- array set cnvt {row y column x}
- foreach dim {row column} {
- set stuff [blt_table $dim $table sizes all]
-
- # The table doesn't always start at the edge of the frame!
- # calculate the offset based on the first grid lines.
- # sum contains the offsets of each column from the edge of the master
-
- set sum [expr [winfo $cnvt($dim) $table.$dim@1] - [$table cget -bd]]
- set cnt 0
- set data(${dim}s) [llength $stuff]
- if {$data(${dim}s) == 0} {error "Empty table $table in table_setup"}
- foreach i $stuff {
-
- # this is optional experimental grid gravity
- # if {!$cnt&1} {incr i -3} {incr i 3}
-
- lappend ${dim}_coords $sum
- set data(${dim}_$cnt) $sum
- incr sum $i; incr cnt
- }
- lappend ${dim}_coords $sum
- set data(${dim}_coords) [set ${dim}_coords]
- set data(${dim}_$cnt) $sum
- dputs $table ${dim}s: $data(${dim}_coords)
- }
-
- # extract info for each widget in the table
-
- set match {([0-9]+),([0-9]+)} ;# match row,col info
- foreach slave [blt_table slaves $table] {
- set info [blt_table info $slave]
- regexp $match $info coords row col ;# extract coords
- if {(($row | $col) & 1) == 1} {
- continue ;# skip grid points (row or column is odd)
- }
- set col_span [lindex $info 13]
- set row_span [lindex $info 11]
-
- # create coords for all slots containing the widget
- # This should be addae to blt_table
-
- set x1 $data(column_$col)
- set y1 $data(row_$row)
- set last_row [expr $row + $row_span]
- set last_col [expr $col + $col_span]
- set x2 $data(column_$last_col)
- set y2 $data(row_$last_row)
-
- set data($slave) " \
- -x [expr $x1 + $overlap] \
- -y [expr $y1 + $overlap] \
- -width [expr $x2 - $x1 - 2 * $overlap] \
- -height [expr $y2 - $y1 - 2 * $overlap] \
- "
-
- # create row,col to widget name mapping for all slots
- # containing the widget (gone)
- }
-
- # experiment to avoid tbl bug
-
- while {$old_columns >= $data(columns)} {
- blt_table column $table configure $old_columns -width 0 -resize none
- # puts "zapping old column $old_columns"
- incr old_columns -1
- }
- while {$old_rows >= $data(rows)} {
- blt_table row $table configure $old_rows -height 0 -resize none
- # puts "zapping old row $old_rows"
- incr old_rows -1
- }
- return $handle
- }
-
- # delete a handle
-
- proc highlight_delete {handle} {
- upvar $handle data
- if {![info exists data(HighLightHandle)]} {
- error "$handle is not a highlight handle"
- }
- # rename $data(row_proc) ""
- # rename $data(com_proc) ""
- uplevel "unset $handle"
- }
-
- # extract the row and column minimum size information
-
- proc blt_size {master what} {
- }
-