Steel Hard
Steel Hard

Reputation: 37

Pixel is there but .getpixel isn't detecting it

I'm currently having an issues with my program that im not too sure how to fix.

I am doing the following:

x = 0
y = 0
im = ImageGrab.grab()
time.sleep(1)
while True:
    xy = (x, y)
    x = x + 1
    if im.getpixel(xy) == (0,158,187):
        time.sleep(0.3)
        pyautogui.click(x,y)
        break
    if x >= 1200:
        x = 0
        y = y + 1
        print('cant find pixel')
    if y >= 950:
        y = 0
        x = 0

And it works about 90% of the time and then theres this random time it just says it can't detect the pixel despite the pixel being there 100%.

EDIT: Managed to catch the following error in the 10% it happens:

AttributeError: 'NoneType' object has no attribute 'getpixel'

Which makes no sense since I'm doing im = ImageGrab.grab() beforehand and it works 90% of the time

Upvotes: 1

Views: 684

Answers (1)

Mark Setchell
Mark Setchell

Reputation: 207670

You should check your ImageGrab() was successful before using the data, so something like:

im = ImageGrab.grab()
if im is not None:
   processImage

You'll be there all day if you run double for loops over an image and call a function for every one! Try to get in the habit of using Numpy vectorised code for images in Python.

Basically, you appear to be testing if any pixel in your 1200x950 image matches all three RGB components (0,158,187).

You can do that with Numpy like this:

 np.any(np.all(na==(0,158,187), axis=-1))

In the demo below the double for loops take 800ms and the Numpy test takes 20ms, so 40x faster.

#!/usr/bin/env python3

import numpy as np
from PIL import Image

def loopy(im):
   for x in range(im.width):
      for y in range(im.height):
         if im.getpixel((x,y)) == crucialPixel:
            return True

   return False


def me(im):
    # Make image into Numpy array
    na = np.array(im)
    # Test if there is any pixel where all RGB components match crucialPixel
    return np.any(np.all(na==crucialPixel, axis=-1))

# Define our beloved crucial pixel
crucialPixel = (0,158,187)

# Construct a new, solid black image
im = Image.new('RGB', (1200,950))

# Neither should find crucialPixel in black image
result = loopy(im)
result = me(im)

# Insert the crucial pixel
im.putpixel((600,475), crucialPixel)

# Both should find crucialPixel
result = loopy(im)
result = me(im)

Upvotes: 1

Related Questions