jQuery UI ダイアログがあるプログラムがあります。ユーザーが問題のダイアログの外のどこかをクリックするなど、フォーカスを失ったときにこれらのダイアログが閉じられることを望みます。
一見、これは単純な問題のように見えますが、blurイベントはまったく機能しませんでした。その後、 と にfocusin進みfocusoutましたが、奇妙な問題に遭遇しました。
ダイアログがあり、ダイアログを含む要素 (呼び出した要素の親) にアタッチfocusinした場合。ダイアログが表示された後の最初のクリックは、クリックの場所に関係なく、常にイベントを生成します。focusoutdialogfocusout
したがって、でダイアログを破棄したい場合focusout、ダイアログは破棄されるべきではないときに破棄されます。これが私の問題を示すjsFiddleです。
最初の を無視するためにいくつかのトリックを使用できることはfocusoutわかっていますが、これを正しく機能させる方法があるかどうかを知りたいです。つまり、ユーザーが最初のダイアログの外側をクリックしたときに唯一のイベントが生成されます。時間。
アップデート:
の助けを借りて、私の質問に対する納得のいく答えを見つけましたunderscore.js。
私は自分の問題を部品に分解しました:
- 最初の
focusoutクリックで発生 - クリックがダイアログの外にある場合、それ以上のイベントはありませんでした
- クリックがダイアログ内であった場合、
focusinイベントが続きました
focusoutそのため、一連の->があると、望ましくない動作が発生しましたfocusin。deferこの問題に取り組むために、アンダースコアの機能とブール修飾子を使用しました
onFocusout: function(event) {
console.log('focus out');
this.hasFocus = false;
var self = this;
_.defer(function() {
if (!self.hasFocus) alert('DESTROY DIALOG');
});
},
onFocusin: function() {
console.log('focus in');
this.hasFocus = true;
},
deferコール スタックがクリアされるまで関数を待機させ (不適切な動作の場合、focusinスタック内で待機しているイベントがあります)、それを実行します。そのため、変数が に変更されonFocusinた直後に が起動され、遅延関数がダイアログを破棄することはありません!onFocusouthasFocustrue
回答ありがとうございます。