これは私にとって特別な問題ではないと思います。誰もがこの問題に遭遇したことがあるかもしれません。適切に説明するために、単純な UI を次に示します。
ご覧のとおり、これら 2 つのスピナーは単一の変数「A」を制御しています。唯一の違いは、異なるビューを使用して制御することです。
この 2 つのスピナーの表示値は同期しているため、周期的なイベントが表示されます。
上のスピナーを変更すると、「A」が変更され、それに応じて下のスピナーの値も更新されます。ただし、下部スピナーの呼び出し (setValue など) を更新すると、下部スピナーの値に基づいて更新するように上部スピナーに指示する別のイベントもトリガーされます。したがって、最終的に StackOverFlow 例外を引き起こす可能性のある悪いサイクルが作成されます。
私の以前の解決策はちょっと面倒です.2番目の更新呼び出しを実行する必要があるかどうかを示すために、保護ブール値を配置しました。
ここで、「どうすればそのような状況をエレガントに処理できますか? (一般的に、スピナーに固有ではありません)」と尋ねたいと思います。
どうも
アップデート:
オブザーバー構造を利用することを示唆する2つの回答があるので、それについて何か言わなければなりません。
私が言ったように、それは素晴らしいですが、完璧には程遠いです. その固有の複雑さのためだけでなく、問題を解決できないこともあります。
なんで?その理由を理解するには、Java Swing における View と Model-Controllerの密結合を理解する必要があります。例として、私のスピナー UI を見てみましょう。変数 A が実際には Observer オブジェクトであるとします。次に、一番上のスピナーから最初の状態変更イベントを発生させた後、オブザーバー "A" はその値を更新し、PropertyChange イベントを発生させて一番下のスピナーに通知します。次に、下部スピナーのビューを更新する 2 番目の更新が行われます。ただし、ボトム スピナーのビューを変更すると、「A」の値を再度設定しようとする冗長なイベントが必然的にトリガーされます。その後、致命的なループが完全に構築され、スタック オーバーフローがスローされます。
理論的には、オブザーバー モデルは、2 つの独立したフィードバック パスを導入することで直接的なサイクルを解決しようとします。チェーン化された更新オッズ (イベント応答コード内) は、暗黙的に両方のパスを接続するブリッジを形成し、再びサイクルを作ります。