【テスト】pywinautoの簡単な使い方(インストール、共通オブジェクト、要素コントロール、マウス操作、キーボード操作)

1. 説明

pywinauto は、Windows システム ソフトウェア (GUI) に適した自動化用の Python モジュールです。Pywinauto を介してウィンドウ (ダイアログ ボックス) とウィンドウ内のコントロールを移動でき、マウスとキーボードの入力も制御できるため、これまで以上のことができます。 pysimplegui の前に導入されましたさらに表示

2.インストール

通常、インストールには pip を使用します

pip install pywinauto

公式 Web サイトのドキュメント: https://pywinauto.readthedocs.io/en/latest/

3.申請

ソフトウェアを制御したい最初のことは、Windows ソフトウェアを起動することです。各ソフトウェア (プロセス) は Application オブジェクトです。

Application オブジェクトをインスタンス化するときに、バックエンド パラメーターを渡すことができます。オプションの値は ですwin32(默认)和 uia

win32 用のフレームワーク: MFC、VB6、VCL、シンプルな WinForms コントロール、およびほとんどの古いレガシー アプリケーション
uia 用のフレームワーク: WinForms、WPF、ストア アプリ、Qt5、ブラウザー フレームワークには 2 種類あり、使用するものと表示する
ものがあります。どちらかを選択できます。 1 つはより包括的なものです。Inspect と Spy++ は自分でインストールする必要がありますInspect(对应uia)Spy++(对应win32)

Application オブジェクトの主なメソッドは次のとおりです。

方法 共通パラメータ 説明する
始める() cmd_line、timeout、retry_interval cmdコマンドでソフトウェア(プロセス)を起動する
接続する() プロセス、ハンドル、パス、タイムアウト プロセスに接続するには、通常、プロセス番号を使用します (タスク マネージャーで確認できます)。
ウインドウ上部() / アプリケーションのトップレベルウィンドウを取得する
窓() title、title_re、class_name、best_match 単一のウィンドウを取得する (WindowSpecific)
ウィンドウズ() タイトル、タイトルレ、クラス名 複数のウィンドウを取得する (UIAWrapper)
は64ビット() / 64ビットアプリケーションかどうか
CPU使用率 間隔 CPU使用率
wait_cpu_usage_ lower() しきい値、タイムアウト CPU 使用率が特定のしきい値を下回るのを待機します
アクティブ()() / 検索するとアクティブなウィンドウが返されます
殺す() 柔らかい 最終過程
wait_for_process_exit() タイムアウト、再試行間隔 プロセスが終了するまで待ちます

たとえば、WeChat アプリケーションを起動し、プロセス番号を介して接続します。プロセス番号はタスク マネージャーに详细信息表示される PIDです。
タスクマネージャーでプロセス番号を確認する

from pywinauto import Application

app = Application(backend="uia")
# app.start(r"D:\Program Files (x86)\Tencent\WeChat\WeChat.exe")
app.connect(process=6556)
print("is64bit:", app.is64bit())
print("cpu_usage:", app.cpu_usage())
app.wait_cpu_usage_lower()
# app.active()  # 如果指定时间内不激活则报错
print("kill:", app.kill())
print("wait_for_process_exit:", app.wait_for_process_exit())

4.窓の仕様

ウィンドウを取得したいと考えています。ウィンドウは、WindowSpecificationApplication オブジェクトの window() メソッドを通じて取得できるオブジェクトです。パラメータには、title、classname、または best_match などを指定できます。これらは、inspect.exe で確認できます。ただし、表示される名前は実際には window() の title パラメータに対応していることに注意することが重要です。
ここに画像の説明を挿入

WindowSpecific オブジェクトの一般的に使用されるメソッドは次のとおりです。

方法 共通パラメータ 説明する
最大化() / ウィンドウを最大化する
最小化() / ウィンドウを最小化する
復元する() / 回復期間
近い() / 窓を閉めて
get_show_state() / ウィンドウのステータスを取得します。0 通常、1 最大化、2 最小化
was_maximized() / 現在最大化されていますか
描画アウトライン() 色、厚さ 位置決めのためにウィンドウの周囲に枠を描画します
print_control_identifiers() / すべての子ウィンドウと子要素を出力します (対応する control_type が出力されます)。
子ウィンドウ() タイトル、コントロールタイプ 子ウィンドウを取得する
存在します() タイムアウト 窓は存在しますか
待って() wait_for、タイムアウト ウィンドウが特定の状態 (存在、表示、有効、準備完了、アクティブ) になるまで待ちます。
wait_not() 待機しない、タイムアウト ウィンドウが特定の状態 (存在、表示、有効、準備完了、アクティブ) にならないまで待ちます。

