zoukankan      html  css  js  c++  java
  • python学习——截图工具编写

    学习一门语言最好的方法便是实践,想要拿Python写一个截图工具,网上一搜资料果然已经很多,前辈们都已经做的很到位了。现在就一步步来学习一下:

    首先学习截图整个桌面的方法,可以使用Python中的PIL(Python Imaging Library)库里边的ImageGrab.grab()函数来获取截图。然后使用save()函数将图片保存下来。简单的不能再简单了,源码如下:

    from PIL import ImageGrab
    pic = ImageGrab.grab()
    pic.save("D:\picture.jpg")


    这样我们便可以将整个桌面截图保存在D盘根目录下。So easy。另外关于图片存储格式,使用save()函数保存时路径中文件格式为jpg、bmp、png均可,亲测可行,bmp格式存储空间最大,理论上来说数据失真率也最低。

    下面我们考虑如何将当前窗口截图保存,ImageGrab.grab()函数没有参数时默认将整个屏幕截图,当我们给它传递一个矩形的坐标时,它便可以将制定矩形进行截图。同时这里我们需要在python中调用win32的GUI函数来获取当前窗口的句柄、进而获取当前窗口的位置坐标。同时,我们需要在python中定义一个结构体来存储获取的坐标值,于是我们又学习了python中结构体的定义以及win32 gui函数调用的方法,源码如下:

    import win32gui
    from ctypes import *
    import ctypes
    from PIL import ImageGrab
    import win32api,win32con
    import pyHook
    import pythoncom
    
    #定义结构体,存储当前窗口坐标
    class RECT(ctypes.Structure):
        _fields_ = [('left', ctypes.c_int),
                    ('top', ctypes.c_int),
                    ('right', ctypes.c_int),
                    ('bottom', ctypes.c_int)]
    rect = RECT()
    HWND = win32gui.GetForegroundWindow()#获取当前窗口句柄
    ctypes.windll.user32.GetWindowRect(HWND, ctypes.byref(rect))#获取当前窗口坐标
    coordinate = (rect.left+2, rect.top+2, rect.right-2, rect.bottom-2)#转换为预截图窗口坐标
    pic = ImageGrab.grab(coordinate)#截图
    pic.save("D:\321.jpg")#保存

    其中ctypes中的byref()方法是用来返回结构体的指针,从而将窗口坐标存储在结构体中。

    在实现了全屏截图以及指定窗口截图以后,我们便需要考虑如何实现指定范围截图。我的思路是利用pyHook工具包实现对鼠标事件的监听,在鼠标左键按下时,记录一个坐标,鼠标左键抬起时再记录一个坐标,于是便可以确定整个所要截图区域的矩形坐标,再使用ImageGrab.grab(coordinate)函数实现截图。源码如下:

    coordinate = [1,1,1,1]
    #监听键盘事件
    def on_mouse_event(event):
        if event.MessageName == 'mouse left down':
            coordinate[0:2] = event.Position
        elif event.MessageName == 'mouse left up':
            coordinate[2:4] = event.Position
            win32api.PostQuitMessage()#退出监听循环
            pic = ImageGrab.grab(coordinate)
            pic.save("D:\321.jpg")
        return True
    
    hm = pyHook.HookManager()#创建一个钩子管理对象
    hm.MouseAll = on_mouse_event#监听所有鼠标事件
    hm.HookMouse()#设定鼠标钩子
    pythoncom.PumpMessages()#进入循环,程序一直监听


    这里我们在鼠标完成截图矩形坐标确定后,需要推出鼠标事件的监听。另外,目前存在一个问题,在用鼠标选取范围时会导致窗口焦点的改变,从而影响实际截图内容。因此可以进一步考虑先将屏幕锁定,再进行范围选定。或者也许可以先进行全屏截图,但仅显示而不保存,在显示的全屏截图上再进行区域截图。

    恩,好了,一步步来,慢慢学习。菜鸟慢飞。



  • 相关阅读:
    Java n个线程轮流打印数字的问题
    【我所认知的BIOS】—> uEFI AHCI Driver(6) AtaAtapiPassThruSupported的局部变量们
    设备树学习之(二)点灯【转】
    设备树学习之(一)GPIO中断【转】
    S5PV210开发板 VGA测试【转】
    Linux VGA驱动移植实验【转】
    略过天涯 深入浅出VGA和DVI接口【转】
    基于FPGA的VGA可移植模块终极设计【转】
    字符串函数---strcmp()与strncmp()详解及实现【转】
    关于内存中栈和堆的区别(非数据结构中的堆和栈,区别)
  • 原文地址:https://www.cnblogs.com/pangblog/p/3290172.html
Copyright © 2011-2022 走看看