Skip to content

Commit bb77144

Browse files
Silicon Labs CircuitPython Applications v1.2.0
1 parent 04987f3 commit bb77144

20 files changed

+727
-5
lines changed

README.md

+6-5
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@
1313

1414
# Silicon Labs CircuitPython Applications #
1515

16-
[![Version Badge](https://img.shields.io/badge/-v1.1.0-green)](https://github.com/SiliconLabs/circuitpython_applications/releases)
16+
[![Version Badge](https://img.shields.io/badge/-v1.2.0-green)](https://github.com/SiliconLabs/circuitpython_applications/releases)
1717
[![CircuitPython](https://img.shields.io/badge/CircuitPython-v8.2.0+-green)](https://circuitpython.org/downloads?q=silabs)
1818
![License badge](https://img.shields.io/badge/License-Zlib-green)
1919

@@ -27,10 +27,11 @@ All examples in this repository are considered to be EXPERIMENTAL QUALITY, which
2727
| 1 | CircuitPython - Bluetooth - Distance Monitor (VL53L1X) | [Click Here](./cp_bluetooth_distance_monitor)|
2828
| 2 | CircuitPython - Bluetooth - Environmental Sensing (CCS811/BME280) | [Click Here](./cp_bluetooth_environmental_sensing) |
2929
| 3 | CircuitPython - Bluetooth - Neopixel Humidity Gauge (SHTC3) | [Click Here](./cp_bluetooth_neopixel_humidity_gauge) |
30-
| 4 | CircuitPython - Non-Wireless Display Demo (IS31FL3741) | [Click Here](./cp_non_wireless_display_demo) |
31-
| 5 | CircuitPython - RGB Display Drawing (ILI9341) | [Click Here](./cp_rgb_display_drawing_ili9341) |
32-
| 6 | CircuitPython - Temperature and Humidity Monitor with LED Matrix Display (SI2071/IS31FL3741) | [Click Here](./cp_temperature_and_humidty_monitor) |
33-
| 7 | CircuitPython - xG24 Dev Kit Sensors (ILI9341) | [Click Here](./cp_xg24_dev_kit_sensors) |
30+
| 4 | CircuitPython - Bluetooth - Light Detector (AS7265x) | [Click Here](./cp_bluetooth_light_detector) |
31+
| 5 | CircuitPython - Non-Wireless Display Demo (IS31FL3741) | [Click Here](./cp_non_wireless_display_demo) |
32+
| 6 | CircuitPython - RGB Display Drawing (ILI9341) | [Click Here](./cp_rgb_display_drawing_ili9341) |
33+
| 7 | CircuitPython - Temperature and Humidity Monitor with LED Matrix Display (SI2071/IS31FL3741) | [Click Here](./cp_temperature_and_humidty_monitor) |
34+
| 8 | CircuitPython - xG24 Dev Kit Sensors (ILI9341) | [Click Here](./cp_xg24_dev_kit_sensors) |
3435

3536

3637
## Get CircuitPython firmware ##

cp_bluetooth_light_detector/README.md

+135
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,135 @@
1+
# CircuitPython - Bluetooth - Light Detector (AS7265x) #
2+
3+
## Overview ##
4+
5+
This project aims to implement a wireless light detector system using Sparkfun Thing Plus for Matter - MGM240 development kits and external sensors integrated with the BLE wireless stack and CircuitPython.
6+
7+
8+
The overview of this application is shown in the image below:
9+
10+
![overview](docs/overview.png)
11+
12+
The wireless light detector system is composed of a sensor and a client device:
13+
14+
**Sensor Device**
15+
16+
The sensor device is a Sparkfun Thing Plus Matter - MGM240P kit connected to a SparkFun Triad Spectroscopy Sensor - AS7265x (Qwiic) board.
17+
18+
The sensor device will measure the intensity of 6 colors in the spectral range: red, orange, yellow, green, blue, and violet. This device implements a GATT Server and provides the measured values via BLE Characteristics. The client device can connect to the sensor and gather the provided environmental data by reading the BLE Characteristics.
19+
20+
**Client Device**
21+
22+
The client device is a Sparkfun Thing Plus Matter - MGM240P kit connected to a NeoPixel 1/4 60 Ring - 5050 RGBW LED w/ Integrated Drivers display.
23+
24+
The client device connects to the sensor device via BLE and reads the provided light data via BLE characteristics. The gathered light data is displayed on the connected 1/4 NeoPixel Ring.
25+
26+
## Hardware Required ##
27+
28+
### Sensor ###
29+
30+
- [SparkFun Thing Plus Matter - MGM240P](https://www.sparkfun.com/products/20270)
31+
- [SparkFun Triad Spectroscopy Sensor - AS7265x (Qwiic)](https://www.sparkfun.com/products/15050)
32+
33+
### Client ###
34+
35+
- [SparkFun Thing Plus Matter - MGM240P](https://www.sparkfun.com/products/20270)
36+
- [NeoPixel 1/4 60 Ring - 5050 RGBW LED w/ Integrated Drivers - Natural White](https://www.adafruit.com/product/2874)
37+
38+
## Connections Required ##
39+
40+
The Spectroscopy Sensor and SparkFun Thing Plus Matter board can easily connect via a Qwiic I2C connector.
41+
42+
The NeoPixel and SparkFun Thing Plus Matter board can connect via SPI. Connect the DIN pin on NeoPixel to a GPIO pin on the SparkFun Thing Plus Matter board that is configured as a MOSI pin.
43+
44+
## Prerequisites ##
45+
46+
Getting started with [CircuitPython on EFR32 boards](../doc/running_circuitpython.md).
47+
48+
## Setup ##
49+
50+
To run the example you need to install **Thonny** editor and then follow the steps below:
51+
52+
1. Flash the corresponding CircuitPython binary for your board. You can visit [circuitpython.org/downloads](https://circuitpython.org/downloads?q=silabs) to download the binary.
53+
54+
> **_NOTE:_** The examples in this repository require CircuitPython v8.2.0 or higher.
55+
56+
2. Install the necessary libraries from Adafruit CircuitPython bundle. You can download the bundle from [here](https://circuitpython.org/libraries). The libraries that are used in this project and their version are listed in the table below.
57+
- Sensor device
58+
59+
| Library | Version |
60+
|:----------------- |:------------------|
61+
| adafruit_as726x | 1.9.15 |
62+
63+
- Client device
64+
65+
| Library | Version |
66+
|:----------------- |:------------------|
67+
| neopixel_spi | 1.6.1 |
68+
69+
3. Upload all the libraries and files of the lib folder to the CircuitPython device. The files in the binary folder should not be uploaded to the lib folder in the device, they should have the same hierarchy as the **code.py** file.
70+
71+
4. Copy the content of the **code.py** and paste it to the **code.py** file on the CircuitPython device.
72+
73+
- Sensor device: [code.py](sensor/src/code.py)
74+
75+
- Client device: [code.py](client/src/code.py)
76+
77+
5. Run the scripts on boards.
78+
79+
## How it Works ##
80+
81+
### Sensor ###
82+
83+
- **Initialization process**
84+
85+
![Initialization](docs/sensor_init.png)
86+
87+
- **GATT Database:**
88+
- [Service] Light Sensing
89+
- [Char] Color R
90+
- [R, N] Get red color value
91+
- [Char] Color O
92+
- [R, N] Get orange color value
93+
- [Char] Color Y
94+
- [R, N] Get yellow color value
95+
- [Char] Color G
96+
- [R, N] Get green color value
97+
- [Char] Color B
98+
- [R, N] Get blue color value
99+
- [Char] Color V
100+
- [R, N] Get violet color value
101+
102+
- **Runtime operation**: The sensor device periodically measures the environmental data every 2 seconds.
103+
104+
![Runtime operation](docs/sensor_runtime.png)
105+
106+
- **BLE**
107+
- Read characteristics
108+
109+
![sensor_read](docs/sensor_read.png)
110+
111+
### Client ###
112+
113+
- **Initialization process**
114+
115+
![Initialization](docs/client_init.png)
116+
117+
- **Runtime operation**
118+
119+
![Runtime operation](docs/client_runtime.png)
120+
121+
## Output Display ##
122+
123+
The Neopixel ring changes colors based on the change of light measured by the Spectroscopy sensor. The ring is equipped with 15 LEDs, organized into six groups, with each group corresponding to a specific light sensing channel on the sensor. The first two LEDs are red, followed by two orange LEDs, then two yellow LEDs. The subsequent three LEDs are green, another three are blue, and the last three are violet.
124+
125+
The brightness of each LEDs group is determined by the intensity of the corresponding color channel on the sensor. The more intense the value on a specific channel, the more intense the brightness with the corresponding color on the ring.
126+
127+
Run the **code.py** file on both sensor and client device and monitor the NeoPixel you will see the result below.
128+
129+
![result](docs/result.png)
130+
131+
Sensor Shell
132+
133+
![sensor_result](docs/sensor_result.png)
134+
135+
From the log and picture, you can see that value of the violet channel is the highest so the brightness of the violet LEDs group is also the highest, the red channel has the lowest value so the red LEDs group also has the lowest brightness, similar to other channels.
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,77 @@
1+
"""
2+
*****************************************************************************
3+
Copyright 2023 Silicon Laboratories Inc. www.silabs.com
4+
*****************************************************************************
5+
SPDX-License-Identifier: Zlib
6+
7+
The licensor of this software is Silicon Laboratories Inc.
8+
9+
This software is provided \'as-is\', without any express or implied
10+
warranty. In no event will the authors be held liable for any damages
11+
arising from the use of this software.
12+
13+
Permission is granted to anyone to use this software for any purpose,
14+
including commercial applications, and to alter it and redistribute it
15+
freely, subject to the following restrictions:
16+
17+
1. The origin of this software must not be misrepresented; you must not
18+
claim that you wrote the original software. If you use this software
19+
in a product, an acknowledgment in the product documentation would be
20+
appreciated but is not required.
21+
2. Altered source versions must be plainly marked as such, and must not be
22+
misrepresented as being the original software.
23+
3. This notice may not be removed or altered from any source distribution.
24+
25+
*****************************************************************************
26+
# EXPERIMENTAL QUALITY
27+
This code has not been formally tested and is provided as-is. It is not
28+
suitable for production environments. In addition, this code will not be
29+
maintained and there may be no bug maintenance planned for these resources.
30+
Silicon Labs may update projects from time to time.
31+
******************************************************************************
32+
"""
33+
34+
from time import monotonic
35+
from adafruit_ble import BLERadio
36+
from adafruit_ble.advertising.standard import ProvideServicesAdvertisement
37+
from LightSensingService import LightSensingService
38+
from NeoPixelDisplay import Display
39+
40+
class ClientApp:
41+
def __init__(
42+
self,
43+
display: Display,
44+
ble: BLERadio,
45+
) -> None:
46+
print("Initialize application...")
47+
self.display = display
48+
self.ble = ble
49+
self.connection = None
50+
self.service = None
51+
self.sensor_data = None
52+
self.current = 0
53+
self.display.clear()
54+
self.display.fill_color(0xffffff)
55+
56+
def main_function(self, *args, **kwargs) -> None:
57+
if monotonic() - self.current >= 0.5:
58+
if not self.ble.connected:
59+
print("start scanning...")
60+
for adv in self.ble.start_scan(ProvideServicesAdvertisement):
61+
if LightSensingService in adv.services:
62+
print("sensor device found.")
63+
self.ble.stop_scan()
64+
self.connection = self.ble.connect(adv)
65+
elif self.ble.connected:
66+
self.service = self.connection[LightSensingService]
67+
self.sensor_data = [
68+
int(self.service.color_R),
69+
int(self.service.color_O),
70+
int(self.service.color_Y),
71+
int(self.service.color_G),
72+
int(self.service.color_B),
73+
int(self.service.color_V),
74+
]
75+
print("Updating data from sensor device.")
76+
self.display.draw_LightSensingData(self.sensor_data)
77+
self.current = monotonic()
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,76 @@
1+
"""
2+
*****************************************************************************
3+
Copyright 2023 Silicon Laboratories Inc. www.silabs.com
4+
*****************************************************************************
5+
SPDX-License-Identifier: Zlib
6+
7+
The licensor of this software is Silicon Laboratories Inc.
8+
9+
This software is provided \'as-is\', without any express or implied
10+
warranty. In no event will the authors be held liable for any damages
11+
arising from the use of this software.
12+
13+
Permission is granted to anyone to use this software for any purpose,
14+
including commercial applications, and to alter it and redistribute it
15+
freely, subject to the following restrictions:
16+
17+
1. The origin of this software must not be misrepresented; you must not
18+
claim that you wrote the original software. If you use this software
19+
in a product, an acknowledgment in the product documentation would be
20+
appreciated but is not required.
21+
2. Altered source versions must be plainly marked as such, and must not be
22+
misrepresented as being the original software.
23+
3. This notice may not be removed or altered from any source distribution.
24+
25+
*****************************************************************************
26+
# EXPERIMENTAL QUALITY
27+
This code has not been formally tested and is provided as-is. It is not
28+
suitable for production environments. In addition, this code will not be
29+
maintained and there may be no bug maintenance planned for these resources.
30+
Silicon Labs may update projects from time to time.
31+
******************************************************************************
32+
"""
33+
34+
from adafruit_ble.services import Service
35+
from adafruit_ble.uuid import VendorUUID, StandardUUID
36+
from adafruit_ble.attributes import Attribute
37+
from adafruit_ble.characteristics import Characteristic
38+
from adafruit_ble.characteristics.int import Uint32Characteristic
39+
40+
class LightSensingService(Service):
41+
uuid=StandardUUID(0x181A)
42+
43+
color_R = Uint32Characteristic(
44+
uuid = VendorUUID("51ad213f-e568-4e35-84e4-67af89c79ef0"),
45+
properties=(Characteristic.READ | Characteristic.NOTIFY),
46+
write_perm=Attribute.NO_ACCESS,
47+
)
48+
color_O = Uint32Characteristic(
49+
uuid = VendorUUID("51ad213f-e568-4e35-84e4-67af89c79ef1"),
50+
properties=(Characteristic.READ | Characteristic.NOTIFY),
51+
write_perm=Attribute.NO_ACCESS,
52+
)
53+
color_Y = Uint32Characteristic(
54+
uuid = VendorUUID("51ad213f-e568-4e35-84e4-67af89c79ef2"),
55+
properties=(Characteristic.READ | Characteristic.NOTIFY),
56+
write_perm=Attribute.NO_ACCESS,
57+
)
58+
color_G = Uint32Characteristic(
59+
uuid = VendorUUID("51ad213f-e568-4e35-84e4-67af89c79ef3"),
60+
properties=(Characteristic.READ | Characteristic.NOTIFY),
61+
write_perm=Attribute.NO_ACCESS,
62+
)
63+
color_B = Uint32Characteristic(
64+
uuid = VendorUUID("51ad213f-e568-4e35-84e4-67af89c79ef4"),
65+
properties=(Characteristic.READ | Characteristic.NOTIFY),
66+
write_perm=Attribute.NO_ACCESS,
67+
)
68+
color_V = Uint32Characteristic(
69+
uuid = VendorUUID("51ad213f-e568-4e35-84e4-67af89c79ef5"),
70+
properties=(Characteristic.READ | Characteristic.NOTIFY),
71+
write_perm=Attribute.NO_ACCESS,
72+
)
73+
74+
def __init__(self, service=None):
75+
super().__init__(service=service)
76+
self.connectable = True
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,82 @@
1+
"""
2+
*****************************************************************************
3+
Copyright 2023 Silicon Laboratories Inc. www.silabs.com
4+
*****************************************************************************
5+
SPDX-License-Identifier: Zlib
6+
7+
The licensor of this software is Silicon Laboratories Inc.
8+
9+
This software is provided \'as-is\', without any express or implied
10+
warranty. In no event will the authors be held liable for any damages
11+
arising from the use of this software.
12+
13+
Permission is granted to anyone to use this software for any purpose,
14+
including commercial applications, and to alter it and redistribute it
15+
freely, subject to the following restrictions:
16+
17+
1. The origin of this software must not be misrepresented; you must not
18+
claim that you wrote the original software. If you use this software
19+
in a product, an acknowledgment in the product documentation would be
20+
appreciated but is not required.
21+
2. Altered source versions must be plainly marked as such, and must not be
22+
misrepresented as being the original software.
23+
3. This notice may not be removed or altered from any source distribution.
24+
25+
*****************************************************************************
26+
# EXPERIMENTAL QUALITY
27+
This code has not been formally tested and is provided as-is. It is not
28+
suitable for production environments. In addition, this code will not be
29+
maintained and there may be no bug maintenance planned for these resources.
30+
Silicon Labs may update projects from time to time.
31+
******************************************************************************
32+
"""
33+
import neopixel_spi as neopixel
34+
35+
36+
# Update this to match the number of LEDs.
37+
NUMPIXELS_DEFAULT = 15
38+
39+
#start pixel position of each color on neopixel
40+
pixel_offset=[0, 2, 4, 6, 9, 12]
41+
42+
#number pixels present for each color from start position
43+
num_pixel_by_color = [2, 2, 2, 3, 3, 3]
44+
45+
#color code in rgb
46+
rgb_code = [
47+
[255, 0, 0], #red
48+
[242, 140, 4], #orange
49+
[255, 255, 0], #yellow
50+
[0, 255, 0], #green
51+
[0, 0, 255], #blue
52+
[255, 0, 255], #violet
53+
]
54+
55+
class Display(neopixel.NeoPixel_SPI):
56+
def __init__(self, spi, brightness) -> None:
57+
super().__init__(spi, NUMPIXELS_DEFAULT, brightness=brightness, bpp=4, auto_write=False)
58+
59+
def fill_color(self, color):
60+
self.fill(color)
61+
self.show()
62+
63+
def clear(self):
64+
self.fill(0x00)
65+
self.show()
66+
67+
def draw_pixels(self, num_pixel:int, position:int, intensity:int, rgb_code:list):
68+
color = int(intensity*rgb_code[0]/255)<<16 | int(intensity*rgb_code[1]/255)<<8 | int(intensity*rgb_code[2]/255)
69+
for i in range(num_pixel):
70+
self[i+position] = color
71+
self.show()
72+
73+
def draw_LightSensingData(self, data_channel:list):
74+
for color in range(6):
75+
intensity = data_channel[color]/10000*255
76+
self.draw_pixels(num_pixel_by_color[color],
77+
pixel_offset[color],
78+
intensity,
79+
rgb_code[color])
80+
81+
82+
Binary file not shown.

0 commit comments

Comments
 (0)