The C64 OS Programmer's Guide is being written

This guide is being written and released and few chapters at a time. If a chapter seems to be empty, or if you click a chapter in the table of contents but it loads up Chapter 1, that's mostly likely because the chapter you've clicked doesn't exist yet.

Discussion of development topics are on-going about what to put in this guide. The discusssions are happening in the C64 OS Community Support Discord server, available to licensed C64 OS users.

C64 OS PROGRAMMER'S GUIDE


Chapter 4: Using the KERNAL → Input (module)

Pointer Control

These routines allow for showing and hiding the mouse pointer. They can be used to kill the mouse pointer completely, stopping pointer events from being queued, and can be used to bring the pointer back, optionally reloading the sprites into memory.

initmouse

Purpose Enable the mouse pointer, optionally reload the sprites from disk.
Module offset 0
Communication registers Status
Stack requirements 12 bytes
Zero page usage $1c, $1d
Registers affected A, X, Y
Input parameters C → CLR to load from disk
C → SET to just enable without load
Output parameters None

Description: If called with the carry set, it skips loading the sprites from disk. It enables the sprites, resets their bounds, toggles a flag in the musflgs workspace variable defined by //os/s/:input.s and resets the acceleration to the value defined by settings. If called with the carry clear, it does everything described above but it also loads the selected pointer sprites from //os/pointers/. Stash use is only 4 bytes if not loading sprites from disk.

killmouse

Purpose Disable the mouse pointer, stop scanning the mouse and queueing events.
Module offset 3
Communication registers Status
Stack requirements 5 bytes
Zero page usage None
Registers affected A
Input parameters None
Output parameters C ← Set if the mouse was killed
C ← Clear if the mouse was already off

Description: Use this routine to turn off the mouse pointer sprites, which clears a flag in the musflgs workspace variable defined by //os/s/:input.s and stops calling the driver to poll the hardware. It therefore also stops queueing new mouse events. The carry result indicates if the mouse was already off when this call was made. This allows code that temporarily disables the mouse to know whether it should call initmouse when it's finished. If the mouse was already off, the code that tried to turn it off should leave it off.

hidemouse

Purpose Turn off the mouse pointer sprites.
Module offset 6
Communication registers None
Stack requirements 8 bytes
Zero page usage None
Registers affected None
Input parameters None
Output parameters C ← Always returns set, without meaning anything.

Description: Hiding the mouse is a much lighter-weight way of disabling the mouse than killmouse. Killmouse calls hidemouse as part of its internal implementation. Hidemouse only temporarily disables the mouse pointer sprites, but the input driver is still being polled, and the mouse pointer automatically gets re-enabled on any mouse activity.

This routine is used to very temporarily hide the pointer. For example, when typing into a text field, the TKInput class calls hidemouse so the pointer does not obscure the text in the field. If a video or animation began, and the mouse pointer would be distractingly displayed above it, that code could call hidemouse to remove the distraction. The pointer automatically reappears the moment the user moves the mouse.

mouserc

Purpose Convert a mouse event from pixel precision to text row and column precision.
Module offset 9
Communication registers A, X, Y
Stack requirements 3 bytes
Zero page usage None
Registers affected X, Y
Input parameters A → Mouse event flags
X → X Position (in pixels)
Y → Y Position (in pixels)
Output parameters A ← Mouse event flags (unchanged)
X ← X Position (in text columns)
Y ← Y Position (in text rows)

Description: The input parameters to this routine are exactly the output parameters from readmouse. A, X and Y hold the 3 bytes that constitute a low-level mouse event. Call this routine with the mouse event in A, X and Y, and the pixel coordinates stored in X and Y (plus a single high bit in the mouse event flags) are converted into text row and column coordinates, and returned in X and Y.


Event Queue

The following series of 6 routines are used for managing the low-level input event queue. The read… routines can be called as many times as needed. They always return the event from the top of their respective queue without affecting the queue. The deq… routines are not called by typical high-level software, they are called automatically at the end of the main event loop to pop the top events of their queues.

readmouse

Purpose Access the current mouse event.
Module offset 12
Communication registers A, X, Y
Stack requirements 2 bytes
Zero page usage None
Registers affected A, X, Y
Input parameters None
Output parameters C ← Set if there is no event queued
A ← Mouse event flags
X ← X Position (in pixels)
Y ← Y Position (in pixels)

Description: Call this routine to get the current mouse event in the A, X and Y registers. If the carry comes back set, there is no queued mouse event and only X register is affected. If there is no event, the X register is set to zero, A and Y are unaffected.

Under normal circumstances, you will not poll this routine. The main event loop messages an Application or a Utility by calling the mouse event handling routine specified by the screen layer structure. When that event handling routine is called, it is because an event exists. Readmouse can then be called as many times as necessary to handle the event. The main event loop itself uses readmouse and checks the state of the carry to determine when an event is available to be dispatched.

