PR

PythonのGUIが固まる理由とThreadの使い方【XYテーブル自作 第8.5回】

RaspberryPi
スポンサーリンク

はじめに

XYテーブル製作シリーズ 第8.5回

スポンサーリンク

はじめに:なぜ Thread を使う必要があるのか

第8回でTkinterのGUIからXYテーブルを操作できるようになりました。しかし、なぜ Thread を使う必要があるのでしょうか? Thread を使わないと、GUIは簡単に固まってしまいます。今回はその理由と、Threadによる解決方法を解説します。

この記事で分かること

  • GUIは「イベントループ」で動いていて、それは1つのメインスレッドで回っている
  • 時間のかかるモーター処理を同じスレッドで実行するとイベント処理が止まる=GUIが固まる
  • threading.Thread でモーター処理を別スレッドに逃がすとGUIが止まらない
  • ThreadからGUIを直接触るとエラーになるので queue.Queue で通信する(定番パターン)

スポンサーリンク

GUIプログラムの仕組み(イベントループ)

Tkinterなどの GUI はイベントループで動いています。

イベント待ち → ボタンが押された? → 処理実行 → 画面更新 → イベント待ち …

この処理は1つのスレッド(GUIメインスレッド)で回っています。

スポンサーリンク

GUIが固まる原因

ボタンを押したときにモーター制御を直接実行するとします。

def start_xy():
    run_motor()   # forループ → GPIO制御 → time.sleep() を数千回

この処理は数秒〜数十秒かかります。しかもGUIメインスレッドで実行されるため、その間イベント処理が止まります。

GUIスレッド → モーター処理(長時間)→ イベント処理停止
→ 画面更新されない・ボタン押せない・ウィンドウ動かない = GUIが固まる

スポンサーリンク

Threadで解決する

そこで threading.Thread を使い、モーター処理を別スレッドで実行します。

threading.Thread(
    target=run_motor,
    args=(...)
).start()

すると処理が分かれます。

  • GUIスレッド:画面更新・ボタン操作を受け付け続ける
  • モータースレッド:裏でGPIO制御・ステップループを回す

結果、GUIは操作可能なまま、モーターは裏で動く状態になります。

スポンサーリンク

XY同時制御にもThreadが必要

XYテーブルでは2軸を同時に動かします。XモーターThread と YモーターThread を作れば、XY同時移動ができます。


スポンサーリンク

Threadの問題:GUIとの通信

Threadには問題もあります。GUIスレッド以外から直接GUIを操作するとエラーになることがあるのです(現在位置表示・エラー表示・完了通知など)。

解決方法:queue.Queue

message_queue = queue.Queue()

# モータースレッド側:メッセージを送るだけ
message_queue.put(("pos", axis, current_mm))

# GUIスレッド側:root.after で定期的に取り出して画面更新

モータースレッドは Queue にメッセージを入れるだけ、GUIスレッドが Queue から取り出して画面を更新する——これが Python GUI設計の定番パターンです。実装は第9回で行います。


スポンサーリンク

まとめと次回予告

  • GUIはイベントループ(1メインスレッド)で動く
  • モーター処理は時間がかかる → 同じスレッドで実行するとGUIが固まる
  • Threadを使うとGUIが止まらない
  • Thread → GUI の通信には Queue を使う

次回・第9回では、この設計を踏まえて原点復帰GUI・現在位置表示・ソフトリミットを実装し、本格的なXYテーブルコントローラにします。

次に読む記事

🏠 次回はこちら(第9回) XYテーブルGUIに原点復帰・現在位置表示・ソフトリミットを実装|Queueでスレッド安全にGUI更新 Queueパターンを実際に実装する。 → 🖥️ 前回(第8回) PythonのTkinterでXYテーブルをGUI操作する|移動量入力・XY同時実行・緊急停止ボタン GUIの土台になったコード。 → 🗺️ 全体像 自作XYテーブルの全手順ロードマップ|Raspberry Pi+ステッピングモーターで2軸制御 第0回〜第11回の全工程をまとめたロードマップ。 →

スポンサーリンク

よくある質問(FAQ)

Qtime.sleep をやめれば Thread なしでもGUIは固まりませんか?

Atime.sleep 中もループ自体がGUIメインスレッドを占有するので、sleepを短くしても数千回のステップ出力の間GUIは固まります。root.update() を挟む方法もありますが、応答が不安定になりがちで、別スレッド化のほうが素直です。

Qthreading と multiprocessing はどちらを使うべきですか?

AGPIO制御やtime.sleep主体の待ち処理は threading で十分です(GILの影響が小さい)。CPUをフルに使う重い計算を並列化したいときだけ multiprocessing を検討します。XYテーブル制御は threading が定番です。

QThreadからGUIを直接更新したらたまたま動きました。

ATkinterはスレッドセーフではなく、別スレッドからのGUI操作は「動くこともあるが、たまにクラッシュ・フリーズする」不安定な状態です。queue.Queue + root.after でメインスレッドに処理を戻すのが安全です。

Q緊急停止はThreadをどう止めればいいですか?

APythonのスレッドは外部から強制終了できません。グローバルなフラグ(stop_flag = True)を立て、モーターループが毎回それをチェックして return する「協調的キャンセル」を使います。あわせて GPIO.output(EN, HIGH) で電流も切ります。


スポンサーリンク

XYテーブル製作シリーズ(全12回)

補足記事

⚡ 第1.5回・補足 A4988の電流制限(Vref)調整方法|焼損を防ぐ計算式とテスターでの設定手順 モーターを回す前に必ずやる A4988 の電流調整。 → 🔀 番外編 L6470が動かない原因|A4988との違いとSPI通信・デイジーチェーンの罠 高機能ドライバ L6470 を A4988 と同じ感覚で使ってハマった話。 → 🗺️ 全体像 自作XYテーブルの全手順ロードマップ|Raspberry Pi+ステッピングモーターで2軸制御 第0回〜第11回の全工程をまとめたロードマップ。 →

ニンジン🥕アイコン

Follow me on X

本ブログの中の人「ニンジン🥕」はXやってます。新着記事はいち早くポストでお知らせしているので、見逃したくない方は @ninjin_py_vba をフォローしてみてください🥕

@ninjin_py_vba をフォロー

この記事が役に立ったら、シェアしてもらえると嬉しいです🥕

Xでポスト はてブ LINE Pocket

PROJECT LOG — SERIES INDEX
スポンサーリンク

シリーズ記事一覧

電子工作・自動化ツールの製作記録をシリーズごとにまとめています。気になるテーマからお読みください。


GPSロガーのCSVを地図に表示する方法|Pico 2 WでGT-502MGG-NとATGM336Hを車に積んで走行・トンネル比較【Python・folium】
GPSロガーで記録したCSVを、Pythonのfoliumと地理院タイルで地図に表示する方法。GT-502MGG-NとATGM336Hを車に積んで4回走り、再起動の原因やトンネルでの違いも比べました。
今週の注目ガジェット〜10/19週〜|電子工作・自作向け新製品まとめ(Romu/W1700K SDR ほか)
大手が拾わないニッチな新製品を毎週チェック。今週はe-Paper開発キット、超小型USBボード、自作SDRなど5本立て。
GT-502MGG-NとATGM336Hの使い方|Raspberry Pi Pico 2 WとMicroPythonでGPSを受信して2台を比較
GT-502MGG-NとATGM336Hの使い方を、Pico 2 W×MicroPythonで解説。北斗で衛星数が多いATGM336H、信号が強いGT-502MGG-N。単精度floatで緯度経度が約1.4m刻みになる落とし穴も紹介します。
今週の注目ガジェット〜10/12週〜|電子工作・自作向け新製品まとめ(Q8botOne/Sipeed SLogic32U3 ほか)
大手が拾わないニッチな新製品を毎週チェック。今週は四足歩行ロボット、ロジックアナライザー、広告ブロッカーなど5本立て。
MOSFETはPicoの3.3Vで足りる?DCソレノイド駆動でゲート電圧不足を実測【Pico 2 W】
Pico 2 WとMOSFET(IRLU3410)で12VのDCソレノイドを駆動。ゲート3.3Vでは発振し、オン抵抗も約2.4倍に。レベル変換で5V駆動にした比較と、電流が8割止まりだった本当の原因を実測で紹介します。
まとめハブ
RaspberryPiXYテーブル自作しようハードウェア制御 / 電子工作
スポンサーリンク

コメント