Code for Doug, Elizabeth, and Maruchi's team project: a Mario Kart controller.
Dependencies: PinDetect USBDevice mbed
main.cpp
- Committer:
- douglasc
- Date:
- 2014-09-29
- Revision:
- 0:0c8c5c9f7586
File content as of revision 0:0c8c5c9f7586:
/** * Interactive Device Design, Fall 2014 * Homework 3 - Mario Kart Wii Game Controller * * Elizabeth Lin * Doug Cook * Maruchi Kim * * This program will setup the mbed device to act * as a Gamecube controller by emulating a mouse * with input data from an accelerometer. It also * provides buttons to support other gamepad * functions specific to Mario Kart. * * The Dolphin Emulator (dolphin-emu.org) can be * configured to accept this device (a USB Mouse) * as the joystick for an emulated Wiimote/GCPad. * */ #include "mbed.h" #include "USBMouseKeyboard.h" #include "PinDetect.h" #include "KeyManager.h" // ********************************************************** // constants const int PINDETECT_SAMPLE_FREQUENCY = 20000; const int GAIN = 15000; const int ADAFRUIT_ACC_RANGE_MIDPOINT = 32768; // ********************************************************** // ********************************************************** // Adafruit Accelerometer Input and calibration variables AnalogIn xAxisIn(A2); AnalogIn yAxisIn(A1); AnalogIn zAxisIn(A0); uint16_t addBias = false; int bias = 0; int sensitivity = 1; float read_correct(AnalogIn input) { float result = (float) input.read_u16(); result = result - ADAFRUIT_ACC_RANGE_MIDPOINT; return (result - (float)bias) / (float) sensitivity; } // ********************************************************** // LED and Serial Interface for 'Ready' feedback and debugging DigitalOut greenLed(LED2); Serial pc(USBTX, USBRX); // ********************************************************** // minimum function for unsigned 16-bit integers uint16_t min(uint16_t a, uint16_t b) { return (a < b) ? a : b; } // ********************************************************** int main() { // Perform accelerometer calibration at startup // (assume the accelerometer is flat and // face-down on a level surface). greenLed = 1; uint16_t initialX = xAxisIn.read_u16(); uint16_t correctX = 32768; bias = initialX - correctX; sensitivity = (zAxisIn.read_u16() - 32768 - bias); greenLed = 0; // Keyboard init and config USBMouseKeyboard key_mouse = USBMouseKeyboard(ABS_MOUSE); KeyManager keys = KeyManager(); PinDetect buttonA(D7); PinDetect buttonB(D6); buttonA.mode(PullUp); buttonB.mode(PullUp); buttonA.setSampleFrequency( PINDETECT_SAMPLE_FREQUENCY ); buttonA.attach_asserted(&keys, &KeyManager::keyAOn); buttonA.attach_deasserted(&keys, &KeyManager::keyAOff); buttonB.setSampleFrequency( PINDETECT_SAMPLE_FREQUENCY ); buttonB.attach_asserted(&keys, &KeyManager::keyBOn); buttonB.attach_deasserted(&keys, &KeyManager::keyBOff); // analog-in to joystick calculation variables uint16_t xAxis; uint16_t yAxis; uint16_t xCenter = (X_MAX_ABS - X_MIN_ABS)/2; uint16_t yCenter = (Y_MAX_ABS - Y_MIN_ABS)/2; uint32_t xOrigin = xCenter; uint32_t yOrigin = yCenter; uint16_t lastXAxis = 0; uint16_t lastYAxis = 0; while(1) { xAxis = min(floor(.5*lastXAxis + .5*(uint16_t)(floor(atan(read_correct(xAxisIn)/read_correct(yAxisIn))*GAIN)+xOrigin)),X_MAX_ABS); yAxis = floor(.5*lastYAxis + .5*(uint16_t)(-1*floor(atan(read_correct(zAxisIn)/read_correct(yAxisIn))*GAIN)+yOrigin)); lastXAxis = xAxis; lastYAxis = yAxis; key_mouse.move(xAxis, yAxis); // read button pads if (keys.keysPressed()) { key_mouse.keyDown(keys.getCharacter()); } else { key_mouse.keyUp(); } } }