-
Notifications
You must be signed in to change notification settings - Fork 4
/
Copy pathTED.FTH
344 lines (293 loc) · 6.8 KB
/
TED.FTH
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
\ TED.FTH TED - Text EDitor
\ Author: Robert van Engelen
.( Loading TED...)
ANEW _TED_
DECIMAL
VOCABULARY TEDDY
TEDDY DEFINITIONS
0 VALUE file.id
0 VALUE file.len
14 BUFFER: file.name
0 VALUE text.size
0 VALUE text.pos
0 VALUE text.row
0 VALUE text.col
\ -----------
\ LOAD & SAVE
\ -----------
: text HERE 40 + ;
: file file.name file.len ;
: >file ( c-addr u -- )
-TRAILING
\ get the drive character, if any, assign it, remove it
DUP 2 U> IF
OVER 1+ C@ ': = IF
NEXT-CHAR DRIVE C!
1 /STRING
THEN
THEN
\ save the file name length
12 UMIN DUP TO file.len
\ save the file name string
file.name SWAP CMOVE
\ add .FTH extension if no extension present
file 8 MIN S" ." SEARCH NIP NIP 0= IF
file.len 8 UMIN TO file.len
S" .FTH" file + SWAP CMOVE 4 +TO file.len
THEN
;
S" WORKFILE.FTH" >file
: parse-file BL PARSE-WORD ?DUP IF >file ELSE DROP THEN ;
: ?fits ( size -- ) DUP UNUSED 42 - U> ABORT" file too large" ;
: ?size file.id FILE-SIZE THROW D>S ?fits DUP TO text.size ;
: gulp text ?size file.id READ-FILE THROW TO text.size ;
: spit text text.size file.id WRITE-FILE THROW ;
: close file.id ?DUP IF CLOSE-FILE DROP 0 TO file.id THEN ;
: lf+! ( pos -- ) text + $0a SWAP C! 1 +TO text.size ;
: load-file
close
file R/O OPEN-FILE IF
DROP
0 TO text.size
ELSE
TO file.id
CR ." Loading " file TYPE
['] gulp CATCH
close
THROW
THEN
\ trim trailing control characters, if any
text.size
BEGIN
DUP WHILE
DUP text + 1- C@ BL U< WHILE
1-
REPEAT THEN
DUP TO text.size
lf+!
;
: save-file
BEGIN
PAGE ." Saving " file TYPE
file W/O CREATE-FILE ?DUP WHILE
CR ." Error " . ." try a different file"
file 14 SWAP 0 0 EDIT >file
REPEAT
TO file.id
['] spit CATCH
close
THROW
;
: norm-file
text text.size
BEGIN
?DUP WHILE
NEXT-CHAR DUP BL U< IF
CASE
$0a OF ENDOF
$0d OF
OVER C@ $0a <> OVER 0= OR IF
OVER $0a SWAP 1- C!
THEN
ENDOF
BL 3 PICK 1- C!
ENDCASE
ELSE
DROP
THEN
REPEAT
DROP
;
\ ------
\ CURSOR
\ ------
: home 0 TO text.pos 0 TO text.row ;
: len ( -- u )
text.pos
BEGIN
DUP text + C@ DUP $0a <> SWAP $0d <> AND WHILE
1+
REPEAT
text.pos -
;
: crlf+ ( pos -- pos )
DUP text + C@ CASE
$0a OF 1+ ENDOF
$0d OF 2+ ENDOF
ENDCASE
;
: up? ( -- flag )
FALSE
text.pos IF
text.pos 1-
BEGIN
DUP WHILE
DUP text + 1- C@ $0a <> WHILE
1-
REPEAT THEN
TO text.pos
-1 +TO text.row
INVERT
THEN
;
: down? ( -- flag )
text.pos len + crlf+ DUP text.size U< IF
TO text.pos
1 +TO text.row
TRUE
ELSE
DROP
FALSE
THEN
;
\ ---------
\ EDIT LINE
\ ---------
0 VALUE temp.len
PAD CONSTANT temp.buf
255 CONSTANT temp.max
: alert 100 MS 195 500 BEEP ;
: line ( -- c-addr u ) text text.pos + len ;
: temp ( -- buf len ) temp.buf temp.len ;
: line>temp line temp.max UMIN DUP TO temp.len temp.buf SWAP CMOVE ;
: temp>line
temp.len len - \ delta
DUP \ delta delta
text.size \ delta delta oldsize
+ \ delta newsize
DUP UNUSED 42 - U> IF
\ out of memory, cannot update line
2DROP
alert
ELSE
\ update text.size and move the rest of text afer the line
DUP TO text.size \ delta newsize
text.pos temp.len + - \ delta newsize-(pos+len)=restsize
SWAP \ restsize delta
text text.pos + \ restsize delta text+pos
temp.len + \ restsize delta text+to
TUCK SWAP - \ restsize text+to text+from
SWAP ROT \ text+from text+to restsize
\ move text+from to text+to, if text+from<>text+to
MOVE
\ insert updated line
temp text text.pos + SWAP CMOVE
THEN
;
: edit-line
0 0 AT-XY
line>temp
temp \ buf len
temp.max \ buf len max
SWAP \ buf max len
text.col \ buf max len text.col
OVER UMIN 0 EDIT TO temp.len DROP
temp>line
;
\ -------
\ DISPLAY
\ -------
: disp
PAGE
text.pos \ save old pos
text.row \ save old row
160 \ oldpos oldrow num
BEGIN
text text.pos + len \ num text+pos len
2 PICK UMIN \ num text+pos min(num,len)
ROT OVER DUP 0<> + 40 / 1+ 40 * - \ text+pos min(num,len) num-40*floor(min-1/40+1)
-ROT \ num-40*floor(min-/40+1) text+pos min
TYPE CR \ num-40*floor(min-/40+1)
DUP 0> WHILE
down? WHILE
REPEAT THEN
0 ?DO '~ EMIT CR 40 +LOOP
TO text.row \ restore row
TO text.pos \ restore pos
0 4 AT-XY
;
\ ---------
\ EDIT FILE
\ ---------
: new
text.size UNUSED 42 - U> IF
alert
ELSE
text text.pos + \ text+pos
DUP 1+ \ text+pos text+pos+1
text.size text.pos - \ text+pos text+pos+1 restsize
CMOVE>
text.pos lf+!
THEN
;
: cut
line>temp
text.pos \ oldpos
DUP len + crlf+ \ oldpos downpos
text.size OVER - \ oldpos downpos movesize
-ROT \ movesize oldpos downpos
2DUP - +TO text.size
text + SWAP text + ROT \ text+downpos text+oldpos movesize
CMOVE
text.pos text.size U< INVERT IF
text.size lf+!
THEN
;
: copy line>temp ;
: paste new temp>line ;
: insert new disp 0 TO text.col edit-line ;
: enter
down? INVERT IF
text.size UNUSED 42 - U> INVERT IF
text.size lf+!
THEN
down? DROP
THEN
insert
;
: menu-file 6 0 AT-XY file 14 SWAP DUP 0 EDIT >file ;
: menu
PAGE
." File: " file REVERSE-TYPE text.size
19 0 AT-XY DEC. 25 0 AT-XY ." [CCE] exit/save" CR
." [SPC] insert before [ENTER] insert after" CR
." [DEL] cut [STO] copy [ANS]/[RCL] paste" CR
." [UP]/[DN] scroll [LFT]/[RGT] edit line" CR
EKEY CASE
$0c ( CCE ) OF RDROP EXIT ENDOF
$1c ( RIGHT ) OF menu-file ENDOF
$1d ( LEFT ) OF menu-file ENDOF
$-04 ( OFF ) OF POWER-OFF ENDOF
ENDCASE
;
: edit-file
home
BEGIN
disp
EKEY CASE
$0c ( CCE ) OF EXIT ENDOF
$0d ( ENTER ) OF enter ENDOF
$1c ( RIGHT ) OF 0 TO text.col edit-line ENDOF
$1d ( LEFT ) OF -1 TO text.col edit-line ENDOF
$1e ( UP ) OF up? DROP ENDOF
$1f ( DOWN ) OF down? DROP ENDOF
$20 ( SPACE ) OF insert ENDOF
$7f ( DEL ) OF cut ENDOF
$-04 ( OFF ) OF POWER-OFF ENDOF
$-06 ( MENU ) OF menu ENDOF
$-90 ( RCL ) OF paste ENDOF
$-91 ( STO ) OF copy ENDOF
alert
ENDCASE
AGAIN
;
: start ( "name" -- ) 40 XMAX! 4 YMAX! parse-file load-file norm-file ;
: resume edit-file save-file ;
\ -----
\ FORTH
\ -----
FORTH DEFINITIONS
: TED [ TEDDY ] start resume [ FORTH ] ;
: TEDI TED [ TEDDY ] file [ FORTH ] INCLUDED ;
: TED-RESUME [ TEDDY ] resume [ FORTH ] ;
: TEDI-RESUME TED-RESUME [ TEDDY ] file [ FORTH ] INCLUDED ;