pimoroni-pico/micropython/examples/badger2040w/lib/badger2040w.py

182 wiersze
4.8 KiB
Python

import machine
import micropython
from picographics import PicoGraphics, DISPLAY_INKY_PACK
import network
from network_manager import NetworkManager
import WIFI_CONFIG
import uasyncio
import time
import gc
import wakeup
BUTTON_DOWN = 11
BUTTON_A = 12
BUTTON_B = 13
BUTTON_C = 14
BUTTON_UP = 15
BUTTON_USER = None # User button not available on W
BUTTON_MASK = 0b11111 << 11
SYSTEM_VERY_SLOW = 0
SYSTEM_SLOW = 1
SYSTEM_NORMAL = 2
SYSTEM_FAST = 3
SYSTEM_TURBO = 4
UPDATE_NORMAL = 0
UPDATE_MEDIUM = 1
UPDATE_FAST = 2
UPDATE_TURBO = 3
LED = 22
ENABLE_3V3 = 10
BUSY = 26
WIDTH = 296
HEIGHT = 128
SYSTEM_FREQS = [
4000000,
12000000,
48000000,
133000000,
250000000
]
BUTTONS = {
BUTTON_DOWN: machine.Pin(BUTTON_DOWN, machine.Pin.IN, machine.Pin.PULL_DOWN),
BUTTON_A: machine.Pin(BUTTON_A, machine.Pin.IN, machine.Pin.PULL_DOWN),
BUTTON_B: machine.Pin(BUTTON_B, machine.Pin.IN, machine.Pin.PULL_DOWN),
BUTTON_C: machine.Pin(BUTTON_C, machine.Pin.IN, machine.Pin.PULL_DOWN),
BUTTON_UP: machine.Pin(BUTTON_UP, machine.Pin.IN, machine.Pin.PULL_DOWN),
}
WAKEUP_MASK = 0
def woken_by_button():
return wakeup.get_gpio_state() & BUTTON_MASK > 0
def pressed_to_wake(button):
return wakeup.get_gpio_state() & (1 << button) > 0
def reset_pressed_to_wake():
wakeup.reset_gpio_state()
def pressed_to_wake_get_once(button):
global WAKEUP_MASK
result = (wakeup.get_gpio_state() & ~WAKEUP_MASK & (1 << button)) > 0
WAKEUP_MASK |= (1 << button)
return result
def system_speed(speed):
try:
machine.freq(SYSTEM_FREQS[speed])
except IndexError:
pass
class Badger2040W():
def __init__(self):
self.display = PicoGraphics(DISPLAY_INKY_PACK)
self._led = machine.PWM(machine.Pin(LED))
self._led.freq(1000)
self._led.duty_u16(0)
self._update_speed = 0
def __getattr__(self, item):
# Glue to redirect calls to PicoGraphics
return getattr(self.display, item)
def update(self):
t_start = time.ticks_ms()
self.display.update()
t_elapsed = time.ticks_ms() - t_start
delay_ms = [4700, 2600, 900, 250][self._update_speed]
if t_elapsed < delay_ms:
time.sleep((delay_ms - t_elapsed) / 1000)
def set_update_speed(self, speed):
self.display.set_update_speed(speed)
self._update_speed = speed
def led(self, brightness):
brightness = max(0, min(255, brightness))
self._led.duty_u16(int(brightness * 256))
def invert(self, invert):
raise RuntimeError("Display invert not supported in PicoGraphics.")
def thickness(self, thickness):
raise RuntimeError("Thickness not supported in PicoGraphics.")
def halt(self):
time.sleep(0.05)
enable = machine.Pin(ENABLE_3V3, machine.Pin.OUT)
enable.off()
while not self.pressed_any():
pass
def pressed(self, button):
return BUTTONS[button].value() == 1 or pressed_to_wake_get_once(button)
def pressed_any(self):
for button in BUTTONS.values():
if button.value():
return True
return False
@micropython.native
def icon(self, data, index, data_w, icon_size, x, y):
s_x = (index * icon_size) % data_w
s_y = int((index * icon_size) / data_w)
for o_y in range(icon_size):
for o_x in range(icon_size):
o = ((o_y + s_y) * data_w) + (o_x + s_x)
bm = 0b10000000 >> (o & 0b111)
if data[o >> 3] & bm:
self.display.pixel(x + o_x, y + o_y)
def image(self, data, w, h, x, y):
for oy in range(h):
row = data[oy]
for ox in range(w):
if row & 0b1 == 0:
self.display.pixel(x + ox, y + oy)
row >>= 1
def status_handler(self, mode, status, ip):
print(mode, status, ip)
self.display.set_pen(15)
self.display.clear()
self.display.set_pen(0)
if status:
self.display.text("Connected!", 10, 10, 300, 0.5)
self.display.text(ip, 10, 30, 300, 0.5)
else:
self.display.text("Connecting...", 10, 10, 300, 0.5)
self.update()
def isconnected(self):
return network.WLAN(network.STA_IF).isconnected()
def ip_address(self):
return network.WLAN(network.STA_IF).ifconfig()[0]
def connect(self):
if WIFI_CONFIG.COUNTRY == "":
raise RuntimeError("You must populate WIFI_CONFIG.py for networking.")
self.display.set_update_speed(2)
network_manager = NetworkManager(WIFI_CONFIG.COUNTRY, status_handler=self.status_handler)
uasyncio.get_event_loop().run_until_complete(network_manager.client(WIFI_CONFIG.SSID, WIFI_CONFIG.PSK))
gc.collect()