In questo tutorial imparerai come utilizzare il sensore di prossimità e luce APDS-9930 con un Arduino o qualsiasi altro microcontrollore comune (ESP32/ESP8266).
L’APDS-9930 è un sensore molto piccolo spesso usato in smartphone e tablet per la regolazione automatica della luminosità dello schermo e il rilevamento di prossimità durante le chiamate. Puoi anche usarlo come semplice rilevatore di gesti che attiva luci o altri dispositivi quando muovi la mano davanti ad esso.
Componenti necessari
Per questo progetto ti serviranno un sensore APDS-9930 e un microcontrollore. Ho usato un Arduino Uno, ma qualsiasi altro Arduino o ESP32/ESP8266 andrà bene, purché fornisca un’uscita di alimentazione a 3.3V.

Sensore APDS-9930

Arduino Uno

Cavo USB per Arduino UNO

Set di fili Dupont

Breadboard
Makerguides is a participant in affiliate advertising programs designed to provide a means for sites to earn advertising fees by linking to Amazon, AliExpress, Elecrow, and other sites. As an Affiliate we may earn from qualifying purchases.
Caratteristiche del sensore di prossimità e luce APDS-9930
L’APDS-9930 è un sensore minuscolo (3.94 x 2.36 x 1.35 mm) per il rilevamento di prossimità e la misurazione digitale della luce ambientale. L’immagine sotto mostra il retro e il fronte del chip APDS-9930.

Il sensore misura la prossimità di un oggetto inviando un impulso IR tramite il LED IR integrato e misurando l’intensità della luce riflessa. La luce ambientale viene rilevata da due fotodiodi. Un fotodiodo rileva luce visibile più infrarossa (Ch0) e l’altro rileva solo infrarossi (Ch1). Un microprocessore integrato combina i due segnali per calcolare un livello di luce ambientale (ALS) che approssima la risposta dell’occhio umano. Vedi l’immagine sotto con il diagramma a blocchi funzionale dell’APDS-9930:

L’APDS-9930 permette anche di impostare soglie superiori e inferiori per i valori di luce e prossimità, e invia un segnale di interrupt (INT) se queste soglie vengono superate. Per la comunicazione e la programmazione, l’APDS-9930 fornisce un’interfaccia I2C (SCL, SDA)
La lista seguente riassume le principali caratteristiche dell’APDS-9930:
- Rilevamento della luce ambientale (ALS)
- Risposta approssimativa alla visione umana
- Capacità di interrupt programmabile con soglie superiori e inferiori
- Risoluzione fino a 16 bit
- Funzionamento ad alta sensibilità dietro vetro scuro
- Prestazioni a basso lumen di 0,1 lux
- Rilevamento di prossimità
- Completamente calibrato per rilevamento fino a 100 mm
- LED infrarosso integrato e driver LED sincrono
- Elimina la calibrazione in fabbrica del sensore di prossimità
- Timer di attesa programmabile
- Consumo in stato di attesa – tipico 90μA
- Intervallo programmabile da 2,7 ms a oltre 8 secondi
- Interfaccia I2C compatibile
- Fino a 400kHz (modalità I2C veloce)
- Pin di interrupt dedicato
- Consumo in modalità sleep – tipico 2,2μA
Per informazioni più dettagliate consulta il datasheet linkato qui sotto:
Scheda breakout per APDS-9930
Il chip APDS-9930 è troppo piccolo per collegarlo direttamente a un Arduino. Di solito serve una scheda breakout come quella mostrata sotto:

Le schede breakout per l’APDS-9930 solitamente hanno sei pin:
- VCC : Alimentazione (2.4 – 3.6V)
- GND : Massa
- VL : Alimentazione LED IR
- SDA : Segnale dati I2C
- SCL : Segnale clock I2C
- INT : Pin di interrupt
Nella maggior parte dei casi ti serviranno solo i pin di alimentazione (VCC, GND) e i pin per la comunicazione I2C (SCL, SDA). Il pin INT si attiva se la luce ambientale o la prossimità superano le soglie programmabili.
VL ti permette di fornire alimentazione esterna al LED IR. Sul retro della scheda breakout c’è un ponticello di saldatura che devi chiudere se vuoi usare VL per alimentare il LED IR.
Nota che l’APDS-9930 funziona a 3.3V e che la maggior parte delle schede breakout solitamente non ha un regolatore di tensione. Questo significa che devi collegare VCC a 3.3V e non puoi usare l’uscita 5V di un Arduino!
Collegare l’APDS-9930 ad Arduino
Grazie all’interfaccia I2C dell’APDS-9930, collegarlo ad Arduino è semplice. Prima collega il pin SCL della scheda breakout APDS-9930 ad A5 dell’Arduino. Allo stesso modo, collega SDA ad A4 dell’Arduino. Poi collega la massa a GND e 3.3V a VCC dell’APDS-9930.

