Page 1 of 1

PNG to outline/contour x,y coordinates - python script

Posted: Sun Mar 10, 2024 5:52 pm
by gcmartijn
Maybe someone in the future needs this tools, but I guess you can ask chatgpt like I did.

I did use my own scripts to convert a PNG image into a outline line x,y coordinates.
Today I want to change that code, and don't want to build it myself.

The new version return an array with all outlines, using all objects (the previous code did only one object) in a transparent PNG file.

So I did ask the free chatgpt version to create a python3 script.
It was failing over and over, so it cost me some extra time to get the correct result.
To simplify the coordinates use 0.01

use --output_path only when you want to see a black and white example (debugging)

Code: Select all

# pip3 install pillow
# pip3 install opencv-python
# python3 outline.py
import sys
import cv2
import numpy as np
import json
import os
import argparse

def find_outer_contours(image_path, simplify=0):
    img = cv2.imread(image_path, cv2.IMREAD_UNCHANGED)

    mask = img[:, :, 3] > 0

    contours, _ = cv2.findContours(mask.astype(np.uint8), cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)

    min_contour_size = 5
    filtered_contours = [contour for contour in contours if cv2.contourArea(contour) > min_contour_size]

    if simplify > 0:
        simplified_contours = []
        for contour in filtered_contours:
            epsilon = simplify * cv2.arcLength(contour, True)
            simplified_contour = cv2.approxPolyDP(contour, epsilon, True)
            simplified_contours.append(simplified_contour)
        return simplified_contours
    else:
        return filtered_contours

def draw_and_save_contours(contours, output_path, original_size):
    img = np.zeros((original_size[1], original_size[0]), dtype=np.uint8)

    cv2.drawContours(img, contours, -1, (255), thickness=1)

    cv2.imwrite(output_path, img)

def contour_coordinates_to_json(contours):
    contour_coordinates_list = []

    for contour in contours:
        contour_coordinates = []
        for point in contour:
            x, y = point[0]
            contour_coordinates.append([int(x), int(y)])
        
        if len(contour_coordinates) % 2 != 0:
            contour_coordinates.append([contour_coordinates[-1][0], contour_coordinates[-1][1]])

        contour_coordinates_list.append(contour_coordinates)

    return json.dumps(contour_coordinates_list)

def apply_convex_hull(contours):
    combined_contour = np.concatenate(contours)

    hull = cv2.convexHull(combined_contour)

    return [hull]

if __name__ == "__main__":
    parser = argparse.ArgumentParser(description='Find outer contours of a transparent image.')
    parser.add_argument('image_path', type=str, help='Path to the image file.')
    parser.add_argument('--simplify', type=float, default=0.01, help='Simplify factor for contour approximation. Set to 0 to disable simplification.')
    parser.add_argument('--hull', action='store_true', help='Apply convex hull to the contours.')
    parser.add_argument('--output_path', type=str, default='', help='Path to save the output image. If not provided, the image will not be saved.')
    args = parser.parse_args()

    image_path = args.image_path

    original_img = cv2.imread(image_path, cv2.IMREAD_UNCHANGED)
    original_size = (original_img.shape[1], original_img.shape[0])

    contours = find_outer_contours(image_path, simplify=args.simplify)

    if args.hull:
        contours = apply_convex_hull(contours)

    if args.output_path:
        draw_and_save_contours(contours, output_path, original_size)


    json_output = contour_coordinates_to_json(contours)
    print(json_output)

Re: PNG to outline/contour x,y coordinates - python script

Posted: Tue Mar 12, 2024 4:37 pm
by dusoft
It would be even better if the source code was in Lua. But indeed, it can be useful.

Re: PNG to outline/contour x,y coordinates - python script

Posted: Wed Mar 13, 2024 6:09 am
by zorg
Consider not posting ChatGPT drivel in here in the future, and this can be achieved in lua as well, so as to not force people to use another programming language and interpreter when they don't need to.

Re: PNG to outline/contour x,y coordinates - python script

Posted: Wed Mar 13, 2024 8:15 am
by darkfrei
ChatGPT can make Lua / Love2D code as well, also translate one language to other. With mistakes, that is hard to find, yeah.