This is the full program listing for the microwave clock demo program. Click on the code below to convert it into a text editor with a built-in assembler, and then click RUN
at the bottom to run the program. You can edit the code and rerun to see the effect of each change.
( Program metadata lives at the start of the program. ) JMPr*:0018 'BEDROCK' metadata/name metadata/authors metadata/descrip metadata/bg metadata/fg 0000 0000 ( Assign names to common jump instructions. ) %CALL: JMS:; %GOTO: JMP:; %RETURN JMPr; ( Assign names to system device ports. ) %SYSTEM.SLEEP 00; ( Assign names to math device ports. ) %MATH.X 20; %MATH.XL 21; %MATH.Y 22; %MATH.QUOTL 2D; %MATH.MODL 2F; ( Assign names to clock device ports. ) %CLOCK.HOUR 33; %CLOCK.MINUTE 34; %CLOCK.SECOND 35; %CLOCK.TIMER1 38; ( Assign names to each of the screen ports. ) %SCREEN.X 50; %SCREEN.Y 52; %SCREEN.WIDTH 54; %SCREEN.HEIGHT 56; %SCREEN.PALETTE 58; %SCREEN.SELECT 5A; %SCREEN.SPRITE 5C; %SCREEN.DRAW 5E; %SCREEN.MOVE 5F; ( Quick macros for drawing to the screen. ) %MOVE! STD:SCREEN.MOVE ; %DRAW! STD:SCREEN.DRAW ; %DRAW!* STD*:SCREEN.DRAW; ( Load the segment sprite into the sprite buffer. ) *:7FFF STD*:SCREEN.SPRITE *:7F3F STD*:SCREEN.SPRITE *:0000 STD*:SCREEN.SPRITE *:0000 STD*:SCREEN.SPRITE ( Load three colours into the colour palette. ) *:0000 STD*:SCREEN.PALETTE *:12F7 STD*:SCREEN.PALETTE *:2010 STD*:SCREEN.PALETTE ( Set the screen width and height. ) *:0068 STD*:SCREEN.WIDTH *:0024 STD*:SCREEN.HEIGHT ( Load a denominator into the math device. ) *:000A STD*:MATH.Y ( Redraw the clock to the screen every minute. ) @main ( Calculate a position for the top-left corner of the clock so that the clock is drawn at the center of the screen. ) LDD*:SCREEN.WIDTH SHR*:01 SUB*:0032 STD*:SCREEN.X LDD*:SCREEN.HEIGHT SHR*:01 SUB*:0010 STD*:SCREEN.Y ( Erase the background layer. ) :20 DRAW! ( Draw the hour and minute digits. ) LDD:CLOCK.HOUR CALL:draw-digit-pair :09 MOVE! LDD:CLOCK.MINUTE CALL:draw-digit-pair ( Draw the two dots between the hour and minute. ) *:[B4 4A] CALL:draw-dot *:[47 83] CALL:draw-dot ( Set a timer to expire at the start of the next minute. ) :3C LDD:CLOCK.SECOND SUB :00 STD*:CLOCK.TIMER1 ( Sleep until a clock or screen event. ) *:1400 STD*:SYSTEM.SLEEP GOTO:main ( Draw a pair of digits. `val` can range from decimal 0 to 99. ) @draw-digit-pair ( val -- ) STD:MATH.XL LDD:MATH.QUOTL CALL:draw-digit LDD:MATH.MODL GOTO:draw-digit ( Move twice and then draw a square dot. ) @draw-dot ( move move -- ) MOVE! MOVE! *:[03 02] DRAW!* :42 MOVE! :61 DRAW! RETURN ( Draw a single digit to the screen. `digit` can range from 0 to 9. ) @draw-digit ( digit -- ) SWP:00 ADD*:digit-map LDA ( Segment 1 ) CALL:~load-colour :05 MOVE! *:[18 07] DRAW!* *:[19 89] DRAW!* ( Segment 2 ) CALL:~load-colour :42 MOVE! *:[1C 81] DRAW!* :46 MOVE! *:[1D c6] DRAW!* ( Segment 3 ) CALL:~load-colour :0C MOVE! *:[1E 81] DRAW!* :46 MOVE! *:[1F 89] DRAW!* ( Segment 4 ) CALL:~load-colour :42 MOVE! *:[1A 06] DRAW!* :44 MOVE! *:[19 89] DRAW!* ( Segment 5 ) CALL:~load-colour :42 MOVE! *:[1C 81] DRAW!* :46 MOVE! *:[1D c6] DRAW!* ( Segment 6 ) CALL:~load-colour :0C MOVE! *:[1E 81] DRAW!* :46 MOVE! *:[1F 89] DRAW!* ( Segment 7 ) CALL:~load-colour :42 MOVE! *:[1A 07] DRAW!* *:[1B 0e] DRAW!* :D8 MOVE! POP RETURN &load-colour ( map -- map ) SHR:01 DUP AND:01 INC STD:SCREEN.SELECT RETURN ( Maps a value in the range 0..9 to a segment map. Each bit maps to a segment of the digit, with a segment being on if the bit is 0. ) @digit-map ( 0 ) 10 ( 00010000 ) ( 1 ) B6 ( 10110110 ) ( 2 ) 44 ( 01000100 ) ( 3 ) 24 ( 00100100 ) ( 4 ) A2 ( 10100010 ) ( 5 ) 28 ( 00101000 ) ( 6 ) 08 ( 00001000 ) ( 7 ) B4 ( 10110100 ) ( 8 ) 00 ( 00000000 ) ( 9 ) 20 ( 00100000 ) ( Program metadata values. ) @metadata &name "Microwave clock" &authors "Ben Bridle" &descrip "Minimal digital clock." &bg 0000 &fg 02F7