diff options
| author | user <user@clank> | 2026-07-16 16:46:21 +0200 |
|---|---|---|
| committer | user <user@clank> | 2026-07-16 16:46:21 +0200 |
| commit | 0db949c3a3ab07b264c21c3a15efea6b6055be0d (patch) | |
| tree | 2d6cdae9ee9983d53838d29a6d7041d26cfab58c /src/term.asm | |
| parent | term/osk: view-offset scroll region (lossless backlog on OSK toggle) (diff) | |
| download | gbos-0db949c3a3ab07b264c21c3a15efea6b6055be0d.tar.gz gbos-0db949c3a3ab07b264c21c3a15efea6b6055be0d.tar.xz gbos-0db949c3a3ab07b264c21c3a15efea6b6055be0d.zip | |
term: compute the OSK view offset from the cursor row (keep input visible)
A fixed offset of OSK_ROWS pushed the cursor off the top of the screen when
there was little backlog (e.g. a fresh terminal: cursor at logical row 0 ->
screen row -3, hidden). Now the offset is max(0, wCurRow - 14): 0 when the
cursor is within the visible area, growing only enough to keep the cursor
line at the bottom visible row (14) once the terminal has filled past it.
compute_offset (from wOskVisible + wCurRow) runs at the top of
term_write_tilemap; cursor_down re-runs the tilemap when the cursor changes
rows while the OSK is up; osk_toggle just re-runs it. Shared OSK_DOCK
constant in gbos.inc keeps term.asm and osk.asm in sync.
Verified: fresh terminal + OSK shows the input at row 0; filling past row 14
shifts the view to hold the input at row 14; full screen + OSK puts it at
row 14; toggle on+off is still lossless.
Diffstat (limited to '')
| -rw-r--r-- | src/term.asm | 38 |
1 files changed, 29 insertions, 9 deletions
diff --git a/src/term.asm b/src/term.asm index fb6e870..64e45aa 100644 --- a/src/term.asm +++ b/src/term.asm @@ -80,10 +80,10 @@ term_init:: xor a ld [wCurRow], a ld [wCurCol], a + ld [wViewTop], a ; view starts unshifted (all 18 rows) + ld [wOskVisible], a ; OSK hidden until toggled ld a, 1 ld [wCursorOn], a - xor a - ld [wViewTop], a ; view starts unshifted (all 18 rows) ; clear the buffer (all slots) to spaces ld hl, TERM_BUF @@ -108,6 +108,7 @@ term_init:: ; line-slot tiles. Pass 1 = indices (bank 0), pass 2 = attributes (bank 1). ; ----------------------------------------------------------------------------- term_write_tilemap:: + call compute_offset xor a ld [rVBK], a ld c, 0 ; screen row @@ -494,18 +495,37 @@ cursor_down: inc a cp TROWS jr c, .ok - call term_scroll + call term_scroll ; rewrites the tilemap (offset recomputed) ld a, TROWS-1 -.ok ld [wCurRow], a ret +.ok + ld [wCurRow], a + ; the cursor changed rows; if the OSK is up the view offset may need to move + ld a, [wOskVisible] + or a + ret z + jp term_write_tilemap -; term_set_view - A = view-top offset. screen row -> logical row + A. 0 shows all -; 18 rows; OSK_ROWS shifts the view up so the cursor line clears the keyboard. -; No content is scrolled/lost - just remapped. -term_set_view:: +; compute_offset - set wViewTop so the cursor line is always on screen: 0 when +; the OSK is hidden; otherwise max(0, wCurRow - 14) so the cursor sits at the +; bottom visible row (14) once the terminal has filled past it, but stays put +; while there is little content (no shifting the cursor off the top). +compute_offset:: + ld a, [wOskVisible] + or a + jr nz, .osk + xor a ld [wViewTop], a - jp term_write_tilemap + ret +.osk + ld a, [wCurRow] + sub TROWS - OSK_DOCK - 1 ; wCurRow - 14 + jr nc, .store + xor a ; cursor above row 14 -> no shift +.store + ld [wViewTop], a + ret ; ----------------------------------------------------------------------------- ; term_putc - A = character. Print at the cursor, advance, handle \n \r \b. |
