Hello fellow iOS Developers! Today I decided to stop using makeappicon.com to generate my app icons. Instead, I coded a small script in Python which works like a charm. You put the image you want to use as your app icon in the same directory as the script and the script will generate all the resized images you need and put them in the Xcode format “AppIcon.appiconset” folder. The only thing left for you to do is to drag that folder in your Xcode project assests.

Download => iOSAppIconGenerator.py
On Github: iOSAppIconGenerator.git

How to use my script:

  • You have to have python 3.x installed. Look at python.org for instructions.
  • You need to have the library ‘Pillow’ installed. Just run this in terminal:
pip3 install Pillow
  • Download the script: iOSAppIconGenerator.py
  • The image you want to use must be in the same folder as the script (*.png or *.jpg).
  • You have two options for running the script. You can run it with Python Launcher if you installed python from python.org or you can just run it from terminal. So 2 options are:
  • Just right click the script and open with Python Launcher. The script will automatically find the image in its current folder and create a new folder within with resized images and a contents.json file.
  • Change directory (cd) to the directory you have the script and the picture from terminal and run the script. Keep in mind you might need to type python3 iOSAppIconGenerator.py instead of the below:
cd "YOUR PATH WITHOUT QUOTES"
python iOSAppIconGenerator.py
  • Check out here if you don’t know how to use terminal <Terminal Basics>.
  • The asset folder is ready! Just drag the created folder in your Xcode project assets. Don’t forget to delete the old empty asset folder named “AppIcon” and rename the new folder to the same name.

Please keep in mind that this is just a 2 hours project and the script has no error handling whatsoever. So if you come across any bugs leave a comment below!

You can peek at the code below:

#!/usr/local/bin/python3
import os, sys
import json from PIL
import Image from PIL import ImageFilter 

valid_images = [".jpg",".png"]
filename = None
for f in os.listdir():
  ext = os.path.splitext(f)[1]
  if ext.lower() in valid_images:
    filename = f
    break

print("\n<- iOS Icon Generator Script by DG ->\nPlease make sure the script is in the same folder as the image.")

if filename is None:
  sys.exit("Couldn't find an image(.jpg/.png) in the folder. Please try again.")

json_data = { "images":[ { "idiom":"iphone", "size":"29x29", "scale":"1x", "filename":"Icon-App-29x29@1x.png" }, { "idiom":"iphone", "size":"29x29", "scale":"2x", "filename":"Icon-App-29x29@2x.png" }, { "idiom":"iphone", "size":"29x29", "scale":"3x", "filename":"Icon-App-29x29@3x.png" }, { "idiom":"iphone", "size":"40x40", "scale":"1x", "filename":"Icon-App-40x40@1x.png" }, { "idiom":"iphone", "size":"40x40", "scale":"2x", "filename":"Icon-App-40x40@2x.png" }, { "idiom":"iphone", "size":"40x40", "scale":"3x", "filename":"Icon-App-40x40@3x.png" }, { "idiom":"iphone", "size":"60x60", "scale":"1x", "filename":"Icon-App-60x60@1x.png" }, { "idiom":"iphone", "size":"60x60", "scale":"2x", "filename":"Icon-App-60x60@2x.png" }, { "idiom":"iphone", "size":"60x60", "scale":"3x", "filename":"Icon-App-60x60@3x.png" }, { "idiom":"ipad", "size":"29x29", "scale":"1x", "filename":"Icon-App-29x29@1x.png" }, { "idiom":"ipad", "size":"29x29", "scale":"2x", "filename":"Icon-App-29x29@2x.png" }, { "idiom":"ipad", "size":"40x40", "scale":"1x", "filename":"Icon-App-40x40@1x.png" }, { "idiom":"ipad", "size":"40x40", "scale":"2x", "filename":"Icon-App-40x40@2x.png" }, { "idiom":"ipad", "size":"76x76", "scale":"1x", "filename":"Icon-App-76x76@1x.png" }, { "idiom":"ipad", "size":"76x76", "scale":"2x", "filename":"Icon-App-76x76@2x.png" }, { "idiom":"ipad", "size":"76x76", "scale":"3x", "filename":"Icon-App-76x76@3x.png" }, { "idiom":"ipad", "size":"83.5x83.5", "scale":"2x", "filename":"Icon-App-83.5x83.5@2x.png" } ], "info":{ "version":1, "author":"Doruk Gezici" } }

if os.access("AppIcon.appiconset", os.W_OK) == False:
  os.mkdir("AppIcon.appiconset")
  file = open("AppIcon.appiconset/Contents.json", mode="w")
  json.dump(json_data, file, indent=4, sort_keys=True, separators=(',', ':')) file.close() 

def get_size(image): size_str = image["size"] i = size_str.find("x")
  size = (float(size_str[:i]),float(size_str[i+1:]))
  scale_str = image["scale"]
  j = scale_str.find("x")
  scale = int(scale_str[:j])
  return (scale * int(size[0]), scale * int(size[1]))

with open("AppIcon.appiconset/Contents.json", mode="r") as data_file:
  data = json.load(data_file)
  images = data["images"]
  try:
    im = Image.open(filename)
    print(im.format, im.size, im.mode)
  except IOError: print("Image not found")

for image in images:
  size = get_size(image)
  
out = im.resize(size, Image.ANTIALIAS)
out.save("AppIcon.appiconset/"+image["filename"], format="PNG")