栗をあげる

dlg = app.window(class_name="WeChatMainWndForPC")
# dlg = app.window(title="微信")
print("get_show_state:", dlg.get_show_state())
print("was_maximized:", dlg.was_maximized())
dlg.print_control_identifiers()
dlg.draw_outline()
dlg.maximize()
dlg.restore()
dlg.minimize()
dlg.close()

5. 要素コントロール

一般にウィンドウ内には、ボタン(Button)、編集バー(Edit)、ツリービュー(Tree View)、チェックボックス(CheckBox)、ダイアログボックス(Dialog)、ツールバー(Toolbar)、ステータスバー(StatusBar)などのさまざまな要素があります。 )、リスト ボックス (ListBox)、ペイン (Pane)、メニュー (Menu)、メニュー バー (MenuItem)、静的コンテンツ (Static)、ツール ヒント (ToolTips)、リスト コントロール (ListView)、RadioButton、ComboBox、TabControl、GroupBox、ポップアップメニュー、ヘッダーなど

コントロールの種類が多すぎて 1 つずつ学習することはできませんが、それらはすべて、アクセス後にelement_info継承されたオブジェクト (UIAElementInfo または HwndElementInfo) を返すプロパティを持っていますElementInfo。より重要なプロパティまたはメソッドは次のとおりです。

メソッドまたはプロパティ 共通パラメータ 説明する
名前 / 要素の実際の名前 (通常はタイトル)
見える / 要素が表示されるかどうか
リッチテキスト / 要素の完全な名前
矩形 / 要素の位置、幅、高さを返します。
クラス名 / クラス名
有効 / 要素が利用可能かどうか
/ 親要素を返す
子供たち() title、title_re、class_name、best_match 要件を満たす子要素(リスト)を返します。
iter_children() title、title_re、class_name、best_match 適格な子要素を反復処理する (ジェネレーター)

一部の要素の主な情報を取得するだけでなくelement_info、これらの要素も Wrapper にパッケージ化されているため、BaseWrapper共通のメソッドと属性を学ぶこともできます。実際BaseWrapper、これらのメソッドは基本的にElementInfoさらにパッケージ化するためのものであり、次の表に示すように、いくつかのメソッドのみをリストします。

メソッドまたはプロパティ 共通パラメータ 説明する
要素情報 / 返回当前元素的ElementInfo对象
from_point() x、y 通过坐标查找ElementInfo
class_name() / 类名,实际是调用element_info.class_name
friendly_class_name() / 友好的类名,同上
window_text() / 元素的文本,实际是调用element_info.rich_text
is_visible() / 元素是否可见,实际是调用element_info.visible
is_enabled() / 元素是否可用,实际是调用element_info.enabled
rectangle() / 元素的位置和宽高,实际是调用element_info.rectangle
process_id() / 进程号,实际是调用element_info.process_id
draw_outline() colour、thickness 给当前元素画个框
click_input() button、coords、double 鼠标操作,实际是调用mouse模块的_perform_click_input()
type_keys() / 键盘操作,实际是调用keyboard模块的send_keys()
dlg = app.window(class_name="WeChatMainWndForPC")
list_data = dlg.child_window(title="会话", control_type="List")
for item in list_data:
    print(type(item))
    element_info = item.element_info
    print(type(element_info))
    print("window_text:", )
    print("rich_text:", element_info.rich_text)
    print("name:", element_info.name)
    print("visible:", element_info.visible)
    print("rectangle:", element_info.rectangle)
    print("class_name:", element_info.class_name)
    print("enabled:", element_info.enabled)
    print("parent:", element_info.parent)
    print("children:", element_info.children())
    print("iter_children:", element_info.iter_children())
    if item.window_text() == "文件传输助手":
        item.click_input()
        item.type_keys("冰冷的希望")
        item.type_keys("{VK_RETURN}")
    print()

说明一下,每个控件元素都有对应的Wrapper,所以上面的方法也不一定都用,需要根据实际情况进行测试区分。另外,比较有用的click_input()type_keys()这两个方法分别用于操作鼠标和键盘(输入),下面我会单独拿出来说一下

6.鼠标操作

鼠标点击肯定离不开点击的位置,桌面就是一个坐标,左上角为坐标原点,往右是X轴正向,往下是Y轴正向。pywinauto提供了一个mouse模块用于鼠标操作,最核心的方法是_perform_click_input(),不过它是一个私有方法,我们调用的是基于它的封装方法,如下表

方法 参数
click() button、coords 单击鼠标某个键
double_click() button、coords 双击鼠标某个键
right_click() coords 单击鼠标右键
move() coords 移动鼠标
press() button、coords 按下鼠标
release() button、coords 放开鼠标
scroll() coords、wheel_dist 滚动鼠标滚轮
wheel_click() coords 单击鼠标滚轮

