]> git.piffa.net Git - sketchbook_andrea/blob - libraries/CapacitiveSensor/CapacitiveSensor.cpp
Capacitance fir st commit,
[sketchbook_andrea] / libraries / CapacitiveSensor / CapacitiveSensor.cpp
1 /*
2  CapacitiveSense.h v.04 - Capacitive Sensing Library for 'duino / Wiring
3  https://github.com/PaulStoffregen/CapacitiveSensor
4  http://www.pjrc.com/teensy/td_libs_CapacitiveSensor.html
5  http://playground.arduino.cc/Main/CapacitiveSensor
6  Copyright (c) 2009 Paul Bagder  All right reserved.
7  Version 05 by Paul Stoffregen - Support non-AVR board: Teensy 3.x, Arduino Due
8  Version 04 by Paul Stoffregen - Arduino 1.0 compatibility, issue 146 fix
9  vim: set ts=4:
10  */
11
12 #if ARDUINO >= 100
13 #include "Arduino.h"
14 #else
15 #include "WProgram.h"
16 #include "pins_arduino.h"
17 #include "WConstants.h"
18 #endif
19
20 #include "CapacitiveSensor.h"
21
22 // Constructor /////////////////////////////////////////////////////////////////
23 // Function that handles the creation and setup of instances
24
25 CapacitiveSensor::CapacitiveSensor(uint8_t sendPin, uint8_t receivePin)
26 {
27         // initialize this instance's variables
28         // Serial.begin(9600);          // for debugging
29         error = 1;
30         loopTimingFactor = 310;         // determined empirically -  a hack
31
32         CS_Timeout_Millis = (2000 * (float)loopTimingFactor * (float)F_CPU) / 16000000;
33         CS_AutocaL_Millis = 20000;
34
35         // Serial.print("timwOut =  ");
36         // Serial.println(CS_Timeout_Millis);
37
38         // get pin mapping and port for send Pin - from PinMode function in core
39
40 #ifdef NUM_DIGITAL_PINS
41         if (sendPin >= NUM_DIGITAL_PINS) error = -1;
42         if (receivePin >= NUM_DIGITAL_PINS) error = -1;
43 #endif
44
45         pinMode(sendPin, OUTPUT);                                               // sendpin to OUTPUT
46         pinMode(receivePin, INPUT);                                             // receivePin to INPUT
47         digitalWrite(sendPin, LOW);
48
49         sBit = PIN_TO_BITMASK(sendPin);                                 // get send pin's ports and bitmask
50         sReg = PIN_TO_BASEREG(sendPin);                                 // get pointer to output register
51
52         rBit = PIN_TO_BITMASK(receivePin);                              // get receive pin's ports and bitmask
53         rReg = PIN_TO_BASEREG(receivePin);
54
55         // get pin mapping and port for receive Pin - from digital pin functions in Wiring.c
56         leastTotal = 0x0FFFFFFFL;   // input large value for autocalibrate begin
57         lastCal = millis();         // set millis for start
58 }
59
60 // Public Methods //////////////////////////////////////////////////////////////
61 // Functions available in Wiring sketches, this library, and other libraries
62
63 long CapacitiveSensor::capacitiveSensor(uint8_t samples)
64 {
65         total = 0;
66         if (samples == 0) return 0;
67         if (error < 0) return -1;            // bad pin
68
69
70         for (uint8_t i = 0; i < samples; i++) {    // loop for samples parameter - simple lowpass filter
71                 if (SenseOneCycle() < 0)  return -2;   // variable over timeout
72 }
73
74                 // only calibrate if time is greater than CS_AutocaL_Millis and total is less than 10% of baseline
75                 // this is an attempt to keep from calibrating when the sensor is seeing a "touched" signal
76
77                 if ( (millis() - lastCal > CS_AutocaL_Millis) && abs(total  - leastTotal) < (int)(.10 * (float)leastTotal) ) {
78
79                         // Serial.println();               // debugging
80                         // Serial.println("auto-calibrate");
81                         // Serial.println();
82                         // delay(2000); */
83
84                         leastTotal = 0x0FFFFFFFL;          // reset for "autocalibrate"
85                         lastCal = millis();
86                 }
87                 /*else{                                // debugging
88                         Serial.print("  total =  ");
89                         Serial.print(total);
90
91                         Serial.print("   leastTotal  =  ");
92                         Serial.println(leastTotal);
93
94                         Serial.print("total - leastTotal =  ");
95                         x = total - leastTotal ;
96                         Serial.print(x);
97                         Serial.print("     .1 * leastTotal = ");
98                         x = (int)(.1 * (float)leastTotal);
99                         Serial.println(x);
100                 } */
101
102         // routine to subtract baseline (non-sensed capacitance) from sensor return
103         if (total < leastTotal) leastTotal = total;                 // set floor value to subtract from sensed value
104         return(total - leastTotal);
105
106 }
107
108 long CapacitiveSensor::capacitiveSensorRaw(uint8_t samples)
109 {
110         total = 0;
111         if (samples == 0) return 0;
112         if (error < 0) return -1;                  // bad pin - this appears not to work
113
114         for (uint8_t i = 0; i < samples; i++) {    // loop for samples parameter - simple lowpass filter
115                 if (SenseOneCycle() < 0)  return -2;   // variable over timeout
116         }
117
118         return total;
119 }
120
121
122 void CapacitiveSensor::reset_CS_AutoCal(void){
123         leastTotal = 0x0FFFFFFFL;
124 }
125
126 void CapacitiveSensor::set_CS_AutocaL_Millis(unsigned long autoCal_millis){
127         CS_AutocaL_Millis = autoCal_millis;
128 }
129
130 void CapacitiveSensor::set_CS_Timeout_Millis(unsigned long timeout_millis){
131         CS_Timeout_Millis = (timeout_millis * (float)loopTimingFactor * (float)F_CPU) / 16000000;  // floats to deal with large numbers
132 }
133
134 // Private Methods /////////////////////////////////////////////////////////////
135 // Functions only available to other functions in this library
136
137 int CapacitiveSensor::SenseOneCycle(void)
138 {
139     noInterrupts();
140         DIRECT_WRITE_LOW(sReg, sBit);   // sendPin Register low
141         DIRECT_MODE_INPUT(rReg, rBit);  // receivePin to input (pullups are off)
142         DIRECT_MODE_OUTPUT(rReg, rBit); // receivePin to OUTPUT
143         DIRECT_WRITE_LOW(rReg, rBit);   // pin is now LOW AND OUTPUT
144         delayMicroseconds(10);
145         DIRECT_MODE_INPUT(rReg, rBit);  // receivePin to input (pullups are off)
146         DIRECT_WRITE_HIGH(sReg, sBit);  // sendPin High
147     interrupts();
148
149         while ( !DIRECT_READ(rReg, rBit) && (total < CS_Timeout_Millis) ) {  // while receive pin is LOW AND total is positive value
150                 total++;
151         }
152         //Serial.print("SenseOneCycle(1): ");
153         //Serial.println(total);
154
155         if (total > CS_Timeout_Millis) {
156                 return -2;         //  total variable over timeout
157         }
158
159         // set receive pin HIGH briefly to charge up fully - because the while loop above will exit when pin is ~ 2.5V
160     noInterrupts();
161         DIRECT_WRITE_HIGH(rReg, rBit);
162         DIRECT_MODE_OUTPUT(rReg, rBit);  // receivePin to OUTPUT - pin is now HIGH AND OUTPUT
163         DIRECT_WRITE_HIGH(rReg, rBit);
164         DIRECT_MODE_INPUT(rReg, rBit);  // receivePin to INPUT (pullup is off)
165         DIRECT_WRITE_LOW(sReg, sBit);   // sendPin LOW
166     interrupts();
167
168 #ifdef FIVE_VOLT_TOLERANCE_WORKAROUND
169         DIRECT_MODE_OUTPUT(rReg, rBit);
170         DIRECT_WRITE_LOW(rReg, rBit);
171         delayMicroseconds(10);
172         DIRECT_MODE_INPUT(rReg, rBit);  // receivePin to INPUT (pullup is off)
173 #else
174         while ( DIRECT_READ(rReg, rBit) && (total < CS_Timeout_Millis) ) {  // while receive pin is HIGH  AND total is less than timeout
175                 total++;
176         }
177 #endif
178         //Serial.print("SenseOneCycle(2): ");
179         //Serial.println(total);
180
181         if (total >= CS_Timeout_Millis) {
182                 return -2;     // total variable over timeout
183         } else {
184                 return 1;
185         }
186 }