Arduino Nano 33 BLE Sense

Peringatan

Papan ini tidak lagi didukung. Rilis firmware OpenMV terakhir untuk Arduino Nano 33 BLE Sense adalah 4.7.0. Tidak ada pembaruan firmware, perbaikan bug, atau fitur baru yang akan diterbitkan untuk target ini. Informasi di bawah ini dipertahankan untuk pengguna yang menjalankan versi 4.7.0 atau sebelumnya.

Arduino Nano 33 BLE Sense adalah papan berukuran 45 × 18 mm berformat Arduino‑Nano yang dibangun di sekitar Nordic Semiconductor nRF52840 — sebuah ARM Cortex‑M4 tunggal dengan FPU yang berjalan pada 64 MHz dengan 256 KB SRAM internal dan 1 MB flash internal. BLE berasal dari radio on‑die, dan papan ini dilengkapi dengan IMU 9 sumbu, barometer LPS22HB, sensor suhu/kelembapan HTS221/HS3003, sensor cahaya ambien/warna/proksimitas/gestur APDS9960, dan mikrofon PDM MP34DT05. Firmware OpenMV mengontrol semuanya dari MicroPython.

Arduino Nano 33 BLE Sense

Untuk datasheet lengkap, foto, dan dimensi, lihat halaman produk Arduino Nano 33 BLE Rev2.

Sorotan

  • Nordic nRF52840 Cortex‑M4 dengan FPU pada 64 MHz dengan 256 KB SRAM internal dan 1 MB flash internal.

  • Bluetooth LE 5.0 melalui radio on‑die dan Nordic SoftDevice s140.

  • IMU 9 sumbuLSM9DS1 pada Rev 1, BMI270 + BMM150 pada Rev 2. Driver beku imu mendeteksi keduanya saat boot.

  • LPS22HB barometer, HTS221 / HS3003 sensor suhu dan kelembapan, APDS9960 sensor cahaya ambien / warna / proksimitas / gestur, dan mikrofon PDM MP34DT05.

  • Konektor Micro USB untuk daya, pemrograman, dan REPL CDC.

  • 22 pin I/O pengguna pada header Nano standar — TX/RX, D2D13 (digital), A0A7 (analog).

Pinout

Arduino Nano 33 BLE Sense Pinout

Referensi pin

Nama pin

Referensi

Fungsi

TX

3.3 V

UART1 TX

RX

3.3 V

UART1 RX

D2

3.3 V

PWM

D3

3.3 V

PWM

D4

3.3 V

PWM

D5

3.3 V

PWM

D6

3.3 V

PWM

D7

3.3 V

PWM

D8

3.3 V

PWM

D9

3.3 V

PWM

D10

3.3 V

PWM

D11

3.3 V

PWM / SPI0 MOSI

D12

3.3 V

PWM / SPI0 MISO

D13

3.3 V

PWM / SPI0 SCK

A0

3.3 V

ADC / PWM

A1

3.3 V

ADC / PWM

A2

3.3 V

ADC / PWM

A3

3.3 V

ADC / PWM

A4 / I2C_SDA

3.3 V

ADC / PWM / I2C0 SDA

A5 / I2C_SCL

3.3 V

ADC / PWM / I2C0 SCL

A6

3.3 V

ADC / PWM

A7

3.3 V

ADC / PWM

RESET

3.3 V

tekan tombol RESET di papan atau tarik ke GND untuk mereset

LED_BUILTIN

LED pengguna oranye pada D13

LED_RED

Saluran merah LED RGB (aktif rendah)

LED_GREEN

Saluran hijau LED RGB (aktif rendah)

LED_BLUE

Saluran biru LED RGB (aktif rendah)

Peringatan

Pin I/O Nano 33 BLE Sense hanya 3.3 Vtidak toleran terhadap 5 V. Menerapkan 5 V ke pin tersebut akan merusak nRF52840.

Pin daya

  • VIN — input 4.5 – 21 V. Memberi daya pada papan melalui regulator on‑board. Juga diumpankan melalui dioda dari rel 5 V USB, sehingga USB dan VIN dapat hadir secara bersamaan tanpa saling mengemudi balik.

  • +5V — tidak terhubung secara default.

  • +3V3 — output regulator 3.3 V.

  • AREF — pin referensi analog. Tidak terhubung ke nRF52840 pada papan ini — ADC selalu direferensikan ke 3.3 V.

  • GND — ground bersama.