参数说明:
参数button的默认值都是“left”,即鼠标左键,可选值有left、right、middle、move、wheel、x
参数coords 的默认值都是元组(0, 0),元组里的两个整数分别是X、Y轴的值
参数wheel_dist表示滚动的距离,大于0是向上滚动,小于0是向下滑动

举个栗子

from pywinauto import Application, mouse

app = Application(backend="uia")
app.connect(process=4352)
dlg = app.window(class_name="WeChatMainWndForPC")
list_data = dlg.child_window(title="会话", control_type="List")
for item in list_data:
    if item.window_text() == "文件传输助手":
        # item.click_input()
        rectangle = item.element_info.rectangle
        x = int((rectangle.left + rectangle.right) / 2)
        y = int((rectangle.top + rectangle.bottom) / 2)
        mouse.click(button='left', coords=(x, y))
        time.sleep(1)
        mouse.click("right", (x, y))
        time.sleep(1)
        mouse.move((x - 50, y))  # 往左边移动50个像素
        time.sleep(1)
        mouse.click(coords=(x, y))
        break

7.键盘操作

键盘操作主要是按下键盘上的按键,相关方法在keyboard模块,最最主要的是send_keys()方法,第一个参数keys就是我们需要按下的按键,其他参数比如说with_spaces、with_tabs、with_newlines、turn_off_numlock、set_foreground、vk_packet,一看就知道作用,而且都是布尔值,此处不进行举例

pywinauto支持的完整的按键可以在官方文档查看,https://pywinauto.readthedocs.io/en/latest/code/pywinauto.keyboard.html
下面我列举出的是一些比较常用的按键

按键 符号 说明
Shift VK_SHIFT 上档键
Ctrl VK_CONTROL、VK_LCONTROL、VK_RCONTROL Ctrl键、左右Ctrl键
Alt VK_MENU Alt键
Windows VK_LWIN、VK_RWIN 左右win键
Space VK_SPACE 空格键
backspace BACKSPACE 退格键
enter ENTER 回车键
esc ESC 退出键
table VK_TAB 制表键
left、right、up、down VK_LEFT、VK_RIGHT、VK_UP、VK_DOWN 上下左右方向键
f1~f24 VK_F1、VK_F2…VK_F24 f1~f24
キャップスロック キャップスロック 大文字キー

手順:
1. ボタンを使用する場合は中かっこが必要です。たとえば、Enter キーを押すと '{ENTER}' (是字符串)
2. Windows プラットフォームでは、デフォルトで仮想ボタンが送信され、VK_で始まるボタンはすべて仮想ボタンです。VK_プレフィックスを削除してvk_packetパラメータを変更してください。 send_keys() のFalse宛先

単一のボタンを押したり離したりするだけでは十分ではありません。多くの場合、キーの組み合わせが必要です。このとき、修飾子が必要です。中かっこで使用して、ボタンを押したり離したりするタイミングを制御できます。数字を追加するdownup、その後に、押された回数が表示されます。

list_data = dlg.child_window(title="会话", control_type="List")
for item in list_data:
    if item.window_text() == "文件传输助手":
        item.click_input()
        # item.type_keys("冰冷的希望")
        send_keys("   ")  # 随便输入字符串
        send_keys("{VK_CONTROL down} a {VK_CONTROL up}")  # 快捷键Ctrl+a(先按下Ctrl,再按下a,最后放开Ctrl)
        send_keys("{BACKSPACE}")  # 按下退格键删除文本
        send_keys("{. 6}")  # 按6次小数点
        send_keys("冰冷的希望{ENTER}")  # 输入文本,按下回车键

もちろん、多くの場合、使用downと変更は十分に簡潔ではないため、 pywinauto は、「代わりに使用」 、「代わりに使用」 、「代わり使用」upという簡略化された書き方も提供します。+{VK_SHIFT}^{VK_CONTROL}%{VK_MENU}

send_keys('^a^c') # 按下Ctrl+a之后再按下Ctrl+c,即全选复制
send_keys('+{INS}') # 按下Shift+Ins键
send_keys('%{F4}') # 按下Alt+F4键

ボタンを押さずに単純な文字列を入力したい場合は、エスケープを解除する必要があります。修飾子とボタンの書き方が異なることに注意してください。

send_keys('{^}a{^}c{%}') # 输入字符串"^a^c%"而不是当成快捷键
send_keys('{
    
    {}ENTER{}}') # 输入字符串"{ENTER}"而不是按下回车键

おすすめ

転載: blog.csdn.net/qq_39147299/article/details/132409817