# Experiment D: I2C & SPI Communication
# Uses MPU-6050 (I2C) and 74HC595 (SPI)
import machine
import utime
import ustruct
# --- 1. INIT I2C for MPU-6050 ---
i2c = machine.I2C(0, scl=machine.Pin(1), sda=machine.Pin(0), freq=400000)
MPU6050_ADDR = 0x68 # Default I2C address
# Wake up the MPU-6050 (it starts in sleep mode)
try:
i2c.writeto_mem(MPU6050_ADDR, 0x6B, b'\x00')
print("✅ MPU-6050 I2C Initialized")
except Exception as e:
print(f"❌ I2C Init Error: {e}")
# --- 2. INIT SPI for 74HC595 ---
spi = machine.SPI(0,
baudrate=100000,
polarity=0,
phase=0,
sck=machine.Pin(2),
mosi=machine.Pin(7),
miso=machine.Pin(4))
cs = machine.Pin(3, machine.Pin.OUT)
cs.value(1)
def read_mpu6050_temp():
"""Read the temperature from MPU-6050's internal sensor."""
try:
# Temperature register address is 0x41 (high byte) and 0x42 (low byte)
data = i2c.readfrom_mem(MPU6050_ADDR, 0x41, 2)
# Convert raw data (big-endian signed short)
raw_temp = ustruct.unpack('>h', data)[0]
# Formula from datasheet: Temp = (raw_temp / 340.0) + 36.53
temp_c = (raw_temp / 340.0) + 36.53
return temp_c
except Exception as e:
print(f"⚠️ I2C Read Error: {e}")
return 25.0 # Default fallback
print("🎯 Experiment D: I2C (MPU-6050) + SPI (74HC595)")
print("📡 Reading Temp from MPU-6050, controlling LEDs via 74HC595")
print("-" * 50)
patterns = [
0b00000001, 0b00000011, 0b00000111, 0b00001111,
0b00011111, 0b00111111, 0b01111111, 0b11111111,
0b01111111, 0b00111111, 0b00011111, 0b00001111,
0b00000111, 0b00000011
]
pattern_index = 0
try:
while True:
# --- A. READ TEMPERATURE via I2C ---
temp_c = read_mpu6050_temp()
# --- B. DECIDE ACTION based on temperature ---
if temp_c > 30.0:
delay = 100
max_pattern = 0b11111111
elif temp_c < 20.0:
delay = 500
max_pattern = 0b00000001
else:
delay = 300
max_pattern = 0b00001111
current_pattern = patterns[pattern_index] & max_pattern
cs.value(0)
spi.write(bytes([current_pattern]))
cs.value(1)
pattern_index = (pattern_index + 1) % len(patterns)
print(f"🌡️ Temp: {temp_c:5.1f}°C | LEDs: {current_pattern:08b}")
utime.sleep_ms(delay)
except KeyboardInterrupt:
# Cleanup: Turn off all LEDs on exit
cs.value(0)
spi.write(bytes([0b00000000]))
cs.value(1)
print("\n🛑 Experiment D safely stopped. LEDs off.")