Skip to content

Commit 14aba81

Browse files
hlym123lbuque
authored andcommitted
libs/base: Add support for Motion Base v1.1
Signed-off-by: hlym123 <[email protected]>
1 parent 6fe3042 commit 14aba81

File tree

7 files changed

+362
-12
lines changed

7 files changed

+362
-12
lines changed

docs/en/base/motion.rst

Lines changed: 65 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,32 +1,57 @@
1-
21
Motion Base
32
===========
43

54
.. include:: ../refs/base.motion.ref
65

76
Atomic Motion Base is a servo and DC motor driver designed specifically for the ATOM series controllers. It integrates an STM32 control chip internally and uses I2C communication for control. Atomic Motion Base provides 4 servo channels and 2 DC motor interfaces, offering convenience for scenarios that require control of multiple servos or motor drivers, such as multi-axis servo robotic arms or small car motor control.
87

8+
Atomic Motion Base v1.1 adds INA226 to implement current and voltage detection.
9+
910
Support the following products:
1011

1112
|Motion|
1213

14+
|Motion Base v1.1|
15+
1316

1417
Micropython Example:
18+
----------------------------
19+
20+
Motion Base
21+
++++++++++++++++++++++++++++
1522

1623
.. literalinclude:: ../../../examples/base/motion/atoms3_lite_motion_base_example.py
1724
:language: python
1825
:linenos:
1926

27+
Motion Base v1.1
28+
++++++++++++++++++++++++++++
2029

21-
UIFLOW2 Example:
30+
.. literalinclude:: ../../../examples/base/motion/atoms3_motion_base_v1.1_example.py
31+
:language: python
32+
:linenos:
2233

23-
|example.png|
34+
UIFlow2.0 Example:
35+
----------------------------
36+
37+
Motion Base
38+
++++++++++++++++++++++++++++
2439

40+
|example.png|
2541

2642
.. only:: builder_html
2743

2844
|atoms3_lite_motion_base_example.m5f2|
2945

46+
Motion Base v1.1
47+
++++++++++++++++++++++++++++
48+
49+
|motion_base_v1.1_example.png|
50+
51+
.. only:: builder_html
52+
53+
|atoms3_motion_base_v1.1_example.m5f2|
54+
3055

3156
class Motion
3257
------------
@@ -41,11 +66,10 @@ Constructors
4166
- ``i2c``: I2C port to use.
4267
- ``address``: I2C address of the servo8.
4368

44-
UIFLOW2:
69+
UIFlow2.0:
4570

4671
|__init__.png|
4772

48-
4973
Methods
5074
-------
5175

@@ -55,7 +79,7 @@ Methods
5579

5680
- ``ch``: Servo channel (1 to 4).
5781

58-
UIFLOW2:
82+
UIFlow2.0:
5983

6084
|get_servo_angle.png|
6185

@@ -66,7 +90,7 @@ Methods
6690
- ``ch``: Servo channel (1 to 4).
6791
- ``angle``: Angle of the servo (0 to 180).
6892

69-
UIFLOW2:
93+
UIFlow2.0:
7094

7195
|set_servo_angle.png|
7296

@@ -76,7 +100,7 @@ Methods
76100

77101
- ``ch``: Servo channel (1 to 4).
78102

79-
UIFLOW2:
103+
UIFlow2.0:
80104

81105
|get_servo_pulse.png|
82106

@@ -87,7 +111,7 @@ Methods
87111
- ``ch``: Servo channel (1 to 4).
88112
- ``pulse``: Pulse width of the servo (500 to 2500).
89113

90-
UIFLOW2:
114+
UIFlow2.0:
91115

92116
|write_servo_pulse.png|
93117

@@ -97,7 +121,7 @@ Methods
97121

98122
- ``ch``: Motor channel (1 or 2).
99123

100-
UIFLOW2:
124+
UIFlow2.0:
101125

102126
|get_motor_speed.png|
103127

@@ -112,4 +136,35 @@ Methods
112136

