I am very new to Python. I just started today.
I am trying desperately to save an image to a fixed path, such as:
/Users/myname/Sites/Tester/images/
So if I have an image, called "1.jpg", it will be placed here:
/Users/myname/Sites/Tester/images/1.jpg
This is my script:
from PIL import Image
import tempfile
def set_image_dpi(file_path):
im = Image.open(file_path)
length_x, width_y = im.size
factor = min(1, float(1024.0 / length_x))
size = int(factor * length_x), int(factor * width_y)
im_resized = im.resize(size, Image.ANTIALIAS)
temp_file = tempfile.NamedTemporaryFile(delete=False, suffix='.jpg')
temp_filename = temp_file.name
im_resized.save(temp_filename, dpi=(300, 300))
return temp_filename
However, this saves the file in:
/var/folders/1n/hdyfv8z96v5_hcb9tsgvt7cr0000gn/T/tmp91rams5v.jpg
How can I do, so it will save in the path I specifies?
"MY_PATH / temp_filename"
No need for the tempfile module here, you just need to specify the path when calling .save():
from PIL import Image
import os
def set_image_dpi(file_path, save_folder):
im = Image.open(file_path)
length_x, width_y = im.size
factor = min(1, float(1024.0 / length_x))
size = int(factor * length_x), int(factor * width_y)
im_resized = im.resize(size, Image.ANTIALIAS)
save_path = os.path.join(save_folder,'test.png')
# creates path: C:\Users\User\Pictures\test.png
im_resized.save(save_path, dpi=(300, 300))
set_image_dpi('test.png','C:\\Users\\User\\Pictures')
I'm guessing your main problem is building the result path from the original path (something like /where/images/are/taken/from/1.jpg) and your destination directory (/Users/myname/Sites/Tester/images/). The methods in the os.path package can help (see https://docs.python.org/3/library/os.path.html):
import os
dest_dir = '/Users/myname/Sites/Tester/images/'
...
base = os.path.basename(file_path) # this will be '1.jpg'
dest_path = os.path.join(dest_dir, base) # this will be the full path
im_resized.save(dest_path)
As others have said in the comments, you don't need tempfile here.
Related
Basically, I copied and paste a script, and merged it with other script, and now the script doesn't work, it says an error "NoneType object has no attribute save"Screenshot
And here's the script:
` from PIL import Image
import PIL
import os
from glob import glob
imgs = [y for x in os.walk(".") for y in glob(os.path.join(x[0], '*.png'))]
size = 32, 32
lastdir = None
for file in imgs:
img = Image.open(file)
img = img.thumbnail(size, resample=PIL.Image.NEAREST)
file = file.replace('img', 'icon', 1)
dir = os.path.dirname(file)
try:
os.makedirs(dir)
except:
pass
if dir!=lastdir:
print(dir)
lastdir = dir
img.save(file + ".png", "PNG")`
Resize various images on various directories and save them, but the images are not saving.
The thumbnail() method modifies its object rather than returning a new one. So, this line:
img = img.thumbnail(size, resample=PIL.Image.NEAREST)
should be:
img.thumbnail(size, resample=PIL.Image.NEAREST)
I am going to resize image file which located in Desktop with set of subfolder.
I try following command and it works without rename save new.
from PIL import Image
import os, sys
import glob
root_dir='./././Desktop/python/'
def resize():
for filename in glob.iglob(root_dir + '**/*.jpg', recursive=True):
print(filename)
im = Image.open(filename)
imResize = im.resize((450,600), Image.ANTIALIAS)
imResize.save(filename , 'JPEG', quality=90)
resize()
My question is how can I add the correct command to save the renewe resized image file with append 'f + _thumbnail' + .jpg?
E.g file1 > file1_thumbnail.jpg
I tried add followings to row print(filename) but show error.
f, e = os.path.splitext(path+item)
size = im.size
ratio = float(final_size) / max(size)
new_image_size = tuple([int(x*ratio) for x in size])
im = im.resize(new_image_size, Image.ANTIALIAS)
new_im = Image.new("RGB", (final_size, final_size))
new_im.paste(im, ((final_size-new_image_size[0])//2, (final_size-new_image_size[1])//2))
new_im.save(f + 'resized.jpg', 'JPEG', quality=90)
May I know how can fix it?
Many Thanks
You can use python slicing of strings for this -
You can modify your code to -
from PIL import Image
import os, sys
import glob
root_dir='./././Desktop/python/'
def resize():
for filename in glob.iglob(root_dir + '**/*.jpg', recursive=True):
print(filename)
im = Image.open(filename)
imResize = im.resize((450,600), Image.ANTIALIAS)
filename = filename[:-4] + " _thumbnail" + filename[-4:]
imResize.save(filename , 'JPEG', quality=90)
resize()
The ".jpg" can be sliced at the end.
Im trying to write a python script which will walk through a directory and traverse the all sub directories and if any jpg or png image has higher resolution than 2048*2048 then print out the name of those images. I am not able to traverse the sub-directories. Can anyone plz look into the code
import os
import matplotlib.image as plt
root_path = 'E:\newfolder'
img_list = os.listdir(root_path)
for img_name in img_list:
if img_name.endswith(('.png', '.jpg')):
img = plt.imread(root_path+'/'+img_name)
if img.shape[0] > 2048 and img.shape[1] > 2048:
print(root_path, img_name)
Here's a complete and tested solution that is similar to answers by #Paul and #BrainCity. You'll see that I prefer using small, clear functions, since these encourage reusable code.
You can do the image processing using matplotlib as you do in your question, but you need to install Pillow in order to handle .JPG images, since matplotlib only supports PNG natively. I prefer using Pillow directly unless you're already using matplotlib for other stuff.
from pathlib import Path
from PIL import Image
def print_high_res_images(directory: str):
root_path = Path(directory).resolve()
high_res_images = get_high_res_images(root_path)
if high_res_images:
print('High resolution images:')
for file_path in high_res_images:
print(file_path)
def get_high_res_images(root_path: Path) -> []:
return [path for path in root_path.rglob("*.*") if is_high_res_image(path)]
def is_high_res_image(file_path: Path) -> bool:
if is_image(file_path):
image = Image.open(file_path)
width, height = image.size
return width > 2048 and height > 2048
return False
def is_image(file: Path) -> bool:
return file.suffix.lower() in ['.png', '.jpg']
# Test our new function:
print_high_res_images(r'E:\newfolder')
If you're using Python 3.5+, you can use the pathlib module, and then use a recursive glob pattern to find all files in all subdirectories. Then, you filter the paths and retain only those whose suffix is .png or .jpg:
from pathlib import Path
for path in [path for path in Path("dir/to/images").rglob("*.*") if path.suffix.lower() in (".png", ".jpg")]:
# image = Image(path)
# if image dimensions greater than 2048 x 2048:
# print(path)
print(path) will print out the entire absolute path of the current image, but if you just want to print out the name, you can print(path.name), which will include the suffix (file extension). If you just want the name of the file without the extension, you can print(path.stem).
crawl subdirectory using os.walk
import os
import pathlib
from PIL import Image
def crawlImages(directory):
allowedExtensions = ['.jpg', '.png']
for root, dirs, files in os.walk(directory):
for f in files:
if pathlib.Path(f).suffix in allowedExtensions:
fileName = os.path.abspath(os.path.join(root, f))
image = Image.open(fileName)
width, height = image.size
# checking minimum image width and height
if width > 2400 and height > 2400:
print(fileName, width, height)
crawlImages('E:\\music')
Currently I am trying to crop all images inside a folder under the address of: C:\\Users\\xie\\Desktop\\tiff\\Bmp and then resave them into the same folder. Below is the code I am trying to experiment with, both run without error but does nothing. Also note I am using windows as platform.
Code 1:
from PIL import Image
import os.path, sys
path = "C:\\Users\\xie\\Desktop\\tiff\\Bmp"
dirs = os.listdir(path)
def crop():
for item in dirs:
if os.path.isfile(path+item):
im = Image.open(path+item)
f, e = os.path.splitext(path+item)
imCrop = im.crop(30, 10, 1024, 1004)
imCrop.save(f + 'Cropped.bmp', "BMP", quality=100)
crop()
Code 2:
for f in os.listdir("C:\\Users\\xie\\Desktop\\tiff\\Bmp"):
for f in ("C:\\Users\\xie\\Desktop\\tiff\\Bmp"):
if f.endswith('.bmp'):
print (f, end=" ")
i = Image.open(f)
area = (30, 10, 1024, 1004)
cropped_i = i.crop(area)
cropped_i.show()
cropped_i.save('Cropped{}.bmp', "BMP", quality=100, optimize=True)
Thanks, any help or suggestions are greatly appreciated!
Code 1 : Corrected
This is your corrected code, you almost had it right, you have to join the path correctly, in your code you weren't adding a separator / between the path and the filename. by using os.path.join you can combine a directory path and a filename.
Furthermore, crop takes a tuple of 4, not 4 arguments.
from PIL import Image
import os.path, sys
path = "C:\\Users\\xie\\Desktop\\tiff\\Bmp"
dirs = os.listdir(path)
def crop():
for item in dirs:
fullpath = os.path.join(path,item) #corrected
if os.path.isfile(fullpath):
im = Image.open(fullpath)
f, e = os.path.splitext(fullpath)
imCrop = im.crop((30, 10, 1024, 1004)) #corrected
imCrop.save(f + 'Cropped.bmp', "BMP", quality=100)
crop()
This is more or less a rough version of code, I used with opencv, it should work the same for PIL also
import glob
import numpy as np
from PIL import Image
image_list = []
for filename in glob.glob('name_of_folder/*.jpg'):
im=Image.open(filename)
image_list.append(im)
a=0
c=[]
for i in range(0,len(image_list)):
#ur image cropping and other operations in here for each image_list[i]
c.append(image_list[i])
c[i].save()
I'm learning Python and try to use Pillow to resize images in a folder, then save them to another folder with the same filename. However, the program runs well, when I check the destination folder, there're no images...
My code is as below:
from PIL import Image
import os, glob, sys
src_path = "D:/Test_A/src/*.png"
dst_path = "D:/Test_A/dst/"
img_list = glob.glob(src_path)
for XXPNG in img_list:
fn = os.path.basename(XXPNG)
im = Image.open(XXPNG)
print(fn, im.size)
nim = im.resize((119, 119), Image.ANTIALIAS)
nim.save("dst_path","PNG")
print("Resize Done")
Please help me find my bug, or give my any advise.
Thank you very much for help and bearing my poor English.
"dst_path" with " is a normal text, not variable dst_path - so you save in file with name "dst_path".
You need dst_path without " - plus filename
nim.save(dst_path + fn, "PNG")
or with os.path.join()
nim.save(os.path.join(dst_path, name), "PNG")
Code:
from PIL import Image
import os, glob, sys
src_path = "D:/Test_A/src/*.png"
dst_path = "D:/Test_A/dst/"
img_list = glob.glob(src_path)
for fullpath in img_list:
name = os.path.basename(fullpath)
im = Image.open(fullpath)
print(name, im.size, '=>', os.path.join(dst_path, name))
nim = im.resize((119, 119), Image.ANTIALIAS)
nim.save(os.path.join(dst_path, name), "PNG")
#nim.save(dst_path + name, "PNG")
print("Resize Done")