Implemented generic setup file and VL53L3CX Sensor

This commit is contained in:
Maximilian Giller 2023-11-24 18:27:05 +01:00
parent b85ee8ab25
commit 16ebe4a670
7 changed files with 105 additions and 55 deletions

View file

@ -1,12 +1,10 @@
from sensors.people_counter import PeopleCounter
from sensors.vl53l1x_sensor import VL53L1XSensor
import logging
from setup import sensor
counter = PeopleCounter(VL53L1XSensor())
counter = PeopleCounter(sensor)
peopleCount = 0
logging.getLogger().setLevel(logging.INFO)
def countChange(change: int) -> None:
global peopleCount

View file

@ -1,30 +1,26 @@
from sensors import Directions, VL53L1XSensor
from sensors import Directions
from time import sleep
from setup import sensor
import logging
DELAY_SECONDS = 1
logging.getLogger().setLevel(logging.INFO)
sensor = VL53L1XSensor()
sensor.open()
try:
while True:
sensor.setDirection(Directions.INSIDE)
distance_inside = sensor.getDistance()
sensor.setDirection(Directions.OUTSIDE)
distance_outside = sensor.getDistance()
logging.info("----------")
logging.info(f"Inside: {distance_inside} cm")
logging.info(f"Outside: {distance_outside} cm")
sleep(DELAY_SECONDS)
finally:
sensor.close()

View file

@ -1,3 +1,4 @@
from sensors.vl53l1x_sensor import VL53L1XSensor
from sensors.vl53l3cx_sensor import VL53L3CXSensor
from sensors.people_counter import PeopleCounter
from sensors.tof_sensor import Directions

View file

@ -0,0 +1,61 @@
from sensors.tof_sensor import Directions, ToFSensor
import VL53L1X
# Reference: https://github.com/pimoroni/vl53l1x-python
#
# Left, right, top and bottom are relative to the SPAD matrix coordinates,
# which will be mirrored in real scene coordinates.
# (or even rotated, depending on the VM53L1X element alignment on the board and on the board position)
#
# ROI in SPAD matrix coords:
#
# 15 top-left
# | X____
# | | |
# | |____X
# | bottom-right
# 0__________15
#
class VL53L3CXSensor(ToFSensor):
def __init__(self) -> None:
super().__init__()
def open(self, ranging_mode: int = 3) -> None:
self.sensor = VL53L1X.VL53L1X(i2c_bus=1, i2c_address=0x52)
self.sensor.open()
self.roi = VL53L1X.VL53L1xUserRoi()
# Optionally set an explicit timing budget
# These values are measurement time in microseconds,
# and inter-measurement time in milliseconds.
# If you uncomment the line below to set a budget you
# should use `tof.start_ranging(0)`
# tof.set_timing(66000, 70)
self.ranging = ranging_mode
# 0 = Unchanged
# 1 = Short Range
# 2 = Medium Range
# 3 = Long Range
def setDirection(self, direction: Directions) -> None:
"""Configure sensor to pick up the distance in a specific direction."""
direction_roi = {
Directions.INSIDE: VL53L1X.VL53L1xUserRoi(6, 3, 9, 0),
Directions.OUTSIDE: VL53L1X.VL53L1xUserRoi(6, 15, 9, 12),
}
self.roi = direction_roi[direction]
def getDistance(self) -> float:
"""Returns new distance in cm."""
self.sensor.set_user_roi(self.roi)
self.sensor.start_ranging(self.ranging)
distance = self.sensor.get_distance()
self.sensor.stop_ranging()
return distance / 10
def close(self) -> None:
self.sensor.close()

28
src/setup.py Normal file
View file