113137
|set_motor_speed.png|
114138

139+
.. method:: Motion.read_voltage() -> float
140+
141+
Read voltage (unit: V)
142+
143+
.. note::
144+
This method is supported only on Motion Base v1.1 and later versions.
145+
146+
UIFlow2.0
147+
148+
|read_voltage.png|
149+
150+
.. method:: Motion.read_current() -> float
151+
152+
Read voltage (unit: A)
153+
154+
.. note::
155+
This method is supported only on Motion Base v1.1 and later versions.
156+
157+
UIFlow2.0
158+
159+
|read_current.png|
160+
161+
.. method:: Motion.read_power() -> float
162+
163+
Read power (unit: W)
164+
165+
.. note::
166+
This method is supported only on Motion Base v1.1 and later versions.
167+
168+
UIFlow2.0
115169

170+
|read_power.png|

docs/en/refs/base.motion.ref

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,12 @@
1111
.. |write_servo_pulse.png| image:: https://static-cdn.m5stack.com/mpy_docs/base/motion/write_servo_pulse.png
1212
.. |get_motor_speed.png| image:: https://static-cdn.m5stack.com/mpy_docs/base/motion/get_motor_speed.png
1313
.. |set_motor_speed.png| image:: https://static-cdn.m5stack.com/mpy_docs/base/motion/set_motor_speed.png
14+
.. |read_voltage.png| image:: https://static-cdn.m5stack.com/mpy_docs/base/motion/read_voltage.png
15+
.. |read_voltage.png| image:: https://static-cdn.m5stack.com/mpy_docs/base/motion/read_current.png
16+
.. |read_power.png| image:: https://static-cdn.m5stack.com/mpy_docs/base/motion/read_power.png
1417

1518
.. |example.png| image:: https://static-cdn.m5stack.com/mpy_docs/base/motion/example.png
19+
.. |motion_base_v1.1_example.png| image:: https://static-cdn.m5stack.com/mpy_docs/base/motion/motion_base_v1.1_example.png
1620

1721
.. |atoms3_lite_motion_base_example.m5f2| raw:: html
1822

