diff --git a/.flake8 b/.flake8 new file mode 100644 index 0000000..9f41f6e --- /dev/null +++ b/.flake8 @@ -0,0 +1,213 @@ +[flake8] +ignore = + E501, + F405, + F403 +builtins = + Buffer, + Voice, + pen, + tick, + init, + reset, + play, + clip, + blend, + target, + camera, + spritesheet, + clear, + pixel, + line, + hline, + vline, + rect, + frect, + circle, + fcircle, + ellipse, + fellipse, + poly, + fpoly, + blit, + sprite, + text, + text_width, + rgb, + hsv, + intersects, + intersection, + contains, + pressed, + button, + battery, + led, + backlight, + UP, + DOWN, + LEFT, + RIGHT, + A, + B, + X, + Y, + COPY, + ALPHA, + MASK, + CHERRY, + APPLE, + BANANA, + ORANGE, + AUBERGINE, + CARROT, + POTATO, + LEAF, + PARSNIP, + MEAT, + BEAN, + RADISH, + STRAWBERRY, + PUMPKIN, + CUCUMBER, + SALT1, + SWORD1, + SWORD2, + SWORD3, + AXE1, + DAGGER, + MACE1, + BOW, + ARROW1, + ARROW2, + ARROW3, + TRIDENT1, + SPEAR, + TRIDENT2, + MACHINEGUN, + PISTOL, + SHOTGUN, + GEM1, + GEM2, + GEM3, + GEM4, + GEM5, + GEM6, + AMULET, + FOLDER, + COIN1, + IDOL1, + IDOL2, + IDOL3, + IDOL4, + SWEETCORN, + BROCCOLI, + BISCUIT, + BERRIES, + SCEPTRE, + FIRE, + LASERGUN1, + LASERGUN2, + HELMET1, + HELMET2, + HELMET3, + HELMET4, + __1, + __2, + __3, + __4, + HEART1, + SLIME, + COIN2, + SWORD4, + SWORD5, + __5, + DYNAMITE, + MEDPACK, + GOGGLES, + HELMET5, + BOMB, + OILCAN, + SHIRT1, + SHIRT2, + SPEECH, + DREAM, + HEART2, + HEART3, + HEART4, + __6, + TORCH, + ICE, + __7, + __8, + __9, + __10, + UPARROW, + RING1, + RING2, + RING3, + RING4, + __11, + TOKEN, + VIAL1, + VIAL2, + RING5, + RING6, + BLOCK1, + BLOCK2, + BLOCK3, + BLOCK4, + BLOCK5, + BLOCK6, + BLOCK7, + BLOCK8, + BLOCK9, + SHIELD1, + SACK, + BUTTON, + VIAL3, + VIAL4, + TOOTH, + BONE, + HALFBLOCK1, + HALFBLOCK2, + HALFBLOCK3, + HALFBLOCK4, + HALFBLOCK5, + HALFBLOCK6, + HALFBLOCK7, + HALFBLOCK8, + HALFBLOCK9, + SHIELD2, + SHIELD3, + FLOWER1, + FLOWER2, + FLOWER3, + FLOWER4, + STAFF1, + STAFF2, + STAFF3, + STICK1, + SPIKEBALL, + MACE2, + AXE2, + __12, + SWORD6, + SWORD7, + SWORD8, + CROWN1, + GOLD, + GEM7, + GEM8, + GEM9, + AXE3, + MUSHROOM, + SALT2, + STICK2, + VIAL5, + VIAL6, + DOT, + HELMET6, + SWORD9, + SWORD10, + SWORD11, + CROWN2, \ No newline at end of file diff --git a/.github/workflows/python.yml b/.github/workflows/python.yml index 0e15cc6..dc5156c 100644 --- a/.github/workflows/python.yml +++ b/.github/workflows/python.yml @@ -32,5 +32,5 @@ jobs: - name: Lint shell: bash run: | - python3 -m flake8 --ignore E501,F405,F821,F403 micropython/examples - python3 -m flake8 --ignore E501,F405,F821,F403,F401 micropython/modules_py \ No newline at end of file + python3 -m flake8 micropython/examples + python3 -m flake8 --ignore E501,F405,F403,F401 micropython/modules_py \ No newline at end of file diff --git a/examples/audio/audio.cpp b/examples/audio/audio.cpp index 81e3fc6..a7e819e 100644 --- a/examples/audio/audio.cpp +++ b/examples/audio/audio.cpp @@ -151,7 +151,7 @@ void draw_dial(std::string name, int32_t x, int32_t y) { } // draw the world -void draw() { +void draw(uint32_t tick) { // draw top row of dials pen(10, 12, 4); frect(0, 60, 240, 60); diff --git a/examples/colour/colour.cpp b/examples/colour/colour.cpp index eebfea3..7f58c1e 100644 --- a/examples/colour/colour.cpp +++ b/examples/colour/colour.cpp @@ -108,7 +108,7 @@ void draw_slider(slider_t &slider, int32_t x, int32_t y) { frect(x + 2, y + h - sh - 2, w - 4, sh); } -void draw() { +void draw(uint32_t tick) { // clear the screen pen(1, 1, 1); clear(); diff --git a/examples/music/music.cpp b/examples/music/music.cpp index 890e2e4..376d929 100644 --- a/examples/music/music.cpp +++ b/examples/music/music.cpp @@ -133,7 +133,7 @@ void update(uint32_t tick) { } // draw the world -void draw() { +void draw(uint32_t tick) { // reset the camera and clear the framebuffer camera(); pen(1, 2, 3); diff --git a/examples/shapes/shapes.cpp b/examples/shapes/shapes.cpp index 308ffb2..163e5f5 100644 --- a/examples/shapes/shapes.cpp +++ b/examples/shapes/shapes.cpp @@ -61,7 +61,7 @@ void label(std::string s) { text(s + ":", 2, 15); } -void draw() { +void draw(uint32_t tick) { pen(0, 0, 0); clear(); @@ -147,4 +147,14 @@ void draw() { frect(0, 0, 120, 11); pen(0, 0, 0); text("Shapes Test", 2, 2); + + pen(0, 0, 0, 8); + frect(0, 60, 120, 60); + + pen(15, 15, 15); + text("fps: " + str(stats.fps), 10, 70); + text("draw us: " + str(stats.draw_us), 10, 80); + text("update us: " + str(stats.update_us), 10, 90); + text("tick us: " + str(stats.tick_us), 10, 100); + text("idle: " + str(stats.idle) + "%", 10, 110); } \ No newline at end of file diff --git a/examples/snake/snake.cpp b/examples/snake/snake.cpp index 9fae71c..5d403b0 100644 --- a/examples/snake/snake.cpp +++ b/examples/snake/snake.cpp @@ -124,7 +124,7 @@ void update(uint32_t tick) { } // draw the world -void draw() { +void draw(uint32_t tick) { // clear the screen in noxious 3310 backlight green and draw everything in // a faint blended black to get that cheap 90s LCD feel pen(10, 12, 0); diff --git a/examples/sprites/sprites.cpp b/examples/sprites/sprites.cpp index f4b04ba..1cbe10f 100644 --- a/examples/sprites/sprites.cpp +++ b/examples/sprites/sprites.cpp @@ -54,7 +54,7 @@ float deg_to_rad(float d) { } // draw the world -void draw() { +void draw(uint32_t tick) { // clear the background pen(2, 3, 4); clear(); diff --git a/examples/text/text.cpp b/examples/text/text.cpp index b81b343..909b971 100644 --- a/examples/text/text.cpp +++ b/examples/text/text.cpp @@ -11,7 +11,7 @@ void update(uint32_t tick) { wrap_width = (fsin(time() / 1000.0f) * 40.0f) + 76; } -void draw() { +void draw(uint32_t tick) { pen(0, 0, 0); clear(); diff --git a/libraries/hardware.cpp b/libraries/hardware.cpp index d0edeaf..f97028f 100644 --- a/libraries/hardware.cpp +++ b/libraries/hardware.cpp @@ -300,7 +300,6 @@ namespace picosystem { #ifndef NO_OVERCLOCK // overclock the rp2040 to 250mhz set_sys_clock_khz(250000, true); - #endif // configure control io pins @@ -366,7 +365,7 @@ namespace picosystem { _screen_command(VRHS, 1, "\x12"); _screen_command(VDVS, 1, "\x20"); _screen_command(PWRCTRL1, 2, "\xA4\xA1"); - _screen_command(FRCTRL2, 1, "\x0f"); + _screen_command(FRCTRL2, 1, "\x15"); _screen_command(GMCTRP1, 14, "\xD0\x04\x0D\x11\x13\x2B\x3F\x54\x4C\x18\x0D\x0B\x1F\x23"); _screen_command(GMCTRN1, 14, "\xD0\x04\x0C\x11\x13\x2C\x3F\x44\x51\x2F\x1F\x1F\x20\x23"); _screen_command(INVON); @@ -399,7 +398,7 @@ namespace picosystem { // initialise dma channel for transmitting pixel data to screen // via the screen updating pio program - dma_channel = 0; //dma_claim_unused_channel(true); // avoid MicroPython soft-reset timebomb + dma_channel = 0; dma_channel_config config = dma_channel_get_default_config(dma_channel); channel_config_set_bswap(&config, true); channel_config_set_dreq(&config, pio_get_dreq(screen_pio, screen_sm, true)); diff --git a/libraries/picosystem.cpp b/libraries/picosystem.cpp index 74b46e6..01d09c1 100644 --- a/libraries/picosystem.cpp +++ b/libraries/picosystem.cpp @@ -8,7 +8,7 @@ namespace picosystem { - uint32_t _debug; + stat_t stats; color_t _pen; uint8_t _a = 15; @@ -99,45 +99,59 @@ int main() { // setup for world state etc init(); - uint32_t update_rate_ms = 10; - uint32_t pending_update_ms = 0; - uint32_t last_ms = time(); - uint32_t tick = 0; + uint32_t last_frame_ms = 0; _io = _gpio_get(); while(true) { - uint32_t ms = time(); - - // work out how many milliseconds of updates we're waiting - // to process and then call the users update() function as - // many times as needed to catch up - pending_update_ms += (ms - last_ms); - while(pending_update_ms >= update_rate_ms) { - _lio = _io; - _io = _gpio_get(); - - update(tick++); - pending_update_ms -= update_rate_ms; - } + uint32_t start_tick_us = time_us(); + + // store previous io state and get new io state + _lio = _io; + _io = _gpio_get(); + + // call users update() function + uint32_t start_update_us = time_us(); + update(tick++); + stats.update_us = time_us() - start_update_us; - // if current flipping the framebuffer in the background - // then wait until that is complete before allow the user - // to render + // if we're currently transferring the the framebuffer to the screen then + // wait until that is complete before allowing the user to do their drawing + uint32_t wait_us = 0; + uint32_t start_wait_flip_us = time_us(); while(_is_flipping()) {} + wait_us += time_us() - start_wait_flip_us; // call user render function to draw world - draw(); + uint32_t start_draw_us = time_us(); + draw(tick); + stats.draw_us = time_us() - start_draw_us; // wait for the screen to vsync before triggering flip // to ensure no tearing + uint32_t start_wait_vsync_us = time_us(); _wait_vsync(); + wait_us += time_us() - start_wait_vsync_us; // flip the framebuffer to the screen _flip(); - last_ms = ms; + tick++; + + stats.tick_us = time_us() - start_tick_us; + + // calculate fps and round to nearest value (instead of truncating/floor) + stats.fps = (1000000 - 1) / stats.tick_us + 1; + + if(stats.fps > 40) { + // if fps is high enough then we definitely didn't miss vsync + stats.idle = (wait_us * 100) / stats.tick_us; + }else{ + // if we missed vsync then we overran the frame time and hence had + // no idle time + stats.idle = 0; + } } } diff --git a/libraries/picosystem.hpp b/libraries/picosystem.hpp index 84bb804..a4b2378 100644 --- a/libraries/picosystem.hpp +++ b/libraries/picosystem.hpp @@ -11,8 +11,8 @@ #include "pico/stdlib.h" void init(); -void update(uint32_t time_ms); -void draw(); +void update(uint32_t tick); +void draw(uint32_t tick); namespace picosystem { @@ -20,6 +20,16 @@ namespace picosystem { typedef uint16_t color_t; + struct stat_t { + uint32_t fps; // current frames per second + uint32_t idle; // cpu idle time percentage + uint32_t tick_us; // last full tick time in microseconds + uint32_t update_us; // last update() call time in microseconds + uint32_t draw_us; // last draw() call time in microseconds + }; + + extern stat_t stats; + struct buffer_t { int32_t w, h; color_t *data; diff --git a/micropython/examples/picosystem/colour.py b/micropython/examples/picosystem/colour.py index 28f855e..07c9b88 100644 --- a/micropython/examples/picosystem/colour.py +++ b/micropython/examples/picosystem/colour.py @@ -1,8 +1,6 @@ import math import time -from picosystem import * - blip = Voice(10, 0, 80, 0, 0, 0, 0, 100) picker = Buffer(68, 68) @@ -107,7 +105,7 @@ def draw_slider(slider, x, y): frect(x + 2, y + h - sh - 2, w - 4, sh) -def draw(): +def draw(tick): # clear the screen pen(1, 1, 1) clear() diff --git a/micropython/examples/picosystem/launcher.py b/micropython/examples/picosystem/launcher.py index e5f49e1..2a0d9cd 100644 --- a/micropython/examples/picosystem/launcher.py +++ b/micropython/examples/picosystem/launcher.py @@ -3,7 +3,18 @@ import time import gc -from picosystem import * + +last_note = 0 +note_duration = 0 +note_idx = 0 +intro_melody = True + + +notes = [ + (None, 100), ("G6", 10), ("E6", 30), ("A6", 10), ("G6", 30), (None, 100), ("B7", 1), ("C7", 1) +] +intro = Voice() +intro.envelope(attack=50, decay=10, sustain=70, release=2000) files = [file for file in os.listdir() if file.endswith(".py") and file not in ("main.py", "launcher.py")] @@ -32,9 +43,24 @@ def get_item_angle(index): return 360.0 / filecount * index +def update_melody(tick): + global last_note, note_idx, note_duration, intro_melody + if tick - last_note > note_duration: + last_note = tick + note, note_duration = notes[note_idx] + if note: + intro.play(note, note_duration * 4) + note_idx += 1 + if note_idx >= len(notes): + intro_melody = False + + def update(tick): global selected, target_angle, running + if intro_melody: + update_melody(tick) + if pressed(LEFT): selected -= 1 blip.play(1600, 30, 100) @@ -51,13 +77,20 @@ def update(tick): target_angle = -get_item_angle(selected) -def draw(): - global current_angle +def draw(tick): + global current_angle, intro_melody # clear the background pen(1, 1, 1) clear() + if intro_melody: + pen(15, 15, 15) + label = "".join(["", "Pi", "co", "Sys", "tem"][0:min(note_idx, 5)]) + label_width = text_width(label) + text(label, int(60 - (label_width / 2)), 60) + return + pen(10, 10, 10) text("Run a file:", 10, 10) @@ -93,11 +126,13 @@ def draw(): while running: tick() - time.sleep(1.0 / 500) __launch_file__ = files[selected] -del get_item_angle, selected, draw, update, blip, ding, current_angle, target_angle, running +for k in locals().keys(): + if k not in ("gc", "__launch_file__"): + del locals()[k] + gc.collect() reset() __import__(__launch_file__) diff --git a/micropython/examples/picosystem/shapes.py b/micropython/examples/picosystem/shapes.py index 26651db..df8f3cb 100644 --- a/micropython/examples/picosystem/shapes.py +++ b/micropython/examples/picosystem/shapes.py @@ -1,7 +1,7 @@ -from picosystem import * from math import sin, cos from random import randrange + view = -1 shapes = [] @@ -41,12 +41,12 @@ def move(): s.r += 3 -def update(ticks): +def update(tick): global view move() - if not (ticks % 250): + if not (tick % 250): reset() view += 1 @@ -63,7 +63,7 @@ def label(s): text(s + ":", 2, 15) -def draw(): +def draw(tick): global view global shapes diff --git a/micropython/examples/picosystem/sprites.py b/micropython/examples/picosystem/sprites.py index 05d4e3c..b65c34e 100644 --- a/micropython/examples/picosystem/sprites.py +++ b/micropython/examples/picosystem/sprites.py @@ -1,14 +1,12 @@ import math import time -from picosystem import * - weapons = [ (TRIDENT1, "Trident"), (SWORD1, "Sword"), (LASERGUN1, "Laser Gun"), - (MACE, "Mace"), + (MACE1, "Mace"), (DAGGER, "Dagger"), (SPEAR, "Spear"), (BOW, "Bow"), @@ -45,7 +43,7 @@ def update(tick): # draw the world -def draw(): +def draw(tick): global current_angle # clear the background diff --git a/micropython/examples/picosystem/spritesheets.py b/micropython/examples/picosystem/spritesheets.py index 9fdb1f8..87d3309 100644 --- a/micropython/examples/picosystem/spritesheets.py +++ b/micropython/examples/picosystem/spritesheets.py @@ -1,5 +1,3 @@ -from picosystem import * - spritesheets = [ "s4m_ur4i-dingbads.16bpp", "s4m_ur4i-pirate-characters.16bpp", @@ -16,17 +14,17 @@ current_sheet = 0 -def update(ticks): +def update(tick): global last_update, current_sheet - if ticks - last_update > 100: - last_update = ticks + if tick - last_update > 100: + last_update = tick open(spritesheets[current_sheet], "rb").readinto(buffer) current_sheet += 1 if current_sheet >= len(spritesheets): current_sheet = 0 -def draw(): +def draw(tick): pen(0, 0, 0) clear() for x in range(int(120 / 8)): diff --git a/micropython/examples/picosystem/test.py b/micropython/examples/picosystem/test.py index d942abd..64514fb 100644 --- a/micropython/examples/picosystem/test.py +++ b/micropython/examples/picosystem/test.py @@ -1,10 +1,8 @@ -from picosystem import * - fh = 0 col = 0 -def update(ticks): +def update(tick): global h global col print("UP: ", button(UP), end=", ") @@ -34,7 +32,7 @@ def update(ticks): h -= 1.0 -def draw(): +def draw(tick): pen(col) frect(10, 10, 100, 100) pen(15, 15, 15) diff --git a/micropython/modules/picosystem/micropython.cmake b/micropython/modules/picosystem/micropython.cmake index b467e76..03db55d 100644 --- a/micropython/modules/picosystem/micropython.cmake +++ b/micropython/modules/picosystem/micropython.cmake @@ -11,6 +11,7 @@ target_sources(usermod_${MOD_NAME} INTERFACE ${CMAKE_CURRENT_LIST_DIR}/primitives.cpp ${CMAKE_CURRENT_LIST_DIR}/utility.cpp ${CMAKE_CURRENT_LIST_DIR}/hardware.cpp + ${CMAKE_CURRENT_LIST_DIR}/stats.cpp ${CMAKE_CURRENT_LIST_DIR}/../../../libraries/picosystem.cpp ${CMAKE_CURRENT_LIST_DIR}/../../../libraries/audio.cpp ${CMAKE_CURRENT_LIST_DIR}/../../../libraries/blend.cpp diff --git a/micropython/modules/picosystem/picosystem.c b/micropython/modules/picosystem/picosystem.c index d1ed67e..bb02179 100755 --- a/micropython/modules/picosystem/picosystem.c +++ b/micropython/modules/picosystem/picosystem.c @@ -62,10 +62,17 @@ const mp_obj_type_t PicosystemVoice_type = { /***** Module Functions *****/ + +// picosystem.cpp + MP_DEFINE_CONST_FUN_OBJ_0(picosystem_init_obj, picosystem_init); MP_DEFINE_CONST_FUN_OBJ_0(picosystem_reset_obj, picosystem_reset); MP_DEFINE_CONST_FUN_OBJ_0(picosystem_tick_obj, picosystem_tick); +// stats.cpp + +MP_DEFINE_CONST_FUN_OBJ_0(picosystem_stats_obj, picosystem_stats); + // voice.cpp MP_DEFINE_CONST_FUN_OBJ_KW(picosystem_play_obj, 2, picosystem_audio_play); diff --git a/micropython/modules/picosystem/picosystem.cpp b/micropython/modules/picosystem/picosystem.cpp index d2249c7..e65982b 100644 --- a/micropython/modules/picosystem/picosystem.cpp +++ b/micropython/modules/picosystem/picosystem.cpp @@ -130,55 +130,69 @@ mp_obj_t picosystem_init() { } mp_obj_t picosystem_tick() { + uint32_t start_tick_us = time_us(); if(update_callback_obj == mp_const_none) { update_callback_obj = pimoroni_mp_load_global(qstr_from_str("update")); if(update_callback_obj == mp_const_none) { //TODO switch out this URL for the final one - mp_raise_msg(&mp_type_NameError, "a function named 'update(ticks)' is not defined. Check out https://github.com/pimoroni/picosystem-micropython/README.md for instructions"); + mp_raise_msg(&mp_type_NameError, "a function named 'update(ticks)' is not defined. Check out https://github.com/pimoroni/picosystem/blob/main/micropython/README.md for instructions"); } } + if(draw_callback_obj == mp_const_none) { draw_callback_obj = mp_load_global(qstr_from_str("draw")); if(draw_callback_obj == mp_const_none) { //TODO switch out this URL for the final one - mp_raise_msg(&mp_type_NameError, "a function named 'draw()' is not defined. Check out https://github.com/pimoroni/picosystem-micropython/README.md for instructions"); + mp_raise_msg(&mp_type_NameError, "a function named 'draw()' is not defined. Check out https://github.com/pimoroni/picosystem/blob/main/micropython/README.md for instructions"); } } - //while(true) { - uint32_t ms = time(); - - // work out how many milliseconds of updates we're waiting - // to process and then call the users update() function as - // many times as needed to catch up - pending_update_ms += (ms - last_ms); - while(pending_update_ms >= update_rate_ms) { - _lio = _io; - _io = _gpio_get(); + // store previous io state and get new io state + _lio = _io; + _io = _gpio_get(); - mp_call_function_1(update_callback_obj, mp_obj_new_int(tick++)); - pending_update_ms -= update_rate_ms; - } + // call users update() function + uint32_t start_update_us = time_us(); + mp_call_function_1(update_callback_obj, mp_obj_new_int(tick++)); + stats.update_us = time_us() - start_update_us; - // if current flipping the framebuffer in the background - // then wait until that is complete before allow the user - // to render + // if we're currently transferring the the framebuffer to the screen then + // wait until that is complete before allowing the user to do their drawing + uint32_t wait_us = 0; + uint32_t start_wait_flip_us = time_us(); while(_is_flipping()) {} + wait_us += time_us() - start_wait_flip_us; // call user render function to draw world - mp_call_function_0(draw_callback_obj); + uint32_t start_draw_us = time_us(); + mp_call_function_1(draw_callback_obj, mp_obj_new_int(tick)); + stats.draw_us = time_us() - start_draw_us; // wait for the screen to vsync before triggering flip // to ensure no tearing + uint32_t start_wait_vsync_us = time_us(); _wait_vsync(); + wait_us += time_us() - start_wait_vsync_us; // flip the framebuffer to the screen _flip(); - last_ms = ms; - //} + tick++; + stats.tick_us = time_us() - start_tick_us; + + // calculate fps and round to nearest value (instead of truncating/floor) + stats.fps = (1000000 - 1) / stats.tick_us + 1; + + if(stats.fps > 40) { + // if fps is high enough then we definitely didn't miss vsync + stats.idle = (wait_us * 100) / stats.tick_us; + }else{ + // if we missed vsync then we overran the frame time and hence had + // no idle time + stats.idle = 0; + } return mp_const_none; } diff --git a/micropython/modules/picosystem/picosystem.h b/micropython/modules/picosystem/picosystem.h index 0c2047c..f5bf49d 100644 --- a/micropython/modules/picosystem/picosystem.h +++ b/micropython/modules/picosystem/picosystem.h @@ -57,6 +57,9 @@ extern mp_obj_t picosystem_init(); extern mp_obj_t picosystem_tick(); extern mp_obj_t picosystem_reset(); +// stats.cpp +extern mp_obj_t picosystem_stats(); + // buffer.cpp extern void PicosystemBuffer_print(const mp_print_t *print, mp_obj_t self_in, mp_print_kind_t kind); extern mp_obj_t PicosystemBuffer_make_new(const mp_obj_type_t *type, size_t n_args, size_t n_kw, const mp_obj_t *all_args); diff --git a/micropython/modules/picosystem/stats.cpp b/micropython/modules/picosystem/stats.cpp new file mode 100644 index 0000000..97e3e45 --- /dev/null +++ b/micropython/modules/picosystem/stats.cpp @@ -0,0 +1,26 @@ +#include "hardware/spi.h" +#include "hardware/sync.h" +#include "pico/binary_info.h" + +#include "libraries/picosystem.hpp" + +#define MP_OBJ_TO_PTR2(o, t) ((t *)(uintptr_t)(o)) + +using namespace picosystem; + +extern "C" { +#include "picosystem.h" +#include "math.h" +#include "cstring" + +mp_obj_t picosystem_stats() { + mp_obj_t tuple[5]; + tuple[0] = mp_obj_new_int(stats.fps); + tuple[1] = mp_obj_new_int(stats.idle); + tuple[2] = mp_obj_new_int(stats.tick_us); + tuple[3] = mp_obj_new_int(stats.update_us); + tuple[4] = mp_obj_new_int(stats.draw_us); + return mp_obj_new_tuple(5, tuple); +} + +} \ No newline at end of file diff --git a/micropython/modules_py/boot.py b/micropython/modules_py/boot.py index 30e2f3d..10ee49b 100644 --- a/micropython/modules_py/boot.py +++ b/micropython/modules_py/boot.py @@ -1,7 +1,6 @@ # PicoSystem boot script -# Imports the whole PicoSystem API and runs init() -from picosystem import * +# Runs the PicoSystem init() and launches the launcher if A is held. init() if button(A): - import launcher + import launcher # noqa: F401 diff --git a/template/main.cpp b/template/main.cpp index 2b93197..09bd551 100644 --- a/template/main.cpp +++ b/template/main.cpp @@ -8,5 +8,5 @@ void init() { void update(uint32_t tick) { } -void draw() { +void draw(uint32_t tick) { } \ No newline at end of file