Nano 33 BLE Sense dapat diberi daya melalui salah satu jalur berikut:

  • Micro USB — menyuplai 5 V ke regulator on‑board.

  • Pin VIN — gunakan catu daya teregulasi 4.5 – 21 V.

Catatan

Jumper solder di bagian bawah papan berlabel VUSB menjembatani +5V ke rel 5 V USB. Tutup untuk membuat pin header +5V benar‑benar membawa 5 V.

Catatan

Jumper solder yang biasanya tertutup pada output regulator switching 4.5–21 V on‑board dapat dipotong untuk menonaktifkan regulator, sehingga papan dapat diberi daya langsung dari catu daya eksternal 3.3 V pada +3V3.

Pin pemulihan dan debug

  • RESET — baik pad yang terekspos maupun tombol RESET sesaat di bagian atas papan, terhubung ke jalur reset nRF52840. Tarik ke GND atau tekan tombol untuk mereset.

Nano 33 BLE Sense menggunakan double‑tap reset standar Arduino untuk masuk ke bootloader Arduino. Tekan tombol RESET dua kali dengan cepat — papan memasuki mode bootloader dan OpenMV IDE dapat mem-flash citra firmware baru.

Sinyal SWD nRF52840 terekspos pada pad berlapis di bagian belakang papan. Semua sinyal debug direferensikan ke 3.3 V.

Periferal on‑board

LED

Nano 33 BLE Sense memiliki LED RGB pengguna — dikendalikan melalui saluran LED_RED, LED_GREEN, dan LED_BLUE yang tertera di silkscreen — ditambah LED_BUILTIN oranye terpisah pada D13. Keempat LED dapat dikontrol melalui perangkat lunak menggunakan machine.LED

from machine import LED

LED("LED_RED").on()
LED("LED_GREEN").on()
LED("LED_BLUE").on()
LED("LED_BUILTIN").on()

LED daya hijau terpisah pada papan menyala setiap kali rel +3.3 V aktif dan tidak dapat dikontrol oleh pengguna.

Sensor kamera

Firmware OpenMV pada Nano 33 BLE Sense mendukung sensor CMOS paralel OmniVision OV7670. Papan ini tidak memiliki sensor citra on‑board — hubungkan modul OV7670 ke pin header yang tertera di silkscreen di bawah ini dan kendalikan melalui modul csi --- sensor kamera

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()

Catatan

OV7670 membutuhkan 14 pin. Firmware menghubungkannya sebagai berikut:

Sinyal sensor

Pin Nano 33 BLE Sense

D0

D10

D1

TX

D2

RX

D3

D2

D4

D3

D5

D5

D6

D6

D7

D4

HSYNC

A1

VSYNC

D8

PXCLK

A0

MXCLK

D9

POWER

A3

RESET

A2

SCL

A5 (I²C 0)

SDA

A4 (I²C 0)

Bus kontrol I²C OV7670 adalah I²C 0 eksternal yang sama yang terekspos pada A5/A4. Sensor berada di alamat 7‑bit 0x21 — perangkat pengguna pada bus tersebut harus menghindari alamat ini saat kamera terhubung.

IMU

IMU 9 sumbu diekspos melalui modul beku imu, yang secara otomatis mendeteksi apakah papan memiliki LSM9DS1 (Rev 1) atau BMI270 + BMM150 (Rev 2) dan menyajikan kelas imu.IMU yang terpadu. Sensor berada pada bus I²C 1 internal (P14 / P15):

import time
from machine import I2C, Pin
from imu import IMU

bus = I2C(1, scl=Pin("P15"), sda=Pin("P14"))
sensor = IMU(bus)

while True:
    print(sensor.accel())     # (x, y, z) in g
    print(sensor.gyro())      # (x, y, z) in deg/s
    print(sensor.magnet())    # (x, y, z) magnetometer
    time.sleep_ms(100)

Untuk akses langsung ke fitur seperti deteksi ketukan atau FIFO, impor driver beku yang sesuai (lsm9ds1, bmi270, atau bmm150) dan instansikan pada bus yang sama.

Sensor lingkungan

Barometer (LPS22HB) dan sensor suhu / kelembapan (HTS221 pada Rev 1, HS3003 pada Rev 2) berbagi bus I²C 1 internal yang sama dengan IMU:

import time
from machine import I2C, Pin
from lps22h import LPS22H
from hts221 import HTS221

bus = I2C(1, scl=Pin("P15"), sda=Pin("P14"))
lps = LPS22H(bus)
try:
    hts = HTS221(bus)
except OSError:
    from hs3003 import HS3003
    hts = HS3003(bus)

