( 54K . Grail | MEDENAGAN ) |00 @System &vector $2 &expansion $2 &wst $1 &rst $1 &metadata $2 &r $2 &g $2 &b $2 &debug $1 &state $1 |20 @Screen &vector $2 &width $2 &height $2 &auto $1 &pad $1 &x $2 &y $2 &addr $2 &pixel $1 &sprite $1 |90 @Mouse &vector $2 &x $1 &lx $1 &y $1 &ly $1 &state $1 &chord $1 &pad $4 &scrolly &scrolly-hb $1 &scrolly-lb $1 |a0 @File &vector $2 &success $1 &success-lb $1 &stat $2 &delete $1 &append $1 &name $2 &length $2 &read $2 &write $2 |0050 @Varvara/version |000 @L $1 @D $1 @R $1 @U $1 |000 @mode $1 |100 @on-reset ( -> ) ;meta #06 DEO2 ( | theme ) #e0cf .System/r DEO2 #e0c9 .System/g DEO2 #e0c6 .System/b DEO2 ( | size ) #0100 .Screen/width DEO2 #0100 .Screen/height DEO2 ;on-mouse .Mouse/vector DEO2 BRK @on-mouse ( -> ) [ LIT2 00 -Mouse/state ] DEI NEQ #41 ADD ;cursor-icn [ LIT2 &last $1 -Mouse/state ] DEI #00 NEQ DUP ,&last STR DUP2 #0001 EQU2 ?on-mouse-down DUP2 #0101 EQU2 ?on-mouse-drag DUP2 #0100 EQU2 ?on-mouse-up POP2 BRK @on-mouse-down ( states* -> ) POP2 .Mouse/ly DEI DUP get-mode .Mouse/lx DEI SWP BRK @on-mouse-drag ( states* -> ) POP2 ( | push ) .Mouse/lx DEI .Mouse/ly DEI BRK @on-mouse-up ( states* -> ) POP2 ( | draw ) ;/last-pos LDA2 .Mouse/lx DEI .Mouse/ly DEI DUP2 #0f ( | toggle punctuation mode ) ;/last-dir LDA INC ?{ [ LIT2 02 -mode ] LDZ NEQ ?{ [ LIT ". ] BRK } BRK } ( | cap ) ( release ) #00 BRK @meta $1 ( ) "Grail 0a ( ) "Shorthand 20 "Recognnizer 0a ( ) "By 20 "Devine 20 "Lu 20 "Linvega 0a ( ) "6 20 "Jun 20 "2026 $1 ( . ) 02 ( - ) 56 =Varvara/version ( - ) 83 =appicon ( @|core ) @get-bounds ( -- end* dict* ) [ LIT2 02 -mode ] LDZ EQU ?&punctuation [ LIT2 03 -mode ] LDZ EQU ?&control ;core/end ;core JMP2r &punctuation ( -- end* dict* ) ;punctuation/end ;punctuation JMP2r &control ( -- end* dict* ) ;control/end ;control JMP2r @ ( -- ) [ LITr 00 ] get-bounds &>l LDA2k find-match #ffff EQU2 ?{ INCr } INC2 INC2 GTH2k ?&>l POP2 POP2 STHkr ?&found ( | no candidates ) POPr #03 ! &found ( -- ) STHr #01 EQU ?{ JMP2r } find-valid INC2k ORA ?{ POP2 JMP2r } LDA !/resume @ ( char -- ) [ LIT2 00 -mode ] LDZ EQU ?{ capitalize } #18 DEO #02 ! @find-valid ( -- addr* ) ;/ptr LDA2 ;directions SUB2 ,&tlen STR POP get-bounds &>l LDA2k INC2 LDA INC [ LIT &tlen $1 ] NEQ ?{ LDA2k find-match INC2k ORA ?&found POP2 } INC2 INC2 GTH2k ?&>l POP2 POP2 #ffff JMP2r &found ( -- ) NIP2 NIP2 JMP2r @find-match ( lib* -- ptr* ) INC2k INC2 STH2 ;/ptr LDA2 ;directions &>l LDAk LDAkr STHr NEQ ?&fail INC2r INC2 GTH2k ?&>l POP2 POP2 POP2r JMP2r &fail ( -- ) POP2 POP2 POP2 POP2r #ffff JMP2r @ ( x y -- ) DUP2 #0f DUP2 ;/last-pos STA2 #ff ;/last-dir STA &resume ( -- ) ;stroke ;/ptr STA2 ;directions ;/ptr STA2 JMP2r @ ( -- ) find-valid DUP2 #ffff EQU2 ?{ LDAk } POP2 JMP2r @get-direction ( x1 y1 -- color ) ( 0 ) STH2k GTH ( 1 ) STH2kr abs GTH ADD ( 2 ) STHr STHr abs LTH ADD JMP2r @get-mode ( y -- mode ) .Mouse/state DEI #02 LTH ?{ POP #03 JMP2r } ( ) DUP #3f GTH ?{ POP #01 JMP2r } ( ) DUP #c0 LTH ?{ POP #02 JMP2r } POP #00 JMP2r @ ( mode -- ) .mode STZ ! @thin ( x1 y1 x2 y2 -- f ) ROT SUB abs STH SUB abs STHr ADD ( ) #01 SFT #04 LTH JMP2r @ ( x y -- ) ( | thin ) DUP2 [ LIT2 &last-pos &lastx $1 &lasty $1 ] thin ?{ [ LIT2 &ptr =stroke ] STA2k INC2 INC2 ,&ptr STR2 ( | get direction ) ( ) DUP2 ,&lasty LDR SUB #80 ADD SWP ( ) ,&lastx LDR SUB #80 ADD SWP get-direction [ LIT &last-dir $1 ] ( | stroke ) OVR2 ,&last-pos LDR2 EQUk ?{ OVR OVR2 #05 } POP ,&last-dir STR DUP2 ,&last-pos STR2 } POP2 ! @ ( dir -- ) [ LIT2 &ptr =directions ] STAk INC2 ,&ptr STR2 POP #05 ! ( @|drawing ) @ ( -- ) #0000 DUP2 .Screen/x DEO2 .Screen/y DEO2 [ LIT2 80 -Screen/pixel ] DEO #0040 .Screen/y DEO2 #00c0 .Screen/y DEO2 ( >> ) @ ( -- ) #0008 .Screen/x DEO2 #00e8 .Screen/y DEO2 ;button-icn .Screen/addr DEO2 [ LIT2 16 -Screen/auto ] DEO [ LIT2 01 -Screen/sprite ] DEOk DEO ( | icon ) #000c .Screen/x DEO2 #00ec .Screen/y DEO2 [ LIT2 00 -mode ] LDZ #30 SFT2 ;modes-icn ADD2 .Screen/addr DEO2 [ LIT2 00 -Screen/auto ] DEO [ LIT2 00 -mode ] LDZ NEQ INC .Screen/sprite DEO JMP2r @ ( -- ) ;dash-icn .Screen/addr DEO2 [ LIT2 f2 -Screen/auto ] DEO #0000 .Screen/x DEO2 [ LIT2 02 -Screen/sprite ] DEO .Screen/y DEI2k #0008 SUB2 ROT DEO2 #0080 .Screen/x DEO2 [ LIT2 02 -Screen/sprite ] DEO JMP2r @ ( color -- ) ,&color STR #0020 .Screen/x DEO2 #00ec .Screen/y DEO2 [ LIT2 01 -Screen/auto ] DEO ;/ptr LDA2 ;directions &>l EQU2k ?&end LDAk #00 SWP #30 SFT2 ;arrows-icn ADD2 .Screen/addr DEO2 [ LIT2 &color $1 -Screen/sprite ] DEO INC2 GTH2k ?&>l &end POP2 POP2 JMP2r @ ( x y color -- ) STH prom #0002 SUB2 .Screen/y DEO2 #0002 SUB2 .Screen/x DEO2 ;point-icn .Screen/addr DEO2 [ LITr -Screen/sprite ] DEOr JMP2r @ ( color addr* -- ) [ LIT2 00 -Screen/auto ] DEO ;fill-icn .Screen/addr DEO2 #40 .Mouse/x DEI2 ,/x STR2 .Mouse/y DEI2 ,/y STR2 .Screen/addr DEO2 ( >> ) @ ( color -- ) [ LIT2 &x $2 ] .Screen/x DEO2 [ LIT2 &y $2 ] .Screen/y DEO2 .Screen/sprite DEO JMP2r @ ( a* b* -- ) STH2 prom STH2r prom #01 ( >> ) @ ( x1* y1* x2* y2* color -- ) ,&color STR ,&y STR2 ,&x STR2 ,&y2 STR2 ,&x2 STR2 ,&x LDR2 ,&x2 LDR2 SUB2 abs2 ,&dx STR2 #0000 ,&y LDR2 ,&y2 LDR2 SUB2 abs2 SUB2 ,&dy STR2 #ffff [ LIT2 00 _&x2 ] LDR2 ,&x LDR2 lts2 DUP2 ADD2 ADD2 ,&sx STR2 #ffff [ LIT2 00 _&y2 ] LDR2 ,&y LDR2 lts2 DUP2 ADD2 ADD2 ,&sy STR2 [ LIT2 &dx $2 ] [ LIT2 &dy $2 ] ADD2 STH2 &w ( -- ) [ LIT2 &x2 $2 ] DUP2 .Screen/x DEO2 [ LIT2 &x $2 ] EQU2 [ LIT2 &y2 $2 ] DUP2 .Screen/y DEO2 [ LIT2 &y $2 ] EQU2 [ LIT2 &color $1 -Screen/pixel ] DEO AND ?&end STH2kr DUP2 ADD2 DUP2 ,&dy LDR2 lts2 ?&skipy STH2r ,&dy LDR2 ADD2 STH2 ,&x2 LDR2 [ LIT2 &sx $2 ] ADD2 ,&x2 STR2 &skipy ( -- ) ,&dx LDR2 gts2 ?&w STH2r ,&dx LDR2 ADD2 STH2 ,&y2 LDR2 [ LIT2 &sy $2 ] ADD2 ,&y2 STR2 !&w &end POP2r JMP2r ( @|theme ) @ ( -- ) ;&path .File/name DEO2 #0002 .File/length DEO2 [ LIT2 -System/debug -System/r ] &>l ;&buf .File/read DEO2 [ LIT2 00 -File/success-lb ] DEI EQU ?{ [ LIT2r &buf $2 ] STHk DEO2r INC INC NEQk ?&>l } POP2 JMP2r &path ".theme $1 ( @|stdlib ) @abs ( a -- b ) DUP #80 AND #00 EQU ?{ #00 SWP SUB } JMP2r @prom ( a b -- a* b* ) ,&b STR ,&a STR [ LIT2 00 &a $1 ] [ LIT2 00 &b $1 ] JMP2r @abs2 ( a* -- f ) DUP2 #0f SFT2 EQU ?{ #0000 SWP2 SUB2 } JMP2r @lts2 ( a* b* -- f ) SUB2 POP #07 SFT JMP2r @gts2 ( a* b* -- f ) SWP2 SUB2 POP #07 SFT JMP2r @capitalize ( char -- char ) DUP [ LIT "a ] LTH ?{ DUP [ LIT "z ] GTH ?{ #20 SUB } } JMP2r ( @|assets ) @appicon [ 0000 0000 0000 0001 0000 0000 0000 0000 0000 0000 7088 8808 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0101 0101 0000 0000 0000 0000 0000 0000 0810 1010 a0a0 8040 0000 0000 0000 0000 0000 0000 0000 0208 0000 0000 0000 0000 0102 6418 0000 0000 0000 0000 0000 0000 2018 0700 0000 0000 0000 0000 0000 0000 1060 8000 0000 0000 0000 0000 0000 0000 ] @cursor-icn [ 80c0 e0f0 f8e0 1000 ] @fill-icn [ ffff ffff ffff ffff ] @point-icn [ 0020 7020 0000 0000 ] @dash-icn [ ee00 0000 0000 0000 ] @button-icn [ 001f 2040 4040 4040 00f8 0402 0202 0202 4040 4040 4020 1f00 0202 0202 0204 f800 ] @modes-icn [ 0000 183c 3c18 0000 0018 3c7e 1818 1800 0000 3838 3808 1000 0018 1866 6618 1800 ] @arrows-icn [ 0010 307e 7e30 1000 0018 1818 7e3c 1800 0008 0c7e 7e0c 0800 0018 3c7e 1818 1800 ] @lib ( @|numbers ) &0 "0 _{ -R -D -L -U } &0a "0 _{ -D -L -U -R } &1 "1 _{ -D -L -R } &1a "1 _{ -L -R -D } &2 "2 _{ -R -D -L -D -R } &2a "2 _{ -R -D -R } &3 "3 _{ -R -L -R -D -L } &3a "3 _{ -R -D -L -R -D -L } &4 "4 _{ -D -R -U -D } &4a "4 _{ -D -R -D } &5 "5 _{ -L -D -R -D -L } &5a "5 _{ -L -D -R -L } &6 "6 _{ -D -R -U -L } &7 "7 _{ -R -D } &8 "8 _{ -D -R -D -L -U -R -U -L } &8a "8 _{ -D -L -U -R -U -L } &9 "9 _{ -L -U -R -D } &9a "9 _{ -L -D -R -D } ( @|alphabet ) &a "a _{ -L -D -R -U -D } &b "b _{ -D -U -R -D -L } &c "c _{ -L -D -R } &d "d _{ -D -U -L -D -R } &e "e _{ -R -U -L -D -R } &f "f _{ -L -D -L -U -R } &g "g _{ -L -D -R -U -D -L } &h "h _{ -D -U -R -D } &i "i _{ -U } &j "j _{ -D -L } &k "k _{ -D -U -R } &l "l _{ -D } &la "l _{ -D -R } &m "m _{ -U -D -U -D } &ma "m _{ -U -R -D -U -R -D } &n "n _{ -U -D } &na "n _{ -U -R -D } &o "o _{ -L -D -R -U } &oa "o _{ -L -D -R -U -L } &p "p _{ -U -R -D -L } &q "q _{ -U -L -D -R } &r "r _{ -U -R } &s "s _{ -L -R -L } &t "t _{ -R -L -D } &ta "t _{ -L -D } &u "u _{ -D -R -U } &v "v _{ -D -U } &w "w _{ -D -U -D -U } &x "x _{ -R -U -D } &xa "x _{ -R -U -L -D } &y "y _{ -D -U -D } &ya "y _{ -D -U -D -L } &z "z _{ -R -L -R } &za "z _{ -L -D -L } ( @|special ) &mrk "? _{ -R -D -L -D } &bsp 08 _{ -L } &wsp 20 _{ -R } &tab 09 _{ -U -R } &brk 0a _{ -D -R } ( @|punctuation ) <h "< _{ -L -R } >h "> _{ -R -L } &mul "* _{ -R -U -D } &add "+ _{ -D -U -L -R } &equ "= _{ -R -L -R } &div "/ _{ -D -L -D } &and "& _{ -U -L -D -R -D } &adr "@ _{ -U -L -D -R } &dash "- _{ -R } &undr "_ _{ -L } &hash "# _{ -U -R -D -L } &pipe "| _{ -U } &excl "! _{ -D } &apos "' _{ -D -U } &comma ", _{ -D -L } &colon ": _{ -U -L -R } &semic "; _{ -D -L -R } &caret "^ _{ -U -D } &tilde "~ _{ -R -D -R } "e "" _{ -D -U -D } &parena "( _{ -L -D -R } &parenb ") _{ -R -D -L } &bracka "[ _{ -L -U -R } &brackb "] _{ -R -U -L } &bracea "{ _{ -L -R -D } &braceb "} _{ -R -L -D } &dollar "$ _{ -L -D -R -D -L } &percent "% _{ -D -R -D } ( @|control ) &sela 06 _{ -U -R } &moveu 11 _{ -U } &moved 12 _{ -D } &movel 13 _{ -L } &mover 14 _{ -R } &selb 06 _{ -U -L } @core [ =lib/0 =lib/1 =lib/2 =lib/3 =lib/4 =lib/5 =lib/6 =lib/7 =lib/8 =lib/9 =lib/a =lib/b =lib/c =lib/d =lib/e =lib/f =lib/g =lib/h =lib/i =lib/j =lib/k =lib/l =lib/m =lib/n =lib/o =lib/p =lib/q =lib/r =lib/s =lib/t =lib/u =lib/v =lib/w =lib/x =lib/y =lib/z =lib/0a =lib/1a =lib/2a =lib/3a =lib/4a =lib/5a =lib/8a =lib/9a =lib/la =lib/ma =lib/na =lib/oa =lib/ta =lib/xa =lib/ya =lib/za =lib/mrk =lib/wsp =lib/bsp ] &end @punctuation [ =lib/lth =lib/gth =lib/mul =lib/div =lib/add =lib/equ =lib/and =lib/adr =lib/hash =lib/pipe =lib/excl =lib/apos =lib/comma =lib/colon =lib/semic =lib/caret =lib/tilde =lib/quote =lib/parena =lib/parenb =lib/bracea =lib/braceb =lib/bracka =lib/brackb =lib/dollar =lib/percent =lib/dash =lib/undr =lib/tab =lib/brk ] &end @control [ =lib/moveu =lib/moved =lib/movel =lib/mover =lib/sela =lib/selb ] &end ( @|buffers ) @directions $100 @stroke $400