Search code examples
pythonopencvcomputer-visionrgbface-detection

How to convert RGB values from .txt file to display an image in Python


I have a .txt file which contains RGB values, when I open and read the files, the pixel values are in str format. How do I convert these values to display an image in python. image.

This is the value gotten when I tried reading the values. They are all in a string format.

Edit: You can find the link for the file here https://drive.google.com/file/d/1mAxlcMj_SVeK0axJhbPJqO4k_egJoYli/view?usp=sharing


Solution

  • This does the trick quite simply:

    #!/usr/bin/env python3
    
    import re
    import numpy as np
    from PIL import Image
    from pathlib import Path
    
    # Open image file, slurp the lot
    contents = Path('image.txt').read_text()
    
    # Make a list of anything that looks like numbers using a regex...
    # ... taking first as height, second as width and remainder as pixels
    h, w, *pixels = re.findall(r'[0-9]+', contents)
    
    # Now make pixels into Numpy array of uint8 and reshape to correct height, width and depth
    na = np.array(pixels, dtype=np.uint8).reshape((int(h),int(w),3))
    
    # Now make the Numpy array into a PIL Image and save
    Image.fromarray(na).save("result.png")
    

    enter image description here


    If you want to write the output image with OpenCV instead of with PIL/Pillow, change the last line above to the following so it does RGB->BGR reordering and uses cv2.imwrite() instead:

    # Save with OpenCV instead
    cv2.imwrite('result.png', na[...,::-1])
    

    If you want to write a PPM file (compatible with Photoshop, GIMP, OpenCV, PIL/Pillow and ImageMagick), without using PIL/Pillow or OpenCV or any extra libraries, and have it around 1/4 the size of your original file, you can write it very simply in binary by replacing the last line above with:

    # Save "na" as binary PPM image
    with open('result.ppm','wb') as f:
       f.write(f'P6\n{w} {h}\n255\n'.encode())
       f.write(na.tobytes())
    

    In fact, you don't need any Python, you can do it directly at the command line in Terminal if you write a NetPBM file that can be read by Photoshop, GIMP, PIL/Pillow

    awk 'NR==1{$0="P3\n" $2 " " $1 "\n255"} {gsub(/,/,"\n")} 1' image.txt > result.ppm
    

    That script basically "massages" your first line so it goes from this:

    418 870
    ... rest of your data ...
    

    to this:

    P3
    870 418
    255
    ... rest of your data ...