while True:
    print("pressure:    %.2f hPa" % lps.pressure())
    print("temperature: %.2f C"   % lps.temperature())
    print("humidity:    %.2f %%"  % hts.humidity())
    time.sleep_ms(500)

Cahaya / warna / proksimitas / gestur

Broadcom APDS9960 berada pada bus I²C 1 internal yang sama dan menyediakan cahaya ambien, warna RGB, proksimitas, dan penginderaan gestur:

import time
from machine import I2C, Pin
from apds9960 import uAPDS9960 as APDS9960

bus = I2C(1, scl=Pin("P15"), sda=Pin("P14"))
apds = APDS9960(bus)
apds.enableLightSensor()

while True:
    print("ambient light:", apds.readAmbientLight())
    time.sleep_ms(250)

Mikrofon

Mikrofon PDM MP34DT05 on‑board diambil melalui audio --- Modul Audio. Setiap buffer tiba sebagai PCM 16‑bit bertanda bytearray, siap diumpankan ke ulab/numpy untuk DSP:

import audio
from ulab import numpy as np

def loudness(pcmbuf):
    samples = np.array(np.frombuffer(pcmbuf, dtype=np.int16), dtype=np.float)
    rms = np.sqrt(np.mean(samples ** 2))
    if rms > 10000:
        print("Loud!", int(rms))

audio.init(channels=1, frequency=16000, gain_db=24)
audio.start_streaming(loudness)

while True:
    pass

Bluetooth

Radio Bluetooth LE 5.0 nRF52840 berjalan di atas Nordic SoftDevice s140 dan diekspos melalui modul warisan ubluepy — API modern bluetooth / aioble --- Async BLE tidak diaktifkan dalam build ini. Peran periferal (server GATT, iklan) dan sentral (pengamat GAP / pemindai + sambung) keduanya tersedia.

Iklankan sebagai periferal dengan satu layanan Environmental Sensing dan karakteristik suhu yang dapat dinotifikasi — callback event_handler terpicu saat sambung, putus, dan penulisan CCCD:

from ubluepy import Service, Characteristic, UUID, Peripheral, constants
from machine import LED

def event_handler(event_id, handle, data):
    if event_id == constants.EVT_GAP_CONNECTED:
        LED("LED_GREEN").on()
    elif event_id == constants.EVT_GAP_DISCONNECTED:
        LED("LED_GREEN").off()
        periph.advertise(device_name="Nano 33", services=[svc])

svc = Service(UUID("181A"))                          # Environmental Sensing
char = Characteristic(UUID("2A6E"),                  # Temperature
                      props=Characteristic.PROP_NOTIFY | Characteristic.PROP_READ,
                      attrs=Characteristic.ATTR_CCCD)
svc.addCharacteristic(char)

periph = Peripheral()
periph.addService(svc)
periph.setConnectionHandler(event_handler)
periph.advertise(device_name="Nano 33", services=[svc])

Pindai perangkat yang sedang mengiklan di dekatnya dalam peran sentral:

from ubluepy import Scanner

for entry in Scanner().scan(1_000):                  # 1 second window
    print(entry.addr(), entry.rssi(), "dBm")

Lihat referensi ubluepy untuk API lengkap — UUID, Service, Characteristic, Peripheral, Scanner, ScanEntry, dan namespace constants.

Referensi bus

GPIO

Gunakan machine.Pin untuk membaca atau menggerakkan salah satu pin yang tertera di silkscreen. Output adalah CMOS 3.3 V — 15 mA per pin, 25 mA total di seluruh GPIO.

from machine import Pin

out = Pin("D2", Pin.OUT)
out.on()
out.off()
out.value(1)

inp = Pin("D3", Pin.IN, Pin.PULL_UP)
print(inp.value())

Pin input mana pun juga dapat memicu interupsi pada transisi tepi:

def handler(pin):
    print("triggered:", pin)

Pin("D3", Pin.IN, Pin.PULL_UP).irq(
    handler, Pin.IRQ_FALLING | Pin.IRQ_RISING,
)

UART

Bus

TX

RX

UART1

TX

RX

Gunakan nama silkscreen TX/RX dengan machine.UART

from machine import UART

uart = UART(1, baudrate=115200)
uart.write("hello")
uart.read(5)

I²C

Bus

SDA

SCL

I2C0

I2C_SDA / A4

I2C_SCL / A5

I2C1

P14

P15

Kedua bus membutuhkan pin yang diteruskan secara eksplisit ke machine.I2C

from machine import I2C, Pin

