Untitled
unknown
plain_text
10 months ago
4.9 kB
3
Indexable
import time
import board
import busio
import adafruit_vl53l0x
from adafruit_tca9548a import TCA9548A
import statistics
import sys
import tty
import termios
import threading
import os
# Initialize I2C bus
i2c = busio.I2C(board.SCL, board.SDA)
# Initialize the TCA9548A multiplexer
mux = TCA9548A(i2c)
# Create sensor objects on channels 1, 2, and 4-7
sensors = {
1: adafruit_vl53l0x.VL53L0X(mux[1]),
2: adafruit_vl53l0x.VL53L0X(mux[2]),
4: adafruit_vl53l0x.VL53L0X(mux[4]),
5: adafruit_vl53l0x.VL53L0X(mux[5]),
6: adafruit_vl53l0x.VL53L0X(mux[6]),
7: adafruit_vl53l0x.VL53L0X(mux[7])
}
# Constants
MAX_DISTANCE = 400 # 0%
MIN_DISTANCE = 0 # 100%
FULL_THRESHOLD = 50 # Threshold for "bin full" message
SAMPLING_TIME = 1.5 # Time in seconds to collect readings
SAMPLING_RATE = 0.05 # Time between individual readings
def clear_screen():
"""Clear the terminal screen"""
os.system('cls' if os.name == 'nt' else 'clear')
def print_header():
"""Print a nice header"""
print("╔════════════════════════════════════════╗")
print("║ Fill Level Measurement ║")
print("╚════════════════════════════════════════╝")
print("\nPress any key to take a measurement")
print("Press 'q' to quit\n")
def print_measuring():
"""Print measuring message"""
print("\n⏳ Measuring...\n")
def print_result(percentage=None, is_full=False):
"""Print the result in a nice format"""
print("\n╔════════════════════════════════════════╗")
if is_full:
print("║ ⚠️ BIN FULL ⚠️ ║")
else:
fill_bar = create_fill_bar(percentage)
print(f"║ Fill Level: {percentage:>5.1f}% ║")
print("║ ║")
print(f"║ {fill_bar} ║")
print("╚════════════════════════════════════════╝\n")
def create_fill_bar(percentage):
"""Create a visual fill bar"""
bar_length = 20
filled_length = int(percentage / 100 * bar_length)
bar = '█' * filled_length + '░' * (bar_length - filled_length)
return bar
def distance_to_percentage(distance):
"""Convert distance to percentage where 400mm = 0% and 0mm = 100%"""
distance = min(max(distance, MIN_DISTANCE), MAX_DISTANCE)
percentage = ((MAX_DISTANCE - distance) / (MAX_DISTANCE - MIN_DISTANCE)) * 100
return round(percentage, 1)
def get_measurements():
"""Take multiple measurements over SAMPLING_TIME seconds"""
end_time = time.time() + SAMPLING_TIME
all_readings = []
while time.time() < end_time:
readings = []
for sensor in sensors.values():
try:
readings.append(sensor.range)
except Exception:
continue
if readings:
all_readings.extend(readings)
time.sleep(SAMPLING_RATE)
return all_readings
def getch():
"""Get a single character from standard input"""
fd = sys.stdin.fileno()
old_settings = termios.tcgetattr(fd)
try:
tty.setraw(sys.stdin.fileno())
ch = sys.stdin.read(1)
finally:
termios.tcsetattr(fd, termios.TCSADRAIN, old_settings)
return ch
def main():
clear_screen()
print_header()
while True:
# Wait for keypress
char = getch()
if char.lower() == 'q':
clear_screen()
print("\nThank you for using the Fill Level Measurement system!")
break
clear_screen()
print_header()
print_measuring()
# Take multiple measurements
readings = get_measurements()
if not readings:
print("Error: No valid readings from sensors")
continue
# Check if any reading indicates bin is full
if any(reading <= FULL_THRESHOLD for reading in readings):
print_result(is_full=True)
else:
# Calculate median of all readings
median_distance = statistics.median(readings)
percentage = distance_to_percentage(median_distance)
print_result(percentage=percentage)
if __name__ == "__main__":
try:
# Give sensors a moment to initialize
time.sleep(1)
main()
except Exception as e:
print(f"\nAn error occurred: {str(e)}")
finally:
print("\nExiting...")Editor is loading...
Leave a Comment