Skip to content

Commit 975fd3c

Browse files
Kaan OzenKaan Ozen
authored andcommitted
feat(lis2mdl): Add OLED digital compass example.
1 parent 5086533 commit 975fd3c

1 file changed

Lines changed: 103 additions & 0 deletions

File tree

Lines changed: 103 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,103 @@
1+
"""Digital compass example using LIS2MDL and SSD1327 OLED.
2+
3+
Reads the magnetic heading using the built-in flat heading method,
4+
and draws a dynamic compass needle on the display using lines.
5+
Includes a preliminary calibration step.
6+
"""
7+
8+
from math import cos, pi, sin
9+
from time import sleep_ms
10+
11+
import ssd1327
12+
from lis2mdl import LIS2MDL
13+
from machine import I2C, SPI, Pin
14+
15+
# Layout Constants for Round Screen
16+
CENTER_X = 64
17+
CENTER_Y = 54
18+
COMPASS_RADIUS = 42 # Radius for the outer border of the compass
19+
NEEDLE_LENGTH = 35
20+
TEXT_HEAD_X = 36
21+
TEXT_HEAD_Y = 100
22+
TEXT_DIR_X = 36
23+
TEXT_DIR_Y = 112
24+
CARD_N_X = 60
25+
CARD_N_Y = 16
26+
CARD_S_X = 60
27+
CARD_S_Y = 84
28+
CARD_E_X = 96
29+
CARD_E_Y = 50
30+
CARD_W_X = 24
31+
CARD_W_Y = 50
32+
CALIB_MSG1_X = 12
33+
CALIB_MSG1_Y = 50
34+
CALIB_MSG2_X = 4
35+
CALIB_MSG2_Y = 70
36+
37+
# Hardware Initialization
38+
i2c = I2C(1)
39+
mag = LIS2MDL(i2c)
40+
41+
spi = SPI(1)
42+
dc = Pin("DATA_COMMAND_DISPLAY")
43+
res = Pin("RST_DISPLAY")
44+
cs = Pin("CS_DISPLAY")
45+
display = ssd1327.WS_OLED_128X128_SPI(spi, dc, res, cs)
46+
47+
try:
48+
# Calibration Phase
49+
display.fill(0)
50+
display.text("Calibrating...", CALIB_MSG1_X, CALIB_MSG1_Y, 15)
51+
display.text("Move in 8-shape", CALIB_MSG2_X, CALIB_MSG2_Y, 15)
52+
display.show()
53+
sleep_ms(100)
54+
55+
print("Calibrate the magnetometer by moving it in a figure-eight pattern.")
56+
mag.calibrate_minmax_3d()
57+
print("Calibration complete.")
58+
59+
# Main Compass Loop
60+
while True:
61+
heading_deg = mag.heading_flat_only()
62+
direction = mag.direction_label(heading_deg)
63+
64+
# Convert to radians for the trigonometric functions
65+
# 0 degrees is North (Up), 90 is East (Right)
66+
heading_rad = heading_deg * pi / 180.0
67+
68+
# Calculate the end coordinates of the compass needle
69+
end_x = CENTER_X + int(NEEDLE_LENGTH * sin(heading_rad))
70+
end_y = CENTER_Y - int(NEEDLE_LENGTH * cos(heading_rad))
71+
72+
# Drawing Phase
73+
display.fill(0)
74+
75+
# Draw the compass outer border (circle)
76+
display.framebuf.ellipse(CENTER_X, CENTER_Y, COMPASS_RADIUS, COMPASS_RADIUS, 15)
77+
78+
# Draw Cardinal Points (N, E, S, W)
79+
display.text("N", CARD_N_X, CARD_N_Y, 15)
80+
display.text("S", CARD_S_X, CARD_S_Y, 15)
81+
display.text("E", CARD_E_X, CARD_E_Y, 15)
82+
# Si tu préfères l'initiale française pour Ouest, remplace le "W" par "O" ici :
83+
display.text("W", CARD_W_X, CARD_W_Y, 15)
84+
85+
# Draw the center dot and the needle
86+
display.framebuf.fill_rect(CENTER_X - 1, CENTER_Y - 1, 3, 3, 15)
87+
display.framebuf.line(CENTER_X, CENTER_Y, end_x, end_y, 15)
88+
89+
# Display the heading text and direction label at the bottom
90+
display.text("{} deg".format(int(heading_deg)), TEXT_HEAD_X, TEXT_HEAD_Y, 15)
91+
display.text("Dir: {}".format(direction), TEXT_DIR_X, TEXT_DIR_Y, 15)
92+
93+
display.show()
94+
sleep_ms(50)
95+
96+
except KeyboardInterrupt:
97+
pass
98+
finally:
99+
# Clean up and power off display on exit
100+
display.fill(0)
101+
display.show()
102+
sleep_ms(100)
103+
display.power_off()

0 commit comments

Comments
 (0)