bus0 = I2C(0, scl=Pin("I2C_SCL"), sda=Pin("I2C_SDA"), freq=400_000)
bus0.scan()

bus1 = I2C(1, scl=Pin("P15"), sda=Pin("P14"), freq=400_000)
bus1.scan()

Catatan

Bus 1 adalah bus sensor internal pada P14/P15 (tidak pada header pengguna) — melayani IMU, barometer, sensor lingkungan, dan APDS9960. Driver sensor beku menggunakannya langsung; kode pengguna dapat memindainya juga tetapi alamat sudah digunakan oleh sensor on‑board.

SPI

Bus

MOSI

MISO

SCK

CS

SPI0

D11

D12

D13

D10

Jalur CS tidak dikendalikan oleh periferal SPI — konfigurasikan D10 sebagai output dan toggle secara manual di sekitar transfer:

from machine import SPI, Pin

spi = SPI(0, baudrate=10_000_000)
cs = Pin("D10", Pin.OUT, value=1)   # CS is not driven by the SPI peripheral

cs.value(0)
spi.write(b"hello")
cs.value(1)

Catatan

D13 juga berfungsi sebagai LED_BUILTIN oranye — menjalankan SPI pada bus ini akan membuat LED berkedip sesuai dengan clock bus.

ADC

nRF52840 memiliki delapan saluran ADC 12‑bit (SAADC) yang terekspos pada A0–A7, semuanya direferensikan ke 3.3 Vread_u16 mengembalikan 0–65535 di rentang 0–3.3 V pada pin. Pin AREF papan tidak terhubung, sehingga referensi selalu 3.3 V:

from machine import ADC
import time

adc = ADC("A0")
while True:
    voltage = adc.read_u16() * 3.3 / 65535
    print(voltage)
    time.sleep_ms(100)

PWM

nRF52840 mengekspos empat periferal PWM (PWM0PWM3), masing‑masing menggerakkan empat saluran, sehingga total 16 slot PWM hardware. Tidak seperti port dengan fungsi tetap, periferal merutekan melalui matriks GPIOTE — GPIO mana pun dapat menjadi output PWM, sehingga tidak ada pemetaan pin-ke-slice. Biaya dari fleksibilitas tersebut adalah dua batasan yang tertanam dalam silikon:

  • Keempat saluran dalam satu modul berbagi satu periode/frekuensi.

  • Setiap saluran memiliki siklus kerja dan polaritasnya sendiri.

Secara konseptual, 16 slot terlihat seperti ini:

Modul

Ch 0

Ch 1

Ch 2

Ch 3

PWM0

duty

duty

duty

duty

PWM1

duty

duty

duty

duty

PWM2

duty

duty

duty

duty

PWM3

duty

duty

duty

duty

Setiap baris berjalan pada satu frekuensi; keempat sel dalam satu baris masing‑masing menggerakkan pin yang dipilih secara independen dengan siklus kerjanya sendiri. Baris yang berbeda dapat berjalan pada frekuensi yang sangat berbeda.

Gerakkan pin yang tertera di silkscreen mana pun (atau LED on‑board) melalui machine.PWM

from machine import Pin, PWM

pwm = PWM(Pin("D3"), freq=1_000, duty_u16=32768)

Peringatan

Alokasi otomatis mengonsumsi seluruh modul per panggilan. Saat Anda membuat PWM tanpa argumen device=/channel=, driver mengambil modul bebas pertama dan mengikat pin Anda ke saluran 0-nya saja. Tiga saluran lainnya dari modul tersebut tidak aktif dan hanya dapat dijangkau melalui device=/channel= eksplisit. Hal ini membatasi panggilan PWM(Pin(...)) tanpa bantuan hingga empat sebelum driver memunculkan ValueError: all PWM devices in use — meskipun secara teknis masih ada dua belas slot yang kosong.

Untuk menggunakan lebih dari empat PWM, atau untuk sengaja berbagi frekuensi di seluruh pin, teruskan device (0–3) dan channel (0–3):

# Two PWMs on the same module → forced to share frequency,
# but each gets its own duty cycle.
pwm_a = PWM(Pin("D3"), device=0, channel=0,
            freq=1_000, duty_u16=32768)
pwm_b = PWM(Pin("D5"), device=0, channel=1,
            freq=1_000, duty_u16=16384)

# A third PWM on a separate module, free to pick any frequency.
pwm_c = PWM(Pin("D6"), device=1, channel=0,
            freq=20_000, duty_u16=49152)

