是否可以 pyscreeze.locate(needleImage, haystackImage): 每次都不从文件中读取 haystackImage?

问题描述

我目前正在使用 pyautogui 作为在 needleImage搜索 haystackImage 的定位函数。文档提供的示例采用图像路径。但是,我有一个函数可以将一系列 needleImage 与单个 haystackImages 进行比较,并且读取同一个图像文件需要检查的次数非常低效。

有没有办法避免每次都读heystackImage?如果没有,pyautogui/pyscreeze 的使用 bufferedImage 的 locate 函数有什么替代方法吗?

...
checks = {
        "recieve.png": 'recieve',"next.png": 'next',"start.png": 'start',"black.png": 'loading',"loading.png": 'loading',"gear.png": 'home',"factory.png": 'factory',"bathtub.png": 'bathtub',"refit.png": 'refit',"supply.png": 'supply',"dock.png": 'dock',# SPE
        "spepage.png": 'spe',"expeditionpage.png": 'expedition',"sortiepage.png": 'sortie',"practice.png": 'practice',"practiceinfo.png": 'practice',"oquest.png": 'quest',"quest.png": 'quest'
    }
    for key in checks:
        if (detect(key,cache=True)):
            return checks[key]
def detect(imgDir,confidence=0.85,cache=False):
    if (pyautogui.locate(os.path.join('images',imgDir),'images\\capture.jpeg',confidence=confidence)) is not None:
        return True
    else:
        return False

解决方法

pyautogui.locate() 还接受 numpy 数组和 PIL 图像作为输入。您可以将 haystack 图像读入一个 numpy 数组 (BGR) 或 PIL 图像,然后传递它而不是文件名。

def detect(imgDir,haystackImage,confidence=0.85,cache=False):
    if (pyautogui.locate(os.path.join('images',imgDir),confidence=confidence)) is not None:
        return True
    else:
        return False

from matplotlib import image
hsImage = image.imread('images\\capture.jpeg')
hsImage = hsImage[:,:,::-1] # convert RGB to BGR
detect('needleImg.png',hsImage,cache=True)

# Alternate method
from PIL import Image
hsImage = Image.open('images\\capture.jpeg')
detect('needleImg.png',cache=True)

第二种方法可能比第一种方法慢,因为 pyautogui.locate() 最终将 PIL 图像作为 numpy 数组加载,这需要额外的处理。