Become a subscriber (Free)

Join 29,000 other subscribers to receive subscriber sale discounts and other free resources.
:
:
Don't worry -- youre-mail address is totally secure. I promise to use it only to send you MicroZine.

Arduino Capacitive Sensor

Arduino Capacitive Sensor: Here you can find out how to use a single pin and no external hardware to create a button that operates through wood, plastic or glass.

For some designs you need a push button that is hidden and this is the ideal method to do it - capacitive touch sensing. The actual technique is really measuring capacitance by measuring the charging time of the external capacitance.


Standard Arduino Capacitive Sensor Method

The usual method for detecting a capacitive touch input is to use two pins with a high value resistor between them. In this setup the capacitance at the sensor pin is measured by manipulating two pins. The CapacitiveSensor library is used for this (two-pin) method.

  • One pin is the controller.
  • One pin is the sensor.

When the controller pin is set high the capacitance at the sensor is charged through the resistor. When the input voltage at the sensor reaches the input high threshold voltage (Vih) it indicates a valid input (logic level high).

The total capacitance at the sensor and the resistance from capacitor to input determines the rise time (charging rate) and when you add more capacitance, by placing your finger near the sensor, capacitance increases (slowing the charging rate). This is because capacitances in parallel add together.

Measuring the rise time allows you to detect the presence of a finger!

Note: You can use the same control pin for multiple capacitive sensors when you use the CapacitiveSensor library.

The CapacitiveSensor library documentation talks about changing the value of the resistance as follows:

  • 1 MOhm absolute touch
  • 10 MOhm 4-6 inch detection
  • 40 MOhm 12-24 inch detection

You can choose these parameters based on your design. Using the single pin ADC method below you can adjust the sensitivity by changing the adc threshold measured.

Tip: You can even use just a length of wire as the detector!

ADC Arduino Capacitive Sensor

The advantage of this ADC Arduino capacitive sensor method is that it only needs a single analogue pin per input.

So this method is most appropriate for pin constrained designs such as an ATtiny85 (8 pins - 6 useable) whereas the CapacitiveSensor library is useful if you have many inputs because you have greater control over the sensing ability when selecting external components.

There are three elements required by the method:

  1. A sample and hold capacitor with a known value (14pF).
  2. A controllable pull-up.
  3. The ability to ground the ADC sample and hold capacitor.

How the ADC Capacitive Sensor Works

Arduino ADC and pin Block diagram

If you draw out the above elements as a single diagram then you get:


 adc touch block diagram operation capacitive touch using adc

Attach a small copper plate to an analogue input pin (with series resistor for ESD protection -not shown). When an object (or finger) is brought near the plate its capacitance increases.

The idea is to compare the external capacitance to the internal sample and hold capacitance - if they are similar then the ADC will read 2.5V and become lower as C increases.

Charge External and ground internal cap

To do that the external capacitor is charged to 5V while the internal capacitor is discharged to ground:

initialise capacitive touch using adc

Remove charge and connect pin to ADC

Now disconnect the pullup and connect the capacitors then charge distributes according to the relative capacitance values.

internal cap connect operation capacitive touch using adc

Now Make an ADC reading to detect the capacitance change.

Arduino Library

Library for the Capacitive Touch Sensor : ADCTouch

Download from :https://github.com/martin2250/ADCTouch and unzip to the libraries folder (usually c:/users//Documents/Arduino/libraries).

Or use the library manager, searching for ADCTouch.

Library installation details are here.

ADCTouch Souce Code

This source code for the capacitive touch sensor is from the ADCTouch library showing the core operational code.

Later code has been updated to accommodate ATTiny devices, as the register values used different, so you should use the latest version but the code below is for the Arduino Uno and is easier to read (from github 2016).

/*
  ADCTouch.cpp - Library for Capacittive touch sensors using only one ADC PIN
  Created by martin2250, April 23, 2014.
  Released into the public domain.
*/
#include "Arduino.h"
#include "ADCTouch.h"

int ADCTouchClass::read(byte ADCChannel, int samples)
{
	long _value = 0;
	for(int _counter = 0; _counter < samples; _counter ++)
	{
		pinMode(ADCChannel, INPUT_PULLUP);

		ADMUX |=   0b11111;
		ADCSRA |= (1<<ADSC); //start conversion
		while(!(ADCSRA & (1<<ADIF))); //wait for conversion to finish
		ADCSRA |= (1<<ADIF); //reset the flag

		pinMode(ADCChannel, INPUT);
		_value += analogRead(ADCChannel);
	}
	return _value / samples;
}

The latest code has a few more comments but the basic operation is this:

  1. Set the input pull-up active to charge the external capacitor.
  2. Set the Mux to select ground as input to discharge the S&H capacitor.
  3. Perform a conversion (not sure this is strictly necessary).
  4. Release the pull-up - set inactive.
  5. Perform an ADC read
  6. Repeat from 1 'samples' times, then divide the result by the number of 'samples' taken to get the average value.

