Last active
November 28, 2020 23:43
-
-
Save rubo77/164e671f82f335943ab936e0ba715907 to your computer and use it in GitHub Desktop.
converts a jpeg file with a planet on black background to a transparent png
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
#!/usr/bin/python3 | |
# converts a jpeg file with a planet on black background to a transparent png | |
# like this imagemagick function does: | |
# for i in planet_*.jpg; do nr=$(echo ${i/planet_/}|sed s/.jpg//g|xargs); convert $i -fuzz 1% -transparent black trans/planet_${nr}.png; done | |
# but the python script will create them without arkifacts | |
# needs | |
# sudo apt install python3-opencv python3-sklearn python3-skimage | |
# make sure, you created the subfolders thresh/, circle/, mask/, transparent/ and crop/ | |
# mkdir thresh circle mask transparent crop | |
# call with | |
# for i in planet_*.jpg; do nr=$(echo ${i/planet_/}|sed s/.jpg//g|xargs); python planet2png.py -i $i -o planet_${nr}.png; done | |
import cv2 | |
import numpy as np | |
import sys, getopt | |
import skimage.exposure | |
def main(argv): | |
inputfile = '' | |
outputfile = '' | |
try: | |
opts, args = getopt.getopt(argv,"hi:o:",["ifile=","ofile="]) | |
except getopt.GetoptError: | |
print ('planet2png.py -i <inputfile> -o <outputfile>') | |
sys.exit(2) | |
for opt, arg in opts: | |
if opt == '-h': | |
print ('planet2png.py -i <inputfile> -o <outputfile>') | |
sys.exit() | |
elif opt in ("-i", "--ifile"): | |
inputfile = arg | |
elif opt in ("-o", "--ofile"): | |
outputfile = arg | |
if inputfile == '': | |
print ("missing inputfile") | |
sys.exit() | |
if outputfile == '': | |
print ("missing outputfile") | |
sys.exit() | |
print ("crop",inputfile) | |
# read image | |
img = cv2.imread(inputfile) | |
h, w, c = img.shape | |
# convert to grayscale | |
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) | |
# threshold | |
thresh = cv2.threshold(gray, 0, 255, cv2.THRESH_BINARY+cv2.THRESH_OTSU)[1] | |
# get contour | |
contours = cv2.findContours(thresh, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE) | |
contours = contours[0] if len(contours) == 2 else contours[1] | |
big_contour = max(contours, key=cv2.contourArea) | |
# get enclosing circle | |
center, radius = cv2.minEnclosingCircle(big_contour) | |
cx = int(round(center[0])) | |
cy = int(round(center[1])) | |
rr = int(round(radius)) | |
# draw outline circle over input | |
circle = img.copy() | |
cv2.circle(circle, (cx,cy), rr, (0, 0, 255), 1) | |
# draw white filled circle on black background as mask | |
mask = np.full((h,w), 0, dtype=np.uint8) | |
cv2.circle(mask, (cx,cy), rr, 255, -1) | |
# antialias | |
blur = cv2.GaussianBlur(mask, (0,0), sigmaX=1, sigmaY=1, borderType = cv2.BORDER_DEFAULT) | |
mask = skimage.exposure.rescale_intensity(blur, in_range=(127,255), out_range=(0,255)) | |
# put mask into alpha channel to make outside transparent | |
imgT = cv2.cvtColor(img, cv2.COLOR_BGR2BGRA) | |
imgT[:,:,3] = mask | |
# crop the image | |
ulx = int(cx-rr+0.5) | |
uly = int(cy-rr+0.5) | |
brx = int(cx+rr+1) | |
bry = int(cy+rr+1) | |
print(ulx,brx,uly,bry) | |
crop = imgT[uly:bry, ulx:brx] | |
# write result to disk | |
#cv2.imwrite("thresh/"+outputfile, thresh) | |
#cv2.imwrite("circle/"+outputfile, circle) | |
#cv2.imwrite("mask/"+outputfile, mask) | |
cv2.imwrite("transparent/"+outputfile, imgT) | |
cv2.imwrite("crop/"+outputfile, crop) | |
# display it | |
#cv2.imshow("thresh", thresh) | |
#cv2.imshow("circle", circle) | |
#cv2.imshow("mask", mask) | |
#cv2.waitKey(0) | |
if __name__ == "__main__": | |
main(sys.argv[1:]) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Those are all planets, I want to convert: https://framadrop.org/lufi/r/xZyupNVL_p#pf9g8cvzJU4wgFVgJAb9sGdN9V+l+IZZCdEcA/j90hc=