A Four Function Calculator

[Sun Home | Tcl Plugin | Demos]


Here's the calculator for when you just can't do it in your head:

Source:


Here is the source for the calculator:

# calc - A simple calculator for use as a plug-in demo. # Sydney R. Polk, Sun Microsystems # # The global variable state is used to keep track of what the user has # done. It has several fields: Whether or not the last button was a # CE, the current value of the expression, the current value of the # entry window. proc doClear {} { global state set state(entry) "0." set state(dot) 0 if {$state(entrystarted) == 0} { set state(result) "0." set state(operation) "" } set state(entrystarted) 0 } proc doDot {} { global state set state(dot) 1 } proc doAppend {what} { global state if {$state(entrystarted) == 0} { set state(entry) "0." } if {[string compare $state(operation) ""] == 0} { set state(result) "0." } if {!($what == 0 && [string compare $state(entry) "0."] == 0)} { set state(entrystarted) 1 if {$state(dot) == 1} { set state(entry) [format "%s%s" $state(entry) $what] } else { regexp {([-0123456789]+).} $state(entry) foo integer if {[string compare $integer "0"] == 0} { set state(entry) [format "%s." $what] } else { set state(entry) [format "%s%s." $integer $what] } } } } proc doOperation {what} { global state if {[string compare $state(operation) ""] != 0} { doEqual } set state(operation) $what set state(result) $state(entry) set state(entrystarted) 0 set state(dot) 0 } proc doEqual {} { global state if {[string compare $state(operation) ""] != 0} { set state(result) \ [expr "$state(result) $state(operation) $state(entry)"] } else { set state(result) $state(entry) } set state(entry) $state(result) set state(entrystarted) 0 set state(operation) "" set state(dot) 0 } proc doSign {} { global state if {[string compare $state(entry) "0."] != 0} { set sign "" set abs "" regexp {([-]?)([0-9.]+)} $state(entry) foo sign abs if {[string compare $sign "-"] == 0} { set state(entry) $abs } else { set state(entry) [format "-%s" $abs] } set state(entrystarted) 1 } } set state(result) "0." set state(entry) "0." set state(operation) "" set state(dot) 0 set state(entrystarted) 0 label .label -textvariable state(entry) -justify right -anchor e foreach {number} {0 1 2 3 4 5 6 7 8 9} { set buttons($number) [button .$number -text $number \ -command "doAppend $number"] } set buttons(clear) [button .clear -text C/CE -padx 1 -command "doClear"] foreach {label operation} {div / mult * minus - plus +} { set buttons($label) [button .$label -text $operation \ -command "doOperation $operation"] } set buttons(dot) [button .dot -text . -command "doDot"] set buttons(sign) [button .sign -text +/- -padx 1 -command "doSign"] set buttons(equal) [button .equal -text = -command "doEqual"] grid .label -column 0 -row 0 -columnspan 4 -sticky news grid $buttons(clear) $buttons(div) $buttons(mult) $buttons(minus) -sticky news grid $buttons(7) $buttons(8) $buttons(9) -sticky news grid $buttons(4) $buttons(5) $buttons(6) -sticky news grid $buttons(1) $buttons(2) $buttons(3) -sticky news grid $buttons(0) $buttons(dot) $buttons(sign) -sticky news grid $buttons(plus) -column 3 -row 2 -rowspan 2 -sticky news grid $buttons(equal) -column 3 -row 4 -rowspan 2 -sticky news