opencv实现元素的图片坐标定位

桌面应用程序的UI自动化,除了解析应用层级控件外,还可以通过图片定位获取目标元素位置,对其进行点击、双击、滚动等操作。
python可用opencv库操作图片。

opencv安装

  • sudo apt install python-opencv

图片比对

import cv2
import pyautogui

def match_img(small_image, big_image=None, confidence_value=0.9):
    """
    small_image: 目标图片的路径
    big_image: 需要匹配的图片,在大图中去匹配目标图片
    confidence_value: 匹配度,0-1
    """
    # 屏幕截图
    screen = pyautogui.screenshot()
    screen.save('/tmp/screen.png')
    # 获取屏幕截图数组信息
    screen_array = cv2.imread('/tmp/screen.png')
    if big_image:
        # 获取大图的数组信息
        big_img_array = cv2.imread('/tmp/screen.png')
        # 先获取大图在屏幕中的位置
        res = cv2.matchTemplate(screen_array, big_img_array, cv2.TM_CCOEFF_NORMED)
        # 从一个矩阵中找出全局的最大值和最小值
        minmax = cv2.minMaxLoc(res)
        # 取匹配度最大的坐标,这个也代表了大图的顶点坐标
        pos_start_big = minmax[3]
    else:
        # 如果没有传入大图,则用屏幕截图当做大图
        big_img_array = screen_array
        pos_start_big = [0, 0]

    # 获取目标图片的数组信息
    small_img_array = cv2.imread(small_image)
    # 调用matchTemplate方法进行匹配,cv.TM_CCOEFF_NORMED是匹配的方法:该方法使用归一化的平方差进行匹配,最佳匹配在结果为0处
    res = cv2.matchTemplate(big_img_array, small_img_array, cv2.TM_CCOEFF_NORMED)
    # 从一个矩阵中找出全局的最大值和最小值
    minmax = cv2.minMaxLoc(res)
    # 取匹配度最大的坐标,注意这是相对大图的顶点坐标
    pos_start = minmax[3]
    # 匹配对象的中心坐标x y,这里获取的是绝对坐标
    x = int(pos_start_big[0] + pos_start[0]) + int(small_img_array.shape[1] / 2)
    y = int(pos_start_big[1] + pos_start[1]) + int(small_img_array.shape[0] / 2)

    # 取最大的匹配度值
    similarity = minmax[1]
    # 如果匹配度不满足条件,直接返回空
    if similarity < confidence_value:
        return None
    # 否则返回目标图片的中心位置
    return x, y

# 调用方法
res = match_img('./img.png', './img_1.png', confidence_value=0.9)
# 通过鼠标移动验证获取的图片位置正确
pyautogui.moveTo(res[0], res[1])

以上代码实现了一个图片匹配方法,返回匹配到的图片坐标。有2种使用方式:

  1. 直接传入目标图片,这样会在整个屏幕截图中查找目标图片;
  2. 在一张大图中匹配目标图片,返回的也是目标图片的绝对坐标位置;
<think>嗯,用户想提高PyAutoGUI截图的清晰度。首先,我需要考虑截图清晰度可能受哪些因素影响。屏幕本身的分辨率应该是一个关键点,如果屏幕分辨率低,截图自然不清晰。所以建议用户检查显示设置,确保分辨率调到最高。然后,缩放设置也可能有影响,特别是在Windows系统里,如果缩放比例不是100%,截图可能会模糊。比如125%或150%的缩放会让图像拉伸,导致截图不清晰。 接下来,PyAutoGUI截图默认的region参数是整数,但如果有缩放,可能需要调整坐标和尺寸。比如系统缩放125%,那么实际截图区域可能需要乘以1.25。不过用户可能需要用其他方法获取准确的坐标,比如用pygetwindow库来获取窗口的真实坐标。 然后,截图后的处理也很重要。使用OpenCV的插值方法,比如cv2.INTER_CUBIC或cv2.INTER_LANCZOS4,可以在放大图像时保持清晰度。另外,锐化处理也能提升清晰度,比如用高斯滤波器和核运算来增强边缘。还有,保存图片时选择高质量压缩,比如调整JPEG的质量参数到95以上,或者使用无损格式如PNG。 硬件方面,外接高分辨率显示器或者调整显卡设置可能会有帮助。比如确保显卡驱动是最新的,关闭可能影响画质的后期处理效果。 最后,可能需要结合其他库,比如D3DShot来提高截图速度和质量,或者PIL库进行图像处理。用户可能需要实际测试不同方法的效果,找到最适合他们系统设置的方案。</think>### 提高PyAutoGUI截图清晰度的方法 1. **调整屏幕分辨率与缩放设置** - **系统显示设置**:在操作系统中将分辨率设置为最高值(如$3840 \times 2160$),并确保缩放比例设置为$100\%$。Windows系统中,非整数缩放(如$125\%$)可能导致截图模糊[^1]。 - **代码适配缩放**:若系统缩放非$100\%$,需在代码中对截图区域坐标和尺寸进行比例换算: ```python scale_factor = 1.25 # 根据实际缩放比例调整 scaled_region = (int(x * scale_factor), int(y * scale_factor), int(width * scale_factor), int(height * scale_factor)) screenshot = pyautogui.screenshot(region=scaled_region) ``` 2. **优化截图参数与后处理** - **抗锯齿处理**:使用OpenCV的插值算法提升放大后的图像质量: ```python resized_image = cv2.resize(image, (new_width, new_height), interpolation=cv2.INTER_LANCZOS4) ``` - **锐化滤波**:通过卷积核增强边缘清晰度: ```python kernel = np.array([[-1,-1,-1], [-1,9,-1], [-1,-1,-1]]) sharpened_image = cv2.filter2D(image, -1, kernel) ``` - **保存优化**:使用无损压缩格式(如PNG)或调整JPEG质量参数: ```python cv2.imwrite('high_quality.png', image, [cv2.IMWRITE_PNG_COMPRESSION, 0]) cv2.imwrite('high_quality.jpg', image, [cv2.IMWRITE_JPEG_QUALITY, 95]) ``` 3. **硬件与驱动优化** - 外接高DPI显示器(如$4K$分辨率)可显著提升原始截图质量。 - 更新显卡驱动并关闭动态对比度、抗锯齿等后处理功能[^1]。 4. **替代方案(针对高性能需求)** - 使用`D3DShot`库直接访问GPU帧缓存,避免缩放干扰: ```python import D3DShot d = D3DShot.create() image = d.screenshot(region=(x, y, x+width, y+height)) ``` --- ###
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值