Example Test code

Using hardware: Arduino Uno.

The following code for the Arduino capacitive sensor is an example that shows reading of two capacitive touch sensor inputs attached to analogue input pins A0 and A1. Note that with the standard sensing method you would need three pins to do this plus two resistors and possibly two more capacitors.

All you need here is a wire and a copper pad (I used a piezo disc using only the wire connected to the copper pad). All you do is place these connections in A0 and A1 pins on an Arduino Uno.

The copper disc was attached to A0 while the wire was attached to A1. You can see the output results below the sketch.

#include <ADCTouch.h>

int ref0, ref1;     //reference values to remove offset

void setup()
{
    // No pins to setup, pins can still be used regularly, although it will affect readings

    Serial.begin(9600);

    ref0 = ADCTouch.read(A0, 500);    //create reference values to
    ref1 = ADCTouch.read(A1, 500);    //account for the capacitance of the pad
}

void loop()
{
    int value0 = ADCTouch.read(A0);   //no second parameter
    int value1 = ADCTouch.read(A1);   //   --> 100 samples

    value0 -= ref0;       //remove offset
    value1 -= ref1;

    Serial.print(value0 > 40);    //send (boolean) pressed or not pressed
    Serial.print("\t");           //use if(value > threshold) to get the state of a button

    Serial.print(value1 > 40);
    Serial.print("\t\t");

    Serial.print(value0);             //send actual readingc
    Serial.print("\t");

    Serial.println(value1);
    delay(100);
}

ADCTouchClass ADCTouch;

Example code Results


0	0		1	2
0	0		1	1
0	0		0	2
0	0		1	0
0	0		1	0
0	0		1	1
0	0		1	3
0	0		0	1
0	0		1	0
0	0		1	1
0	0		0	2
0	0		2	1
0	0		5	1
1	0		293	8
1	0		338	8
1	0		382	2
1	0		355	3
0	0		1	0
0	0		1	0
0	0		1	2
0	0		0	2
0	0		1	4
0	0		1	6
0	0		0	10
0	0		1	15
0	1		2	70
0	1		1	78
0	1		2	77
0	1		2	79
0	1		2	84
0	1		2	70
0	0		1	5
0	0		1	2
0	0		1	0

Results on the left show 1 if the finger was sensed. On the right are the raw ADC values. Since the copper disc was attached to A0 the values of capacitance are higher as show in the results.

 

New! Comments

Have your say about what you just read! Leave me a comment in the box below.




Privacy Policy | Contact | About Me

Site Map | Terms of Use



Visit our Facebook Page:
To Visit Click Here


Recent Articles

  1. A Real Time Clock design (DS1307) with a PIC microcontroller

    Real Time Clock Design (FREE): A Free and Complete RTC design using the DS1307 and a PIC micro (16F88) also re-targetable. This PIC project uses an I2C Clock chip and 7-segment display to create a fou…

    Read more

  2. How to use the ADXL345 for movement sensing and more.

    With the ADXL345 acellerometer you can detect up to 16g! You can also find out how to use it for tap detection and more.

    Read more

  3. Arduino Interrupt : There are Some You May Never Have Heard About!

    Arduino Interrupt Tutorial: Find out how many external there are on an Arduino Uno - The answer is more than two!

    Read more

  4. Easy Switch Debounce

    Switch debounce: Three different ways to debounce input push switches with one amazing method that you can't miss.

    Read more

  5. How to use the ADS1115

    A tutorial on using the ADS1115 precision 16 bit ADC for low power use.

    Read more

  6. ESP8266 Webserver in Lua

    ESP8266 Webserver: This code shows you how to use lua to create a webserver using html button inputs to contrtol an LED on the ESP module.

    Read more

Readers Comments

"I wanted to thank
you so so so much
for all the information
you have provided in
your site it's

SUPERB and FANTASTIC."

- Ranish Pottath

"This site really is
the best and my favorite.
I find here many useful
projects and tips."

- Milan

bursach<at>gmail.com<

"Awesome site,
very, very easy and nice
to navigate!"


- Matt
matt_tr<at>
wolf359.cjb.net


Learn Microcontrollers

"Interested in
Microcontrollers?"

Sign up for The
Free 7 day guide:

FREE GUIDE : CLICK HERE


"I am a newbie to PIC
and I wanted to say
 how great your
site has been for me."


- Dave

de_scott<at>bellsouth.net

"Your site is a great
and perfect work.
congratulations."


- Suresh

integratredinfosys<at>
yahoo.com

"I couldn't find the correct
words to define
yourweb site.

Very useful, uncovered,
honest and clear.

Thanks so much for
your time and works.
Regards."


- Anon

Back to Top