Last active
December 12, 2021 00:28
-
-
Save samneggs/2eb074730b51b7cc0ff23148514e497d to your computer and use it in GitHub Desktop.
Pi Pico Flood Fill and Line Fill
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from LCD_3inch5 import LCD_3inch5 | |
from machine import Pin, UART | |
import framebuf | |
from time import sleep_ms, sleep_us, ticks_diff, ticks_us, sleep | |
from micropython import const | |
import array | |
from usys import exit | |
import gc | |
from random import randint | |
MAXSCREEN_X = const(240) | |
MAXSCREEN_Y = const(240) | |
NUM_POINTS = const(1200)#350 | |
xc=array.array('h', 0 for _ in range(NUM_POINTS)) | |
yc=array.array('h', 0 for _ in range(NUM_POINTS)) | |
l=array.array('h', 0 for _ in range(NUM_POINTS)) | |
dx2=array.array('i',(-1,0,1,-1,1,-1,0,1)) | |
dy2=array.array('i',(-1,-1,-1,0,0,1,1,1)) | |
dx=array.array('i',(0,1,0,-1)) | |
dy=array.array('i',(-1,0,1,0)) | |
rand=array.array('h', randint(0,99) for _ in range(NUM_POINTS)) | |
# Flood fill, 0.37 seconds for non-displayed fill of 240x240 | |
# display = 1 for display while filling (slower) | |
@micropython.viper | |
def ffill(x:int,y:int,display:int,color:int): | |
screen_addr=ptr16(display_buffer) | |
xc_addr=ptr16(xc) | |
yc_addr=ptr16(yc) | |
dx_addr=ptr32(dx) | |
dy_addr=ptr32(dy) | |
l_addr=ptr16(l) | |
rand_addr=ptr16(rand) | |
xc_addr[0]=x | |
yc_addr[0]=y | |
alive=1 | |
l_addr[0]=1 | |
done = False | |
addr=y*MAXSCREEN_Y+x | |
back_color=screen_addr[addr] | |
while not done: | |
done = True | |
for i in range(0,NUM_POINTS-100): | |
r=rand_addr[i] | |
if not r: | |
continue | |
if l_addr[i]: | |
for j in range(0,4): | |
y=yc_addr[i]+dy_addr[j] | |
x=xc_addr[i]+dx_addr[j] | |
if x and y and x<240 and y<240: | |
addr=y*MAXSCREEN_Y+x | |
read_color=screen_addr[addr] | |
if read_color==back_color: | |
xc_addr[alive]=x | |
yc_addr[alive]=y | |
alive+=1 | |
l_addr[alive]=1 | |
screen_addr[addr]=color | |
done = False | |
if alive>NUM_POINTS-100: | |
alive=0 | |
if display: | |
lcd.show_xy(0,0,MAXSCREEN_X-1,MAXSCREEN_Y-1,display_buffer) |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from LCD_3inch5 import LCD_3inch5 | |
from machine import Pin, UART | |
import framebuf | |
from time import sleep_ms, sleep_us, ticks_diff, ticks_us, sleep | |
from micropython import const | |
import array | |
from usys import exit | |
import gc | |
from random import randint | |
MAXSCREEN_X = const(240) | |
MAXSCREEN_Y = const(240) | |
NUM_POINTS = const(1200)#350 | |
xc=array.array('h', 0 for _ in range(NUM_POINTS)) | |
yc=array.array('h', 0 for _ in range(NUM_POINTS)) | |
l=array.array('h', 0 for _ in range(NUM_POINTS)) | |
dx2=array.array('i',(-1,0,1,-1,1,-1,0,1)) | |
dy2=array.array('i',(-1,-1,-1,0,0,1,1,1)) | |
dx=array.array('i',(0,1,0,-1)) | |
dy=array.array('i',(-1,0,1,0)) | |
rand=array.array('h', randint(0,99) for _ in range(NUM_POINTS)) | |
# Line fill | |
# display = 1 for display while filling (slower) | |
@micropython.viper | |
def lfill(x:int,y:int,display:int,color:int): | |
screen_addr=ptr16(display_buffer) | |
xc_addr=ptr16(xc) | |
yc_addr=ptr16(yc) | |
dx2_addr=ptr32(dx2) | |
dy2_addr=ptr32(dy2) | |
l_addr=ptr16(l) | |
rand_addr=ptr16(rand) | |
xc_addr[0]=x | |
yc_addr[0]=y | |
alive=1 | |
update=0 | |
l_addr[0]=1 | |
done = False | |
addr=y*MAXSCREEN_Y+x | |
back_color=screen_addr[addr] | |
while not done: | |
done = True | |
for i in range(0,NUM_POINTS-100): | |
if l_addr[i]: | |
for j in range(0,8): | |
y=yc_addr[i]+dy2_addr[j] | |
x=xc_addr[i]+dx2_addr[j] | |
if x and y and x<240 and y<240: | |
addr=y*MAXSCREEN_Y+x | |
read_color=screen_addr[addr] | |
if read_color==back_color: | |
xc_addr[alive]=x | |
yc_addr[alive]=y | |
alive+=1 | |
l_addr[alive]=1 | |
screen_addr[addr]=color | |
done = False | |
if alive>NUM_POINTS-100: | |
alive=0 | |
update+=1 | |
if display and update>10: | |
lcd.show_xy(0,0,MAXSCREEN_X-1,MAXSCREEN_Y-1,display_buffer) | |
update = 0 |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment