Reputation: 111
I'm trying to create a for-loop function that will run through every pixel to add contrast to the image. I think I'm close, but right now the image only brightens. If possible, try your best to stick closely to what I have formulated already (FYI, I'm trying to avoid libraries like OpenCV). Thanks for any contributions.
def contrast(img):
for x in range(img.size[0]):
for y in range(img.size[1]):
if (x, y) > 128:
(r, g, b) = img.getpixel((x, y))
img.putpixel((x, y), (r+80, g+80, b+80))
else:
if(x, y) < 128:
(r, g, b) = img.getpixel((x, y))
img.putpixel((x, y), (r-80, g-80, b-80))
Upvotes: 2
Views: 2688
Reputation: 123463
The problem you're having is that the (x, y) > 128
is comparing a tuple to a single value which is probably not what you want to. The other problem is img.getpixel((x, y))
returns a tuple of three separate color components for RGB images, not the brightness of pixel.
What you need is an image processing technique that will change the contrast of color images. I found an article titled Image Processing Algorithms Part 5: Contrast Adjustment that describes a simple way to do it.
Here's an implementation of it using the pillow
version of PIL
(the Python Imaging Library) module:
from PIL import Image
# level should be in range of -255 to +255 to decrease or increase contrast
def change_contrast(img, level):
def truncate(v):
return 0 if v < 0 else 255 if v > 255 else v
if Image.isStringType(img): # file path?
img = Image.open(img)
if img.mode not in ['RGB', 'RGBA']:
raise TypeError('Unsupported source image mode: {}'.format(img.mode))
img.load()
factor = (259 * (level+255)) / (255 * (259-level))
for x in range(img.size[0]):
for y in range(img.size[1]):
color = img.getpixel((x, y))
new_color = tuple(truncate(factor * (c-128) + 128) for c in color)
img.putpixel((x, y), new_color)
return img
result = change_contrast('test_image1.jpg', 128)
result.save('test_image1_output.jpg')
print('done')
Here's the results of a test run I did showing the before image on the left and the resulting image on the right — and it looks like it works:
Upvotes: 1
Reputation: 117681
These lines:
if (x, y) > 128:
Should be comparing the brightness of a pixel to 128, and not pixel coordinates.
Upvotes: 2