|
|
View previous topic :: View next topic |
Author |
Message |
ressas
Joined: 15 Nov 2019 Posts: 135
|
FDC1004 Capacitive Sensor |
Posted: Sat May 16, 2020 6:46 am |
|
|
Hello to everyone.
I also tried the last capacitive integration I have.
But I saw that the values in him also slipped.
I have tried MPR121 before.
His datasheet and appnotes are too long.
I made progress with the help of Ttelmah and temtronic.
But I did not get proper results.
The integrated FDC1004 I have just tried. Its code and datasheet are shorter.
I am throwing my own code below. Please tell me what I did wrong. The values I read are shifting by themselves. However, they should have changed only when the object approached.
I was unable to make any progress for the MPR121. I think this will be my last try.
Thank you for your help
FDC1004.H
Code: |
//This registers for read value
#define MEAS1_MSB 0x00 // Read FOR Firs channel MSB (16 bit)
#define MEAS1_LSB 0x01 // Read FOR Firs channel LSB (8 bit msb)
#define MEAS2_MSB 0x02 // Read FOR Second channel MSB (16 bit)
#define MEAS2_LSB 0x03 // Read FOR Second channel LSB (8 bit msb)
#define MEAS3_MSB 0x04 // Read FOR Third channel MSB (16 bit)
#define MEAS3_LSB 0x05 // Read FOR Third channel LSB (8 bit msb)
#define MEAS4_MSB 0x06 // Read FOR fourth channel MSB (16 bit)
#define MEAS4_LSB 0x07 // Read FOR fourth channel LSB (8 bit msb)
//Measurement Configuration
#define CONF_MEAS1 0x08 // Firs channel
#define CONF_MEAS2 0x09 // Second channel
#define CONF_MEAS3 0x0A // Third channel
#define CONF_MEAS4 0x0B // Fourth channel
//FDC1004 General Configuration
#define FDC_CONF 0x0C
//Adding internal capacitance
#define OFFSET_CAL_CIN1 0x0D
#define OFFSET_CAL_CIN2 0x0E
#define OFFSET_CAL_CIN3 0x0F
#define OFFSET_CAL_CIN4 0x10
//Fain Offset
#define GAIN_CAL_CIN1 0x11
#define GAIN_CAL_CIN2 0x12
#define GAIN_CAL_CIN3 0x13
#define GAIN_CAL_CIN4 0x14
#define Manufacturer_ID 0xFE // ?
#define Device_ID 0xFF // ?
#define dev_adds 0xA0 // FDC1004 i2c address
|
FDC1004.C
Code: |
#include "fdc1004.h"
//This i2c function sends 16 bits data
void FDC1004_write( unSIGNED INT16 address, unSIGNED INT16 data) {
i2c_start();
i2c_write(dev_adds);
i2c_write(address & 0xff);
i2c_write(data >>8);
i2c_write(data);
i2c_stop();
}
//This i2c function receive 16 bits data
unSIGNED INT16 FDC1004_read(unSIGNED INT8 address) {
unSIGNED INT16 data;
i2c_start();
i2c_write(dev_adds);
i2c_write(address);
i2c_start();
i2c_write(dev_adds + 1);
unSIGNED INT8 datahigh=i2c_read();
unSIGNED INT8 datalow=i2c_read(0);
data=make16(datahigh,datalow);
i2c_stop();
return data;
}
void FDC1004_init()
{
//Measurement Configuration
// ||CHA (+) slct ||CHB (-) slct ||CAPDAC ||Reserved
FDC1004_write(CONF_MEAS1, 0x0000); // ||000 ||000 ||00000 ||00000
FDC1004_write(CONF_MEAS2, 0x2400); // ||001 ||001
FDC1004_write(CONF_MEAS3, 0x4800); // ||010 ||010
FDC1004_write(CONF_MEAS4, 0x6C00); // ||011 ||011
//FDC1004 General Configuration
FDC1004_write(FDC_CONF, 0x01F0); // ||RST/NRML ||Reserved ||Sample Rate ||Reserved ||Repead Mesurement
// || /1 ||000 ||01 ||0 ||1
// ||CH 1 2 3 4 Select ||Mesurement Done 1 2 3 4 [READ ONLY]
// || 1 1 1 1 || 0 0 0 0 [READ ONLY]
// used to add capacitance above the measured value. (+ - 16pf)
// It is used to subtract the measured value above the parasites.
// I'm not sure it has ideal values
FDC1004_write(OFFSET_CAL_CIN1, 0x4fff); //
FDC1004_write(OFFSET_CAL_CIN2, 0x4fff); //
FDC1004_write(OFFSET_CAL_CIN3, 0x4fff); //
FDC1004_write(OFFSET_CAL_CIN4, 0x4fff); //
//Gain: I'm not sure what these registers do
// I'm not sure it has ideal values
FDC1004_write(GAIN_Cal_CIN1, 0x4000); //Gain = 1
FDC1004_write(GAIN_Cal_CIN2, 0x4000); //Gain = 1
FDC1004_write(GAIN_Cal_CIN3, 0x4000); //Gain = 1
FDC1004_write(GAIN_Cal_CIN4, 0x4000); //Gain = 1
}
|
Main.C
Code: |
#include <18f46k22.h>
//#fuses clko
#fuses INTRC_IO,NOWDT,NOPROTECT,PUT,LVP,NOBROWNOUT ,PLLEN, NOmclr
#use delay(clock=64000000)
#use rs232(baud=9600,parity=N,xmit=PIN_c6,rcv=PIN_c7,bits=8)
#use i2c(Master,sda=PIN_c4,scl=PIN_c3)
#include "FDC1004.c"
void main ()
{
setup_oscillator(OSC_64MHZ , OSC_PLL_ON);
FDC1004_init();
//1. Channel Variable
unSIGNED INT16 MEAS1_MSB_1=0;
unSIGNED INT16 MEAS1_LSB_1=0;
unSIGNED INT8 MEAS1_LSB_1_H=0;
unSIGNED INT8 MEAS1_LSB_1_L=0;
unSIGNED INT16 done1 = 0 ;
//2. Channel Variable
unSIGNED INT16 MEAS2_MSB_1=0;
unSIGNED INT16 MEAS2_LSB_1=0;
unSIGNED INT8 MEAS2_LSB_1_H=0;
unSIGNED INT8 MEAS2_LSB_1_L=0;
//3. Channel Variable
unSIGNED INT16 MEAS3_MSB_1=0;
unSIGNED INT16 MEAS3_LSB_1=0;
unSIGNED INT8 MEAS3_LSB_1_H=0;
unSIGNED INT8 MEAS3_LSB_1_L=0;
//4. Channel Variable
unSIGNED INT16 MEAS4_MSB_1=0;
unSIGNED INT16 MEAS4_LSB_1=0;
unSIGNED INT8 MEAS4_LSB_1_H=0;
unSIGNED INT8 MEAS4_LSB_1_L=0;
unSIGNED INT32 value_1=0;
unSIGNED INT32 value_2=0;
unSIGNED INT32 value_3=0;
unSIGNED INT32 value_4=0;
while(true){
//1.Channel Read
done1 = FDC1004_read(FDC_CONF); //Read FDC_Conf Register
if(bit_test(done1,3)) // 3. bit ?= 1
{
MEAS1_LSB_1 = FDC1004_read(MEAS1_LSB); //Read Fisrt channel LSB
MEAS1_MSB_1 = FDC1004_read(MEAS1_MSB); //Read Fisrt channel MSB
MEAS1_LSB_1_H = make8(MEAS1_LSB_1,1);
MEAS1_LSB_1_L = make8(MEAS1_LSB_1,0);
value_1=make32(MEAS1_MSB_1,MEAS1_LSB_1_H); //[MEAS1_MSB 16 bit ]+ [MEAS1_LSB 8 bit] = 24 bit
}
//2.Channel Read
if(bit_test(done1,2))
{
MEAS2_LSB_1 = FDC1004_read(MEAS2_LSB);
MEAS2_MSB_1 = FDC1004_read(MEAS2_MSB);
MEAS2_LSB_1_H = make8(MEAS2_LSB_1,1);
MEAS2_LSB_1_L = make8(MEAS2_LSB_1,0);
value_2=make32(MEAS2_MSB_1,MEAS2_LSB_1_H);
}
//3.Channel Read
if(bit_test(done1,1))
{
MEAS3_LSB_1 = FDC1004_read(MEAS3_LSB);
MEAS3_MSB_1 = FDC1004_read(MEAS3_MSB);
MEAS3_LSB_1_H = make8(MEAS3_LSB_1,1);
MEAS3_LSB_1_L = make8(MEAS3_LSB_1,0);
value_3=make32(MEAS3_MSB_1,MEAS3_LSB_1_H);
}
//4.Channel Read
if(bit_test(done1,0))
{
MEAS4_LSB_1 = FDC1004_read(MEAS4_LSB);
MEAS4_MSB_1 = FDC1004_read(MEAS4_MSB);
MEAS4_LSB_1_H = make8(MEAS4_LSB_1,1);
MEAS4_LSB_1_L = make8(MEAS4_LSB_1,0);
value_4=make32(MEAS4_MSB_1,MEAS4_LSB_1_H);
}
printf(" %ld %ld %ld %ld\n" , value_1, value_2, value_3, value_4);
}}
|
|
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19504
|
|
Posted: Sat May 16, 2020 7:11 am |
|
|
Seriously, as pointed out before, a huge amount depends on the actual
design of your sensor. How the board is laid out...
Now that you have a second chip also experiencing bad drift, says to me
that you have not really got a good design.
Careful design of the sensor pads, can reduce EMI, and how much
things in directions that are not required, affect the reading.
Consider not using a chip at ll, but just using the PIC. All can do capacitive
sensing. For some the relaxation oscillator and counter approach, others
have the CSM or CTMU modules giving alternative ways of doing the
sensing.
Learn how the values change, and then write the code to compensate.
All capacitive sensors will drift. Temperature, humidity, and nearby mechanical
changes will affect the output. The key in the design is to have some way
to slowly adjust for such changes. |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9224 Location: Greensville,Ontario
|
|
Posted: Sat May 16, 2020 9:51 am |
|
|
As Mr. T points out the actual sensor is CRITCAL and NO amount of code can compensate for a poorly designed/built sensor. You could fill a library with 1,000s of books written about 'how to design/build/calibrate' capacitive sensors and in the end it always takes a LOT of 'testing on the bench' to get it 'right'.
In addition to the design, you need to compensate for ever changing environmental conditions, especially humidity.
We don't know your actual requirement for the 'sensor' is, perhaps there's a better option, maybe IR, uwave, ????
Jay |
|
|
|
|
You cannot post new topics in this forum You cannot reply to topics in this forum You cannot edit your posts in this forum You cannot delete your posts in this forum You cannot vote in polls in this forum
|
Powered by phpBB © 2001, 2005 phpBB Group
|