--- title: "Things To Do" id: 57654 type: "computer_media" slug: "things-to-do" url: "http://localhost/computer_media/things-to-do/" markdown_url: "http://localhost/computer_media/things-to-do.md" published_at: "2024-10-06T01:32:42+00:00" modified_at: "2026-04-03T07:58:08+00:00" author: "David Anderson" featured_image: url: "http://localhost/wp-content/uploads/2024/10/things-to-do.png" excerpt: "A to-do list manager with six menu options—add, prioritise, delete, view, and tape-save—dispatching via a neat GOTO VAL Y$*1000 trick." category: - name: "Archived Media" slug: "archived-media" taxonomy: "category" url: "http://localhost/category/archived-media/" post_tag: - name: "Downloadable" slug: "downloadable" taxonomy: "post_tag" url: "http://localhost/tag/downloadable/" - name: "TS 1000" slug: "ts1000" taxonomy: "post_tag" url: "http://localhost/tag/ts1000/" model: - name: "Timex/Sinclair 1000" slug: "ts-1000" taxonomy: "model" url: "http://localhost/model/ts-1000/" indiv: - name: "Gene G. Buza" slug: "gene-g-buza" taxonomy: "indiv" url: "http://localhost/indiv/gene-g-buza/" genre: - name: "Home" slug: "home" taxonomy: "genre" url: "http://localhost/type/home/" media_contents: - id: 56728 title: "Synchro-Sette September 1983" type: "computer_media" url: "http://localhost/computer_media/synchro-sette-september-1983/" media_type: "Program" programmers: - name: "Gene G. Buza" slug: "gene-g-buza" taxonomy: "indiv" url: "http://localhost/indiv/gene-g-buza/" mediadate: "September 1983" images: - url: "http://localhost/wp-content/uploads/2024/10/things-to-do.png" media_type_tags: "Home" --- This program implements a simple to-do list manager, storing up to 22 items of up to 30 characters each in a two-dimensional string array. It presents a menu-driven interface with six options: adding items, setting priorities (reordering), deleting items, clearing the file (via RUN), viewing the file, and saving to tape. Priority setting works by prompting the user to re-enter items in desired order into a second array B$, then copying back to A$. The program uses POKE 16418 to control the system’s display mode flag and exploits INKEY$ key codes (29–34, corresponding to digits 1–6) for menu navigation, dispatching via GOTO VAL Y$*1000. *** ## Program Structure The program is organised around a central menu loop at line `100`–`380` that dispatches to one of six routines based on the user’s keypress. Each routine ends with `GOTO 100` (or `GOTO VAL "1"*1000` etc.) to return to the menu. The overall flow is: 1. **Initialisation (10–40):** Sets FAST mode, dimensions both string arrays, initialises record counter `R1=0`. 2. **Menu (100–380):** Displays six options, waits for a keypress in range 1–6, dispatches via computed `GOTO`. 3. **Routines at ×1000:** Lines 1000, 2000, 3000, 4000, 5000, 6000 implement each menu option. 4. **Display subroutine (2500–2540):** Shared CLS + list-print used by options 2, 3, and 5. ### Data Storage Two `DIM`ed arrays are used: | Variable | Size | Purpose | | --- | --- | --- | | `A$(22,30)` | 22 rows × 30 chars | Primary to-do list storage | | `B$(22,30)` | 22 rows × 30 chars | Temporary buffer during priority reordering | The variable `R1` tracks how many items have been entered. Items are 1-indexed; the maximum list length is 22 entries. ### Menu Dispatch Technique The menu waits for a keypress at line `330` with `LET Y$=INKEY$` inside a loop. Line `340` validates that `CODE Y$` is between 29 and 34, which correspond to the ZX81 character codes for digits `1` through `6`. Line `380` then uses `GOTO VAL Y$*1000`, converting the digit character to an integer and multiplying by 1000 to reach the correct routine — a compact dispatch idiom that avoids a chain of `IF` statements. ### POKE 16418 Usage Address 16418 (`CDFLAG` / the “slow/fast” flag in ZX81 RAM) is manipulated directly: - `POKE 16418,0` at line `300` — switches the display mode before entering the SLOW input loop. - `POKE 16418,2` at line `370` — restores the flag after menu selection, before dispatching. This is used alongside the `FAST`/`SLOW` keywords to control display flickering and input responsiveness. ### Priority Reordering (Option 2) The reorder routine (lines `2000`–`2130`) works as follows: 1. Display current list via subroutine at `2500`. 2. For each position `I` from 1 to `R1`, ask user to input a source index `A`. 3. Copy `A$(A)` into `B$(I)` and blank out `A$(A)`. 4. After all selections, copy `B$` back to `A$` and clear `B$`. This approach has a notable bug: if the user enters the same source index twice, the second pick will copy a blank string (since `A$(A)` was cleared at line `2040` on the first pick). There is also no bounds checking on the entered index `A`. ### Delete Routine (Option 3) Deletion at lines `3000`–`3070` shifts all elements from position `A+1` downward by one, then decrements `R1`. This is a correct in-place array compaction. After deletion, it falls through to the view routine at `5000` rather than going directly back to the menu. ### Clear and Save Option 4 (`4000`) simply executes `RUN`, which reinitialises all variables and restarts the program — an efficient way to clear all data without explicit array-zeroing code. Option 6 (`6000`) uses `INPUT F$` to obtain a filename, then `SAVE F$` to write the program and all current variable data (including the list arrays) to tape. ### Copy / Print Option Lines `2120` and `5040` both implement the same pattern: `PAUSE 40000` followed by `IF INKEY$="Z" THEN COPY`. This gives the user approximately 40 seconds to press Z to trigger a printer copy of the displayed list before returning to the menu. ## Source Code ``` 10 FAST 20 DIM A$(22,30) 30 DIM B$(22,30) 40 LET R1=0 100 FAST 110 CLS 120 PRINT AT 1,7;"% %T%H%I%N%G%S% %T%O% %D%O% " 130 PRINT AT 5,0;"TO CREATE OR ADD TO FILE;";TAB 30;1 140 PRINT AT 7,0;"TO SET PRIORITIES";TAB 30;2 150 PRINT AT 9,0;"TO DELETE FROM FILE";TAB 30;3 160 PRINT AT 11,0;"TO CLEAR FILE";TAB 30;4 170 PRINT AT 13,0;"TO SEE FILE";TAB 30;5 180 PRINT AT 15,0;"TO SAVE FILE ON TAPE";TAB 30;6 300 POKE 16418,0 310 SLOW 320 PRINT AT 22,3;"% %E%N%T%E%R% %O%N%E% %O%F% %A%B%O%V%E% ";AT 22,3;" ENTER ONE OF ABOVE " 330 LET Y$=INKEY$ 340 IF CODE Y$<29 OR CODE Y$>34 THEN GOTO 320 350 FAST 360 CLS 370 POKE 16418,2 380 GOTO VAL Y$*1000 1000 PRINT AT 18,0;"ENTER ITEMS ONE BY ONE (30 CHAR.MAX. IF YOU HAVE NO MORE TO ENTER, JUST PRESS ENTER :::" 1005 SLOW 1010 FOR N=R1+1 TO 22 1020 SCROLL 1030 PRINT N;" "; 1040 INPUT A$(N) 1050 IF A$(N,1)=" " THEN GOTO 1100 1060 PRINT A$(N) 1070 NEXT N 1100 LET R1=N-1 1110 GOTO 100 2000 FOR I=1 TO R1 2010 GOSUB 2500 2015 SLOW 2020 INPUT A 2025 FAST 2030 LET B$(I)=A$(A) 2040 LET A$(A)="" 2050 NEXT I 2060 FOR N=1 TO R1 2070 LET A$(N)=B$(N) 2080 LET B$(N)="" 2090 NEXT N 2100 GOSUB 2500 2110 PAUSE 40000 2120 IF INKEY$="Z" THEN COPY 2130 GOTO 100 2500 CLS 2510 FOR N=1 TO R1 2520 PRINT N;" ";A$(N) 2530 NEXT N 2540 RETURN 3000 FAST 3003 GOSUB 2500 3005 SLOW 3010 INPUT A 3015 FAST 3020 FOR N=A TO R1-1 3030 LET A$(N)=A$(N+1) 3040 NEXT N 3050 LET R1=R1-1 3060 CLS 3070 GOTO 5000 4000 RUN 5000 GOSUB 2500 5030 PAUSE 40000 5040 IF INKEY$="Z" THEN COPY 5050 GOTO 100 6000 PRINT AT 10,0;"ENTER NAME OF FILE, PREPARE RECORDER AND PRESS ENTER :::" 6010 INPUT F$ 6020 SAVE F$ 6030 GOTO 100 9998 SAVE "TT%D" 9999 RUN ```