Aggiungere canali ADC ad Arduino UNO

Arduino UNO dispone di 6 canali ADC che permettono di acquisire segnali analogici con una risoluzione di 10 bit. Questo significa che il dato analogico può essere espresso con un valore digitale compreso tra 0 e 1024 ( 2^10=1024). Nella maggior parte dei tutorial che ho scritto la risoluzione di 10 bit è stata più che sufficiente per acquisire i segnali proveniente dai sensore analogici che usai.

Capita però che in particolari casi abbiamo bisogno di avere una risoluzione maggiore e piuttosto che cambiare scheda, è possibile utilizzare un convertitore analogico digitale esterno, impiegando un integrato apposito.

Gli ADC possono avere uno o più canali, risoluzioni e velocità di campionamento differenti. Quale scegliere dipende sostanzialmente dalle specifiche di progetto.
In uno degli articoli precedenti ho utilizzato l’integrato PCF8591. Questo integrato ha 4 porte ADC a 8 bit e 1 porta DAC.

In questo articolo invece andremmo ad utilizzare l’integrato MCP3201 che ha un canale con risoluzione di 12 bit.

Il convertitore A/D MCP3201

Questo convertitore a singolo canale di tipo sample & hold, viene interfacciato con il microcontrollore tramite bus SPI. Nella figura seguente viene illustrato lo schema a blocchi.

Convertitore analogico digitale MCP3201
Convertitore analogico digitale MCP3201

L’integrato MCP3201 ha un range di tensioni di lavoro che vanno da 2.7 V a 5.5 Vdc, la corrente di lavoro è di circa 300uA mentre in standby assorbe circa 500nA, quindi si presta in molte applicazioni dove il risparmio energetico è fondamentale.

Nella figura seguente viene proposto lo schema elettrico del circuito di prova.

Collegamenti tra arduino uno e mcp3201
Collegamenti Arduino UNO MCP3201

La prima cosa da notare è che la linea MOSI (pin 11 di Arduino UNO) del bus SPI non viene utilizzata. Questo perchè per ricevere i dati dall’MCP3201 viene utilizzata la line CS e il segnale di clock del bus SPI. Nella figura seguente viene mostrato il grafico dei timing delle linee CS, CLK e Dout:

MCP3201 timing
Andamento dei segnali MCP3201

Il microcontrollore pone a livello basso la linea CS per avviare la comunicazione con l’integrato MCP3201. A questo punto il segnale di clock generato dal microcontrollore viene utilizzato per avviare la conversione analogico digitale. Nella figura seguente viene illustrato dettagliatamente il ciclo di conversione e di trasferimento dei dati.

ADC MCP 3201 timing dettagliato

Osserviamo il segnale di clock, dopo il terzo impulso è disponibile sulla linea Dout il bit più significativo (MSB) del dato analogico. Gli impulsi seguenti del segnale di clock permettono di avere i restanti bit del dato digitale. Da notare che il bit B1 viene ripetuto al sedicesimo clock e deve essere rimosso quando andiamo a ricostruire il dato digitale del segnale analogico. Questo può essere fatto shiftando a destra tutti i bit di una posizione.

Terminata la lettura dei due bute il microcontrollore mette al livello alto la line CS.

Il codice di esempio

Il seguente codice permette di leggere il valore della conversione analogico digitale dell’integrato MCP3201

#include <SPI.h>

#define ADC_SELECT 10

int PrimoByte = 0;
int SecondoByte = 0;
int Lettura = 0;

void setup() {

  pinMode (ADC_SELECT, OUTPUT);

  //init del MCP3201
  digitalWrite(ADC_SELECT, 0);
  delay(100);
  digitalWrite(ADC_SELECT, 1);

  //init seriale
  Serial.begin(9600);
  delay(100);
  
  // init SPI
  SPI.begin();
  delay(100);
}

void loop() {

  digitalWrite(ADC_SELECT, 0);
  PrimoByte = SPI.transfer(0);
  SecondoByte = SPI.transfer(0);
  digitalWrite(ADC_SELECT, 1);

  SPI.endTransaction();

  Lettura = ((PrimoByte & 0x1F) << 8) | SecondoByte;

  //elimino il bit di ridondanza
  Lettura = Lettura >> 1;

  Serial.print("Dato analogico= ");
  Serial.println(Lettura);

  delay(500);

}

Il costo dell’integrato mcp3201 è di circa 2.5€.