mirror of
https://github.com/uffejakobsen/acme.git
synced 2024-11-29 19:50:12 +00:00
e8df8af5c7
git-svn-id: https://svn.code.sf.net/p/acme-crossass/code-0/trunk@324 4df02467-bbd4-4a76-a152-e7ce94205b78
241 lines
8.7 KiB
Plaintext
241 lines
8.7 KiB
Plaintext
;ACME 0.95
|
|
|
|
!ifdef lib_cbm_c128_vdc_a !eof
|
|
lib_cbm_c128_vdc_a = 1
|
|
|
|
; there are three different versions of the C128's Video Display Controller:
|
|
; v0: VDC 8563 R7A in C128 and C128-D
|
|
; v1: VDC 8563 R8/R9 in C128 and C128-D
|
|
; v2: VDC 8568 in C128-DCR
|
|
; 8563 and 8568 have different pinouts, so do not try to use one of them on a
|
|
; board intended for the other!
|
|
|
|
|
|
; hardware differences:
|
|
|
|
; the 8563 uses external circuitry to convert RGBIHV to monochrome/luminance.
|
|
; the 8568 does a part of this internally and therefore needs fewer external
|
|
; components.
|
|
|
|
; the 8568 has an additional register (r37) to change sync polarities.
|
|
|
|
|
|
; software differences:
|
|
|
|
; the horizontal scroll bits of r25 differ between v0 and v1/v2: in v0, set these
|
|
; bits to zero. in v1/v2, set these bits to the same value as bits4-7 of r22.
|
|
; the additional register r37 can be ignored (as the C128 kernal does).
|
|
|
|
|
|
; access macros:
|
|
|
|
!macro vdc_lda {
|
|
- bit vdc_state
|
|
bpl -
|
|
lda vdc_data
|
|
}
|
|
|
|
!macro vdc_sta {
|
|
- bit vdc_state
|
|
bpl -
|
|
sta vdc_data
|
|
}
|
|
|
|
!macro vdc_ldx {
|
|
- bit vdc_state
|
|
bpl -
|
|
ldx vdc_data
|
|
}
|
|
|
|
!macro vdc_stx {
|
|
- bit vdc_state
|
|
bpl -
|
|
stx vdc_data
|
|
}
|
|
|
|
!macro vdc_ldy {
|
|
- bit vdc_state
|
|
bpl -
|
|
ldy vdc_data
|
|
}
|
|
|
|
!macro vdc_sty {
|
|
- bit vdc_state
|
|
bpl -
|
|
sty vdc_data
|
|
}
|
|
|
|
|
|
; color codes:
|
|
|
|
; These are the colors officially available on the C128 - the same names as if
|
|
; using a C64's VIC, but different codes of course.
|
|
|
|
; color name RGBI VIC equivalent
|
|
vdccolor_BLACK = %.... ; 0
|
|
vdccolor_WHITE = %#### ; 15
|
|
vdccolor_RED = %#... ; 8
|
|
vdccolor_CYAN = %.### ; 7
|
|
vdccolor_PURPLE = %#.## ; 11
|
|
vdccolor_GREEN = %.#.. ; 4
|
|
vdccolor_BLUE = %..#. ; 2
|
|
vdccolor_YELLOW = %##.# ; 13
|
|
vdccolor_ORANGE = %#.#. ; 10 (on VDC, this is in fact a dark shade of purple)
|
|
vdccolor_BROWN = %##.. ; 12
|
|
vdccolor_LRED = %#..# ; 9
|
|
vdccolor_GRAY1 = %.##. ; 6 (on VDC, this is in fact a dark shade of cyan)
|
|
vdccolor_GRAY2 = %...# ; 1 (this is almost, but not quite, entirely black)
|
|
vdccolor_LGREEN = %.#.# ; 5
|
|
vdccolor_LBLUE = %..## ; 3
|
|
vdccolor_GRAY3 = %###. ; 14
|
|
|
|
; The following alternative names are much easier to remember when you're used
|
|
; to writing programs for the VDC: There are eight main colors, and each one is
|
|
; available in a light and a dark shade - even black and white!
|
|
|
|
; primary colors RGBI code
|
|
vdccolor_DRED = %#...
|
|
vdccolor_DGREEN = %.#..
|
|
vdccolor_DBLUE = %..#.
|
|
vdccolor_LRED = %#..#
|
|
vdccolor_LGREEN = %.#.#
|
|
vdccolor_LBLUE = %..##
|
|
|
|
; secondary colors RGBI code
|
|
vdccolor_LCYAN = %.###
|
|
vdccolor_LMAGENTA = %#.##
|
|
vdccolor_LYELLOW = %##.#
|
|
vdccolor_DCYAN = %.##.
|
|
vdccolor_DMAGENTA = %#.#.
|
|
vdccolor_DYELLOW = %##..
|
|
|
|
; black & white RGBI code
|
|
vdccolor_DBLACK = %....
|
|
vdccolor_LBLACK = %...#
|
|
vdccolor_LWHITE = %####
|
|
vdccolor_DWHITE = %###.
|
|
|
|
; if you don't like the concept of shaded black/white, then use these:
|
|
|
|
; gray level RGBI code
|
|
vdccolor_BLACK = %.... ; "dark black" => "black"
|
|
vdccolor_DGRAY = %...# ; "light black" => "dark grey"
|
|
vdccolor_LGRAY = %###. ; "dark white" => "light grey"
|
|
vdccolor_WHITE = %#### ; "light white" => "white"
|
|
|
|
|
|
; attribute flags (2rufRGBI)
|
|
vdcattr_2ND = %#....... ; second character set
|
|
vdcattr_REVS = %.#...... ; reverse mode
|
|
vdcattr_UL = %..#..... ; underline
|
|
vdcattr_FLASH = %...#.... ; flash
|
|
vdcattr_R = %....#... ; red
|
|
vdcattr_G = %.....#.. ; green
|
|
vdcattr_B = %......#. ; blue
|
|
vdcattr_I = %.......# ; intensity
|
|
|
|
|
|
!address {
|
|
; direct registers
|
|
vdc_state = $d600 ; READING this location yields status flags, see below
|
|
vdc_reg = $d600 ; WRITING this location selects an indirect register
|
|
vdc_data = $d601 ; data of selected indirect register
|
|
}
|
|
; status flags in vdc_state:
|
|
vdcstate_READY = %#....... ; RAM access is finished
|
|
vdcstate_LIGHTPEN = %.#...... ; light pen has been activated
|
|
vdcstate_IN_BORDER = %..#..... ; electron beam is in upper or lower border
|
|
vdcstate_VERSIONMASK = %...##### ; vdc version (0, 1 or 2)
|
|
|
|
|
|
; indirect registers (default value, see $e179 in C128 kernal)
|
|
vdcr_htotal = 0 ; 126 (127 for PAL, depends on kernal version) characters per line, minus one
|
|
vdcr_columns = 1 ; 80 characters per line, actually displayed
|
|
vdcr_hdisp = 1
|
|
vdcr_hsync_pos = 2 ; 102 character position to send horizontal sync in
|
|
vdcr_syncwidth = 3 ; $49 4b vertical, 4b horizontal
|
|
vdcr_vtotal = 4 ; 32 (39 or 38 for PAL, depends on kernal version) character lines per screen, minus one
|
|
vdcr_vadjust = 5 ; 0 additional scan lines per screen (to fix timings)
|
|
vdcr_lines = 6 ; 25 character lines per screen, actually displayed
|
|
vdcr_vdisp = 6
|
|
vdcr_vsync_pos = 7 ; 29 (32 for PAL) character line to send vertical sync in
|
|
vdcr_interlace = 8 ; 0 interlace mode (0=2=std, 1=jitter, 3=interlace)
|
|
vdcr_charheight_total = 9 ; 7 5b total, minus one
|
|
vdcr_crsr_start = 10 ; $20 2b mode, 5b scanline (top line of cursor)
|
|
vdcr_CRSRSTART_MODE_MASK = %.##.....
|
|
; vdcr_CRSRSTART_MODE_FIXED = %........ ; fixed cursor
|
|
vdcr_CRSRSTART_MODE_OFF = %..#..... ; invisible
|
|
vdcr_CRSRSTART_MODE_FAST = %.#...... ; flashing with 1/16 of refresh freq
|
|
vdcr_CRSRSTART_MODE_SLOW = %.##..... ; flashing with 1/32 of refresh freq
|
|
vdcr_crsr_end = 11 ; 7 5b scanline (bottom line of cursor, plus 1, so should be 8 instead of 7!)
|
|
vdcr_display_hi = 12 ; 0 RAM address of display buffer,
|
|
vdcr_display_lo = 13 ; 0 see "hardscroll" notes below
|
|
vdcr_crsr_hi = 14 ; 0 RAM address of cursor
|
|
vdcr_crsr_lo = 15 ; 0
|
|
vdcr_lp_y = 16 ; -- y position of light pen (lines, plus 1)
|
|
vdcr_lp_x = 17 ; -- x position of light pen (characters, plus 8)
|
|
vdcr_ram_hi = 18 ; -- RAM address of register 31 (reading/writing r31
|
|
vdcr_ram_lo = 19 ; -- automatically increments this address)
|
|
vdcr_attr_hi = 20 ; $08 RAM address of attribute buffer,
|
|
vdcr_attr_lo = 21 ; $00 see "hardscroll" notes below
|
|
vdcr_charwidth = 22 ; $78 4b total minus one, 4b displayed
|
|
vdcr_charheight_disp = 23 ; 8 5b displayed, minus one (so 7 would suffice)
|
|
vdcr_control_v = 24 ; $20 vertical scroll and much other stuff
|
|
vdcr_CONTROLV_BLOCKMODE_MASK = %#.......
|
|
; vdcr_CONTROLV_BLOCKMODE_WRITE = %........ ; writing to register 30 starts block write
|
|
vdcr_CONTROLV_BLOCKMODE_COPY = %#....... ; writing to register 30 starts block copy
|
|
vdcr_CONTROLV_REVERSESCREEN = %.#......
|
|
vdcr_CONTROLV_FLASHFREQ_MASK = %..#.....
|
|
; vdcr_CONTROLV_FLASHFREQ_FAST = %........
|
|
vdcr_CONTROLV_FLASHFREQ_SLOW = %..#.....
|
|
vdcr_CONTROLV_UPSCROLL_MASK = %...#####
|
|
vdcr_control_h = 25 ; $47 ($40 for vdc version 0) horizontal scroll and much other stuff
|
|
vdcr_CONTROLH_MODE_MASK = %#.......
|
|
; vdcr_CONTROLH_MODE_TEXT = %........
|
|
vdcr_CONTROLH_MODE_BITMAP = %#.......
|
|
vdcr_CONTROLH_ATTRIBUTES_MASK = %.#......
|
|
; vdcr_CONTROLH_ATTRIBUTES_OFF = %........
|
|
vdcr_CONTROLH_ATTRIBUTES_ON = %.#......
|
|
vdcr_CONTROLH_SEMIGRAPHICS = %..#.....
|
|
vdcr_CONTROLH_PIXELWIDTH_MASK = %...#....
|
|
; vdcr_CONTROLH_PIXELWIDTH_NARROW = %........
|
|
vdcr_CONTROLH_PIXELWIDTH_WIDE = %...#....
|
|
vdcr_CONTROLH_RIGHTSCROLL_MASK = %....####
|
|
vdcr_color = 26 ; $f0 4b foreground, 4b background
|
|
vdcr_COLOR_FOREGROUND_MASK = %####.... ; only used if attributes are off (see bit 6 of reg 25)
|
|
vdcr_COLOR_BACKGROUND_MASK = %....####
|
|
vdcr_row_inc = 27 ; 0 address increment per row
|
|
vdcr_charset = 28 ; $20 3b charset pointer, 1b RAM type, 4b unused
|
|
vdcr_CHARSET_ADRESS_MASK = %###.....
|
|
vdcr_CHARSET_RAMTYPE_MASK = %...#....
|
|
; vdcr_CHARSET_RAMTYPE_16K = %........
|
|
vdcr_CHARSET_RAMTYPE_64K = %...#....
|
|
vdcr_underline = 29 ; 7 5b scanline
|
|
vdcr_cycles = 30 ; -- number of write- or copy-cycles. 0 means 256.
|
|
vdcr_access = 31 ; -- contents of RAM selected by registers 18/19
|
|
vdcr_source_hi = 32 ; -- start address for block copy (block copying
|
|
vdcr_source_lo = 33 ; -- automatically increments this address)
|
|
vdcr_enable_start = 34 ; 125 column to enable display in (6 is left of text)
|
|
vdcr_enable_end = 35 ; 100 column to disable display in (86 is right of text)
|
|
vdcr_dram_refresh = 36 ; 5 RAM refresh cycles per line (lower 4 bits)
|
|
vdcr_sync_polarity = 37 ; -- only in VDC 8568
|
|
vdcr_HSYNC_POLARITY = %#.......
|
|
vdcr_VSYNC_POLARITY = %.#......
|
|
|
|
!address {
|
|
; the c128 ROMs contain look-up tables to convert vic color values to vdc color
|
|
; values and vice-versa:
|
|
; rom4_* needs "low rom area" enabled ($4000..$7fff)
|
|
; rom8_* needs "middle rom area" enabled ($8000..$bfff)
|
|
; romc_* needs "high rom area" enabled ($c000..$ffff)
|
|
rom4_vic_to_vdc_color_table = $6a4c ; 00 0f 08 07 0b 04 02 0d 0a 0c 09 06 01 05 03 0e
|
|
rom8_vdc_to_vic_color_table = $81f3 ; 00 0c 06 0e 05 0d 0b 03 02 0a 08 04 09 07 0f 01
|
|
romc_vic_to_vdc_color_table = $ce5c ; 00 0f 08 07 0b 04 02 0d 0a 0c 09 06 01 05 03 0e
|
|
}
|
|
|
|
; "hardscroll" notes:
|
|
; the vdc seems to read the values from registers 12/13/20/21 (screen ram and
|
|
; attribute ram) at the _end_ of the display window, so if you change these
|
|
; registers in the lower border, the next frame will still use the old values.
|
|
; this is important if you want to combine hardscroll and softscroll.
|