2

wx(およびwxPython)には、PyQtで見逃している2つのイベントがあります。

  • EVT_IDLEそれはフレームに送信されています。アプリケーションの状態に応じて、さまざまなウィジェットを更新するために使用できます
  • EVT_UPDATE_UIウィジェットを再描画して更新する必要があるときにウィジェットに送信されるので、ハンドラーでその状態を計算できます

さて、PyQtにはこれらがないようで、PyQtの本はupdateUiメソッドを書いてそれを手動で呼び出すことを提案しています。GUIを更新する可能性のあるメソッドからの多くの手動呼び出しを回避するために、タイマーから0.1秒に1回呼び出すことになりました。私は何かが足りないのですか?これを達成するためのより良い方法はありますか?


例:いくつかの処理を開始するスタートボタンを備えたシンプルなアプリがあります。スタートボタンは、メニューを使用してファイルを開いた場合にのみ有効にする必要があります。さらに、ステータスバーには情報を表示する永続的なウィジェットがあります。

私のアプリケーションには次の状態があります。

  1. ファイルを開く前(この状態では、ステータスバーに何か特別なものが表示され、スタートボタンが無効になっています)
  2. ファイルが開かれ、処理が開始されませんでした:スタートボタンが有効になり、ステータスバーに何か他のものが表示されます
  3. 処理が実行中です。スタートボタンに「停止」と表示され、ステータスバーに進行状況が報告されます。

Wxでは、ボタンのUI更新イベントでその状態を処理します。つまり、アプリケーションの状態に応じて、ボタンのテキストと、ボタンが有効になっているかどうかを処理します。ステータスバーについても同じです(または、EVT_IDLEを使用します)。

Qtでは、状態に影響を与える可能性のあるいくつかのメソッドでボタンを更新するか、update_uiメソッドを作成してタイマーで定期的に呼び出す必要があります。より「QT」っぽい方法は何ですか?

4

4 に答える 4

5

wxWidgets での EVT_UPDATE_UI の使用は、wxWidgets と Qt が開発者にコード内のイベントの処理を期待する方法の根本的な違いの 1 つを浮き彫りにしているようです。

Qt では、ユーザー インターフェイスのウィジェット間でシグナルとスロットを接続し、各スロットで「ビジネス ロジック」を処理するか、専用のメソッドに委譲します。再描画要求はすべてイベント キューに配置され、制御がイベント ループに戻ったときに配信されるため、通常、GUI の各ウィジェットに個別の変更を加える必要はありません。いくつかのペイント イベントは、効率のために一緒にマージされることさえあります。

そのため、信号とスロットを使用して状態の変化を処理する通常の Qt アプリケーションでは、アプリケーションの状態を監視してウィジェットを更新するアイドル メカニズムは基本的に必要ありません。これらの更新は自動的に行われるはずだからです。

Qt でこのイベントに相当するものが必要な理由を説明するには、何をしているのかについてもう少し説明する必要があります。

于 2009-03-09T01:40:31.297 に答える
2

状態の変化を示すために Qt シグナルを送信します (例: fileOpened、processingStarted、processingDone)。アイドル イベントで現在の状態を「ポーリング」するのではなく、スタート ボタンとステータス バー ウィジェット (またはサブクラス) を管理するオブジェクトのスロットをこれらのシグナルに接続できます。

シグナルをすぐにではなく後でイベント ループ内で遅延させたい場合 (たとえば、何かを実行するのに少し時間がかかるため)、通常の種類ではなく、"キューに入れられた" シグナルスロット接続を使用できます。

http://doc.trolltech.com/4.5/signalsandslots.html#signals

接続タイプは connect() 関数のオプション パラメータです: http://doc.trolltech.com/4.5/qobject.html#connecthttp://doc.trolltech.com/4.5/qt.html#ConnectionType-列挙

于 2009-03-09T14:06:54.310 に答える
1

私が理解している限り、アプリケーション メッセージ キューが空のときに EVT_IDLE が送信されます。Qt にはそのようなイベントはありませんが、保留中のイベントがないときに Qt で何かを実行する必要がある場合は、QTimer を 0 タイムアウトで使用する必要があります。

于 2009-03-08T21:04:37.683 に答える
1

一般に、より Qt っぽい方法は、更新が必要な関数で必要に応じてボタン/ツールバーを更新するか、機能の一部を統合して、プログラムが必要なときにその関数を直接呼び出すことです (updateUi 関数など)。

Qt では、Ui 要素の属性を変更してもすぐに再描画が行われるのではなく、イベント システムで再描画がキューに入れられ、可能な場合は複数の再描画呼び出しが 1 つに圧縮されることに注意してください。

状態に関連する複数の変更については、状態をより簡単に処理するための Qt への今後の追加について、このブログ投稿をご覧ください。複数の関数で状態変数を遷移させるだけで、UI の他の部分が一致するように更新されるため、これで多くの不満が解消されるようです。これが次の Qt リリースに組み込まれるかどうかは定かではありません (私はそれに賭けるでしょうが)。また、PyQt が Qt リリースをどれほど密接に追跡しているかはわかりません。または、この概念を使用して独自のクラスを作成し、必要に応じて状態を追跡することもできます。

于 2009-03-09T18:31:03.723 に答える