OpenMV Cam RT1062¶
إن OpenMV Cam RT1062 لوحة رؤية آلية منخفضة الطاقة مبنية حول NXP i.MX RT1062 (Cortex‑M7 بتردد 600 MHz). تجمع اللوحة بين شبكات USB‑C عالية السرعة وWi‑Fi/Bluetooth وإيثرنت 10/100 مع مستشعر OV5640 بدقة 5MP على حامل قابل للإزالة. لا تسحب الكاميرا سوى نحو 30 ميكرو أمبير من بطارية LiPo في وضع السبات العميق، مما يجعلها مناسبة تماماً للمشاريع التي تعمل بالبطارية.
للاطلاع على ورقة البيانات الكاملة والصور والأبعاد، راجع صفحة منتج OpenMV Cam RT1062.
أبرز الميزات¶
NXP i.MX RT1062 Cortex‑M7 بتردد 600 MHz.
32 MB من ذاكرة SDRAM الخارجية (16‑بت بتردد 160 MHz، 320 MB/s) بالإضافة إلى 1 MB من ذاكرة SRAM الداخلية و16 MB من ذاكرة QSPI flash (133 MHz 4‑بت SDR، قراءة 66 MB/s)؛ 4 KB EEPROM على إصدار R6+.
مستشعر OV5640 بدقة 5MP وغالق متدحرج (rolling‑shutter).
وحدة IMU مدمجة (مقياس تسارع ثلاثي المحاور بدقة 12‑بت، ±2/4/8 g).
USB‑C عالي السرعة (480 Mb/s، بحد تيار 1.5 A)، وإيثرنت 10/100 Mb/s (داعم لـ PoE عبر درع توسعة)، وWi‑Fi a/b/g/n + Bluetooth 5.1 (هوائي رقاقة أو خيار U.FL).
مقبس microSD — بطاقات SD حتى 2 GB، وSDHC حتى 32 GB، وSDXC حتى 2 TB.
شاحن LiPo (500 mA على R6+، و100 mA على R4/R5)، وساعة RTC مع وسادات بطارية احتياطية. يسحب وضع السبات العميق نحو 30 ميكرو أمبير من البطارية.
14 دبوس إدخال/إخراج، جميعها بإخراج 3.3 V / تحمّل 3.3 V، و4 mA لكل دبوس، وقادرة على المقاطعة.
مؤشر RGB LED للمستخدم، وزر SW للمستخدم، وزر طاقة عتادي (آلة حالات للسبات العميق / الاستيقاظ)، ومؤشر LED حالة منفصل للشحن / USB / طاقة VIN.
تحذير
دبابيس الإدخال/الإخراج في RT1062 غير متحمّلة لـ 5 V. لا توصّل الجهاز مباشرة بمتحكم دقيق يعمل بـ 5 V مثل Arduino Mega. زوّد اللوحة بالطاقة عبر VIN فقط.
مخطط الدبابيس¶
مرجع الدبابيس¶
اسم الدبوس |
الوظيفة |
|---|---|
P0 |
SPI1 MOSI / PWM2 B3 |
P1 |
SPI1 MISO / CAN0 TX |
P2 |
SPI1 SCLK / PWM2 B3 |
P3 |
SPI1 SS / CAN0 RX |
P4 |
I2C1 SCL / UART1 TX / PWM1 X2 |
P5 |
I2C1 SDA / UART1 RX / PWM1 X3 |
P6 |
ADC |
P7 |
PWM2 A0 |
P8 |
PWM2 B0 |
P9 |
PWM1 A3 |
P10 |
PWM1 B3 / إدخال/إخراج مزامنة الإطارات |
P11 |
الاستيقاظ (نشط عند المستوى المنخفض، صِله بـ GND للاستيقاظ) |
P12 |
RESET — اسحبه إلى GND لإعادة تعيين اللوحة (ليس دبوس GPIO) |
P13 |
إدخال/إخراج رقمي |
P14 |
إدخال/إخراج رقمي |
ON/OFF |
وسادة موصّل تكرّر زر الطاقة العتادي (نشط عند المستوى المنخفض) |
SW |
زر المستخدم (نشط عند المستوى المنخفض) |
ST |
منخفض عند الطاقة من VIN، ومرتفع عند الطاقة من USB |
CHG |
نشط عند المستوى المنخفض؛ منخفض أثناء شحن بطارية LiPo متصلة |
PG |
نشط عند المستوى المنخفض؛ منخفض عند وجود طاقة VIN أو USB |
LED_RED |
قناة الأحمر في مؤشر RGB LED (نشطة عند المستوى المنخفض) |
LED_GREEN |
قناة الأخضر في مؤشر RGB LED (نشطة عند المستوى المنخفض) |
LED_BLUE |
قناة الأزرق في مؤشر RGB LED (نشطة عند المستوى المنخفض) |
ملاحظة
خط مزامنة الإطارات P10 هو ناقل مشترك. فهو موصول بالمتحكم الدقيق ودبوس التشغيل / التعريض في مستشعر الكاميرا وموصّل المستخدم في آن واحد. الاتجاه محدّد بحسب التطبيق — يمكن للمتحكم الدقيق أو المستشعر أو إشارة خارجية أن تقود الخط بحسب طريقة إعداد المستشعر. تأكد من أن مشغّلاً واحداً فقط نشط في كل مرة.
ملاحظة
يُرجَع ON/OFF وP11 إلى سكة RAW الدائمة التشغيل (لا إلى سكة 3.3 V المُبدَّلة)، لذا يبقيان فعّالين بينما تكون بقية اللوحة في وضع السبات العميق / منخفض الطاقة. كلا المدخلين نشطان عند المستوى المنخفض.
تمرّ هذه الدبابيس عبر مغيّرات مستوى لتتمكن من العمل على سكة RAW. إذا كنت بحاجة ماسّة إلى سلوك GPIO مباشر بـ 3.3 V على ON/OFF أو P11 (مثلاً لقيادتهما من متحكم دقيق بـ 3.3 V دون المرور عبر المغيّر)، فإن اللوحة توفر وسادات وصلات سحب علوي ووصلات 0 أوم تتيح لك تجاوز المغيّر. هذا تعديل عتادي متقدّم — وعلى معظم المستخدمين تركه دون مساس.
ملاحظة
P13 وP14 هما GPIO عادي افتراضياً دون أي وظيفة خاصة. يمكن اختيارياً إعادة توجيه الوسادتين إلى إشارات أخرى عبر إعادة لحام جسور مقاومة 0 أوم على ظهر اللوحة:
P13 ↔ حالة CHG / JTAG TRSTB
P14 ↔ حالة ST / JTAG TDI
معظم المستخدمين لن يلمسوا هذه الوصلات — اتركها على وضع GPIO الافتراضي ما لم تكن بحاجة تحديداً إلى قراءة إدارة الطاقة أو إلى JTAG.
دبابيس الطاقة¶
3.3V — سكة 3.3 V منظَّمة. للإخراج فقط على RT1062 — لا تغذّ طاقة خارجية إلى هذا الدبوس. يتوفر حتى 1 A لدروع التوسعة.
VIN — دخل 5 V. يزوّد اللوحة وشاحن LiPo المدمج بالطاقة.
RAW — إدخال/إخراج، دائم التشغيل (3.6 V – 5 V). يحمل أي مصدر يكون نشطاً (VIN أو USB أو البطارية المتصلة)، ويمكن استخدامه أيضاً كمدخل. يجب أن تقود RAW عبر ثنائي متسلسل عند تغذية الطاقة إليه — وإلا فسيتدفق التيار عائداً إلى VIN/USB ويتلف مزوّد الطاقة أو الحماية المدمجة.
GND — الأرضي المشترك.
ملاحظة
تختار رقاقة إدارة الطاقة المدمجة تلقائياً أياً من USB أو VIN ذي الجهد الأعلى لتزويد اللوحة وشاحن البطارية بالطاقة. وإذا كانت بطارية LiPo متصلة فإنها تُشحن من الفائض المتبقي، ويرجع المتحكم إلى البطارية للحفاظ على تشغيل اللوحة إذا انخفض جهد VIN/USB أو فُصلا.
ملاحظة
يحتوي ظهر اللوحة على وسادات لحام لـبطارية احتياطية خارجية بـ 3.3 V للـ RTC. يؤدي توصيل خلية على شكل عملة بهذه الوسادات إلى إبقاء RTC قيد التشغيل بينما تكون بقية اللوحة دون طاقة.
نصيحة
استخدم مقدّر عمر البطارية لتقدير المدة التي سيعمل خلالها RT1062 على بطارية ما عند دورة عمل نشطة / سبات عميق معينة.
دبابيس الإيثرنت¶
يعرض RT1062 أزواج MDI الخاصة بطبقة PHY للإيثرنت 10/100 Mb/s على وسادات مخصصة بجوار موصّل GPIO. ليس من الآمن توصيل دبابيس MDI مباشرة بموصّل RJ45 — إذ يُشترط وجود مغناطيسات الإيثرنت (محوّل عزل، إما مدمج في magjack أو على درع التوسعة) بين PHY والكابل. يتضمنها درع OpenMV PoE؛ وإذا كنت تصنع موصّلك بنفسك، فاستخدم RJ45 مدمجاً للمغناطيسات أو محوّلاً خارجياً.
ETH_LED — مؤشر LED للوصلة/النشاط. نشط عند المستوى المنخفض عندما تكون الوصلة قائمة؛ ويومض عند حركة المرور.
ETH_TXP / ETH_TXN — زوج الإرسال.
ETH_RXP / ETH_RXN — زوج الاستقبال.
ملاحظة
يعرض الموصّل أيضاً أربع وسادات منقوش عليها Reserved. وهذه متوافقة في البصمة مع أزواج إيثرنت الجيجابت في OpenMV N6 (DC P/N وDD P/N) بحيث يمكن توصيل درع الإيثرنت / PoE نفسه بأي من اللوحتين. لا تدعم طبقة PHY في RT1062 سوى 10/100 Mb/s، لذا فإن هذه الوسادات الأربع بلا أي توصيل كهربائي — اتركها غير موصولة.
دبابيس الاستعادة والتنقيح¶
RESET — اسحبه إلى GND لإعادة تعيين اللوحة. يؤدي تحريره إلى السماح للمتحكم الدقيق ببدء التشغيل بشكل طبيعي.
SBL — اسحبه إلى 3.3 V أثناء تزويد اللوحة بالطاقة لدخول وضع محمّل الإقلاع من ROM (Serial Boot Loader). يستخدم OpenMV IDE هذا الوضع لإعادة كتابة محمّل الإقلاع المدمج.
تم تركيب موصّل SWD/JTAG من ARM بعشرة دبابيس مخصص، متوافق مع محوّلات ST‑LINK وSEGGER J‑Link.
ملاحظة
يعرض RT1062 تنقيح SWD فقط عبر هذا الموصّل افتراضياً. وليس JTAG الكامل متاحاً جاهزاً.
الطرفيات المدمجة¶
مؤشرات LED¶
يحتوي RT1062 على مؤشري RGB LED:
مؤشر RGB LED للمستخدم — قابل للتحكم بالبرمجيات، ومعروض كـ
LED_REDوLED_GREENوLED_BLUEfrom machine import LED LED("LED_RED").on() LED("LED_GREEN").on() LED("LED_BLUE").on()
مؤشر LED للطاقة — مدفوع مباشرة بعتاد إدارة الطاقة المدمج، دون تحكم برمجي. استخدمه لقراءة ما يفعله مزوّد الطاقة بنظرة سريعة.
أثناء التشغيل:
القناة
المعنى
أزرق
VIN يزوّد اللوحة بالطاقة (مطفأ عند USB)
أخضر
وجود طاقة USB أو VIN
أحمر
شحن بطارية LiPo متصلة
في وضع السبات العميق تكون جميع القنوات مطفأة باستثناء الأحمر، الذي يظل مضيئاً أثناء شحن بطارية LiPo.
دبابيس حالة الطاقة¶
ثلاثة مدخلات حالة نشطة عند المستوى المنخفض من رقاقة إدارة الطاقة المدمجة:
PG — منخفض عند وجود طاقة VIN أو USB. موصول دائماً.
ST — منخفض عندما تعمل اللوحة على VIN، ومرتفع عندما تعمل على طاقة USB. غير موصول افتراضياً.
CHG — منخفض أثناء شحن بطارية LiPo متصلة. غير موصول افتراضياً.
from machine import Pin
power_ok = not Pin("PG", Pin.IN).value()
مستشعر الكاميرا¶
تُقاد OV5640 عبر وحدة csi --- مستشعرات الكاميرا
import csi
cam = csi.CSI()
cam.reset()
cam.pixformat(csi.RGB565)
cam.framesize(csi.QVGA)
cam.snapshot(time=2000) # let auto‑exposure settle
while True:
img = cam.snapshot()
يحتوي OV5640 على ضاغط JPEG مدمج. اضبط csi.CSI.pixformat على csi.JPEG فيسلّم المستشعر إطارات مضغوطة مباشرة إلى الكاميرا عبر ناقل الكاميرا، مما يجعل الالتقاطات عالية الدقة عملية: csi.HD (1280×720) وcsi.FHD (1920×1080) وكامل دقة 5MP عبر csi.WQXGA2 (2592×1944) تُبث جميعها بصيغة JPEG. اضبط الضغط عبر csi.CSI.quality (0‑100، الأعلى = إطارات أكبر وتفاصيل أكثر):
cam.pixformat(csi.JPEG)
cam.framesize(csi.WQXGA2)
cam.quality(90)
يقع المستشعر على وحدة قابلة للإزالة — استبدلها بأي من وحدات كاميرا OpenMV الأخرى (غالق عالمي، حراري، دقة أعلى، إلخ) دون تغيير بقية اللوحة.
تعلّم الآلة¶
يشغّل ml --- التعلم الآلي نماذج TFLite المكمَّمة على Cortex‑M7 بنوى CMSIS‑NN — بسرعة كافية للكواشف المدمجة بمعدل بضعة إطارات في الثانية. تُحمَّل النماذج الموجودة على نظام الملفات للقراءة فقط /rom مباشرة من ذاكرة flash دون نسخها إلى RAM. وفيما يلي كاشف BlazeFace بدقة 128×128 يضع الوجه المكتشف ومعالمه الست فوق كل إطار:
import csi
import time
import ml
from ml.postprocessing.mediapipe import BlazeFace
# Initialize the sensor.
csi0 = csi.CSI()
csi0.reset()
csi0.pixformat(csi.RGB565)
csi0.framesize(csi.VGA)
csi0.window((400, 400))
# Load built-in face detection model
model = ml.Model("/rom/blazeface_front_128.tflite", postprocess=BlazeFace(threshold=0.4))
print(model)
clock = time.clock()
while True:
clock.tick()
img = csi0.snapshot()
# faces is a list of ((x, y, w, h), score, keypoints) tuples
for r, score, keypoints in model.predict([img]):
ml.utils.draw_predictions(img, [r], ("face",), ((0, 0, 255),), format=None)
# keypoints is a ndarray of shape (6, 2)
# 0 - right eye (x, y)
# 1 - left eye (x, y)
# 2 - nose (x, y)
# 3 - mouth (x, y)
# 4 - right ear (x, y)
# 5 - left ear (x, y)
ml.utils.draw_keypoints(img, keypoints, color=(255, 0, 0))
print(clock.fps(), "fps")
IMU¶
لا يوصّل برنامج RT1062 الثابت مقياس التسارع المدمج بوحدة imu --- مستشعر imu. تخاطب معه مباشرة عبر ناقل I²C الداخلي بدلاً من ذلك — توجد الرقاقة على العنوان 0x15 وتحتوي ثلاث قنوات تسارع موقّعة بدقة 12‑بت بالإضافة إلى بايت حرارة بدقة 8‑بت بدءاً من السجل 0x03
import machine
import time
ADDR = 0x15
DATA_REG = 0x03
LSB_PER_G = 1024.0 # ±2 g range
def s12(hi, lo):
v = ((hi << 8) | lo) >> 4
return v - 0x1000 if v & 0x800 else v
bus = machine.I2C(2)
print("Devices on I²C2:", bus.scan())
while True:
d = bus.readfrom_mem(ADDR, DATA_REG, 7)
x = s12(d[0], d[1]) / LSB_PER_G
y = s12(d[2], d[3]) / LSB_PER_G
z = s12(d[4], d[5]) / LSB_PER_G
temp_c = d[6] * 0.586 + 25.0
print("x=%+.2fg y=%+.2fg z=%+.2fg T=%.1f°C" % (x, y, z, temp_c))
time.sleep_ms(100)
EEPROM¶
لوحات R6 وما بعدها تتضمن EEPROM عام بسعة 4 KB عبر I²C على الناقل الداخلي نفسه الذي يضم مقياس التسارع. (لا تحتوي الإصدارات الأقدم عليه — إذ سيؤدي استدعاء هذه المقتطفات على R4/R5 إلى انتهاء المهلة بسبب فقدان إقرار I²C.) استخدم واجهة برمجة machine.I2C القياسية readfrom_mem / writeto_mem بعنوان ذاكرة من 16‑بت:
import machine
import time
EEPROM_ADDR = 0x50 # default address
PAGE_SIZE = 32 # bytes per page (both read and write)
EEPROM_SIZE = 4096
bus = machine.I2C(2)
# Dump the entire 4 KB one page at a time
data = bytearray()
for offset in range(0, EEPROM_SIZE, PAGE_SIZE):
data += bus.readfrom_mem(EEPROM_ADDR, offset, PAGE_SIZE, addrsize=16)
print(len(data), "bytes")
# Write a small payload back at offset 0 (fits in one page)
bus.writeto_mem(EEPROM_ADDR, 0, b"hello, world", addrsize=16)
time.sleep_ms(10) # ~5 ms write cycle after each page
# Read it back
print(bus.readfrom_mem(EEPROM_ADDR, 0, 12, addrsize=16))
يجب أن تبقى كل من عمليات القراءة والكتابة ضمن صفحة من 32 بايت. قسّم أي نقل أكبر إلى استدعاء واحد لكل صفحة، وأضف تأخير دورة الكتابة البالغ نحو 5 ms بين عمليات الكتابة المتتالية.
Wi‑Fi¶
تُعرض وحدة عائلة CYW43 المدمجة عبر network --- تهيئة الشبكة كواجهة محطة. بعد الاتصال، تُرجع ipconfig("addr4") الزوج (ip, netmask)
import network, time
wlan = network.WLAN(network.STA_IF)
wlan.active(True)
wlan.connect("ssid", "password")
while not wlan.isconnected():
time.sleep(1)
print("Wi‑Fi IP:", wlan.ipconfig("addr4")[0])
Bluetooth¶
تعرض الوحدة اللاسلكية نفسها أيضاً Bluetooth 5.1. استخدم aioble --- BLE غير المتزامن لـ BLE المتوافق مع asyncio — على سبيل المثال، الإعلان كطرفية وانتظار اتصال من جهاز مركزي:
import asyncio
import aioble
async def run():
while True:
conn = await aioble.advertise(250_000, name="OpenMV-RT1062")
print("Connected:", conn.device)
await conn.disconnected()
asyncio.run(run())
إيثرنت¶
عند توصيل موصّل RJ45 (مع مغناطيسات) بوسادات MDI، تظهر طبقة PHY بسرعة 10/100 كواجهة LAN. يعمل DHCP تلقائياً بمجرد قيام الوصلة:
import network, time
lan = network.LAN()
lan.active(True)
while not lan.isconnected():
time.sleep(1)
print("Ethernet IP:", lan.ipconfig("addr4")[0])
بطاقة microSD¶
عند إدراج بطاقة، تُركّب تلقائياً على /sdcard وتصبح قابلة للاستخدام عبر نظام الملفات المعتاد:
import os
for entry in os.listdir("/sdcard"):
print(entry)
مرجع الناقلات¶
GPIO¶
استخدم machine.Pin لقراءة أو قيادة أي من الدبابيس المنقوشة. المخرجات هي 3.3 V CMOS ويمكنها امتصاص/مصدرة ما يصل إلى 4 mA لكل دبوس.
from machine import Pin
out = Pin("P0", Pin.OUT)
out.on()
out.off()
out.value(1)
inp = Pin("P1", Pin.IN, Pin.PULL_UP)
print(inp.value())
يمكن لأي دبوس إدخال أيضاً إطلاق مقاطعة عند انتقالات الحافة:
def handler(pin):
print("triggered:", pin)
Pin("P1", Pin.IN, Pin.PULL_UP).irq(
handler, Pin.IRQ_FALLING | Pin.IRQ_RISING,
)
UART¶
الناقل |
TX |
RX |
|---|---|---|
UART1 |
P4 |
P5 |
from machine import UART
uart = UART(1, baudrate=115200)
uart.write("hello")
uart.read(5)
I²C¶
الناقل |
SCL |
SDA |
|---|---|---|
I2C1 |
P4 |
P5 |
from machine import I2C
i2c = I2C(1, freq=400_000)
i2c.scan()
i2c.writeto(0x76, b"hi")
يمكن أيضاً استخدام العتاد نفسه في وضع الهدف (التابع) عبر machine.I2CTarget لعرض منطقة ذاكرة لمتحكم I²C آخر:
from machine import I2CTarget
buf = bytearray(32)
target = I2CTarget(1, addr=0x42, mem=buf)
SPI¶
الناقل |
MOSI |
MISO |
SCK |
CS |
|---|---|---|---|---|
SPI1 |
P0 |
P1 |
P2 |
P3 |
from machine import SPI
from machine import Pin
spi = SPI(1, baudrate=10_000_000)
cs = Pin("P3", Pin.OUT, value=1) # CS is not driven by the SPI peripheral
cs.value(0)
spi.write(b"hello")
cs.value(1)
CAN¶
الناقل |
TX |
RX |
|---|---|---|
CAN1 |
P1 |
P3 |
ملاحظة
CAN غير مدعوم بعد على هذه اللوحة في البرنامج الثابت v5.0.0.
from machine import CAN
can = CAN(1, 500_000)
can.set_filters(None)
can.send(0x123, b"\xDE\xAD\xBE\xEF")
print(can.recv())
ADC¶
دبوس ADC الوحيد للمستخدم هو P6، وهو بنطاق كامل عند نحو 3.3 V:
from machine import ADC
import time
adc = ADC("P6")
while True:
voltage = adc.read_u16() * 3.3 / 65535
print(voltage)
time.sleep_ms(100)
PWM¶
الدبوس |
قناة FlexPWM |
|---|---|
P0 |
PWM2 B3 |
P2 |
PWM2 B3 |
P4 |
PWM1 X2 |
P5 |
PWM1 X3 |
P7 |
PWM2 A0 |
P8 |
PWM2 B0 |
P9 |
PWM1 A3 |
P10 |
PWM1 B3 |
قُد أياً منها عبر machine.PWM
from machine import Pin, PWM
pwm = PWM(Pin("P9"), freq=1_000, duty_u16=32768)
الناقلات المُولَّدة برمجياً (bit‑banged)¶
تعمل machine.SoftI2C وmachine.SoftSPI على أي دبوس GPIO إذا كنت بحاجة إلى ناقل إضافي.
المستشعر الحراري (خارج اللوحة)¶
يتضمن البرنامج الثابت مشغّل fir --- مشغّل المستشعر الحراري (fir == far infrared) لأجهزة التصوير الحراري الموصولة خارجياً:
MLX90621 — مصفوفة أشعة تحت حمراء 16 × 4
MLX90640 — مصفوفة أشعة تحت حمراء 32 × 24
MLX90641 — مصفوفة أشعة تحت حمراء 16 × 12
AMG8833 — مصفوفة أشعة تحت حمراء 8 × 8
وصّل الوحدة بناقل I²C الخاص باللوحة واقرأ الإطارات عبر fir.init() + fir.snapshot()
import time
import image
import fir
fir.init() # auto‑detects the sensor
clock = time.clock()
while True:
clock.tick()
try:
img = fir.snapshot(x_scale=5, y_scale=5,
color_palette=image.PALETTE_IRONBOW,
hint=image.BICUBIC,
copy_to_fb=True)
except OSError:
continue
print(clock.fps())
يتخاطب مشغّل fir مع المستشعر عبر I²C 4 فقط — وصّل الوحدة بـ P4 (SCL) وP5 (SDA).
التوقيت¶
time¶
تغطي وحدة time التأخيرات الحاجبة، والنبضات الرتيبة، وقياس الزمن المنقضي:
import time
time.sleep(1) # seconds
time.sleep_ms(500)
time.sleep_us(10)
start = time.ticks_ms()
# ...do work...
elapsed = time.ticks_diff(time.ticks_ms(), start)
المؤقتات الافتراضية¶
تجدول machine.Timer دوال رد نداء دورية أو ذات إطلاق واحد دون استهلاك خانة مؤقت عتادي. مرّر -1 كمعرّف لاستخدام مؤقت افتراضي (برمجي):
from machine import Timer
one_shot = Timer(-1)
one_shot.init(period=5_000, mode=Timer.ONE_SHOT,
callback=lambda t: print("once"))
periodic = Timer(-1)
periodic.init(period=2_000, mode=Timer.PERIODIC,
callback=lambda t: print("tick"))
قيم الفترة بالميلي ثانية. استدعِ deinit() لإيقاف الخانة وتحريرها.
ساعة الوقت الحقيقي¶
تحافظ machine.RTC على وقت الساعة الجدارية عبر عمليات إعادة التعيين (ومع البطارية الاحتياطية الاختيارية بـ 3.3 V الموصولة بالوسادات الخلفية، انظر دبابيس الطاقة) عبر فقدان الطاقة الكامل:
from machine import RTC
rtc = RTC()
rtc.datetime((2026, 4, 30, 4, 12, 0, 0, 0)) # Y, M, D, weekday, h, m, s, subsec
print(rtc.datetime())
تعمل RTC أيضاً خلال السبات العميق، لذا يمكنك استخدامها كمصدر استيقاظ لـ machine.deepsleep().
المراقب (Watchdog)¶
تعيد machine.WDT تعيين اللوحة إذا تعلّق التطبيق. وبمجرد بدئها لا يمكن إيقافها أو إعادة تهيئتها — أطعمها دورياً داخل حلقتك الرئيسية:
from machine import WDT
wdt = WDT(timeout=5_000) # 5 second window
while True:
# ...do work...
wdt.feed()
معلومات الإقلاع ووقت التشغيل¶
نافذة محمّل الإقلاع عبر USB¶
عند كل تشغيل، تشغّل الكاميرا محمّل إقلاع قصير (بضع ثوانٍ) يتيح لـ OpenMV IDE تحديث البرنامج الثابت دون اضطرار المستخدم للدخول في وضع DFU. وبعد انتهاء النافذة، يسلّم محمّل الإقلاع المهمة إلى boot.py ثم main.py.
يمكن لبرنامج نصي قيد التشغيل إعادة الدخول إلى محمّل الإقلاع عند الطلب باستدعاء machine.bootloader()
import machine
machine.bootloader()
نظام الملفات وترتيب الإقلاع¶
يركّب برنامج RT1062 الثابت ما يصل إلى ثلاثة أنظمة ملفات عند الإقلاع:
ذاكرة flash الداخلية — مركّبة دائماً على
/flash. تحملmain.pyوREADME.txtافتراضياً؛ وتُنشأ عند أول إقلاع على الإطلاق.بطاقة microSD — إذا أُدرجت بطاقة فإنها تُركّب على
/sdcard.ROMFS — نظام ملفات للقراءة فقط مُسقَط في الذاكرة على
/romيُستخدم لشحن أصول بيانات كبيرة (مثل نماذج الذكاء الاصطناعي) تستفيد من الوصول دون نسخ. يركّبه MicroPython تلقائياً عند بدء التشغيل، قبل تشغيل أي شيفرة Python للمستخدم.
بعد التركيب، يُضبط دليل العمل على /sdcard عند وجود البطاقة، وإلا فعلى /flash. ثم يشغّل المفسّر البرامج النصية من ذلك الدليل:
يُنفَّذ
boot.pyعند كل إعادة تعيين ناعمة (إقلاع بارد، أوCtrl‑Dمن REPL، أو كلما عاد البرنامج النصي قيد التشغيل).يُنفَّذ
main.pyعند الإقلاع البارد فقط، مباشرة بعدboot.py. أما عمليات إعادة التعيين الناعمة اللاحقة فتعيد تشغيلboot.pyلكنها تنتقل مباشرة إلى REPL — ولإعادة تشغيلmain.pyعليك إعادة تعيين اللوحة بالكامل.
إن وضع ملف boot.py أو main.py على بطاقة SD يتجاوز النسخة الموجودة في ذاكرة flash دون المساس بها — إذ يُبحث عن كلا الملفين في دليل الإقلاع (/sdcard عند تركيب البطاقة، وإلا /flash).
يقتصر ملف main.py الافتراضي المشحون على لوحة حديثة الكتابة على وميض قناة الأزرق في مؤشر RGB LED للمستخدم كنبضة قلب (نبضتان قصيرتان، وفجوة قصيرة)، بحيث يمكنك معرفة أن البرنامج الثابت أقلع بنجاح دون أي مضيف متصل.
يُوسَّع sys.path ليشمل أنظمة الملفات الثلاثة جميعها وأدلتها الفرعية lib/، بحيث يمكن أن توجد الوحدات القابلة للاستيراد في /flash/lib أو /sdcard/lib أو /rom/lib.
لإجبار النظام على تجاهل بطاقة SD مُدرجة (مثلاً لتشغيل main.py الموجود في flash حتى مع وجود بطاقة)، أنشئ ملفاً فارغاً باسم SKIPSD في جذر /flash.
عند الاتصال عبر USB، يظهر نظام ملفات الإقلاع (/sdcard عند وجود بطاقة، وإلا /flash) أيضاً كقرص تخزين كتلي USB على المضيف، مما يتيح لك تحرير boot.py وmain.py وأي ملفات أخرى مباشرة. أخرِج القرص قبل إعادة تعيين الكاميرا ليُفرّغ المضيف عمليات الكتابة المخزنة مؤقتاً.
ملاحظة
لأن نظام التشغيل يعامل القرص كجهاز كتلي سلبي، فإن الملفات التي تُنشئها أو تعدّلها الشيفرة العاملة على OpenMV Cam لن تظهر حتى يعيد المضيف تركيب القرص. وإذا كتب نظام التشغيل وOpenMV Cam على نظام الملفات نفسه في الوقت نفسه، فسيفوز نظام التشغيل ويستبدل التغييرات التي أجرتها الكاميرا. استخدم بطاقة SD لأي بيانات يكتبها البرنامج النصي، وأعد التركيب قبل قراءة تلك الملفات من المضيف.
ملاحظة
قد تضيء قناة الأحمر في مؤشر RGB LED للمستخدم لوهلة أثناء قراءة المضيف من قرص تخزين USB الكتلي أو الكتابة إليه — وهذا مؤشر نشاط مدفوع بالبرنامج الثابت، وليس عطلاً.
أحجام التخزين¶
يأتي RT1062 مزوداً بـ:
/flash— نظام ملفات FAT بسعة 4 MB، قراءة/كتابة./rom— ROMFS مُسقَط في الذاكرة للقراءة فقط بسعة 8 MB، يُستخدم لشحن البرامج النصية ونماذج تعلّم الآلة التي تستفيد من الوصول عبر mmap دون نسخ./sdcard— الحجم الكامل لأي بطاقة microSD مُدرجة (عند وجودها)، قراءة/كتابة.
مؤشر العطل القاسي (Hard‑fault)¶
إذا كان مؤشر RGB LED للمستخدم يتنقل بسرعة عبر جميع الألوان — بسرعة كافية ليبدو وكأنه مؤشر LED أبيض متلألئ بدلاً من ألوان متمايزة — فهذا يعني أن البرنامج الثابت قد واجه عطلاً قاسياً لا يمكن التعافي منه. أعد كتابة البرنامج الثابت للتعافي؛ وإذا لم تساعد إعادة الكتابة، فقد تكون اللوحة تالفة فيزيائياً.
مكتبات البرمجيات¶
راجع فهرس المكتبة للاطلاع على القائمة الكاملة للوحدات — بما في ذلك الوحدات الفريدة لبناء RT1062.