Assicurati di usare 3.3V come alimentazione. Il sensore APDS-9930 non è progettato per 5V e le schede breakout tipiche per APDS-9930 non hanno un regolatore di tensione.
Installare la libreria APDS-9930
Prima di poter usare l’APDS-9930 dobbiamo installare una libreria. L’unica libreria che ho trovato è la APDS-9930 Library di Depau, che non è più mantenuta ma funziona ancora bene. Per installarla vai su repo e clicca sul pulsante verde “Code”. Poi clicca su “Download Zip” come mostrato sotto:

Poi vai su “Sketch” -> “Include Library” -> “Add .Zip Library..” e seleziona il file “APDS9930-master.zip” che hai appena scaricato:

In alternativa, puoi scaricare l’intero codice del repository, comprimerlo in zip e poi includere la libreria nello stesso modo descritto sopra. Ora siamo pronti per scrivere un po’ di codice.
Misurare la luce ambientale con APDS-9930
Il codice seguente legge le misurazioni della luce ambientale dal sensore APDS-9930.
#include "Wire.h"
#include "APDS9930.h"
APDS9930 sensor = APDS9930();
void setup() {
Serial.begin(9600);
sensor.init();
sensor.enableLightSensor(false);
delay(500);
}
void loop() {
static float light = 0;
if (sensor.readAmbientLightLux(light)) {
Serial.print("light:");
Serial.println(light);
}
delay(500);
}
Iniziamo includendo le librerie necessarie e creando l’oggetto sensore. Nella funzione setup il sensore viene inizializzato e il sensore di luce abilitato.
Il false in enableLightSensor(false) significa che non stiamo usando interrupt durante la misurazione della luce ambientale. Puoi collegare l’uscita INT dell’APDS-9930 a un ingresso digitale dell’Arduino e attivare una Interrupt Service Routine (ISR) quando viene rilevato un certo livello di luce. L’APDS-9930 ha example code per questo.
Nella funzione loop leggiamo il livello di luce tramite readAmbientLightLux(light) e, se la lettura ha successo, lo stampiamo sul Monitor Seriale. Vedi i seguenti esempi di lettura:

E se apri il Serial Plotter e punti l’APDS-9930 verso una fonte di luce, ad esempio una lampada da scrivania in questo caso, dovresti vedere un picco nel grafico:

Misurare la prossimità con APDS-9930
L’APDS-9930 rileva la prossimità di un oggetto inviando un impulso IR dal LED IR interno e misurando la quantità di energia IR riflessa. Più l’oggetto è vicino, più energia viene riflessa.
Il codice per misurare la prossimità è molto simile a quello per misurare la luce ambientale. Le uniche due differenze sono che chiamiamo enableProximitySensor(false) , nella funzione setup e readProximity(proximity) nel loop. Vedi l’esempio sotto:
#include "Wire.h"
#include "APDS9930.h"
APDS9930 sensor = APDS9930();
void setup() {
Serial.begin(9600);
sensor.init();
sensor.enableProximitySensor(false);
delay(500);
}
void loop() {
static uint16_t proximity = 0;
if (sensor.readProximity(proximity)) {
Serial.print("proximity:");
Serial.println(proximity);
}
delay(500);
}
Come prima, il false in enableProximitySensor(false) significa che non usiamo interrupt ma leggiamo continuamente i valori di prossimità. I valori tipici di prossimità variano da circa 300 (nessun oggetto) a 1023 quando l’oggetto è molto vicino.
Se apri il Serial Plotter e avvicini o allontani ripetutamente la mano dal sensore, dovresti vedere un andamento ondulatorio simile a quello mostrato sotto:

Misurare contemporaneamente prossimità e luce con APDS-9930
Infine, ovviamente possiamo misurare contemporaneamente la prossimità e i livelli di luce ambientale. L’esempio di codice sotto abilita il sensore di prossimità e quello di luce nella funzione setup e legge i valori di prossimità e luce nella funzione loop :
#include "Wire.h"
#include "APDS9930.h"
APDS9930 sensor = APDS9930();
void setup() {
Serial.begin(9600);
sensor.init();
sensor.enableProximitySensor(false);
sensor.enableLightSensor(false);
}
void loop() {
static uint16_t proximity = 0;
static float light = 0;
if (sensor.readProximity(proximity)) {
Serial.print("proximity:");
Serial.println(proximity);
}
if (sensor.readAmbientLightLux(light)) {
Serial.print("light:");
Serial.println(light);
}
delay(500);
}
Se esegui questo codice e guardi il Serial Plotter, noterai che il sensore di luce e quello di prossimità mostrano un comportamento negativamente correlato. Vedi l’immagine sotto.

Questo accade perché, se avvicini la mano al sensore, il valore di prossimità è alto ma poiché la mano ostruisce la luce ambientale, il livello di luce misurato è basso. Al contrario, se non c’è nessun oggetto vicino al sensore, il valore di prossimità è basso, ma il livello di luce è più alto (supponendo che ci sia luce).
Regolazione automatica della luminosità con APDS-9930
Per il nostro esempio finale implementiamo l’applicazione tipica dell’APDS-9930. Attiviamo un LED se un oggetto (mano) è vicino al sensore e regoliamo la luminosità del LED in base ai livelli di luce ambientale.
Per questo basta aggiungere un LED al nostro circuito. Nel cablaggio mostrato sotto ho aggiunto un LED con una resistenza da 220Ω al pin 11. Puoi usare un altro pin di uscita, ma deve essere un pin PWM.

Nel codice sotto leggiamo i valori di prossimità e luce. Se la soglia di prossimità supera 500 (mano vicina al sensore), impostiamo la luminosità del LED in relazione al livello di luce ambientale. Più luce ambientale c’è, più il LED è luminoso.
#include "Wire.h"
#include "APDS9930.h"
APDS9930 sensor = APDS9930();
const int ledPin = 11; // PWM
void setup() {
Serial.begin(9600);
sensor.init();
sensor.enableProximitySensor(false);
sensor.enableLightSensor(false);
pinMode(ledPin, OUTPUT);
delay(500);
}
void loop() {
static uint16_t proximity = 0;
static float light = 0;
static float maxLight = 0;
sensor.readProximity(proximity);
sensor.readAmbientLightLux(light);
if (proximity > 500) {
maxLight = max(light, maxLight);
int brightness = map(light, 0, maxLight, 0, 1023);
analogWrite(ledPin, brightness);
} else {
analogWrite(ledPin, 0);
}
delay(100);
}
Poiché non sappiamo a priori quanto può essere luminosa la luce ambientale, il codice aggiorna anche il livello massimo di luce ambientale a ogni iterazione. Ma potresti anche fare dei test e scegliere un livello massimo di luce fisso.
E questo è tutto. Spero ti sia divertito a giocare con il sensore di prossimità e luce APDS-9930 – io sicuramente sì ; )
Conclusioni
In questo tutorial hai imparato come usare il sensore di prossimità e luce APDS-9930 con un Arduino per rilevare oggetti e misurare i livelli di luce ambientale.
Nota che la APDS-9930 Library di Depau ha più funzioni di quelle che abbiamo mostrato qui. In particolare, puoi leggere i valori dei due fotodiodi (Ch0, Ch1), impostare soglie per prossimità e livelli di luce, e reagire agli interrupt. Dai un’occhiata all’esempio code che viene fornito con la libreria.
L’APDS-9930 è un buon sensore per rilevare gesti semplici e reagire alla luce. Per esempio, se vuoi attivare un display muovendo la mano davanti ad esso e regolare anche la luminosità del display in base alla luce ambientale, l’APDS-9930 è perfetto.
Tuttavia, se vuoi misurare con precisione le distanze dagli oggetti, ad esempio per applicazioni robotiche, è meglio usare sensori di distanza a infrarossi come il GP2Y0A710K0F che usano la triangolazione per determinare la distanza da un oggetto. O ancora meglio, scegli un sensore di distanza laser Time-of-Flight (ToF) come il TOF10120 o il VL53L1X library , che possono misurare distanze anche lunghe con grande precisione.
Se hai domande sentiti libero di lasciarle nella sezione commenti.
Buon divertimento con il tinkering ; )

