This is a further development of the Space Game. First I wrote the procedures in tcl, and got them past the "very rough" stage. Then I put them into a Tk script.
Well, I tried to, anyway. For the longest time I could not get the thing to work, because I did not understand how to make a label change after the widget was packed and presented. However, I flipped through Clif Flynt's book BOOK Tcl/Tk for Real Programmers and found an example that showed it could be done. I just needed to figure out how to do it.
This is round two of coding. The best thing I did was start fresh, and delete everything. Well, I kept the "quit" button.....
#!/bin/sh #\ exec wish "$0" "${1+$@}" # EE: Explanation of previous line can be found in page [exec magic] # Are there ever any arguments to this? :) # EE: Doesn't matter. better to have it there for future possibility. #### All the procedures up front # Proc to evaluate the coordinates given # Returns the list of coordinates # Input should be in the form of xxx,yyy,zzz # Split by commas, test for 3 variables, and test for non-numerics. # Then, and only then, return the list as valid. # Needs a Tk based error message instead of an "exit" if fails to # validate. Done 2 jun 01. # Does it need quite the level of math precision? proc validateCoord { coord } { global goodVectors set coordName [ split $coord , ] if {([ llength $coordName ] != "3") || ([regexp {[^0-9 ]} \ "$coordName"])} { # Okay, this was an early issue. If the user entered a bad datum # the program would die. No forgiveness # exit # Change "exit" to: errorMsg $coord set goodVectors false } return $coordName } proc calcVector { hN tT } { # Add the "goodVectors" value global goodVectors # clear goodVectors if set earlier if { [ info exists goodVectors ] } { unset goodVectors } set hereCoord [ validateCoord $hN ] set thereCoord [ validateCoord $tT ] # This was added, it tests for the variable "goodVectors" # If it is set, that means there are problems, and it # sets the output label to show an error. # If the goodVectors is not set, then continue on. The problem # was that the math needed to be wrapped so that it did not # try to compute if the information was bad. # Does that make sense? :) if { [ info exists goodVectors ] } { set distance "error-please redo" } else { foreach x1 $hereCoord x2 $thereCoord { lappend vector [expr {$x2 - $x1}] } foreach {X Y Z} $vector break set distance [expr {hypot($X, hypot($Y,$Z))}] return "${X},${Y},${Z} @ $distance " } } # This whole proc was added to give better error messaging # than a program crash. :) proc errorMsg { badInfo } { # If they blow it, wake them up! bell # This is a failed try to handle 2 sets of exactly similar # bad input. # if { [ info exists errLabel ] } { # set badInfo ${badInfo}2 # } set errLabel $badInfo # The ".ack$badInfo covers if the user inputs a blank toplevel .ack$badInfo message .ack${badInfo}.1 -text "Please use standard Galactic \ format: xx,yy,zz. not $badInfo" wm title .ack${badInfo} "ERROR" pack .ack${badInfo}.1 } #### Put up the UI # Quit button button .quit -text "Quit" -command exit set hN [ entry .e1 -width 12 -textvariable input1 ] set tT [ entry .e2 -width 12 -textvariable input2 ] set out [ label .l1 -width 30 -textvariable output ] set action [ button .b1 -text "Get Vector" -command {\ set output [ calcVector $input1 $input2 ] } ] pack $hN $tT $out $action .quit -side left