| ! Copyright (C) 2018 Andrew Owen. | |
| ! See http://factorcode.org/license.txt for BSD license. | |
| USING: | |
| ui ui.gadgets ui.gadgets.tracks ui.gadgets.labels ui.gadgets.buttons ui.gadgets.packs ui.tools.operations | |
| ui.pens.solid ui.pens.gradient | |
| colors colors.constants | |
| accessors math.parser vocabs.loader io locals | |
| models models.arrow fry | |
| kernel strings sequences math | |
| ; | |
| IN: calculator | |
| TUPLE: calculator-state | |
| { accum initial: "" } | |
| { prev initial: 0 } | |
| { op initial: [ drop drop ] } | |
| ; | |
| : <calculator-state> ( -- new-calc-state ) calculator-state new ; | |
| : calc-clear-all ( state -- ) | |
| [ accum>> "" swap set-model ] keep | |
| prev>> 0 swap set-model | |
| ; | |
| : calc-clear ( state -- ) accum>> "" swap set-model ; | |
| :: set-calc-op ( state quot -- ) | |
| state quot >>op | |
| ! Move the accum value to the prev model | |
| [ accum>> value>> string>number ] [ prev>> ] bi set-model | |
| ! Clear accum | |
| "" state accum>> set-model | |
| ; | |
| :: calculate ( state -- ) | |
| state [ prev>> value>> ] [ accum>> value>> string>number ] bi state op>> call( x y -- result ) | |
| number>string state accum>> set-model | |
| ; | |
| : echoed ( track char model -- track ) | |
| ! Char is actually a string here. | |
| [let :> model :> char | |
| char <label> | |
| ! The value in the model here is a string | |
| [ drop model dup value>> char append swap set-model ] | |
| <border-button> 0.33 track-add | |
| ] | |
| ; | |
| :: operators-layout-init ( state -- gadget ) | |
| vertical <track> | |
| horizontal <track> | |
| "/" <label> [ drop state [ / ] set-calc-op ] <border-button> 0.5 track-add | |
| "AC" <label> [ drop state calc-clear-all ] <border-button> 0.5 track-add | |
| 0.25 track-add | |
| horizontal <track> | |
| "*" <label> [ drop state [ * ] set-calc-op ] <border-button> 0.5 track-add | |
| "C" <label> [ drop state calc-clear ] <border-button> 0.5 track-add | |
| 0.25 track-add | |
| horizontal <track> | |
| "-" <label> [ drop state [ - ] set-calc-op ] <border-button> 0.5 track-add | |
| "" <label> 0.5 track-add | |
| 0.25 track-add | |
| horizontal <track> | |
| "+" <label> [ drop state [ + ] set-calc-op ] <border-button> 0.25 track-add | |
| "=" <label> [ drop state calculate ] <border-button> 0.25 track-add | |
| 0.25 track-add | |
| ; | |
| :: digits-layout-init ( calculator-state -- gadget ) | |
| calculator-state accum>> :> accum | |
| vertical <track> | |
| ! TODO: Figure out the way to build the tracks here. | |
| horizontal <track> { "7" "8" "9" } [ accum echoed ] each 0.25 track-add | |
| horizontal <track> { "4" "5" "6" } [ accum echoed ] each 0.25 track-add | |
| horizontal <track> { "1" "2" "3" } [ accum echoed ] each 0.25 track-add | |
| horizontal <track> { "." "0" "" } [ accum echoed ] each 0.25 track-add | |
| ; | |
| :: calculator-init ( -- gadget ) | |
| <calculator-state> | |
| "" <model> >>accum | |
| 0 <model> >>prev | |
| :> state | |
| vertical <track> | |
| state accum>> <label-control> 0.4 track-add | |
| horizontal <track> | |
| state digits-layout-init 0.6 track-add | |
| state operators-layout-init 0.4 track-add | |
| 0.6 track-add | |
| ; | |
| : calculator-show ( -- ) calculator-init "Calculator" open-window* { 200 300 } >>dim drop ; | |
| <PRIVATE | |
| :: alert ( message -- ) <shelf> message <label> add-gadget message open-window ; | |
| PRIVATE> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment