Skip to content

Commit 49a2908

Browse files
committed
Add LTR507 module
1 parent 8b1564b commit 49a2908

5 files changed

Lines changed: 540 additions & 0 deletions

File tree

Lines changed: 109 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,109 @@
1+
# FILE: ltr507-CustomConfiguration.py
2+
# AUTHOR: Josip Šimun Kuči @ Soldered
3+
# BRIEF: An example showing how to initialize the LTR-507 sensor and get light and proximity measurements
4+
# WORKS WITH: Digital light & proximity sensor LTR-507 breakout: www.solde.red/333063
5+
# LAST UPDATED: 2025-06-10
6+
7+
from machine import I2C, Pin
8+
from time import sleep
9+
from ltr507 import LTR507 # This assumes you have an ltr507.py module with the driver
10+
from ltr507_config import *
11+
12+
"""
13+
Connecting diagram:
14+
15+
IMPORTANT: an IR LED must be connected when measuring proximity!
16+
LTR-507 IR LED
17+
VLED------------------------>CATHODE (-)
18+
VCC------------------------->ANODE (+)
19+
"""
20+
21+
# If you aren't using the Qwiic connector, manually enter your I2C pins
22+
#i2c = I2C(0, scl=Pin(22), sda=Pin(21))
23+
#sensor = LTR507(i2c)
24+
25+
#Initialize I2C communication with the sensor over Qwiic
26+
sensor = LTR507()
27+
28+
#Set up the sensor with its default values
29+
sensor.begin()
30+
# You can change the following settings:
31+
32+
# This turns off the ambient light sensor (ALS) and proximity sensor
33+
# sensor.set_als_mode(False)
34+
# sensor.set_ps_mode(False)
35+
# Setting the parameter to 'True' will turn it back on, this is done by default in init()
36+
37+
# Set the gain of the sensor
38+
# This way you can get more or less sensitivity
39+
# From the datasheet:
40+
# - LTR507_ALS_GAIN_RANGE1: 1 lux to 64k lux (1 lux/count) (default)
41+
# - LTR507_ALS_GAIN_RANGE2: 0.5 lux to 32k lux (0.5 lux/count)
42+
# - LTR507_ALS_GAIN_RANGE3: 0.02 lux to 640 lux (0.01 lux/count)
43+
# - LTR507_ALS_GAIN_RANGE4: 0.01 lux to 320 lux (0.005 lux/count)
44+
sensor.set_als_gain(LTR507_ALS_GAIN_RANGE1)
45+
46+
# Set the automatic measurement rate
47+
# You can use:
48+
# - LTR507_ALS_MEASUREMENT_RATE_100MS (default)
49+
# - LTR507_ALS_MEASUREMENT_RATE_200MS
50+
# - LTR507_ALS_MEASUREMENT_RATE_500MS
51+
# - LTR507_ALS_MEASUREMENT_RATE_1000MS
52+
# - LTR507_ALS_MEASUREMENT_RATE_2000MS
53+
sensor.set_als_meas_rate(LTR507_ALS_MEASUREMENT_RATE_100MS)
54+
55+
# Set the bit width of the ALS measurement
56+
# This changes the time required to complete a single measurement
57+
# So, it's recommended to leave it as default
58+
# sensor.set_als_bitwidth(sensor.ALS_ADC_BIT_WIDTH_16BIT)
59+
60+
# Set the auto measurement rate for proximity
61+
# You can use:
62+
# - LTR507_PS_MEASUREMENT_RATE_12_5MS
63+
# - LTR507_PS_MEASUREMENT_RATE_50MS
64+
# - LTR507_PS_MEASUREMENT_RATE_70MS
65+
# - LTR507_PS_MEASUREMENT_RATE_100MS (default)
66+
# - LTR507_PS_MEASUREMENT_RATE_200MS
67+
# - LTR507_PS_MEASUREMENT_RATE_500MS
68+
# - LTR507_PS_MEASUREMENT_RATE_1000MS
69+
# - LTR507_PS_MEASUREMENT_RATE_2000MS
70+
sensor.set_ps_meas_rate(LTR507_PS_MEASUREMENT_RATE_100MS)
71+
72+
# Set the max current supplied to the IR LED
73+
# You can use:
74+
# - LTR507_LED_PEAK_CURRENT_5MA
75+
# - LTR507_LED_PEAK_CURRENT_10MA
76+
# - LTR507_LED_PEAK_CURRENT_20MA
77+
# - LTR507_LED_PEAK_CURRENT_50MA (default)
78+
sensor.set_led_peak_current(LTR507_LED_PEAK_CURRENT_50MA)
79+
80+
# Set the pulse frequency of the IR LED
81+
# You can use:
82+
# - LTR507_LED_PULSE_FREQ_30KHZ
83+
# - LTR507_LED_PULSE_FREQ_40KHZ
84+
# - LTR507_LED_PULSE_FREQ_50KHZ
85+
# - LTR507_LED_PULSE_FREQ_60KHZ (default)
86+
# - LTR507_LED_PULSE_FREQ_70KHZ
87+
# - LTR507_LED_PULSE_FREQ_80KHZ
88+
# - LTR507_LED_PULSE_FREQ_90KHZ
89+
# - LTR507_LED_PULSE_FREQ_100KHZ
90+
sensor.set_led_pulse_freq(LTR507_LED_PULSE_FREQ_60KHZ)
91+
92+
# Set the number of pulses for a proximity measurement
93+
# You can use any number from 1 to 15, default is 1
94+
sensor.set_ps_num_pulses(1)
95+
96+
# Main loop
97+
while True:
98+
#Measure the light intensity from the sensor in lux
99+
lux = sensor.getLightIntensity()
100+
#Measure the proximity value of the sensor
101+
prox = sensor.getProximity()
102+
103+
# Print the readings
104+
print("Light sensor reading:", lux)
105+
print("Proximity reading:", prox)
106+
print() # Newline
107+
108+
# Wait a bit until the next reading so output isn't too fast
109+
sleep(1)
Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
# FILE: LTR507-LightAndProximity.py
2+
# AUTHOR: Josip Šimun Kuči @ Soldered
3+
# BRIEF: An example showing how to initialize the LTR-507 sensor and get light and proximity measurements
4+
# WORKS WITH: Digital light & proximity sensor LTR-507 breakout: www.solde.red/333063
5+
# LAST UPDATED: 2025-06-10
6+
7+
from machine import I2C, Pin
8+
import time
9+
from ltr507 import LTR507
10+
11+
"""
12+
Connecting diagram:
13+
14+
IMPORTANT: an IR LED must be connected when measuring proximity!
15+
LTR-507 IR LED
16+
VLED------------------------>CATHODE (-)
17+
VCC------------------------->ANODE (+)
18+
"""
19+
20+
# If you aren't using the Qwiic connector, manually enter your I2C pins
21+
#i2c = I2C(0, scl=Pin(22), sda=Pin(21))
22+
#sensor = LTR507(i2c)
23+
24+
#Initialize I2C communication with the sensor over Qwiic
25+
sensor = LTR507()
26+
27+
#Set up the sensor with its default values
28+
sensor.begin()
29+
30+
#Infinite loop
31+
while 1:
32+
#Measure the light intensity from the sensor in lux
33+
lux = sensor.getLightIntensity()
34+
#Measure the proximity value of the sensor
35+
prox = sensor.getProximity()
36+
37+
#Print the values over Serial communication
38+
print("Lux:", lux, "Proximity:", prox)
39+
#Pause for 1 second
40+
time.sleep(1)

