Digital JoyStick function, interrupt driven

Dependencies:   mbed

Revision:
0:1136d6d5aa1c
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/joy.h	Sun Mar 13 13:17:21 2011 +0000
@@ -0,0 +1,214 @@
+/*
+    Copyright (c) 2011 Pro-Serv
+ 
+    Permission is hereby granted, free of charge, to any person obtaining a copy
+    of this software and associated documentation files (the "Software"), to deal
+    in the Software without restriction, including without limitation the rights
+    to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+    copies of the Software, and to permit persons to whom the Software is
+    furnished to do so, subject to the following conditions:
+ 
+    The above copyright notice and this permission notice shall be included in
+    all copies or substantial portions of the Software.
+ 
+    THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+    IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+    FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+    AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+    LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+    OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+    THE SOFTWARE.
+    
+    Usage and assumptions:
+        the digital joystick device is directly attached to the used pins as per
+        function call, common contact to ground, using the internal pull-up's
+        but one can use external pull-up's too or even a small capaitor if device
+        shows signs of contact bounce.
+        
+    Operation modes:
+        By default it's using dynamic mode which means that the main program may
+        not see the expected pressed joystick contact in it's scan loop as another
+        joystick contact may already be active.
+        Using the static mode will capture the first joystick contact untill it's
+        been read by the getJoyValue function
+        
+    To do:
+        Adding a callable service routine to be used by the main program loop
+ */
+
+#ifndef MBED_H
+#include "mbed.h"
+#endif
+
+#ifndef JOY_DELAY_PERIOD
+#define JOY_DELAY_PERIOD 5000
+#endif
+
+#ifndef JOY_STATIC
+#define JOY_STATIC 0
+#endif
+
+#ifndef JOY_CENTER
+#define JOY_CENTER 1
+#endif
+
+#ifndef JOY_RIGHT
+#define JOY_RIGHT 2
+#endif
+
+#ifndef JOY_DOWN
+#define JOY_DOWN 4
+#endif
+
+#ifndef JOY_LEFT
+#define JOY_LEFT 8
+#endif
+
+#ifndef JOY_UP
+#define JOY_UP 16
+#endif
+
+namespace JOY {
+
+ 
+class JoyRead {
+
+protected:
+    InterruptIn *_int0;
+    InterruptIn *_int1;
+    InterruptIn *_int2;
+    InterruptIn *_int3;
+    InterruptIn *_int4;
+    int         _sampleDelay;
+    int         _staticMode;
+    int         _joy_status;
+    
+    void init(PinName px0, PinName px1, PinName px2, PinName px3, PinName px4, PinMode m) {
+        _sampleDelay             = JOY_DELAY_PERIOD;
+        _staticMode              = JOY_STATIC;
+        _joy_status = 0;
+        _int0 = new InterruptIn( px0 ); 
+        _int1 = new InterruptIn( px1 ); 
+        _int2 = new InterruptIn( px2 ); 
+        _int3 = new InterruptIn( px3 ); 
+        _int4 = new InterruptIn( px4 ); 
+        _int0->mode( m );
+        _int1->mode( m );
+        _int2->mode( m );
+        _int3->mode( m );
+        _int4->mode( m );
+        _int0->fall(this, &JoyRead::isr_int0_f);
+        _int1->fall(this, &JoyRead::isr_int1_f);
+        _int2->fall(this, &JoyRead::isr_int2_f);
+        _int3->fall(this, &JoyRead::isr_int3_f);
+        _int4->fall(this, &JoyRead::isr_int4_f);
+        _int0->rise(this, &JoyRead::isr_int0_r);
+        _int1->rise(this, &JoyRead::isr_int1_r);
+        _int2->rise(this, &JoyRead::isr_int2_r);
+        _int3->rise(this, &JoyRead::isr_int3_r);
+        _int4->rise(this, &JoyRead::isr_int4_r);
+    }
+
+public:
+
+    /* PinDetect constructor(s) & overloading */
+    JoyRead() { error("Provide a valid PinName"); }
+
+    JoyRead(PinName px0, PinName px1, PinName px2, PinName px3, PinName px4) {
+        init( px0, px1, px2, px3, px4, PullUp);
+    }
+
+    JoyRead(PinName px0, PinName px1, PinName px2, PinName px3, PinName px4, PinMode m) {
+        init(  px0, px1, px2, px3, px4, m );
+    }
+
+    /* Set the sampling delay time in microseconds. */
+    void setDelaySample(int i = JOY_DELAY_PERIOD) { _sampleDelay = i; }
+    
+    /* Set the sampling delay time in microseconds. */
+    void setJoyStatic(int i = JOY_STATIC) { _staticMode = i; }
+    
+    /* Returns true if any joystick position is active */
+    bool getJoyStatus(void) {
+        if ((_joy_status & 0x80) == 0x80) {
+            return true;
+        } else {
+            return false;
+        }
+    }
+    
+    /* Return true if selected joystick key is active */
+    bool getJoyKey(int i) {
+        if ((_joy_status & 0x1f) == i) {
+            return true;
+        } else {
+            return false;
+        }
+    }
+    
+    /* Return value of all key's active state (may result in upto 3 keys at same time) */
+    int getJoyValue(void) {
+        int tmp;
+        if ((_joy_status & 0x80) == 0x80) {
+            /* in _stiticMode = 1 the getJoyValue will reset joy available */
+            tmp = _joy_status & 0x1f;
+            if (_staticMode == 1) { _joy_status = 0x00;}
+            return tmp;
+        } else {
+            return 0x00;
+        }
+    }
+    
+protected:    
+    /* The interrupt service routines are: fall and rise */
+    void isr_int0_f(void) {
+        _joy_status |= 0x81;
+    }
+    void isr_int1_f(void) {
+        _joy_status |= 0x82;
+    }
+    void isr_int2_f(void) {
+        _joy_status |= 0x84;
+    }
+    void isr_int3_f(void) {
+        _joy_status |= 0x88;
+    }
+    void isr_int4_f(void) {
+        _joy_status |= 0x90;
+    }
+    /* The interrupt service routine for rise is only actively used in case of _staticMode = 0 */
+    void isr_int0_r(void) {
+        if (_staticMode == 0) {
+            _joy_status &= 0x9e;
+            if ((_joy_status & 0x1f) == 0x00) {_joy_status = 0x00;}
+        }
+    }
+    void isr_int1_r(void) {
+        if (_staticMode == 0) {
+            _joy_status &= 0x9d;
+            if ((_joy_status & 0x1f) == 0x00) {_joy_status = 0x00;}
+        }
+    }
+    void isr_int2_r(void) {
+        if (_staticMode == 0) {
+            _joy_status &= 0x9b;
+            if ((_joy_status & 0x1f) == 0x00) {_joy_status = 0x00;}
+        }
+    }
+    void isr_int3_r(void) {
+        if (_staticMode == 0) {
+            _joy_status &= 0x97;
+            if ((_joy_status & 0x1f) == 0x00) {_joy_status = 0x00;}
+        }
+    }
+    void isr_int4_r(void) {
+        if (_staticMode == 0) {
+            _joy_status &= 0x8f;
+            if ((_joy_status & 0x1f) == 0x00) {_joy_status = 0x00;}
+        }
+    }
+};
+
+}; // namespace JOY ends.
+
+using namespace JOY;
\ No newline at end of file