Image Processing with Pillow and OpenCV
This page demonstrates loading, inspecting, cropping, resizing, blurring, changing pixels, and displaying images with Pillow, Matplotlib, and OpenCV.
What you should be able to do
- Open an image from a file path.
- Inspect image size, mode, and array shape.
- Crop, resize, blur, recolor pixels, and convert BGR to RGB.
Reusable patterns
- Pillow reads images as image objects; OpenCV reads them as arrays.
- OpenCV stores color channels as BGR by default.
- Array slicing is the standard technique for cropping image regions.
Listing 1. Opening and processing images
from PIL import Image # opening and processing images
from matplotlib import pyplot as plt # displaying charts and images
from google.colab.patches import cv2_imshow # displaying images while working with OpenCV in ColabListing 2. Code listing 2
image_path = "/content/drive/MyDrive/macka.jpg"
image = Image.open(image_path)Listing 3. Size is the image dimensions; mode is the image type, for example rgb
print(image.size, image.mode) # size is the image dimensions; mode is the image type, for example RGBExpected text output or note
(600, 645) RGBListing 4. Display the image
# display the image
plt.imshow(image)
plt.show()Expected text output or note
<Figure size 640x480 with 1 Axes>
[visual output omitted; run the code to display the image or chart]Listing 5. Rotate the image
# rotate the image
rotated_image = image.rotate(45)
plt.imshow(rotated_image)
plt.show()Expected text output or note
<Figure size 640x480 with 1 Axes>
[visual output omitted; run the code to display the image or chart]Listing 6. Convert to grayscale
# convert to grayscale
gray_image = image.convert("LA")
plt.imshow(gray_image)Expected text output or note
<matplotlib.image.AxesImage at 0x7f992966c470>
<Figure size 640x480 with 1 Axes>
[visual output omitted; run the code to display the image or chart]Listing 7. Code listing 7
gray_image.save("/content/drive/MyDrive/gray_image.png")Listing 8. Use opencv to load images
# use OpenCV to load images
import cv2
cat_image_2 = cv2.imread('/content/drive/MyDrive/macka.jpg')
plt.imshow(cat_image_2)Expected text output or note
<matplotlib.image.AxesImage at 0x7f9928602750>
<Figure size 640x480 with 1 Axes>
[visual output omitted; run the code to display the image or chart]Listing 9. Crop the image
# crop the image
cat_crop = cat_image_2 [50:300, 100:450]
plt.imshow(cat_crop)Expected text output or note
<matplotlib.image.AxesImage at 0x7f9928626270>
<Figure size 640x480 with 1 Axes>
[visual output omitted; run the code to display the image or chart]Listing 10. Code listing 10
cat_crop.shapeExpected text output or note
(250, 350, 3)Listing 11. Code listing 11
v, s, d = cat_crop.shapeListing 12. Resize the cropped part of the image
# resize the cropped part of the image
small_cat_crop = cv2.resize(cat_crop, (175, 125))
plt.imshow(small_cat_crop)Expected text output or note
<matplotlib.image.AxesImage at 0x7f9929630530>
<Figure size 640x480 with 1 Axes>
[visual output omitted; run the code to display the image or chart]Listing 13. Apply a median filter, which creates blur
# apply a median filter, which creates blur
blurred_crop = cv2.medianBlur(cat_crop, 5)
plt.imshow(blurred_crop)Expected text output or note
<matplotlib.image.AxesImage at 0x7f99287b7bc0>
<Figure size 640x480 with 1 Axes>
[visual output omitted; run the code to display the image or chart]Listing 14. Insert the blurred crop back into the original image
# insert the blurred crop back into the original image
cat_image_2[50:300, 100:450] = blurred_crop
plt.imshow(cat_image_2)Expected text output or note
<matplotlib.image.AxesImage at 0x7f9910554a10>
<Figure size 640x480 with 1 Axes>
[visual output omitted; run the code to display the image or chart]Listing 15. Download an image from the internet with a system command
# download an image from the internet with a system command
# the !curl command uses -o for the output file name, followed by the file name and URL
!curl -o downloaded_image https://files.readme.io/069a96b-4d870d7-546212389.jpg
downloaded_image = cv2.imread("downloaded_image")Expected text output or note
% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
0 0 0 0 0 0 0 0 --:--:-- --:--:-- --:--:-- 0
100 119k 100 119k 0 0 764k 0 --:--:-- --:--:-- --:--:-- 766kListing 16. Code listing 16
print(downloaded_image.size, downloaded_image.shape)Expected text output or note
786432 (512, 512, 3)Listing 17. Code listing 17
plt.imshow(downloaded_image)Expected text output or note
<matplotlib.image.AxesImage at 0x7f991048c260>
<Figure size 640x480 with 1 Axes>
[visual output omitted; run the code to display the image or chart]Listing 18. Convert from opencv bgr format to rgb
# convert from OpenCV BGR format to RGB
downloaded_image_RGB = cv2.cvtColor(downloaded_image, cv2.COLOR_BGR2RGB)
plt.imshow(downloaded_image_RGB)Expected text output or note
<matplotlib.image.AxesImage at 0x7f9910489d30>
<Figure size 640x480 with 1 Axes>
[visual output omitted; run the code to display the image or chart]Listing 19. Instead of converting manually, this can also be used
# instead of converting manually, this can also be used:
from google.colab.patches import cv2_imshow
cv2_imshow(downloaded_image)Expected text output or note
<PIL.Image.Image image mode=RGB size=512x512>
[visual output omitted; run the code to display the image or chart]Listing 20. Extract the pixel at position 130, 130
# extract the pixel at position 130, 130
px1 = downloaded_image[130, 130]
print(px1) # the output contains pixel values in BGR orderExpected text output or note
[216 213 199]Listing 21. Change that pixel to white
downloaded_image[130,130]=[255,255,255] # change that pixel to white
downloaded_image[100:120, 105:110]=[200,0,180] # change the selected area to purple
cv2_imshow(downloaded_image)Expected text output or note
<PIL.Image.Image image mode=RGB size=512x512>
[visual output omitted; run the code to display the image or chart]