Siklus kerja menerima duty (0–100%), duty_u16 (0–65535), atau duty_ns. Tambahkan invert=1 untuk membalik polaritas output (berguna untuk LED RGB aktif rendah).

Catatan

Karena frekuensi adalah properti per‑modul, memanggil pwm.freq(new_freq) pada saluran mana pun dari sebuah modul akan menjalankan ulang nrfx_pwm_init untuk seluruh modul dan mengubah frekuensi yang terlihat oleh setiap saluran lain yang berbaginya.

Catatan

Frekuensi yang diizinkan berkisar dari sekitar 4 Hz hingga 5.3 MHz, diturunkan dari clock dasar 16 MHz dengan prescaler 1/2/4/8/16/32/64/128 dan counter periode 15‑bit. Driver memilih pembagi terdekat secara otomatis — freq() melaporkan nilai yang diminta, bukan nilai yang tepat dapat dicapai.

Bus bit‑banged perangkat lunak

machine.SoftI2C dan machine.SoftSPI bekerja pada GPIO mana pun jika Anda membutuhkan bus tambahan.

Sensor termal (off‑board)

Firmware menyertakan driver fir --- driver sensor termal (fir == far infrared) untuk thermal imager yang terhubung secara eksternal:

  • MLX90621 — array IR 16 × 4

  • MLX90640 — array IR 32 × 24

  • MLX90641 — array IR 16 × 12

  • AMG8833 — array IR 8 × 8

Hubungkan modul ke bus I²C papan dan baca bingkai dengan 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())

Driver fir hanya berkomunikasi dengan sensor melalui I²C 0 — hubungkan modul ke pad I2C_SCL / I2C_SDA (A5 / A4).

Pengaturan waktu

time

Modul time mencakup penundaan pemblokiran, tick monotonic, dan pengukuran waktu yang telah berlalu:

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)

Timer virtual

machine.Timer menjadwalkan callback periodik atau sekali tembak tanpa mengonsumsi slot timer hardware. Teruskan -1 sebagai id untuk menggunakan timer virtual (perangkat lunak):

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"))

Nilai periode dalam milidetik. Panggil deinit() untuk menghentikan dan melepaskan slot.

Jam real‑time

machine.RTC menjaga waktu jam dinding di seluruh reset. RTC nRF52840 terikat ke osilator on‑chip dan tidak bertahan setelah kehilangan daya penuh — atur waktu pada setiap cold boot jika hal itu penting untuk aplikasi Anda:

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())

Watchdog

machine.WDT mereset papan jika aplikasi hang. Setelah dimulai, tidak dapat dihentikan atau dikonfigurasi ulang — umpankan secara berkala di dalam loop utama Anda:

from machine import WDT

wdt = WDT(timeout=5_000)   # 5 second window
while True:
    # ...do work...
    wdt.feed()

Info boot dan runtime

Pembaruan firmware

Nano 33 BLE Sense menggunakan double‑tap reset standar Arduino untuk masuk ke bootloader Arduino. Tekan tombol RESET dua kali dengan cepat — papan memasuki mode bootloader dan OpenMV IDE dapat mem-flash citra firmware baru.

Skrip yang berjalan dapat masuk kembali ke bootloader sesuai permintaan dengan memanggil machine.bootloader()

import machine

machine.bootloader()

Filesystem dan urutan boot

Firmware Nano 33 BLE Sense memasang satu filesystem saat boot:

  • Flash internal — selalu dipasang di /flash dan digunakan sebagai direktori kerja. Berisi main.py dan README.txt secara default; dibuat pada boot pertama.

Setelah pemasangan, interpreter kemudian menjalankan skrip dari /flash:

  • boot.py dieksekusi pada setiap soft reset.

  • main.py dieksekusi hanya pada cold boot, segera setelah boot.py.

main.py default yang dikirimkan pada papan yang baru di-flash hanya membuat saluran biru LED RGB pengguna berkedip sebagai heartbeat (dua pulsa pendek, jeda pendek), sehingga Anda dapat mengetahui firmware telah boot dengan bersih tanpa host yang terhubung.

/flash tidak diekspos sebagai drive penyimpanan massal USB pada papan ini.

Ukuran penyimpanan

Nano 33 BLE Sense dikirimkan dengan:

  • /flash — filesystem FAT 64 KB, baca/tulis.

Build Nano 33 BLE Sense tidak menyertakan ROMFS; kirimkan modul Python di /flash langsung.

Pustaka perangkat lunak

Lihat indeks pustaka untuk daftar lengkap modul — termasuk modul mana yang unik untuk build Nano 33 BLE Sense.