@@ -22,3 +26,12 @@
2226
>
2327
atoms3_lite_motion_base_example.m5f2
2428
</a>
29+
30+
.. |atoms3_motion_base_v1.1_example.m5f2| raw:: html
31+
32+
<a
33+
href="https://uiflow2.m5stack.com/?example=https://raw.githubusercontent.com/m5stack/uiflow-micropython/develop/examples/base/motion/atoms3_motion_base_v1.1_example.m5f2"
34+
target="_blank"
35+
>
36+
atoms3_motion_base_v1.1_example.m5f2
37+
</a>
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
{"version":"V2.0","versionNumber":"V2.2.0","type":"atoms3","components":[{"name":"screen","type":"screen","layer":0,"screenId":"builtin","screenName":"","id":"__atoms3_screen","createTime":1737000428283,"x":0,"y":0,"width":128,"height":128,"backgroundColor":"#000000","size":0,"isSelected":true},{"name":"label_speed","type":"label","layer":1,"screenId":"builtin","screenName":"","id":"ilA`GeUDJ*#i45CO","createTime":1737000787880,"x":5,"y":27,"color":"#ffffff","backgroundColor":"#000000","text":"speed:","engine":"gfx","font":"Widgets.FONTS.DejaVu18","rotation":0,"isSelected":false},{"name":"title_e","type":"title","layer":2,"screenId":"builtin","screenName":"","id":"tSDd9b=+Zttk^yn4","createTime":1737000789317,"x":0,"y":0,"color":"#ffffff","backgroundColor":"#0000FF","text":"Motor Ctrl","textOffset":3,"font":"Widgets.FONTS.DejaVu18","isSelected":false},{"name":"label_vol","type":"label","layer":3,"screenId":"builtin","screenName":"","id":"iT64fGl^vT#sV=8y","createTime":1737000919006,"x":5,"y":55,"color":"#ffffff","backgroundColor":"#000000","text":"vol:","engine":"gfx","font":"Widgets.FONTS.DejaVu18","rotation":0,"isSelected":false},{"name":"label_cur","type":"label","layer":4,"screenId":"builtin","screenName":"","id":"odC_LVRfBTOYNV=u","createTime":1737000922201,"x":5,"y":75,"color":"#ffffff","backgroundColor":"#000000","text":"cur:","engine":"gfx","font":"Widgets.FONTS.DejaVu18","rotation":0,"isSelected":false},{"name":"label_pow","type":"label","layer":5,"screenId":"builtin","screenName":"","id":"a@4v@AF7KHQM^qRR","createTime":1737000924900,"x":5,"y":95,"color":"#ffffff","backgroundColor":"#000000","text":"pow:","engine":"gfx","font":"Widgets.FONTS.DejaVu18","rotation":0,"isSelected":false}],"resources":[{"hardware":["hardware_button","hardware_pin_button","imu","ir","i2c"]},{"base":["base_motion"]}],"units":[],"hats":[],"bases":[{"type":"base_motion","name":"motion","id":"xGaulRmedfHIeM`+","createTime":1737010686444,"bus":"i2c0","busList":[],"initBlockType":"base_motion_init","initBlockId":"_!NtF3p$XnYLb2;;zm~V"}],"i2cs":[{"id":"i2c0","portType":"base","userPort":[22,21],"freq":"100000","blockId":"CLvLJm.%v[$EdJK,F)g|"}],"blockly":"<variables><variable id=\"NthEO#lB}@MIqg2+C0`;\">speed</variable><variable id=\"T7UjYo5%;EL7ksVp|@Nl\">voltage</variable><variable id=\"dWt_]_[J-nL[G4vh?$pM\">curent</variable><variable id=\"0wGY;8D_jtYK9JL;;t*n\">last_time</variable><variable id=\"}qBj,kOG)bnVvCKnd67H\">power</variable></variables><block type=\"basic_on_setup\" id=\"setup_block\" deletable=\"false\" x=\"-70\" y=\"-70\"><mutation isBegin=\"true\"></mutation><field name=\"UPDATEOP\">true</field><statement name=\"FUNC\"><block type=\"system_m5_begin\" id=\"system_m5_begin\"><next><block type=\"i2c_init\" id=\"CLvLJm.%v[$EdJK,F)g|\"><field name=\"NAME\">0</field><field name=\"FREQ\">100000</field><value name=\"SCL\"><shadow type=\"math_number\" id=\"gBt~`@,+m)s*PBl%@x)7\"><mutation max=\"Infinity\" min=\"-Infinity\" precision=\"0\"></mutation><field name=\"NUM\">39</field></shadow></value><value name=\"SDA\"><shadow type=\"math_number\" id=\"3TUUyA_sBcdpp%#M6A=~\"><mutation max=\"Infinity\" min=\"-Infinity\" precision=\"0\"></mutation><field name=\"NUM\">38</field></shadow></value><next><block type=\"base_motion_init\" id=\"_!NtF3p$XnYLb2;;zm~V\"><value name=\"ADDR\"><shadow type=\"base_motion_addr_option\" id=\"LhFyLN4daQ56FT:ed%GG\"><field name=\"VALUE\">0x38</field></shadow></value><next><block type=\"variables_set\" id=\"PCN`D2BpXcCyQat`tXpR\"><field name=\"VAR\" id=\"0wGY;8D_jtYK9JL;;t*n\">last_time</field><value name=\"VALUE\"><block type=\"time_get_ticks_us\" id=\"eH(WX2x@`a8%e.:%42Ow\"></block></value><next><block type=\"variables_set\" id=\"0*|$es4oGBc5W19^`$q.\"><field name=\"VAR\" id=\"NthEO#lB}@MIqg2+C0`;\">speed</field><value name=\"VALUE\"><block type=\"math_number\" id=\"~`dw_X)/:2Uh7p%,(lbO\"><mutation max=\"Infinity\" min=\"-Infinity\" precision=\"0\"></mutation><field name=\"NUM\">0</field></block></value><next><block type=\"label_set_text\" id=\"8#-NF7sXJ*(75^0z3I:k\"><field name=\"NAME\">label_speed</field><value name=\"TEXT\"><shadow type=\"text\" id=\"gw(NqCkIIeixELyfi64z\"><field name=\"TEXT\">Label</field></shadow><block type=\"text_add_str\" id=\"eXfvUxj%#tJugc.S^L|l\"><value name=\"VALUE1\"><shadow type=\"text\" id=\"F5n#@1wEc)JPq(hCDbbh\"><field name=\"TEXT\">speed: </field></shadow></value><value name=\"VALUE2\"><block type=\"variables_get\" id=\"1V?99=+HKEJZikap_XA.\"><field name=\"VAR\" id=\"NthEO#lB}@MIqg2+C0`;\">speed</field></block></value></block></value></block></next></block></next></block></next></block></next></block></next></block></statement></block><block type=\"button_callback\" id=\"ta1g)={ypBLM[U-8%*$u\" x=\"430\" y=\"-50\"><field name=\"NAME\">BtnA</field><field name=\"TYPE\">WAS_CLICKED</field><statement name=\"FUNC\"><block type=\"variables_set\" id=\"~1:Wj?QLsYu]+3Oi[QK{\"><field name=\"VAR\" id=\"NthEO#lB}@MIqg2+C0`;\">speed</field><value name=\"VALUE\"><block type=\"math_arithmetic\" id=\"e|Z@AxZp*`Fs:M5n*(8D\"><field name=\"OP\">ADD</field><value name=\"A\"><shadow type=\"math_number\" id=\"HRAxa{[+]R{M)sClzMXb\"><mutation max=\"Infinity\" min=\"-Infinity\" precision=\"0\"></mutation><field name=\"NUM\">1</field></shadow><block type=\"variables_get\" id=\"8H.sD=S}P(we{ATO[6~W\"><field name=\"VAR\" id=\"NthEO#lB}@MIqg2+C0`;\">speed</field></block></value><value name=\"B\"><shadow type=\"math_number\" id=\"m4UK54H,lSkGxr5HHZGt\"><mutation max=\"Infinity\" min=\"-Infinity\" precision=\"0\"></mutation><field name=\"NUM\">20</field></shadow></value></block></value><next><block type=\"controls_if\" id=\"udwNhD#Ru|n,nZ]^}n^a\"><value name=\"IF0\"><block type=\"logic_compare\" id=\"#|bf6-oslLh3Dzy.T?I.\"><field name=\"OP\">GT</field><value name=\"A\"><block type=\"variables_get\" id=\"Gd746%/Dm)h|nZ_9P-DC\"><field name=\"VAR\" id=\"NthEO#lB}@MIqg2+C0`;\">speed</field></block></value><value name=\"B\"><block type=\"math_number\" id=\"rJQ`vT@-c9R,_2UICw^*\"><mutation max=\"Infinity\" min=\"-Infinity\" precision=\"0\"></mutation><field name=\"NUM\">120</field></block></value></block></value><statement name=\"DO0\"><block type=\"variables_set\" id=\"z8`^YeBS#]Ky?ktpkH3h\"><field name=\"VAR\" id=\"NthEO#lB}@MIqg2+C0`;\">speed</field><value name=\"VALUE\"><block type=\"math_number\" id=\":(-?x/(aL;FmFu{Brr}c\"><mutation max=\"Infinity\" min=\"-Infinity\" precision=\"0\"></mutation><field name=\"NUM\">0</field></block></value></block></statement><next><block type=\"base_motion_set_motor_speed\" id=\"dCpj_e]YF_u|@/2*p^Sw\"><value name=\"CHANNEL\"><shadow type=\"base_motion_motor_option\" id=\"AU+^ChVZ6yb(Yoh,]sr1\"><field name=\"VALUE\">1</field></shadow></value><value name=\"VALUE\"><shadow type=\"math_slider\" id=\"OY@vJYAATwW/sl.gO?}c\"><mutation max=\"127\" min=\"-127\" step=\"1\" precision=\"1\"></mutation><field name=\"NUM\">0</field></shadow><block type=\"variables_get\" id=\"~GP[ebEp!:JAdWsmIP6s\"><field name=\"VAR\" id=\"NthEO#lB}@MIqg2+C0`;\">speed</field></block></value><next><block type=\"label_set_text\" id=\"Wtx9WjcIDs|E(HG1Oq~Y\"><field name=\"NAME\">label_speed</field><value name=\"TEXT\"><shadow type=\"text\" id=\"gw(NqCkIIeixELyfi64z\"><field name=\"TEXT\">Label</field></shadow><block type=\"text_add_str\" id=\"0jh/XH|M;7vk.I2mEve_\"><value name=\"VALUE1\"><shadow type=\"text\" id=\"E)hhOyJTr.-F_s2Bh+%)\"><field name=\"TEXT\">speed: </field></shadow></value><value name=\"VALUE2\"><block type=\"variables_get\" id=\"9,2W]]?sLyDORP~Y^v_.\"><field name=\"VAR\" id=\"NthEO#lB}@MIqg2+C0`;\">speed</field></block></value></block></value></block></next></block></next></block></next></block></statement></block><block type=\"basic_on_loop\" id=\"loop_block\" deletable=\"false\" x=\"-70\" y=\"250\"><mutation isUpdate=\"true\"></mutation><field name=\"UPDATEOP\">true</field><statement name=\"FUNC\"><block type=\"system_m5_update\" id=\"system_m5_update\"><next><block type=\"variables_set\" id=\"7fcTPv*U;Je~TH]3!6TB\"><field name=\"VAR\" id=\"T7UjYo5%;EL7ksVp|@Nl\">voltage</field><value name=\"VALUE\"><block type=\"base_motion_read_voltage\" id=\"GP1MyTWm]XtL5ANmHE7)\"></block></value><next><block type=\"variables_set\" id=\"R+E{IUGh@TQ@5b2Ym,-P\"><field name=\"VAR\" id=\"dWt_]_[J-nL[G4vh?$pM\">curent</field><value name=\"VALUE\"><block type=\"base_motion_read_current\" id=\"U#RdgI5|N?DtV3ojvTHc\"></block></value><next><block type=\"variables_set\" id=\"!b15!k%N#AmUzrd_nl{G\"><field name=\"VAR\" id=\"}qBj,kOG)bnVvCKnd67H\">power</field><value name=\"VALUE\"><block type=\"base_motion_read_power\" id=\"z(?+=shb[}F:{t-hV?EC\"></block></value><next><block type=\"label_set_text\" id=\"P#(PQqydg2JK*eTw16=h\"><field name=\"NAME\">label_vol</field><value name=\"TEXT\"><shadow type=\"text\" id=\"gw(NqCkIIeixELyfi64z\"><field name=\"TEXT\">Label</field></shadow><block type=\"text_add_str\" id=\"G^UwpP4j@YRKHc3cV~,-\"><value name=\"VALUE1\"><shadow type=\"text\" id=\"v`?RQ,:a-qPP|]a8=3SQ\"><field name=\"TEXT\">vol: </field></shadow></value><value name=\"VALUE2\"><block type=\"variables_get\" id=\"ziL0ao%=TWS!abt*gK6P\"><field name=\"VAR\" id=\"T7UjYo5%;EL7ksVp|@Nl\">voltage</field></block></value></block></value><next><block type=\"label_set_text\" id=\"CLPiscH6u2Jfcsmxh3#I\"><field name=\"NAME\">label_cur</field><value name=\"TEXT\"><shadow type=\"text\" id=\"gw(NqCkIIeixELyfi64z\"><field name=\"TEXT\">Label</field></shadow><block type=\"text_add_str\" id=\"jCh$Ov9Pu#jtQV*x3g?a\"><value name=\"VALUE1\"><shadow type=\"text\" id=\"`fKmNa66X.mz~aOQ)a)P\"><field name=\"TEXT\">cur: </field></shadow></value><value name=\"VALUE2\"><block type=\"variables_get\" id=\"T/q=vE$#E29-_m[Y{OW$\"><field name=\"VAR\" id=\"dWt_]_[J-nL[G4vh?$pM\">curent</field></block></value></block></value><next><block type=\"label_set_text\" id=\"QjZy8c[pyy6l|Ht(odJI\"><field name=\"NAME\">label_pow</field><value name=\"TEXT\"><shadow type=\"text\" id=\"gw(NqCkIIeixELyfi64z\"><field name=\"TEXT\">Label</field></shadow><block type=\"text_add_str\" id=\"]yx%lp01~]=fbQtrXJj0\"><value name=\"VALUE1\"><shadow type=\"text\" id=\"s@al2jtQ~#HIIP7:k+,*\"><field name=\"TEXT\">pow: </field></shadow></value><value name=\"VALUE2\"><block type=\"variables_get\" id=\"%@#C,vj/d2@,r2hO=Lr2\"><field name=\"VAR\" id=\"}qBj,kOG)bnVvCKnd67H\">power</field></block></value></block></value></block></next></block></next></block></next></block></next></block></next></block></next></block></statement></block>","screen":[{"simulationName":"Built-in","type":"builtin","width":128,"height":128,"scale":1.3,"screenName":"","blockId":"","screenColorType":0,"id":"builtin","createTime":1737000428281}],"logicWhenNum":0,"customList":[]}
Lines changed: 111 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,111 @@
1+
# SPDX-FileCopyrightText: 2025 M5Stack Technology CO LTD
2+
#
3+
# SPDX-License-Identifier: MIT
4+
5+
import os, sys, io
6+
import M5
7+
from M5 import *
8+
from hardware import I2C
9+
from hardware import Pin
10+
from base import Motion
11+
import time
12+
13+
14+
label_speed = None
15+
title_e = None
16+
label_vol = None
17+
label_cur = None
18+
label_pow = None
19+
i2c0 = None
20+
motion = None
21+
speed = None
22+
voltage = None
23+
curent = None
24+
last_time = None
25+
power = None
26+
27+
28+
def btnA_wasClicked_event(state):
29+
global \
30+
label_speed, \
31+
title_e, \
32+
label_vol, \
33+
label_cur, \
34+
label_pow, \
35+
i2c0, \
36+
motion, \
37+
speed, \
38+
voltage, \
39+
curent, \
40+
last_time, \
41+
power
42+
speed = speed + 20
43+
if speed > 120:
44+
speed = 0
45+
motion.set_motor_speed(1, speed)
46+
label_speed.setText(str((str("speed: ") + str(speed))))
47+
48+
49+
def setup():
50+
global \
51+
label_speed, \
52+
title_e, \
53+
label_vol, \
54+
label_cur, \
55+
label_pow, \
56+
i2c0, \
57+
motion, \
58+
speed, \
59+
voltage, \
60+
curent, \
61+
last_time, \
62+
power
63+
M5.begin()
64+
label_speed = Widgets.Label("speed:", 5, 27, 1.0, 0xFFFFFF, 0x000000, Widgets.FONTS.DejaVu18)
65+
title_e = Widgets.Title("Motor Ctrl", 3, 0xFFFFFF, 0x0000FF, Widgets.FONTS.DejaVu18)
66+
label_vol = Widgets.Label("vol:", 5, 55, 1.0, 0xFFFFFF, 0x000000, Widgets.FONTS.DejaVu18)
67+
label_cur = Widgets.Label("cur:", 5, 75, 1.0, 0xFFFFFF, 0x000000, Widgets.FONTS.DejaVu18)
68+
label_pow = Widgets.Label("pow:", 5, 95, 1.0, 0xFFFFFF, 0x000000, Widgets.FONTS.DejaVu18)
69+
BtnA.setCallback(type=BtnA.CB_TYPE.WAS_CLICKED, cb=btnA_wasClicked_event)
70+
i2c0 = I2C(0, scl=Pin(39), sda=Pin(38), freq=100000)
71+
motion = Motion(i2c0, 0x38)
72+
last_time = time.ticks_us()
73+
speed = 0
74+
label_speed.setText(str((str("speed: ") + str(speed))))
75+
76+
77+
def loop():
78+
global \
79+
label_speed, \
80+
title_e, \
81+
label_vol, \
82+
label_cur, \
83+
label_pow, \
84+
i2c0, \
85+
motion, \
86+
speed, \
87+
voltage, \
88+
curent, \
89+
last_time, \
90+
power
91+
M5.update()
92+
voltage = motion.read_voltage()
93+
curent = motion.read_current()
94+
power = motion.read_power()
95+
label_vol.setText(str((str("vol: ") + str(voltage))))
96+
label_cur.setText(str((str("cur: ") + str(curent))))
97+
label_pow.setText(str((str("pow: ") + str(power))))
98+
99+
100+
if __name__ == "__main__":
101+
try:
102+
setup()
103+
while True:
104+
loop()
105+
except (Exception, KeyboardInterrupt) as e:
106+
try:
107+
from utility import print_error_msg
108+
109+
print_error_msg(e)
110+
except ImportError:
111+
print("please update to latest firmware")

