You can easily wire this breakout to any microcontroller, we'll be using an Arduino. For another kind of microcontroller, just make sure it has I2C, then port the code - its pretty simple stuff!
  • Connect Vin to the power supply, 3-5V is fine. Use the same voltage that the microcontroller logic is based off of. For most Arduinos, that is 5V
  • Connect GND to common power/data ground
  • Connect the SCL pin to the I2C clock SCL pin on your Arduino. On an UNO & '328 based Arduino, this is also known as A5, on a Mega it is also known as digital 21 and on a Leonardo/Micro, digital 3
  • Connect the SDA pin to the I2C data SDA pin on your Arduino. On an UNO & '328 based Arduino, this is also known as A4, on a Mega it is also known as digital 20 and on a Leonardo/Micro, digital 2

The MPR121 ADDR pin is pulled to ground and has a default I2C address of 0x5A
You can adjust the I2C address by connecting ADDR to other pins:

  • ADDR not connected: 0x5A
  • ADDR tied to 3V: 0x5B
  • ADDR tied to SDA: 0x5C
  • ADDR tied to SCL: 0x5D

We suggest sticking with the default for the test demo, you can always change it later.

Download Adafruit_MPR121

To begin reading sensor data, you will need to download the Adafruit_MPR121 library from the Arduino library manager.

Open up the Arduino library manager:

Seach for the Adafruit MPR121 library and install it

We also have a great tutorial on Arduino library installation at:

Load Demo

Open up File->Examples->Adafruit_MPR121->MPR121test and upload to your Arduino wired up to the sensor
Thats it! Now open up the serial terminal window at 9600 speed to begin the test.
Make sure you see the "MPR121 found!" text which lets you know that the sensor is wired correctly.

Now touch the 12 pads with your fingertip to activate the touch-detection
For most people, that's all you'll need! Our code keeps track of the 12 'bits' for each touch and has logic to let you know when a contect is touched or released.

If you're feeling more advanced, you can see the 'raw' data from the chip. Basically, what it does it keep track of the capacitance it sees with "counts". There's some baseline count number that depends on the temperature, humidity, PCB, wire length etc. Where's a dramatic change in number, its considered that a person touched or released the wire.

Comment this "return" line to activate that mode:
  // comment out this line for detailed data from the sensor!
Then reupload. Open up the serial console again - you'll see way more text

Each reading has 12 columns. One for each sensor, #0 to #11. There's two rows, one for the 'baseline' and one for the current filtered data reading. When the current reading is within about 12 counts of the baseline, that's considered untouched. When the reading is more than 12 counts smaller than the baseline, the chip reports a touch.
Most people don't need raw data too much, but it can be handy if doing intense debugging. It can be helpful if you are tweaking your sensors to get good responsivity.

Library Reference

Since the sensors use I2C, there's no pins to be defined during instantiation. You can just use:
Adafruit_MPR121 cap = Adafruit_MPR121();
When you initialize the sensor, pass in the I2C address. It can range from 0x5A (default) to 0x5D
begin() returns true if the sensor was found on the I2C bus, and false if not.

Touch detection

99% of users will be perfectly happy just querying what sensors are currentlt touched. You can read all at once with
Which returns a 16 bit value. Each of the bottom 12 bits refers to one sensor. So if you want to test if the #4 is touched, you can use
if (cap.touched() & (1 << 4)) { do something }
You can check its not touched with:
if (! (cap.touched() & (1 << 4)) ) { do something }

Raw Data

You can grab the current baseline and filtered data for each sensor with
It returns a 16-bit number which is the number of counts, there's no unit like "mg" or "capacitance". The baseline is initialized to the current ambient readings when the sensor begin() is called - you can always reinitialize by re-calling begin()! The baseline will drift a bit, that's normal! It is trying to compensate for humidity and other environmental changes.

If you need to change the threshholds for touch detection, you can do that with
setThreshholds(uint8_t touch, uint8_t release)
By default, the touch threshhold is 12 counts, and the release is 6 counts. It's reset to these values whenever you call begin() by the way.

This guide was first published on Jul 25, 2014. It was last updated on Jul 13, 2024.

This page (Arduino) was last updated on Mar 08, 2024.

Text editor powered by tinymce.