mirror of
https://github.com/RobTillaart/Arduino.git
synced 2024-10-03 18:09:02 -04:00
0.1.9 MCP_ADC
This commit is contained in:
parent
a3e2c91f94
commit
531c273094
@ -1,3 +1,18 @@
|
||||
platforms:
|
||||
rpipico:
|
||||
board: rp2040:rp2040:rpipico
|
||||
package: rp2040:rp2040
|
||||
gcc:
|
||||
features:
|
||||
defines:
|
||||
- ARDUINO_ARCH_RP2040
|
||||
warnings:
|
||||
flags:
|
||||
|
||||
packages:
|
||||
rp2040:rp2040:
|
||||
url: https://github.com/earlephilhower/arduino-pico/releases/download/global/package_rp2040_index.json
|
||||
|
||||
compile:
|
||||
# Choosing to run compilation tests on 2 different Arduino platforms
|
||||
platforms:
|
||||
@ -9,3 +24,4 @@ compile:
|
||||
- esp32
|
||||
# - esp8266
|
||||
# - mega2560
|
||||
- rpipico
|
||||
|
39
libraries/MCP_ADC/CHANGELOG.md
Normal file
39
libraries/MCP_ADC/CHANGELOG.md
Normal file
@ -0,0 +1,39 @@
|
||||
# Change Log MCP_ADC
|
||||
|
||||
All notable changes to this project will be documented in this file.
|
||||
|
||||
The format is based on [Keep a Changelog](http://keepachangelog.com/)
|
||||
and this project adheres to [Semantic Versioning](http://semver.org/).
|
||||
|
||||
|
||||
## [0.1.9] - 2022-11-16
|
||||
- add RP2040 in build-CI
|
||||
- add changelog.md
|
||||
- minor edit readme.md
|
||||
- clean up unit test
|
||||
|
||||
|
||||
## [0.1.8] - 2021-12-21
|
||||
- update library.json
|
||||
- update license
|
||||
- minor edits
|
||||
|
||||
----
|
||||
|
||||
## [0.1.7] - 2021-11-07
|
||||
|
||||
## [0.1.6] - 2021-08-01
|
||||
|
||||
## [0.1.5] - 2021-07-31
|
||||
|
||||
## [0.1.4] - 2021-03-31
|
||||
|
||||
## [0.1.3] - 2021-02-04
|
||||
|
||||
## [0.1.2] - 2021-01-01
|
||||
|
||||
## [0.1.1] - 2020-08-14
|
||||
|
||||
## [0.1.0] - 2019-10-24
|
||||
- initial version.
|
||||
|
@ -1,7 +1,7 @@
|
||||
//
|
||||
// FILE: MCP_ADC.cpp
|
||||
// AUTHOR: Rob Tillaart
|
||||
// VERSION: 0.1.8
|
||||
// VERSION: 0.1.9
|
||||
// DATE: 2019-10-24
|
||||
// PURPOSE: Arduino library for MCP3002, MCP3004, MCP3008, MCP3202, MCP3204, MCP3208
|
||||
// URL: https://github.com/RobTillaart/MCP_ADC
|
||||
@ -31,25 +31,25 @@ void MCP_ADC::begin(uint8_t select)
|
||||
if (_hwSPI)
|
||||
{
|
||||
#if defined(ESP32)
|
||||
if (_useHSPI) // HSPI
|
||||
if (_useHSPI) // HSPI
|
||||
{
|
||||
mySPI = new SPIClass(HSPI);
|
||||
mySPI->end();
|
||||
mySPI->begin(14, 12, 13, select); // CLK=14 MISO=12 MOSI=13
|
||||
mySPI->begin(14, 12, 13, select); // CLK=14 MISO=12 MOSI=13
|
||||
}
|
||||
else // VSPI
|
||||
else // VSPI
|
||||
{
|
||||
mySPI = new SPIClass(VSPI);
|
||||
mySPI->end();
|
||||
mySPI->begin(18, 19, 23, select); // CLK=18 MISO=19 MOSI=23
|
||||
mySPI->begin(18, 19, 23, select); // CLK=18 MISO=19 MOSI=23
|
||||
}
|
||||
#else // generic hardware SPI
|
||||
#else // generic hardware SPI
|
||||
mySPI = &SPI;
|
||||
mySPI->end();
|
||||
mySPI->begin();
|
||||
#endif
|
||||
}
|
||||
else // software SPI
|
||||
else // software SPI
|
||||
{
|
||||
pinMode(_dataIn, INPUT);
|
||||
pinMode(_dataOut, OUTPUT);
|
||||
@ -70,7 +70,7 @@ void MCP_ADC::setGPIOpins(uint8_t clk, uint8_t miso, uint8_t mosi, uint8_t selec
|
||||
pinMode(_select, OUTPUT);
|
||||
digitalWrite(_select, HIGH);
|
||||
|
||||
mySPI->end(); // disable SPI
|
||||
mySPI->end(); // disable SPI
|
||||
mySPI->begin(clk, miso, mosi, select);
|
||||
}
|
||||
#endif
|
||||
@ -103,8 +103,8 @@ int16_t MCP_ADC::deltaRead(uint8_t channel)
|
||||
if (channel >= _channels) return 0;
|
||||
|
||||
int16_t val0 = differentialRead(channel & 0xFE);
|
||||
// int16_t val1 = differentialRead(channel | 0x01);
|
||||
// no need to read if val0 has a positive value
|
||||
// int16_t val1 = differentialRead(channel | 0x01);
|
||||
// no need to read if val0 has a positive value
|
||||
int16_t val1 = (val0 > 0) ? 0 : differentialRead(channel | 0x01);
|
||||
|
||||
if (channel & 0x01) return val1 - val0;
|
||||
@ -138,7 +138,7 @@ int16_t MCP_ADC::readADC(uint8_t channel, bool single)
|
||||
}
|
||||
mySPI->endTransaction();
|
||||
}
|
||||
else // Software SPI
|
||||
else // Software SPI
|
||||
{
|
||||
for (uint8_t b = 0; b < bytes; b++)
|
||||
{
|
||||
@ -153,7 +153,7 @@ int16_t MCP_ADC::readADC(uint8_t channel, bool single)
|
||||
}
|
||||
|
||||
|
||||
// MSBFIRST
|
||||
// MSBFIRST
|
||||
uint8_t MCP_ADC::swSPI_transfer(uint8_t val)
|
||||
{
|
||||
uint8_t clk = _clock;
|
||||
@ -175,7 +175,7 @@ uint8_t MCP_ADC::swSPI_transfer(uint8_t val)
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// MCP3002
|
||||
// MCP3002
|
||||
//
|
||||
MCP3002::MCP3002(uint8_t dataIn, uint8_t dataOut, uint8_t clock)
|
||||
:MCP_ADC(dataIn, dataOut, clock)
|
||||
@ -186,17 +186,17 @@ MCP3002::MCP3002(uint8_t dataIn, uint8_t dataOut, uint8_t clock)
|
||||
|
||||
uint8_t MCP3002::buildRequest(uint8_t channel, bool single, uint8_t * data)
|
||||
{
|
||||
// P17 fig 6.1 MCP3002
|
||||
data[0] = 0x44; // start bit + MSB first bit
|
||||
if (single) data[0] |= 0x20; // single read | differential
|
||||
if (channel) data[0] |= (channel << 4); // channel = 0 or 1;
|
||||
// P17 fig 6.1 MCP3002
|
||||
data[0] = 0x44; // start bit + MSB first bit
|
||||
if (single) data[0] |= 0x20; // single read | differential
|
||||
if (channel) data[0] |= (channel << 4); // channel = 0 or 1;
|
||||
return 2;
|
||||
}
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// MCP3004
|
||||
// MCP3004
|
||||
//
|
||||
MCP3004::MCP3004(uint8_t dataIn, uint8_t dataOut, uint8_t clock)
|
||||
:MCP_ADC(dataIn, dataOut, clock)
|
||||
@ -207,17 +207,17 @@ MCP3004::MCP3004(uint8_t dataIn, uint8_t dataOut, uint8_t clock)
|
||||
|
||||
uint8_t MCP3004::buildRequest(uint8_t channel, bool single, uint8_t * data)
|
||||
{
|
||||
// P21 fig 6.1 MCP3004/3008
|
||||
data[0] = 0x01; // start bit
|
||||
if (single) data[1] = 0x80; // single read | differential
|
||||
if (channel) data[1] |= (channel << 4); // channel
|
||||
// P21 fig 6.1 MCP3004/3008
|
||||
data[0] = 0x01; // start bit
|
||||
if (single) data[1] = 0x80; // single read | differential
|
||||
if (channel) data[1] |= (channel << 4); // channel
|
||||
return 3;
|
||||
}
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// MCP3008
|
||||
// MCP3008
|
||||
//
|
||||
MCP3008::MCP3008(uint8_t dataIn, uint8_t dataOut, uint8_t clock)
|
||||
:MCP_ADC(dataIn, dataOut, clock)
|
||||
@ -228,17 +228,17 @@ MCP3008::MCP3008(uint8_t dataIn, uint8_t dataOut, uint8_t clock)
|
||||
|
||||
uint8_t MCP3008::buildRequest(uint8_t channel, bool single, uint8_t * data)
|
||||
{
|
||||
// P21 fig 6.1 MCP3004/3008
|
||||
data[0] = 0x01; // start bit
|
||||
if (single) data[1] = 0x80; // single read | differential
|
||||
if (channel) data[1] |= (channel << 4); // channel
|
||||
// P21 fig 6.1 MCP3004/3008
|
||||
data[0] = 0x01; // start bit
|
||||
if (single) data[1] = 0x80; // single read | differential
|
||||
if (channel) data[1] |= (channel << 4); // channel
|
||||
return 3;
|
||||
}
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// MCP3202
|
||||
// MCP3202
|
||||
//
|
||||
MCP3202::MCP3202(uint8_t dataIn, uint8_t dataOut, uint8_t clock)
|
||||
:MCP_ADC(dataIn, dataOut, clock)
|
||||
@ -249,18 +249,18 @@ MCP3202::MCP3202(uint8_t dataIn, uint8_t dataOut, uint8_t clock)
|
||||
|
||||
uint8_t MCP3202::buildRequest(uint8_t channel, bool single, uint8_t * data)
|
||||
{
|
||||
// P17 fig 6.2 MCP3202
|
||||
data[0] = 0x01; // start bit
|
||||
data[1] = 0x20; // MSB first bit
|
||||
if (single) data[1] |= 0x80; // single read | differential
|
||||
if (channel) data[1] |= (channel << 6); // channel = 0 or 1;
|
||||
// P17 fig 6.2 MCP3202
|
||||
data[0] = 0x01; // start bit
|
||||
data[1] = 0x20; // MSB first bit
|
||||
if (single) data[1] |= 0x80; // single read | differential
|
||||
if (channel) data[1] |= (channel << 6); // channel = 0 or 1;
|
||||
return 3;
|
||||
}
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// MCP3204
|
||||
// MCP3204
|
||||
//
|
||||
MCP3204::MCP3204(uint8_t dataIn, uint8_t dataOut, uint8_t clock)
|
||||
:MCP_ADC(dataIn, dataOut, clock)
|
||||
@ -271,18 +271,18 @@ MCP3204::MCP3204(uint8_t dataIn, uint8_t dataOut, uint8_t clock)
|
||||
|
||||
uint8_t MCP3204::buildRequest(uint8_t channel, bool single, uint8_t * data)
|
||||
{
|
||||
// P21 fig 6.1 MCP3204/3208
|
||||
data[0] = 0x04; // start bit
|
||||
if (single) data[0] |= 0x02; // single read | differential
|
||||
if (channel > 3) data[0] |= 0x01; // msb channel (D2)
|
||||
if (channel) data[1] |= (channel << 6); // other 2 bits (D1 D0)
|
||||
// P21 fig 6.1 MCP3204/3208
|
||||
data[0] = 0x04; // start bit
|
||||
if (single) data[0] |= 0x02; // single read | differential
|
||||
if (channel > 3) data[0] |= 0x01; // MSB channel (D2)
|
||||
if (channel) data[1] |= (channel << 6); // other 2 bits (D1 D0)
|
||||
return 3;
|
||||
}
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// MCP3208
|
||||
// MCP3208
|
||||
//
|
||||
MCP3208::MCP3208(uint8_t dataIn, uint8_t dataOut, uint8_t clock)
|
||||
:MCP_ADC(dataIn, dataOut, clock)
|
||||
@ -293,11 +293,11 @@ MCP3208::MCP3208(uint8_t dataIn, uint8_t dataOut, uint8_t clock)
|
||||
|
||||
uint8_t MCP3208::buildRequest(uint8_t channel, bool single, uint8_t * data)
|
||||
{
|
||||
// P21 fig 6.1 MCP3204/3208
|
||||
data[0] = 0x04; // start bit
|
||||
if (single) data[0] |= 0x02; // single read | differential
|
||||
if (channel > 3) data[0] |= 0x01; // msb channel (D2)
|
||||
if (channel) data[1] |= (channel << 6); // other 2 bits (D1 D0)
|
||||
// P21 fig 6.1 MCP3204/3208
|
||||
data[0] = 0x04; // start bit
|
||||
if (single) data[0] |= 0x02; // single read | differential
|
||||
if (channel > 3) data[0] |= 0x01; // MSB channel (D2)
|
||||
if (channel) data[1] |= (channel << 6); // other 2 bits (D1 D0)
|
||||
return 3;
|
||||
}
|
||||
|
||||
|
@ -2,7 +2,7 @@
|
||||
//
|
||||
// FILE: MCP_ADC.h
|
||||
// AUTHOR: Rob Tillaart
|
||||
// VERSION: 0.1.8
|
||||
// VERSION: 0.1.9
|
||||
// DATE: 2019-10-24
|
||||
// PURPOSE: Arduino library for MCP_ADC
|
||||
// URL: https://github.com/RobTillaart/MCP_ADC
|
||||
@ -13,7 +13,7 @@
|
||||
#include "SPI.h"
|
||||
|
||||
|
||||
#define MCP_ADC_LIB_VERSION (F("0.1.8"))
|
||||
#define MCP_ADC_LIB_VERSION (F("0.1.9"))
|
||||
|
||||
|
||||
class MCP_ADC
|
||||
@ -32,17 +32,17 @@ public:
|
||||
void setSPIspeed(uint32_t speed);
|
||||
uint32_t getSPIspeed() { return _SPIspeed; };
|
||||
|
||||
// debugging
|
||||
// debugging
|
||||
bool usesHWSPI() { return _hwSPI; };
|
||||
|
||||
// ESP32 specific
|
||||
// ESP32 specific
|
||||
#if defined(ESP32)
|
||||
void selectHSPI() { _useHSPI = true; };
|
||||
void selectVSPI() { _useHSPI = false; };
|
||||
bool usesHSPI() { return _useHSPI; };
|
||||
bool usesVSPI() { return !_useHSPI; };
|
||||
|
||||
// to overrule ESP32 default hardware pins
|
||||
// to overrule ESP32 default hardware pins
|
||||
void setGPIOpins(uint8_t clk, uint8_t miso, uint8_t mosi, uint8_t select);
|
||||
#endif
|
||||
|
||||
@ -57,9 +57,9 @@ protected:
|
||||
bool _hwSPI;
|
||||
uint8_t _channels;
|
||||
int16_t _maxValue;
|
||||
uint32_t _SPIspeed = 1000000; // 1MHz is a safe value (datasheet); in a test 4 MHz worked.
|
||||
uint32_t _SPIspeed = 1000000; // 1 MHz is a safe value (datasheet); in a test 4 MHz worked.
|
||||
|
||||
// derived classes must implement this one
|
||||
// derived classes must implement buildRequest() function.
|
||||
virtual uint8_t buildRequest(uint8_t channel, bool single, uint8_t * data) = 0;
|
||||
|
||||
int16_t readADC(uint8_t channel, bool single);
|
||||
@ -75,9 +75,11 @@ protected:
|
||||
uint32_t _count;
|
||||
};
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
//
|
||||
// DERIVED CLASSES
|
||||
//
|
||||
class MCP3002 : public MCP_ADC
|
||||
{
|
||||
public:
|
||||
@ -85,6 +87,7 @@ public:
|
||||
uint8_t buildRequest(uint8_t channel, bool single, uint8_t * data);
|
||||
};
|
||||
|
||||
|
||||
class MCP3004 : public MCP_ADC
|
||||
{
|
||||
public:
|
||||
@ -92,6 +95,7 @@ public:
|
||||
uint8_t buildRequest(uint8_t channel, bool single, uint8_t * data);
|
||||
};
|
||||
|
||||
|
||||
class MCP3008 : public MCP_ADC
|
||||
{
|
||||
public:
|
||||
|
@ -134,10 +134,22 @@ which indicates that the last 2 bits got lost due to signal deformation.
|
||||
For hardware SPI the ESP32 uses the VSPI pins. (see ESP examples).
|
||||
|
||||
|
||||
## Operations
|
||||
|
||||
See examples.
|
||||
|
||||
|
||||
## Future
|
||||
|
||||
#### must
|
||||
- documentation
|
||||
- testing, a lot ...
|
||||
|
||||
|
||||
#### should
|
||||
|
||||
|
||||
#### could
|
||||
- analogRead (mask, int array\[8\] ) read ports (set in mask) in an array in one call.
|
||||
would this save time?
|
||||
|
||||
@ -146,9 +158,5 @@ For hardware SPI the ESP32 uses the VSPI pins. (see ESP examples).
|
||||
|
||||
- get / setF(float A, float B) => float readF(channel) output = A\*value + B;
|
||||
it actually does float mapping. As it implies the same mapping for all it might
|
||||
not be that useful => multmap
|
||||
not be that useful => multimap
|
||||
|
||||
|
||||
## Operations
|
||||
|
||||
See examples.
|
||||
|
@ -13,7 +13,7 @@
|
||||
|
||||
MCP3002 mcp2;
|
||||
MCP3004 mcp4;
|
||||
MCP3008 mcp8(11,12,13); // software spi
|
||||
MCP3008 mcp8(11, 12, 13); // software spi
|
||||
// MCP3008 mcp8; // hardware spi
|
||||
MCP3202 mcp22;
|
||||
MCP3204 mcp24;
|
||||
@ -81,6 +81,24 @@ void setup()
|
||||
test_3();
|
||||
}
|
||||
|
||||
// on UNO there is no difference above 8MHz (half CPU clock)
|
||||
Serial.println("***************************************\n");
|
||||
for (int s = 1; s <= 16; s *= 2)
|
||||
{
|
||||
Serial.println(s * 1000000UL);
|
||||
mcp22.setSPIspeed(s * 1000000UL);
|
||||
test_4();
|
||||
}
|
||||
|
||||
// on UNO there is no difference above 8MHz (half CPU clock)
|
||||
Serial.println("***************************************\n");
|
||||
for (int s = 1; s <= 16; s *= 2)
|
||||
{
|
||||
Serial.println(s * 1000000UL);
|
||||
mcp24.setSPIspeed(s * 1000000UL);
|
||||
test_5();
|
||||
}
|
||||
|
||||
// on UNO there is no difference above 8MHz (half CPU clock)
|
||||
Serial.println("***************************************\n");
|
||||
for (int s = 1; s <= 16; s *= 2)
|
||||
@ -210,6 +228,80 @@ void test_3()
|
||||
}
|
||||
|
||||
|
||||
void test_4()
|
||||
{
|
||||
uint32_t val = 0;
|
||||
|
||||
start = micros();
|
||||
for (int channel = 0; channel < mcp22.channels(); channel++)
|
||||
{
|
||||
val += mcp22.analogRead(channel);
|
||||
}
|
||||
stop = micros();
|
||||
Serial.print("mcp22.analogRead()\t2x: \t");
|
||||
Serial.println(stop - start);
|
||||
delay(10);
|
||||
|
||||
start = micros();
|
||||
for (int channel = 0; channel < mcp22.channels(); channel++)
|
||||
{
|
||||
val += mcp22.differentialRead(channel);
|
||||
}
|
||||
stop = micros();
|
||||
Serial.print("mcp22.differentialRead() 2x: \t");
|
||||
Serial.println(stop - start);
|
||||
delay(10);
|
||||
|
||||
start = micros();
|
||||
for (int channel = 0; channel < mcp22.channels(); channel++)
|
||||
{
|
||||
val += mcp22.deltaRead(channel);
|
||||
}
|
||||
stop = micros();
|
||||
Serial.print("mcp22.deltaRead()\t2x: \t");
|
||||
Serial.println(stop - start);
|
||||
Serial.println();
|
||||
delay(10);
|
||||
}
|
||||
|
||||
|
||||
void test_5()
|
||||
{
|
||||
uint32_t val = 0;
|
||||
|
||||
start = micros();
|
||||
for (int channel = 0; channel < mcp24.channels(); channel++)
|
||||
{
|
||||
val += mcp24.analogRead(channel);
|
||||
}
|
||||
stop = micros();
|
||||
Serial.print("mcp24.analogRead()\t4x: \t");
|
||||
Serial.println(stop - start);
|
||||
delay(10);
|
||||
|
||||
start = micros();
|
||||
for (int channel = 0; channel < mcp24.channels(); channel++)
|
||||
{
|
||||
val += mcp24.differentialRead(channel);
|
||||
}
|
||||
stop = micros();
|
||||
Serial.print("mcp24.differentialRead() 4x: \t");
|
||||
Serial.println(stop - start);
|
||||
delay(10);
|
||||
|
||||
start = micros();
|
||||
for (int channel = 0; channel < mcp24.channels(); channel++)
|
||||
{
|
||||
val += mcp24.deltaRead(channel);
|
||||
}
|
||||
stop = micros();
|
||||
Serial.print("mcp24.deltaRead()\t4x: \t");
|
||||
Serial.println(stop - start);
|
||||
Serial.println();
|
||||
delay(10);
|
||||
}
|
||||
|
||||
|
||||
void test_6()
|
||||
{
|
||||
uint32_t val = 0;
|
||||
|
@ -15,7 +15,7 @@
|
||||
"type": "git",
|
||||
"url": "https://github.com/RobTillaart/MCP_ADC.git"
|
||||
},
|
||||
"version": "0.1.8",
|
||||
"version": "0.1.9",
|
||||
"license": "MIT",
|
||||
"frameworks": "*",
|
||||
"platforms": "*",
|
||||
|
@ -1,5 +1,5 @@
|
||||
name=MCP_ADC
|
||||
version=0.1.8
|
||||
version=0.1.9
|
||||
author=Rob Tillaart <rob.tillaart@gmail.com>
|
||||
maintainer=Rob Tillaart <rob.tillaart@gmail.com>
|
||||
sentence=Arduino library for MCP3002, MCP3004, MCP3008, MCP3202, MCP3204, MCP3208
|
||||
|
@ -47,19 +47,6 @@ unittest_teardown()
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
unittest(test_new_operator)
|
||||
{
|
||||
assertEqualINF(exp(800));
|
||||
assertEqualINF(0.0/0.0);
|
||||
assertEqualINF(42);
|
||||
|
||||
assertEqualNAN(INFINITY - INFINITY);
|
||||
assertEqualNAN(0.0/0.0);
|
||||
assertEqualNAN(42);
|
||||
}
|
||||
*/
|
||||
|
||||
unittest(test_constructor)
|
||||
{
|
||||
MCP3002 ADC2;
|
||||
|
Loading…
Reference in New Issue
Block a user