m5stack/libs/base/motion.py

Lines changed: 31 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
# SPDX-FileCopyrightText: 2024 M5Stack Technology CO LTD
1+
# SPDX-FileCopyrightText: 2025 M5Stack Technology CO LTD
22
#
33
# SPDX-License-Identifier: MIT
44
"""
@@ -12,6 +12,7 @@
1212
# Import necessary libraries
1313
from machine import I2C
1414
import struct
15+
from driver.ina226 import INA226
1516

1617

1718
class Motion:
@@ -43,6 +44,19 @@ def __init__(self, i2c: I2C, address: int | list | tuple = 0x38) -> None:
4344
self.i2c = i2c
4445
self.addr = address
4546
self._available()
47+
self.ina = None
48+
self.addr_ina266 = 0x40
49+
if self.addr_ina266 in self.i2c.scan():
50+
self.ina = INA226(
51+
self.i2c, addr=self.addr_ina266, shunt_resistor=0.02
52+
) # shunt resistor 20mΩ
53+
self.ina.configure(
54+
avg=self.ina.CFG_AVGMODE_16SAMPLES,
55+
vbus_conv_time=self.ina.CFG_VBUSCT_1100us,
56+
vshunt_conv_time=self.ina.CFG_VSHUNTCT_1100us,
57+
mode=self.ina.CFG_MODE_SANDBVOLT_CONTINUOUS,
58+
)
59+
self.ina.calibrate(max_expected_current=3.6) # max expected current 3.6A
4660

4761
def _available(self) -> None:
4862
"""! Check if sensor is available on the I2C bus.
@@ -146,5 +160,20 @@ def set_motor_speed(self, ch, speed) -> None:
146160
speed = int(max(-127, speed))
147161
self.i2c.writeto_mem(self.addr, ch + 0x20, struct.pack("b", speed))
148162

163+
def read_voltage(self):
164+
"""
165+
read bus voltage (unit: V)
166+
"""
167+
return self.ina.read_bus_voltage()
149168

150-
MotionBase = Motion
169+
def read_current(self):
170+
"""
171+
read current (unit: A)
172+
"""
173+
return self.ina.read_current()
174+
175+
def read_power(self):
176+
"""
177+
read power (unit: W)
178+
"""
179+
return self.ina.read_power()

0 commit comments

Comments
 (0)