Software based digital input debouncer

Revision:
0:76aea589cbdd
Child:
1:b59d305c4365
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/DigitalInDebounced.cpp	Tue May 27 23:01:37 2014 +0000
@@ -0,0 +1,71 @@
+#include "DigitalInDebounced.h"
+/*-------------------------------------------------------------
+
+(c) W.D. 2014
+
+-------------------------------------------------------------*/
+
+DigitalInDebounced::DigitalInDebounced(PinName pin_in, unsigned int inDebounceTime)
+{
+   Switch = new DigitalIn(pin_in);
+   DigitalInDebounced_common(Switch, inDebounceTime);
+}
+    
+DigitalInDebounced::DigitalInDebounced(PinName pin_in, PinMode mode, unsigned int inDebounceTime)
+{
+   Switch = new DigitalIn(pin_in, mode);
+   DigitalInDebounced_common(Switch, inDebounceTime);
+}
+
+void DigitalInDebounced::DigitalInDebounced_common(DigitalIn *SwitchIn, unsigned int inDebounceTime)
+{
+    recent = !SwitchIn->read();
+    stable = false;
+    DebounceTime = inDebounceTime;
+    long int DebounceCount = (inDebounceTime*1000l) / timer_user.TickerPeriod_rd();
+    if (DebounceCount > SAMPLES_TO_DEBOUNCE)
+    {
+        PreDivider = DebounceCount / SAMPLES_TO_DEBOUNCE;
+        Divider = DebounceCount / PreDivider;
+    }
+    else
+    {
+        PreDivider = 1;
+        Divider = DebounceCount;
+    }
+        
+    DebounceCounter = Divider;
+    timer_user.Subscribe (this, PreDivider);
+    xCounter = 0;
+}
+
+bool DigitalInDebounced::read(void)
+{
+    if (this->stable) 
+        return this->recent;
+    else
+        return false;
+}
+
+DigitalInDebounced::~DigitalInDebounced()
+{
+    timer_user.UnSubscribe(this);
+}
+
+void DigitalInDebounced::TimerEvent(void)
+{
+    bool temp = !Switch->read();
+    if (temp == recent)
+    {
+        if (!stable)
+            if (0 == (--DebounceCounter))
+                stable = true;
+    }
+    else
+    {
+        stable = false;
+        recent = temp;
+        DebounceCounter = Divider;
+    }
+    xCounter++;
+}