deqmouse

Purpose Dequeue, or requeue, the current mouse event.
Module offset 15
Communication registers A, X, Y
Stack requirements 2 bytes
Zero page usage None
Registers affected A, X
Input parameters C → Set to requeue the current event.
A → Mouse event flags
X → X Position (in pixels)
Y → Y Position (in pixels)
Output parameters None

Description: This is routine is called to dequeue the current mouse event from the mouse events queue. All other mouse events are bumped up one position in the queue. The dequeue the carry must be clear when this routine is called. The A and X registers are modified, the Y register is not. This routine is called internally by the main event loop, and typically does not need to be called by high-level software.

Alternatively, this routine can be used to requeue a modified version of this event. If the carry is set when this routine is called, A, X and Y must hold the mouse event to replace the current mouse event on the queue. When requeuing, A, X and Y are unmodified. Low-level mouse events are propagated from the highest screen layer through to the lowest screen layer. A screenlayer can analyze the event, modify it, and requeue it, before allowing it to be propagated to the next screen layer. This is how the menu layer prevents a Utility's title bar from being dragged under the menu or status bar.

readkcmd

Purpose Access the current keyboard command event.
Module offset 18
Communication registers A, Y
Stack requirements 2 bytes
Zero page usage None
Registers affected A, X, Y
Input parameters None
Output parameters C ← Set if there is no event queued
A ← PETSCII value
Y ← Key command event flags

Description: Call this routine to get the current key command event in the A and Y registers. If the carry comes back set, there is no queued key command event and only the X register is affected. If there is no event, the X register is set to zero, A and Y are unaffected.

Under normal circumstances, you will not poll this routine. The main event loop messages an Application or a Utility by calling the key command event handling routine specified by the screen layer structure. When that event handling routine is called, it is because an event exists. Readkcmd can then be called as many times as necessary to handle the event. The main event loop itself uses readkcmd and checks the state of the carry to determine when an event is available to be dispatched.

deqkcmd

Purpose Dequeue the current key command event.
Module offset 21
Communication registers None
Stack requirements 2 bytes
Zero page usage None
Registers affected A, X
Input parameters None
Output parameters None

Description: This is routine is called to dequeue the current key command event from the key command events queue. All other key command events are bumped up one position in the queue. This routine takes no input parameters and returns nothing. This routine can be called whether there is a queued event or not. This routine is called internally by the main event loop, and typically does not need to be called by high-level software.

readkprnt

Purpose Access the current printable key event.
Module offset 24
Communication registers A
Stack requirements 2 bytes
Zero page usage None
Registers affected A, X
Input parameters None
Output parameters C ← Set if there is no event queued
A ← PETSCII value

Description: Call this routine to get the current printable key event in the A registers. If the carry comes back set, there is no queued printable key event and only the X register is affected. If there is no event, the X register is set to zero, A and Y are unaffected.

Under normal circumstances, you will not poll this routine. The main event loop messages an Application or a Utility by calling the printable key event handling routine specified by the screen layer structure. When that event handling routine is called, it is because an event exists. Readkprnt can then be called as many times as necessary to handle the event. The main event loop itself uses readkprnt and checks the state of the carry to determine when an event is available to be dispatched.

deqkprnt

Purpose Dequeue the current key command event.
Module offset 27
Communication registers None
Stack requirements 2 bytes
Zero page usage $c6
Registers affected A, X
Input parameters None
Output parameters None

Description: This is routine is called to dequeue the current printable key event from the printable key events queue. All other printable key events are bumped up one position in the queue. This routine takes no input parameters and returns nothing. This routine can be called whether there is a queued event or not. This routine is called internally by the main event loop, and typically does not need to be called by high-level software.


Device Polling

Device polling is a part of the KERNAL, however, it relies on calls to runtime loadable hardware drivers. Therefore, how much time device polling takes, what zero page addresses it uses, how much stack it uses, is all dependent on the drivers that are loaded into memory.

polldevices

Purpose Poll hardware devices, enqueue keyboard and mouse events.
Module offset 30
Communication registers None
Stack requirements 2 bytes +
Zero page usage $cb
Registers affected A, X, Y
Input parameters None
Output parameters None

Description: This is routine is called by the C64 OS IRQ service routine. It should never be necessary to call this routine manually. This routine uses an arbitrary amount of stack, because it allows hardware drivers to be linked into the device polling process. This routine is exposed as a KERNAL call because the service KERNAL module implements the IRQ service routine and needs to call this in the input KERNAL module. It is safest to ignore this routine and never call it.



KERNAL Modules in Alphabetical Order

KERNAL Modules in Module Lookup Table Order

Return to Using the KERNAL → KERNAL Modules


Table of Contents



This document is subject to revision updates.

Last modified: Apr 20, 2023