@ -0,0 +1,28 @@
from sensors import VL53L1XSensor, VL53L3CXSensor
from datetime import time
import logging
LOG_FILE_PATH = "log.txt" # Path for logs
logging.getLogger().setLevel(logging.INFO)
sensor = VL53L3CXSensor()
# Should lights already turn on where there is any kind of motion in the sensor
ENABLE_MOTION_TRIGGERED_LIGHT = True
# Should lights change when a certain time in the schedule is reached
ENABLE_SCHEDULE_TRIGGERS = (
False # Not working correctly at the moment, so turned off by default
)
# Schedule (Key is time after scene should be used. Value is scene name to be used.)
# Needs to be sorted chronologically
SCHEDULE: dict[time, str] = {}
# Philips Hue configuration
hue_conf = {
"bridge_ip": "",
"transition_time": 10, # seconds
"light_group": "",
# If file exists, application is considered 'registered' at the bridge
"registered_file": "smart_light_registered.bridge",
} # Custom configuration for philips hue

View file

@ -1,28 +1,15 @@
from datetime import datetime
from services.philips_hue import PhilipsHue
from sensors.people_counter import PeopleCounter
from sensors.vl53l1x_sensor import VL53L1XSensor
import logging
import json
LOG_FILE_PATH = "log.txt" # Path for logs
hue_conf = {
"bridge_ip": "",
"transition_time": 10, # seconds
# Light group to control
"light_group": "",
# If file exists, application is considered 'registered' at the bridge
"registered_file": "smart_light_registered.bridge",
} # Custom configuration for philips hue
from setup import sensor, hue_conf, LOG_FILE_PATH
hue: PhilipsHue = PhilipsHue(hue_conf) # Light interface
counter: PeopleCounter = PeopleCounter(VL53L1XSensor()) # Sensor object
counter: PeopleCounter = PeopleCounter(sensor) # Sensor object
peopleCount: int = 0 # Global count of people on the inside
logging.getLogger().setLevel(logging.INFO)
def change_cb(countChange: int, directionState: dict):
"""Handles basic logging of event data for later analysis.

View file

@ -1,36 +1,15 @@
from datetime import datetime, time, timedelta
from typing import Optional
from services.philips_hue import PhilipsHue
from sensors import PeopleCounter, Directions, VL53L1XSensor
import logging
import json
from timeloop import Timeloop
# Should lights already turn on where there is any kind of motion in the sensor
ENABLE_MOTION_TRIGGERED_LIGHT = True
# Should lights change when a certain time in the schedule is reached
ENABLE_SCHEDULE_TRIGGERS = (
False # Not working correctly at the moment, so turned off by default
)
# Schedule (Key is time after scene should be used. Value is scene name to be used.)
# Needs to be sorted chronologically
SCHEDULE: dict[time, str] = {}
LOG_FILE_PATH = "log.txt" # Path for logs
hue_conf = {
"bridge_ip": "",
"transition_time": 10, # seconds
"light_group": "",
# If file exists, application is considered 'registered' at the bridge
"registered_file": "smart_light_registered.bridge",
} # Custom configuration for philips hue
from setup import sensor, hue_conf, LOG_FILE_PATH, SCHEDULE, ENABLE_SCHEDULE_TRIGGERS
hue: PhilipsHue = PhilipsHue(hue_conf) # Light interface
counter: PeopleCounter = PeopleCounter(VL53L1XSensor()) # Sensor object
counter: PeopleCounter = PeopleCounter(sensor) # Sensor object
peopleCount: int = 0 # Global count of people on the inside
motion_triggered_lights = False # Is light on because of any detected motion
timeloop: Timeloop = Timeloop() # Used for time triggered schedule
@ -55,7 +34,7 @@ def time_minus_time(time_a: time, time_b: time) -> timedelta:
return dt_a - dt_b
def get_scene_for_time(time: time) -> str:
def get_scene_for_time(time: time) -> Optional[str]:
"""Determines the correct scene to activate for a given time.
Args:
@ -185,7 +164,7 @@ def trigger_change(triggerState: dict):
motion_triggered_lights = target_light_state
def set_light_scene(target_scene: str) -> bool:
def set_light_scene(target_scene: str) -> None:
"""Sets the lights to the given scene, but only, if lights are already on. Does not correct count if lights are in an unexpected state.
Args: