from PIL import Image # helpful constants THRESHOLD = 75 # eefault max allowable distance to be similar GREEN = ( 0, 255, 0 ) def dup( original ) : ow, oh = original.size nw, nh = ow, oh new_image = Image.new( "RGB", ( nw, nh ) ) for nx in range( 0 , nw ) : for ny in range( 0, nh ) : nspot = ( nx, ny ) ospot = nspot opixel = original.getpixel( ospot ) npixel = opixel new_image.putpixel( nspot, npixel ) return new_image def rgb_differences( p1, p2 ) : ''' Returns the difference in RGB levels of p1 and p2 ''' r1, g1, b1 = p1 r2, g2, b2 = p2 rdiff = abs( r1 - r2 ) gdiff = abs( g1 - g2 ) bdiff = abs( b1 - b2 ) d = ( rdiff , gdiff , bdiff ) return d def similar( p1, p2, max_allowable=THRESHOLD ) : ''' Returns whether pixels p1 and p2 have RGB dofferences than the max allowable ''' rdiff, gdiff, bdiff = rgb_differences( p1, p2 ) if ( ( rdiff <= THRESHOLD ) and ( gdiff <= THRESHOLD ) and ( bdiff <= THRESHOLD ) ) : return True else : return False def is_background( p, back_screen=GREEN ) : ''' Returns whether p is the back screen color ''' if ( p == back_screen ) : return True else : return False def inbounds( spot, im ) : ''' Returns whether ) is a spot on im ''' w, h = im.size x, y = spot if ( ( x < 0 ) or ( x >= w ) ) : return False elif ( ( y < 0 ) or ( y >= h ) ) : return False else : return True def clean_up( original, back_screen=GREEN ) : ''' Returns a copy of original where pixels similar to the back_screen are set to the back_screen ''' new_image = dup( original ) nw, nh = new_image.size for nx in range( 0, nw ) : for ny in range( 0, nh ) : nspot = ( nx, ny ) pixel = new_image.getpixel( nspot ) if ( similar( pixel, back_screen ) ) : new_image.putpixel( nspot, back_screen ) return new_image def combine( bg, fg, sx, sy, back_screen=GREEN ) : ''' Returns a new image that is a mash up of images bg and fg. The new image has bg as its background. The pixels in fg that are dissimilar to p are copied on top of the background. The copy uses (sx, sy) as the spot in the background as location to start the lay over of fg. ''' bw, bh = bg.size fw, fh = fg.size new_image = dup( bg ) fg = clean_up( fg, back_screen ) for fx in range( 0, fw ) : for fy in range( 0, fh ): fspot = ( fx, fy ) pixel = fg.getpixel( fspot ) nx = sx + fx ny = sy + fy nspot = ( nx, ny ) if ( is_background( pixel, back_screen ) ) : continue elif ( not inbounds( nspot, new_image ) ) : continue else : new_image.putpixel( nspot, pixel ) return new_image if ( __name__ == '__main__' ) : import smashing smashing.test_with_dino() smashing.test_with_beyonce()