LTR507/LTR507/ltr507.py

Lines changed: 203 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,203 @@
1+
# FILE: LTR507.py
2+
# AUTHOR: Josip Šimun Kuči @ Soldered
3+
# BRIEF: A Micropython module for the LTR-507 Light and proximity sensor
4+
# LAST UPDATED: 2025-06-10
5+
6+
from machine import I2C, Pin
7+
from os import uname
8+
from time import sleep_ms
9+
from ltr507_config import *
10+
11+
class LTR507:
12+
def __init__(self, i2c=None, address=0x3A):
13+
"""
14+
Initialize the LTR507 sensor.
15+
16+
:param i2c: Initialized I2C object
17+
:param address: I2C address of the sensor (default 0x3A)
18+
"""
19+
if i2c != None:
20+
self.i2c = i2c
21+
else:
22+
if uname().sysname == "esp32" or uname().sysname == "esp8266":
23+
self.i2c = I2C(0, scl=Pin(22), sda=Pin(21))
24+
else:
25+
raise Exception("Board not recognized, enter I2C pins manually")
26+
self.address = address
27+
self.raw = bytearray(2) # Buffer for reading multi-byte registers
28+
29+
def _read_register(self, reg, length=1):
30+
"""
31+
Read bytes from a sensor register.
32+
33+
:param reg: Register address to read from
34+
:param length: Number of bytes to read (default 1)
35+
:return: Bytes read from the register
36+
"""
37+
return self.i2c.readfrom_mem(self.address, reg, length)
38+
39+
def _write_register(self, reg, data):
40+
"""
41+
Write a single byte to a sensor register.
42+
43+
:param reg: Register address to write to
44+
:param data: Byte value to write
45+
"""
46+
self.i2c.writeto_mem(self.address, reg, bytes([data]))
47+
48+
def _write_registers(self, reg, values):
49+
"""
50+
Write multiple bytes to consecutive sensor registers.
51+
52+
:param reg: Starting register address
53+
:param values: Iterable of byte values to write
54+
"""
55+
self.i2c.writeto_mem(self.address, reg, bytes(values))
56+
57+
def begin(self):
58+
"""
59+
Initialize the sensor with default configuration settings.
60+
Enables ALS and PS modes and sets recommended measurement parameters.
61+
"""
62+
self.set_als_mode(True)
63+
self.set_ps_mode(True)
64+
self.set_als_gain(LTR507_ALS_GAIN_RANGE1)
65+
self.set_als_bitwidth(LTR507_ALS_ADC_BIT_WIDTH_16BIT)
66+
self.set_als_meas_rate(LTR507_ALS_MEASUREMENT_RATE_100MS)
67+
self.set_led_pulse_freq(LTR507_LED_PULSE_FREQ_60KHZ)
68+
self.set_led_duty_cycle(LTR507_LED_CURRENT_DUTY_DEFAULT)
69+
self.set_ps_meas_rate(LTR507_PS_MEASUREMENT_RATE_100MS)
70+
self.set_led_peak_current(LTR507_LED_PEAK_CURRENT_50MA)
71+
self.set_ps_num_pulses(1)
72+
73+
def set_ps_mode(self, mode):
74+
"""
75+
Enable or disable proximity sensing mode.
76+
77+
:param mode: Boolean indicating whether to enable (True) or disable (False) PS mode
78+
"""
79+
val = self._read_register(LTR507_PS_CONTR_REG)[0]
80+
val &= ~LTR507_PS_MODE_MASK
81+
val |= (mode << LTR507_PS_MODE_SHIFT) & LTR507_PS_MODE_MASK
82+
self._write_register(LTR507_PS_CONTR_REG, val)
83+
84+
def set_als_mode(self, mode):
85+
"""
86+
Enable or disable ambient light sensing mode.
87+
88+
:param mode: Boolean indicating whether to enable (True) or disable (False) ALS mode
89+
"""
90+
val = self._read_register(LTR507_ALS_CONTR_REG)[0]
91+
if mode:
92+
val |= 0x02 # Set bit 1
93+
else:
94+
val &= 0xFD # Clear bit 1
95+
self._write_register(LTR507_ALS_CONTR_REG, val)
96+
97+
def set_led_pulse_freq(self, freq):
98+
"""
99+
Set the LED pulse frequency for proximity sensing.
100+
101+
:param freq: Frequency constant (e.g., LTR507_LED_PULSE_FREQ_60KHZ)
102+
"""
103+
val = self._read_register(LTR507_PS_LED_REG)[0]
104+
val &= ~LTR507_LED_PULSE_FREQ_MASK
105+
val |= (freq << LTR507_LED_PULSE_FREQ_SHIFT) & LTR507_LED_PULSE_FREQ_MASK
106+
self._write_register(LTR507_PS_LED_REG, val)
107+
108+
def set_led_duty_cycle(self, duty):
109+
"""
110+
Set the duty cycle of the proximity LED.
111+
112+
:param duty: Duty cycle constant (e.g., LTR507_LED_CURRENT_DUTY_DEFAULT)
113+
"""
114+
val = self._read_register(LTR507_PS_LED_REG)[0]
115+
val &= ~LTR507_LED_DUTY_CYCLE_MASK
116+
val |= (duty << LTR507_LED_DUTY_CYCLE_SHIFT) & LTR507_LED_DUTY_CYCLE_MASK
117+
self._write_register(LTR507_PS_LED_REG, val)
118+
119+
def set_ps_meas_rate(self, rate):
120+
"""
121+
Set the measurement rate for proximity sensing.
122+
123+
:param rate: Measurement rate constant (e.g., LTR507_PS_MEASUREMENT_RATE_100MS)
124+
"""
125+
val = rate & LTR507_PS_MEAS_RATE_MASK
126+
self._write_register(LTR507_PS_MEAS_RATE_REG, val)
127+
128+
def set_led_peak_current(self, current):
129+
"""
130+
Set the peak drive current of the proximity LED.
131+
132+
:param current: Current constant (e.g., LTR507_LED_PEAK_CURRENT_50MA)
133+
"""
134+
val = self._read_register(LTR507_PS_LED_REG)[0]
135+
val &= ~LTR507_LED_PEAK_CURRENT_MASK
136+
val |= current & LTR507_LED_PEAK_CURRENT_MASK
137+
self._write_register(LTR507_PS_LED_REG, val)
138+
139+
def set_ps_num_pulses(self, num_pulses):
140+
"""
141+
Set the number of LED pulses for each proximity measurement.
142+
143+
:param num_pulses: Integer value between 1 and 15
144+
"""
145+
num_pulses = max(1, min(15, num_pulses))
146+
val = num_pulses & LTR507_PS_PULSES_MASK
147+
self._write_register(LTR507_PS_N_PULSES_REG, val)
148+
149+
def set_als_gain(self, gain):
150+
"""
151+
Set the analog gain for ambient light sensing.
152+
153+
:param gain: Gain constant (e.g., LTR507_ALS_GAIN_RANGE1)
154+
"""
155+
val = self._read_register(LTR507_ALS_CONTR_REG)[0]
156+
val &= ~LTR507_ALS_GAIN_MASK
157+
val |= (gain << LTR507_ALS_GAIN_SHIFT) & LTR507_ALS_GAIN_MASK
158+
self._write_register(LTR507_ALS_CONTR_REG, val)
159+
160+
def set_als_bitwidth(self, bitwidth):
161+
"""
162+
Set the ADC resolution (bit width) for ambient light measurements.
163+
164+
:param bitwidth: Bit width constant (e.g., LTR507_ALS_ADC_BIT_WIDTH_16BIT)
165+
"""
166+
val = self._read_register(LTR507_ALS_MEAS_PATE_REG)[0]
167+
val &= ~LTR507_ALS_ADC_BIT_WIDTH_MASK
168+
val |= (bitwidth << LTR507_ALS_ADC_BIT_WIDTH_SHIFT) & LTR507_ALS_ADC_BIT_WIDTH_MASK
169+
self._write_register(LTR507_ALS_MEAS_PATE_REG, val)
170+
171+
def set_als_meas_rate(self, rate):
172+
"""
173+
Set the ambient light sensor measurement rate.
174+
175+
:param rate: Measurement rate constant (e.g., LTR507_ALS_MEASUREMENT_RATE_100MS)
176+
"""
177+
val = self._read_register(LTR507_ALS_MEAS_PATE_REG)[0]
178+
val &= ~LTR507_ALS_MEASURE_RATE_MASK
179+
val |= (rate << LTR507_ALS_MEASURE_RATE_SHIFT) & LTR507_ALS_MEASURE_RATE_MASK
180+
self._write_register(LTR507_ALS_MEAS_PATE_REG, val)
181+
182+
def getLightIntensity(self):
183+
"""
184+
Read and return the current ambient light level.
185+
186+
:return: 16-bit integer light value (0 if data not ready)
187+
"""
188+
status = self._read_register(LTR507_ALS_PS_STATUS_REG)[0]
189+
if not (status & 0x04): # Check if ALS data is valid
190+
return 0
191+
data = self._read_register(LTR507_ALS_DATA_0_REG, 2)
192+
return data[0] | (data[1] << 8) # Combine low and high bytes
193+
194+
def getProximity(self):
195+
"""
196+
Read and return the current proximity sensor value.
197+
198+
:return: 16-bit integer proximity value
199+
"""
200+
data = self._read_register(LTR507_PS_DATA_LOW_REG, 2)
201+
low = data[0] & LTR507_PS_DATA_LOW_MASK
202+
high = data[1] & LTR507_PS_DATA_HIGH_MASK
203+
return low | (high << 8) # Combine low and high bytes

0 commit comments

Comments
 (0)