230 lines
6.1 KiB
C++
230 lines
6.1 KiB
C++
/* ******************************************************************* *
|
|
* Reads X/Y values from a PS/2 mouse connected to an Arduino
|
|
* using the PS2Mouse library available from
|
|
* http://github.com/kristopher/PS2-Mouse-Arduino/
|
|
*
|
|
* ATmeha48, No Bootloader, 48/48A, BOD 2.7V, LTO disabled, 8MHz internal
|
|
* ******************************************************************* *
|
|
|
|
' Circuit diagram
|
|
' ---------------
|
|
' ATtiny 48 / 88 / Mega 168 / Mega 328 Pin map
|
|
' +-\/-+
|
|
' +5V---| 100K |--->1|o |28<-PC5-ADC5-----X_Pot
|
|
' RxD>---------PD0--2| |27<-PC4-ADC4-----Y_Pot
|
|
' TxD<---------PD1--3| |26 PC3 ADC3
|
|
' LED<---------PD2--4| |25 PC2 ADC2
|
|
' PS2-CLK------PD3--5| |24<-PC1-ADC1-----L_Fire
|
|
' PS2-DAT------PD4--6| |23<-PC0-ADC0-----R_Fire
|
|
' VCC 7| |22 GND
|
|
' GND 8| |21 AREF
|
|
' --9| |20 VCC
|
|
' -10| |19 PB5 SCK
|
|
' YB<----------PD5-11| |18 PB4 MISO
|
|
' YA<----------PD6-12| |17 PB3 MOSI
|
|
' XA<----------PD7-13| |16--PB2---------->RB
|
|
' XB<----------PB0-14| |15--PB1---------->LB
|
|
' +----+
|
|
' -------------------------------------------------------------
|
|
'
|
|
* ******************************************************************* *
|
|
|
|
' Mouse Command Description
|
|
' --------------------------
|
|
'
|
|
' ------------------------
|
|
' D7 D6 D5 D4 D3 D2 D1 D0 (The D0 bit (LSB) is sent first)
|
|
' ------------------------
|
|
'(1) YV XV YS XS 1 0 R L (overflow, sign, buttons)
|
|
'(2) X7 X6 X5 X4 X3 X2 X1 X0 (X movement; -128 to +127)
|
|
'(3) Y7 Y6 Y5 Y4 Y3 Y2 Y1 Y0 (Y movement; -128 to +127)
|
|
|
|
'L = Left Button State (1 = pressed down)
|
|
'R = Right Button State (1 = pressed down)
|
|
'XS = Direction of X movement (1 = LEFT)
|
|
'YS = Direction of Y movement (1 = UP)
|
|
'XV = Overflow of X movement value (1 = X overflow occured)
|
|
'YV = Overflow of Y movement value (1 = Y overflow occured)
|
|
'X7,...,X0 : X movement; 8-bit 2's-complement signed byte (-128 to +127)
|
|
'Y7,...,Y0 : Y movement; 8-bit 2's-complement signed byte (-128 to +127)
|
|
|
|
'Here are examples of data sent to the host (PC):
|
|
'------------------------------------------------
|
|
'(The least-significant bit of each data byte is sent first.)
|
|
'Move Left 1 unit : 0x18, 0xFF, 0x00
|
|
'Move Right 1 unit : 0x08, 0x01, 0x00
|
|
'Move Down 1 unit : 0x28, 0x00, 0xFF
|
|
'Move Up 1 unit : 0x08, 0x00, 0x01
|
|
'Press Left Button : 0x09, 0x00, 0x00
|
|
'Release Left Button : 0x08, 0x00, 0x00
|
|
'Press Right Button : 0x0C, 0x00, 0x00
|
|
'Release Right Button : 0x08, 0x00, 0x00
|
|
|
|
'13. Interpret the direction bits (explained in the Mouse Interface section)
|
|
'14. Interpret the X and Y motion bytes
|
|
'15. Update cumulative X,Y motion and display on LCD
|
|
'16. Repeat steps 1-15 indefinitely
|
|
* ******************************************************************* */
|
|
|
|
#include <PS2Mouse.h>
|
|
|
|
#define MOUSE_CLOCK 3 // pin 5
|
|
#define MOUSE_DATA 4 // pin 6
|
|
#define YB 5
|
|
#define YA 6
|
|
#define XA 7
|
|
#define XB 8
|
|
#define LB 9
|
|
#define RB 10
|
|
|
|
#define DEBUG
|
|
|
|
PS2Mouse mouse(MOUSE_CLOCK, MOUSE_DATA, STREAM);
|
|
int16_t data[3];
|
|
|
|
void Left(int16_t steps) {
|
|
for(int16_t i=steps;i=0;i--){
|
|
#ifdef DEBUG
|
|
Serial.println("Left");
|
|
#endif
|
|
digitalWrite(YB, HIGH);
|
|
delayMicroseconds(10);
|
|
digitalWrite(YA, HIGH);
|
|
delayMicroseconds(90);
|
|
digitalWrite(YB, LOW);
|
|
delayMicroseconds(10);
|
|
digitalWrite(YA, LOW);
|
|
delayMicroseconds(90);
|
|
}
|
|
}
|
|
|
|
void Right(int16_t steps) {
|
|
for(int16_t i=steps;i>=256;i++){
|
|
#ifdef DEBUG
|
|
Serial.println("Right");
|
|
#endif
|
|
digitalWrite(YA, HIGH);
|
|
delayMicroseconds(10);
|
|
digitalWrite(YB, HIGH);
|
|
delayMicroseconds(90);
|
|
digitalWrite(YA, LOW);
|
|
delayMicroseconds(10);
|
|
digitalWrite(YB, LOW);
|
|
delayMicroseconds(90);
|
|
}
|
|
}
|
|
|
|
void Up(int16_t steps) {
|
|
for(int16_t i=steps;i=0;i--){
|
|
#ifdef DEBUG
|
|
Serial.println("UP");
|
|
#endif
|
|
digitalWrite(XB, HIGH);
|
|
delayMicroseconds(10);
|
|
digitalWrite(XA, HIGH);
|
|
delayMicroseconds(90);
|
|
digitalWrite(XB, LOW);
|
|
delayMicroseconds(10);
|
|
digitalWrite(XA, LOW);
|
|
delayMicroseconds(90);
|
|
}
|
|
}
|
|
|
|
void Down(int16_t steps) {
|
|
for(int16_t i=steps;i>=256;i++){
|
|
#ifdef DEBUG
|
|
Serial.println("Down");
|
|
#endif
|
|
digitalWrite(XA, HIGH);
|
|
delayMicroseconds(10);
|
|
digitalWrite(XB, HIGH);
|
|
delayMicroseconds(90);
|
|
digitalWrite(XA, LOW);
|
|
delayMicroseconds(10);
|
|
digitalWrite(XB, LOW);
|
|
delayMicroseconds(90);
|
|
}
|
|
|
|
}
|
|
|
|
/* ******** *
|
|
* Setup *
|
|
* ******** */
|
|
void setup()
|
|
{
|
|
pinMode(YB, OUTPUT);
|
|
pinMode(YA, OUTPUT);
|
|
pinMode(XA, OUTPUT);
|
|
pinMode(XB, OUTPUT);
|
|
pinMode(LB, OUTPUT);
|
|
pinMode(RB, OUTPUT);
|
|
|
|
digitalWrite(YA, HIGH);
|
|
digitalWrite(YB, HIGH);
|
|
digitalWrite(XA, HIGH);
|
|
digitalWrite(XB, HIGH);
|
|
digitalWrite(RB, HIGH);
|
|
digitalWrite(LB, HIGH);
|
|
|
|
mouse.initialize();
|
|
|
|
#ifdef DEBUG
|
|
Serial.begin(9600);
|
|
Serial.println("Mouse initialized");
|
|
#endif
|
|
}
|
|
|
|
/* ***************** *
|
|
* Main program loop *
|
|
* ***************** */
|
|
void loop()
|
|
{
|
|
mouse.report(data);
|
|
#ifdef DEBUG2
|
|
Serial.print(data[0]);
|
|
Serial.print(":");
|
|
Serial.print(data[1]);
|
|
Serial.print(";");
|
|
Serial.println(data[2]);
|
|
#endif
|
|
|
|
/* -- Mouse Buttons -- */
|
|
if (data[0] & 1)
|
|
{
|
|
#ifdef DEBUG
|
|
Serial.println("RB");
|
|
#endif
|
|
digitalWrite(RB, LOW);
|
|
} else {
|
|
digitalWrite(RB, HIGH);
|
|
}
|
|
if (data[0] & 2)
|
|
{
|
|
#ifdef DEBUG
|
|
Serial.println("LB");
|
|
#endif
|
|
digitalWrite(LB, LOW);
|
|
}
|
|
else {
|
|
digitalWrite(LB, HIGH);
|
|
}
|
|
|
|
/* -- X Direction -- */
|
|
if (data[1] & 255) {
|
|
if (data[0] & 16) {
|
|
Left(data[1]);
|
|
} else {
|
|
Right(data[1]);
|
|
}
|
|
}
|
|
|
|
/* -- Y Direction -- */
|
|
if (data[2] & 255) {
|
|
if (data[0] & 32) {
|
|
Up(data[2]);
|
|
} else {
|
|
Down(data[2]);
|
|
}
|
|
}
|
|
}
|