geolib.py
Created by
tlake
Created on
August 07, 2024
3.64 KB
from ppn import *
sgn = lambda n :( - 1 , 1 )[ abs ( n ) == n ]
def rec ( name , base , defaut = None ):
try :
return base [ name ]
except :
return defaut
def fill_auto ( x , y , color , param ):
if param == " squared " :
if not (( x - y ) % 2 ): set_pixel ( x , y , color )
elif param == " full " :
set_pixel ( x , y , color )
elif param == " opaque " :
set_pixel ( x , y ,( 248 , 255 , 248 ))
def circle ( x_c , y_c , r , color = ( 0 , 0 , 0 )):
x , y , m = 0 , r , 5 - 4 * r
while x <= y :
a = 2 * ( x , y , - x , - y )
b = ( y , x , y , x , - y , - x , - y , - x )
for i in range ( 8 ):
set_pixel ( a [ i ] + x_c , b [ i ] + y_c , color )
if m > 0 :
y -= 1
m -= 8 * y
x += 1
m += 8 * x + 1
def line ( x1 , y1 , x2 , y2 , color = ( 0 , 0 , 0 )):
d = sorted (( abs ( x2 - x1 ), abs ( y2 - y1 )))
if d != ( abs ( x2 - x1 ), abs ( y2 - y1 )):
s = ( sgn ( y2 - y1 ), sgn ( x2 - x1 ))
coord = [ y1 , x1 ]
x = 1
else :
s = ( sgn ( x2 - x1 ), sgn ( y2 - y1 ))
coord = [ x1 , y1 ]
x = 0
set_pixel ( x1 , y1 , color )
cumul = d [ 1 ] >> 1
for i in range ( d [ 1 ]):
coord [ 1 ] += s [ 1 ]
cumul += d [ 0 ]
if cumul > d [ 1 ]:
cumul -= d [ 1 ]
coord [ 0 ] += s [ 0 ]
set_pixel ( coord [ x ], coord [( x + 1 ) % 2 ], color )
set_pixel ( x2 , y2 , color )
def polygon ( * coord , ** kwargs ):
color = rec ( " color " , kwargs , ( 0 , 0 , 0 ))
fill = rec ( " fill " , kwargs , None )
x , y = list (), list ()
for i in range ( len ( coord ) - 1 ):
x . append ( coord [ i ][ 0 ])
y . append ( coord [ i ][ 1 ])
line ( coord [ i ][ 0 ], coord [ i ][ 1 ], coord [ i + 1 ][ 0 ], coord [ i + 1 ][ 1 ], color )
x . append ( coord [ - 1 ][ 0 ])
y . append ( coord [ - 1 ][ 1 ])
line ( coord [ 0 ][ 0 ], coord [ 0 ][ 1 ], coord [ - 1 ][ 0 ], coord [ - 1 ][ 1 ], color )
if fill :
for i in range ( min ( x ) + 1 , max ( x )):
detect = 0
for j in range ( min ( y ), max ( y )):
if get_pixel ( i , j ) == color : detect += 1
elif detect == 1 : fill_auto ( i , j ,( color [ 0 ] + 8 , color [ 1 ] + 8 , color [ 2 ] + 8 ), fill )
def progress_bar ( x , y , long , larg , prct , color = ( 0 , 255 , 0 )):
polygon (( x , y ),( x + long , y ),( x + long , y + larg ),( x , y + larg ))
line ( x + 2 , y + larg + 1 , x + long + 1 , y + larg + 1 ,( 200 , 200 , 200 ))
line ( x + long + 1 , y + 2 , x + long + 1 , y + larg + 1 ,( 200 , 200 , 200 ))
prct = int (( long * prct ) / 100 ) - 1
if prct < 0 : prct = 1
for i in range ( 1 , larg ):
line ( 1 + x , y + i , x + prct , y + i ,( color [ 0 ] - 7 * i , color [ 1 ] - 7 * i , color [ 2 ] - 7 * i ))
def rectangle ( x , y , long , larg , ** kwargs ):
fill = rec ( " fill " , kwargs , None )
color = rec ( " color " , kwargs , ( 0 , 0 , 0 ))
if fill :
for i in range ( 0 , long ):
for j in range ( 0 , larg ): fill_auto ( i + x , j + y , color , fill )
else : polygon (( x , y ),( x + long , y ),( x + long , y + larg ),( x , y + larg ), color = color )
# http://www.sunshine2k.de/coding/java/TriangleRasterization/TriangleRasterization.html
def hline ( x1 , x2 , y , c ):
while x1 <= x2 :
set_pixel ( x1 , y , c )
x1 += 1
def fillBottomFlatTriangle ( p1 , p2 , p3 , c ):
p2 , p3 = sorted ([ p2 , p3 ], key = lambda x : x [ 0 ])
invslope1 = ( p2 [ 0 ] - p1 [ 0 ]) / ( p2 [ 1 ] - p1 [ 1 ])
invslope2 = ( p3 [ 0 ] - p1 [ 0 ]) / ( p3 [ 1 ] - p1 [ 1 ])
curx1 = p1 [ 0 ]
curx2 = p1 [ 0 ]
for scanlineY in range ( p1 [ 1 ], p2 [ 1 ] + 1 ):
hline ( int ( curx1 ), int ( curx2 ), scanlineY , c )
curx1 += invslope1
curx2 += invslope2
def fillTopFlatTriangle ( p1 , p2 , p3 , c ):
p1 , p2 = sorted ([ p1 , p2 ], key = lambda x : x [ 0 ])
invslope1 = ( p3 [ 0 ] - p1 [ 0 ]) / ( p3 [ 1 ] - p1 [ 1 ]);
invslope2 = ( p3 [ 0 ] - p2 [ 0 ]) / ( p3 [ 1 ] - p2 [ 1 ]);
curx1 = p3 [ 0 ];
curx2 = p3 [ 0 ];
for scanlineY in range ( p3 [ 1 ], p1 [ 1 ], - 1 ):
hline ( int ( curx1 ), int ( curx2 ), scanlineY , c )
curx1 -= invslope1 ;
curx2 -= invslope2 ;
def drawTriangle ( p1 , p2 , p3 , c ):
p1 , p2 , p3 = sorted ([ p1 , p2 , p3 ], key = lambda x : x [ 1 ])
if p2 [ 1 ] == p3 [ 1 ]:
fillBottomFlatTriangle ( p1 , p2 , p3 , c )
elif p1 [ 1 ] == p2 [ 1 ]:
fillTopFlatTriangle ( p1 , p2 , p3 , c )
else :
p4 = (
int ( p1 [ 0 ] + (( p2 [ 1 ] - p1 [ 1 ]) / ( p3 [ 1 ] - p1 [ 1 ])) * ( p3 [ 0 ] - p1 [ 0 ])), p2 [ 1 ]);
fillBottomFlatTriangle ( p1 , p2 , p4 , c )
fillTopFlatTriangle ( p2 , p4 , p3 , c )