Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

PS/2 mouse support #119

Merged
merged 4 commits into from
Oct 27, 2023
Merged

Conversation

stevesims
Copy link
Contributor

mouse support - yay!

works on Console8, and also on other Agon Light machines that have a PS/2 mouse port attached to the GPIO pins that pass thru the appropriate ESP IO pins (IO26 and IO27 for CLK and DATA, as per fab-gl/vdp-gl)

mouse needs to be enabled before a mouse cursor will be made visible.

mouse commands are prefixed with VDU 23, 0, &89, command

Command 0 enables, 1 disables

Command 2 resets the mouse. This reverts all the mouse settings. NB whether the mouse was enabled or disabled is not affected.

Command 3 followed by a 16-bit value will set the mouse cursor. Numbers 0-18 will give you fab-gl cursors. Any other number will be interpreted as a custom cursor ID. To use one of them you'll need to use a new bitmap/sprite command to set a bitmap to be used as a cursor. After selecting a bitmap, VDU 23, 27, &40, hotX, hotY will make a cursor corresponding to that bitmap ID, after which it can be used with VDU 23, 0, &89, 3, bitmapId; to select as a cursor. Choosing an ID that is not assigned to a cursor will result in no cursor being visible. As buffer ID 65535 is reserved, it is recommended to use VDU 23, 0, &89, 3, 65535; to hide the mouse cursor.

Command 4, with two 16-bit value to provide an X and Y position will move the cursor on-screen to that position, if the cursor is active.

Command 5 is currently non-functional. It is intended to be a "set area" command taking four 16-bit values to define an area of screen to limit the mouse cursor to. Those values will be read, but the area will not be restricted (this will need changes in fab-gl to support it).

Command 6, followed by a byte, sets the sample rate in samples per second for reading (and reporting) the mouse position. Valid rates are 10, 20, 40, 60, 80, 100, and 200. Sending 0 will pick the default rate of 60. All other values will be ignored.

Command 7 followed by a byte sets the "resolution" of the mouse system. Valid values are 0-3, where 0 = 1 count/mm (25 dpi), 1 = 2 counts/mm (50 dpi), 2 = 4 counts/mm (100 dpi), 3 = 8 counts/mm (200 dpi). Sending a value of -1 (255) will pick the default, which is 2 (100dpi). All other values will be ignored.

Command 8 followed by a byte sets the mouse scaling factor, which can be 1 or 2. Sending a 0 uses the default, which is 1. All other values will be ignored.

Command 9 followed by a 16-bit value sets the movement acceleration factor. The default value is 180, and the suggested range is 0-2000, but no limits are placed on the number given.

Command 10 followed by a 24-bit value sets the mouse wheel acceleration factor. The default value is 60000 and the suggested range is 0-100000. No limits are placed on the number given.

Commands that are successfully processed will send a new mouse data packet to MOS. The delta values in such packets will be zero, as the mouse will not have moved. Sending VDU 23,0,&89,0 will therefore always report the latest mouse position, even when the mouse has already been enabled..

NB Changing screen mode will reset the cursor position to the middle of the screen
NB2 If the mouse has been enabled then mouse data packets will be sent on mouse movement, even if there is no visible cursor set
NB3 Mouse data packets contain delta information - if you move your mouse left when the pointer is at the left edge of the screen you will still receive a negative X delta value.

experimental hard-coded mouse support.

this won’t work properly - mode changes will effectively break things

needs some refactoring, and control commands added to allow mouse to be explicitly enabled/disabled and configured
also fix a compilation issue
@@ -0,0 +1,363 @@
#ifndef AGON_PS2_H
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this file is actually a rename of agon_keyboard.h, but with mouse things added.

I added in mouse functionality here because the underlying support for keyboard and mouse is linked inside fab-gl/vdp-gl

GitHub thinks this is a new file, rather than a rename... not overly helpful that GitHub 😁

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Did you use git mv <old_filename> <new_filename>?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yup - that's why there was 2 commits - first one only has the mv with no edits which did seem to be recognised

Comment on lines +36 to +37
void setupKeyboardAndMouse() {
_PS2Controller.begin();
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this was previously setupKeyboard...

calling _PS2Controller.begin() will attempt to set up both the keyboard and mouse ports. if no mouse is found connected to IO26+27 then it is essentially harmless.

return false;
}
mouse->resumePort();
return updateMouseEnabled();
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this ensures that the mouse will only be enabled if a mouse is actually available.

in the current implementation if you turn on a machine that does not have a mouse connected, then calling "enable" will fail, and the mouse will not enable even if you subsequently plug a mouse in. to get the mouse to be recognised you either need to call the reset command (VDU 23,0,&89,2) or press the reset button. this is an intentional choice

in principle this code could attempt to reset the mouse system and connect to a mouse if no mouse had previously been detected, but that is very costly and takes a while (up to a couple of seconds), jamming up the VDP in the process. as many Agon Light machines will not have a mouse port, and thus won't have a mouse connected, it's better to make this "enable" fail quickly. similarly most users that do have a mouse will keep it plugged in

Comment on lines +162 to +163
auto hotX = readByte_t(); if (hotX == -1) return;
auto hotY = readByte_t(); if (hotY == -1) return;
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

technically the "hot" position can use a 16-bit position - but that's not practical - so let's not encourage anyone to make such massive mouse cursors 😁

@@ -68,6 +68,17 @@ Point scale(Point p) {
return scale(p.X, p.Y);
}

// Convert to currently active coordinate system
//
Point toCurrentCoordinates(int16_t X, int16_t Y) {
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is used to get OS coordinates from screen coordinates

a mouse position will be reported in whichever coordinate system is active. by default that means OS coordinates, but if you've swapped to using native screen pixel coordinates you'll get pixel coordinates instead.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Great job on this! I was wondering what the mouse coordinates would be, given that there are effectively three different methods in use on the Agon (Graphics (OS) coordinates, Text coordinates and native screen pixel coordinates). Glad to see that mouse support doesn't introduce another :-)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this reminds me that I did want to add support for OS coordinates to bitmaps - probably by just adding in the relevant PLOT code support (which is currently missing). supporting them for sprites will be a teensy bit more involved/complicated. I believe that's the only graphics stuff that doesn't already support both coordinate systems

@breakintoprogram breakintoprogram added the enhancement New feature or request label Oct 26, 2023
@breakintoprogram
Copy link
Owner

@stevesims Not got a mouse wired up to my Agon (yet), so will have difficulty testing this. If it compiles without warnings, and you are happy with it, then I'll merge.

@breakintoprogram breakintoprogram merged commit 1dada17 into breakintoprogram:main Oct 27, 2023
@stevesims
Copy link
Contributor Author

Yeah - it's been working for me 😁 - no warnings

Don't forget to merge in the MOS side too 😄

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
Status: Done
Development

Successfully merging this pull request may close these issues.

4 participants