-
-
Save r-moeritz/369282bc57e4671a4bf116c5acc4374d to your computer and use it in GitHub Desktop.
Mr. Ed: simple C64 fullscreen text editor
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
; Mr. Ed by Chris Miller Jul, 1986 | |
; *** constants *** | |
columns = 40 ; screen size | |
linesize = 250 ; max allowed | |
screenbeg = 1024+40 ; top of text scr | |
screenend = 2024 ; end of text scr | |
rows = 24 ; screenend-screenbeg/columns | |
; *** important memory *** | |
vic = $d011 | |
bkg = 53281 | |
bor = 53280 | |
rptkey = 650 | |
icrunch = $304 | |
input = $200 | |
; *** rom routines *** | |
crunchsrv = $a57c | |
getin = $ffe4 | |
print = $ffd2 | |
ready = $e37b | |
cnvrtdec = $bdcd | |
; *** variables (zero-page) *** | |
vars = $02 | |
row = $02 ; screen row 0-24 | |
col = $03 ; screen col 0-39 | |
shift = $04 ; off screen left | |
line = $05 ; text line counter | |
cnt = $07 ; display line counter | |
num = $08 ; general purpose | |
disflg = $09 ; negative=no display | |
varnum = 8 | |
; *** pointers *** | |
ptr = 61 ; utility pointer | |
top = 63 ; top line of text window | |
sob = 43 ; start of basic | |
eob = 55 ; end of basic memory | |
end = 45 ; end of text | |
txt = 253 ; current text position | |
scr = 251 ; current screen position | |
; *** beginning of code *** | |
.org $cb20 | |
lda #128 ; keys repeat | |
sta rptkey | |
lda #<crunchwdg ; wedge for basic | |
sta icrunch | |
lda #>crunchwdg | |
sta icrunch+1 | |
; entry for ed command from basic | |
start: | |
lda #9 | |
sta vic ; screen off | |
ldx #6 ; blue screen | |
stx bor | |
lda #1 ; white print | |
sta bkg | |
jsr message ; y=0 | |
.byte 5, 147, 14, 8, 158, 0 | |
stx bkg | |
lda #27 ; screen on | |
sta vic | |
topoftext: | |
lda #0 | |
ldx #varnum -1 ; init vars | |
b1: | |
sta vars,x | |
dex | |
bpl b1 | |
jsr initialize | |
jsr window | |
; main key scan loop | |
getkey: ; always return here | |
lda #>getkey | |
pha | |
lda #<getkey-1 | |
pha | |
jsr reverse | |
jsr statusline ; line, col, mem | |
b2: | |
jsr getin | |
beq b2 | |
jsr reverse ; y=0 | |
; check command keys | |
b3: | |
cmp commands,y | |
beq foundkey ; also sets carry | |
iny | |
iny | |
iny | |
cpy #commandnum | |
bcc b3 | |
bcs put ; a typing key | |
foundkey: ; jump to routine | |
lda commands+2,y | |
pha | |
lda commands+1,y | |
pha | |
rts | |
; put character in text buffer | |
put: | |
tax ; save key | |
cmp #13 | |
beq f1 | |
; see if line full | |
lda shift | |
cmp #linesize-40 | |
bne f1 | |
lda col | |
cmp #columns-1 | |
beq r1 | |
f1: | |
jsr testpos ; are we at end? | |
bcc f2 | |
jsr pshend ; make room if can | |
bcs r1 ; out of memory | |
f2: | |
cpx #13 | |
beq cret | |
ldy #0 | |
lda (txt),y | |
cmp #13 ; end of a line check | |
bne f3 | |
jsr insert | |
f3: | |
txa | |
sta (txt),y | |
jsr cnvscr | |
sta (scr),y | |
; cursor right routine | |
right: ; cursor right routine | |
jsr findeoln | |
tya | |
beq r1 ; already at end | |
inc txt | |
bne f4 | |
inc txt+1 | |
f4: | |
lda col | |
cmp #columns-1 | |
bne f5 | |
inc shift | |
jmp window | |
f5: | |
inc col | |
inc scr | |
bne r1 | |
inc scr+1 | |
r1: | |
rts | |
; cursor left routine | |
b4: | |
dec shift ; scroll left | |
jmp window | |
left: | |
lda col | |
ora shift ; check position | |
beq r2 ; cant go left | |
jsr dectxt | |
lda col | |
beq b4 | |
dec col | |
dec scr | |
lda scr | |
cmp #$ff | |
bne f6 | |
dec scr+1 | |
f6: | |
sta scr | |
r2: | |
rts | |
; carriage return handling routine | |
cret: ; handle carriage return | |
jsr findeoln | |
txa ; x=13 | |
sta (txt),y | |
; cursor down routine | |
down: | |
jsr findeoln | |
tay | |
beq r2 ; already at bottom | |
jsr unshift ; all the way left | |
jsr findeoln | |
jsr addy | |
inc line | |
bne f7 | |
inc line+1 | |
f7: | |
lda row | |
cmp #rows-1 ; last row check | |
bne f8 | |
jmp topdown ; scroll down | |
f8: | |
inc row | |
addrow: | |
lda scr | |
clc | |
adc #columns | |
bcc f9 | |
inc scr+1 | |
f9: | |
sta scr | |
rts | |
; cursor up routine | |
up: | |
lda line ; check position | |
ora line+1 ; check position | |
beq r3 ; at top already | |
dec line | |
lda line | |
cmp #$ff | |
bne f10 | |
dec line+1 | |
f10: | |
lda txt | |
sec | |
sbc shift | |
bcs f11 | |
dec txt+1 | |
f11: | |
sta txt | |
jsr unshift ; scroll far left | |
ldy #1 | |
sty num | |
dey | |
b5: | |
jsr dectxt ; go back 2 cr | |
lda (txt),y | |
beq f12 | |
cmp #13 | |
bne b5 | |
dec num | |
bpl b5 | |
f12: | |
inc txt ; then forward 1 char | |
bne f13 | |
inc txt+1 | |
f13: | |
lda row ; top of screen check | |
beq topup ; scroll up | |
dec row ; else move up row | |
lda scr | |
sec | |
sbc #columns | |
bcs f14 | |
dec scr+1 | |
f14: | |
sta scr | |
r3: | |
rts | |
; move window up | |
topup: ; move text window up line | |
ldy #$ff | |
dec top+1 | |
b6: | |
dey | |
lda (top),y | |
beq newtop | |
cmp #13 | |
bne b6 | |
newtop: ; add y to top pointer | |
sec | |
tya | |
adc top | |
bcc f15 | |
inc top+1 | |
f15: | |
sta top | |
jmp window | |
; move window down | |
topdown: ; move window down line | |
ldy #$ff | |
b7: | |
iny | |
lda (top),y | |
beq newtop | |
cmp #13 | |
bne b7 | |
beq newtop | |
; initialize for start of new line | |
unshift: | |
lda scr | |
sec | |
sbc col | |
bcs f16 | |
dec scr+1 | |
f16: | |
sta scr | |
lda txt | |
sec | |
sbc col | |
bcs f17 | |
dec txt+1 | |
f17: | |
sta txt | |
lda #0 | |
sta col | |
sta shift | |
; move text to screen window | |
window: | |
bit disflg ; is display on | |
bmi r4 ; no | |
lda #rows ; screenend-screenbeg/columns | |
sta cnt | |
lda txt+1 | |
pha ; save pointers | |
lda txt | |
pha | |
lda scr+1 | |
pha | |
lda scr | |
pha | |
lda top | |
sta txt ; init pointers | |
lda top+1 | |
sta txt+1 | |
jsr initscr | |
; process next line of text | |
newline: | |
ldy #$ff | |
b8: | |
jsr testeoln | |
beq lineblank | |
cpy shift ; handle right scroll | |
bcc b8 | |
clc | |
jsr addy+1 ; update txt ptr | |
ldy #$ff | |
b9: | |
jsr testeoln | |
beq restblank ; end of line | |
jsr cnvscr ; convert ascii code | |
sta (scr),y ; put on screen | |
cpy #columns-1 | |
bcc b9 | |
jsr findeoln+2 ; dont init .y | |
jsr addy ; point next line | |
addscr: | |
jsr addrow ; to screen ptr | |
dec cnt | |
bne newline | |
fini: | |
pla | |
sta scr ; restore ptrs | |
pla | |
sta scr+1 | |
pla | |
sta txt | |
pla | |
sta txt+1 | |
r4: | |
rts | |
lineblank: | |
jsr addy | |
ldy #0 | |
beq f18 | |
restblank: | |
jsr addy | |
f18: | |
lda #' ' | |
b10: | |
sta (scr),y | |
iny | |
cpy #columns | |
bcc b10 | |
bcs addscr ; start next line | |
addy: ; add y to text ptr | |
sec | |
tya | |
adc txt | |
bcc f19 | |
inc txt+1 | |
f19: | |
sta txt | |
rts | |
dectxt: ; back up text ptr | |
dec txt | |
lda txt | |
cmp #$ff | |
bne f20 | |
dec txt+1 | |
f20: | |
rts | |
; convert ascii to screen code | |
cnvscr: | |
eor #128 | |
bpl f21 | |
eor #128 | |
cmp #64 | |
bcc f21 | |
eor #64 | |
f21: | |
rts | |
reverse: ; reverse cursor char | |
pha | |
ldy #0 | |
lda (scr),y | |
eor #$80 | |
sta (scr),y | |
pla | |
rts | |
testpos: ; test position in text | |
lda txt+1 | |
cmp end+1 | |
bcc f22 | |
bne f22 | |
lda txt | |
cmp end | |
f22: | |
rts | |
insert: ; insert one space | |
lda end+1 | |
pha | |
lda end | |
pha | |
ldy #0 | |
b11: | |
lda (end),y | |
iny | |
sta (end),y | |
dey | |
dec end | |
lda end | |
cmp #$ff | |
bne f23 | |
dec end+1 | |
f23: | |
jsr testpos | |
bcc b11 | |
beq b11 | |
pla | |
sta end | |
pla | |
sta end+1 | |
pshend: ; bump end ptr up | |
lda end+1 | |
cmp eob+1 | |
bcc f24 | |
lda end | |
cmp eob | |
bcs r5 | |
f24: | |
inc end | |
bne r5 | |
inc end+1 | |
r5: | |
rts | |
deletechr: | |
lda #1 | |
sta num | |
jsr left | |
delete: ; number of chars in num | |
lda txt+1 | |
pha | |
lda txt | |
pha | |
b12: | |
ldy num | |
lda (txt),y | |
ldy #0 | |
sta (txt),y | |
inc txt | |
bne f25 | |
inc txt+1 | |
f25: | |
jsr testpos | |
bcc b12 | |
beq b12 | |
pla | |
sta txt | |
pla | |
sta txt+1 | |
jsr testpos | |
bcs f26 | |
lda end | |
sec | |
sbc num | |
sta end | |
bcs f26 | |
dec end+1 | |
f26: | |
jmp window | |
insertln: ; insert chr$(13) | |
jsr insert | |
lda #13 | |
bne f27 | |
insrtspc: ; insert blank | |
jsr insert | |
lda #' ' | |
f27: | |
sta (txt),y | |
jmp window | |
deleteln: ; delete line | |
ror disflg ; display off | |
jsr findeoln | |
tya | |
bne f28 | |
iny | |
f28: | |
sty num | |
jsr delete | |
jmp setwindow | |
pagedown: ; long scroll down | |
ror disflg ; no display | |
ldx #rows-1 ; 23 lines | |
b13: | |
jsr down | |
dex | |
bne b13 | |
beq setwindow | |
pageup: ; long scroll up | |
ror disflg ; no display | |
ldx #rows-1 ; 24 lines | |
b14: | |
jsr up | |
dex | |
bne b14 | |
beq setwindow | |
pageleft: | |
ror disflg | |
ldx #columns-1 | |
b15: | |
jsr left | |
dex | |
bne b15 | |
beq setwindow | |
; scroll sideways to end of line | |
pageright: | |
ror disflg ; no display | |
ldx #columns-1 | |
b16: | |
jsr right | |
dex | |
bne b16 | |
setwindow: | |
lsr disflg | |
jmp window ; display | |
; set y=distance to text eol | |
findeoln: | |
ldy #$ff | |
b17: | |
jsr testeoln | |
bne b17 | |
rts | |
testeoln: | |
iny | |
cpy #$ff | |
beq f29 | |
lda (txt),y | |
beq f29 | |
cmp #13 | |
f29: | |
rts | |
initialize: | |
lda sob | |
ldx sob+1 | |
clc | |
adc #2 | |
bcc f30 | |
inx | |
f30: | |
sta txt | |
sta top | |
stx txt+1 | |
stx top+1 | |
lda end | |
sta ptr | |
lda end+1 | |
sta ptr+1 | |
ldy #0 ; fill zeros | |
tya | |
b18: | |
sta (ptr),y | |
inc ptr | |
bne f31 | |
inc ptr+1 | |
f31: | |
ldx ptr+1 | |
cpx eob+1 | |
bcc b18 | |
ldx ptr | |
cpx eob | |
bcc b18 | |
initscr: | |
lda #<screenbeg | |
sta scr | |
lda #>screenbeg | |
sta scr+1 | |
rts | |
statusline: | |
jsr message | |
.byte 19 ; (home) | |
.asciiz "COLUMN:" | |
lda shift | |
sec | |
adc col | |
tax | |
tya ; =0 | |
jsr cnvrtdec | |
jsr message | |
.asciiz " LINE:" | |
ldy line+1 | |
ldx line | |
inx | |
bne f32 | |
iny | |
f32: | |
tya | |
jsr cnvrtdec | |
jsr message | |
.asciiz " FREE:" | |
lda eob+1 | |
sec | |
sbc end+1 | |
tay | |
lda eob | |
sbc end | |
tax | |
tya | |
jsr cnvrtdec | |
jsr message | |
.asciiz " " ; 3 (spaces) | |
rts | |
; print in source messages | |
message: | |
ldy #0 | |
pla | |
sta ptr | |
pla | |
sta ptr+1 | |
b19: | |
inc ptr | |
bne f33 | |
inc ptr+1 | |
f33: | |
lda (ptr),y | |
beq f34 | |
jsr print | |
bne b19 | |
f34: | |
lda ptr+1 | |
pha | |
lda ptr | |
pha | |
rts | |
; wedge for ed command in basic | |
crunchwdg: ; wedge for ed command | |
lda input | |
cmp #'e' | |
bne f35 | |
lda input+1 | |
cmp #'d' | |
bne f35 | |
jmp start ; call mr. ed | |
f35: | |
jmp crunchsrv ; pass to basic | |
; command entries | |
commands: | |
.byte 148 | |
.word insrtspc-1 ; inst | |
.byte 20 | |
.word deletechr-1 ; del | |
.byte 133 | |
.word deleteln-1 ; f1 | |
.byte 137 | |
.word insertln-1 ; f2 | |
.byte 134 | |
.word pagedown-1 ; f3 | |
.byte 138 | |
.word pageup-1 ; f4 | |
.byte 135 | |
.word pageright-1 ; f5 | |
.byte 139 | |
.word pageleft-1 ; f6 | |
.byte 3 | |
.word ready-1 ; run stop | |
.byte 17 | |
.word down-1 ; (cursor down) | |
.byte 145 | |
.word up-1 ; (cursor up) | |
.byte 157 | |
.word left-1 ; (cursor left) | |
.byte 29 | |
.word right-1 ; (cursor right) | |
commandnum = 39 |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment