2017-02-06 46 views
0

私はUIの構造が間違っていますが、それに目を追加すると、私が見逃しているものを見たり、回避策を見つけてください。Jquery UI:ネストされたiframeモーダルダイアログを閉じます

iframeを含むjquery UIモーダルダイアログを読み込むページがあります。そのiframeは別のiframeを含む別のモーダルを開くことができるページを読み込みます。そのネストされたiframeには、現在のモーダルを閉じるボタンがあるページが含まれています。ただし、そのボタンは機能しません。これはDOMが実際にレイアウトされていないか、概念的であること

- page1 
    - iframe1 
    - page2 
     - iframe2 
     - page3 
      - button -> close iframe2 (fails) 

注:ここでは(各IFRAMEがモーダルdivの中に含まれていることに注意)レイアウトの概念モデルです。また、実際にiframe1を閉じるpage2のボタンがあり、それが動作します。ただし、page3とiframe2の間で同じ機能を試行すると失敗します。それはダイアログdivを見つけることができますが、それは私に "初期化の前にダイアログのメソッドを呼び出すことはできません;メソッド 'close'" jquery UIエラーを呼び出そうとしました。

ここでは、各ダイアログのappendToプロパティのために、ネスティングのレベルにかかわらず、各モーダルdivがメインのトップレベルのbody要素に追加されるように注意するいくつかの注意があります。ダイアログ機能(例では「X」ボタンなど)を介してボタンを追加すると機能します。明らかにうまくいく隠れたフックがあります。 SOに関する他の回答ごとに、各iframeはすでにjQueryの親インスタンスを呼び出して、そのダイアログを閉じようとしています。増加したネスティングレベルを説明するために任意の数の.parentを追加しても問題は解決されません。ここで

は私のサンプルアプリケーションの全文です: ページ1

<html> 
<head> 
<link rel="stylesheet" href="jquery-ui.min.css" /> 
<script type="text/javascript" src="jquery.js"></script> 
<script type="text/javascript" src="jquery-ui.min.js"></script> 
<script type="text/javascript"> 
    function make1() { 
     var self = $("<div id='one'></div>"); 
     var frame = $("<iframe style='width:100%;height:100%' />"); 
     self.html(frame); 
     self.dialog({ 
      title: 'One', 
      autoOpen: false, 
      modal: true, 
      appendTo: $(window.document).find('body'), 
      width: 300, 
      height: 200, 
      overlay: 0.5, 
      close: function() { 
       self.dialog('destroy'); 
      } 
     }); 
     self.dialog('open'); 
     frame.attr("src", "http://localhost:81/page2.html"); 
    } 

</script> 
</head> 
<body> 
<button onclick="make1()">Open 1</button> 
</body> 
</html> 

PAGE2:

<html> 
<head> 
<link rel="stylesheet" href="jquery-ui.min.css" /> 
<script type="text/javascript" src="jquery.js"></script> 
<script type="text/javascript" src="jquery-ui.min.js"></script> 
<script type="text/javascript"> 

    var dialog; 

    function make2() { 
     var self = $("<div id='two'></div>"); 
     dialog = self; 
     var frame = $("<iframe style='width:100%;height:100%' />"); 
     self.html(frame); 
     self.dialog({ 
      title: 'Two', 
      autoOpen: false, 
      modal: true, 
      appendTo: $(window.parent.document).find('body'), 
      width: 300, 
      height: 200, 
      overlay: 0.5, 
      close: function() { 
       self.dialog('destroy'); 
      } 
     }); 
     self.dialog('open'); 
     frame.attr("src", "http://localhost:81/page3.html"); 
    } 

    function kill1() { 
     window.parent.$("#one").dialog('close'); 
    } 


</script> 
</head> 
<body> 
<button onclick="make2()">Open 2</button> 
<button onclick="kill1()">Kill 1</button> 
</body> 
</html> 

...とPAGE3、問題のページ:

<html> 
<head> 
<link rel="stylesheet" href="jquery-ui.min.css" /> 
<script type="text/javascript" src="jquery.js"></script> 
<script type="text/javascript" src="jquery-ui.min.js"></script> 
<script type="text/javascript"> 

    function kill2() { 
     var dialog = window.parent.$("#two") 
     if(dialog.length > 0) { 
      alert("found it; closing dialog..."); 
      dialog.dialog('close'); 
     } 
    } 


</script> 
</head> 
<body> 
<button onclick="kill2()">Kill 2</button> 
</body> 
</html> 

最後に、 "Kill 2"ボタンはエラーで失敗するものです。

答えて

0

これは答えではありませんが、回避策です。簡単に言えば、ダイアログで作成された塊をすべて削除するだけです。 私はこれが非常に最後の手段であることを強調しなければなりません。そして、それでは、それは皆にとってではありません。。これは、ブラウザとJQuery UIのバージョンによって異なるいくつかの実装の詳細に依存します。しかし、クライアントのブラウザにバージョンロックが設定されている場合は、少なくとも調査する価値があります。

function kill2() { 
    var dialog = window.parent.$("[aria-describedby='two']") 
    if(dialog.length > 0) {  
     var zIndex = dialog.css("z-index") -1; 
     var overlay; 
     dialog.siblings(".ui-widget-overlay.ui-front").each(function(index, item) { 
      if($(item).css("z-index") == zIndex) 
       overlay = item; 
     }); 
     if(overlay) { 
      $(overlay).remove(); 
     } 
     dialog.remove(); 
    } 
} 

本質的に、それは(それの実装の詳細それにARIA-desribedby属性を追加することによって、再び)ダイアログの親要素を見つけ、そしてそれはモーダル場合(オーバーレイのその要素の兄弟を検索します:trueが指定されていれば、これが存在します。そうでなければ、存在しません)。任意の数のネストされたダイアログに対して、適切なオーバーレイを見つけるには、ダイアログより1つ小さいZ-インデックスを探します。次に、オーバーレイとダイアログを削除します。

これは明らかに、ダイアログに提供されたclose:メソッド内のロジックをバイパスするということです。この方法でロジックを再作成する必要があります。

関連する問題