javascript 在 IE 中关闭所有子窗口


本文示例源代码或素材下载

  B/S 系统的一个很常见的操作是,在主窗口中打开子窗口(例如单据窗口),在其中打开查找窗口,在查找窗口中打开类别选择子窗口,... 如此一层层下去,形成多级子窗口。然而,当退出 B/S 系统时,却只能一个个关闭这些窗口。

  这是因为,IE 并不提供窗口的级联结构控制,即不能一次性关闭所有子窗口(或者在所有子窗口中执行同一个函数)。这令人不满。

  我写了一个函数库,可以完美解决这个问题,当关闭某个子窗口时,自动关闭其下的所有子窗口。当然,退出系统时,自动关闭所有子窗口。并且,可以在所有子窗口中执行指定的函数。实际上,后者是前者的基础,由于实现了后者的功能,前者就变成了后者的一个具体的应用。

  源码如下:

  1
  2var __winRoot__ = top || parent || window; // 祖先窗口对象
  3var __winParent__ = __winRoot__; // 父窗口对象(默认为祖先窗口)
  4var __winTree__ = {subWinNames:''}; // 本窗口的子窗口对象集合。 subWinNames 记录所有子窗口的名称,方便遍历
  5
  6//--------------------------------------------------------
  7window.closeSub = function()
  8{
  9    __winTree_closeAllSubWins__(); // 关闭所有子窗口
 10    __winTree_closeWin__(); // 关闭当前窗口
 11}
 12
 13window.openSub = function(url, wname, property)
 14{
 15    __winTree_openSubWin__(url, wname, property);
 16}
 17
 18window.onbeforeunload = function()
 19{
 20    var n = window.event.screenX - window.screenLeft;
 21    var b = n > document.documentElement.scrollWidth-20;
 22    if(b && window.event.clientY < 0 || window.event.altKey)
 23    {
 24        window.closeSub();
 25    }
 26}
 27
 28//--------------------------------------------------------
 29//////////////////////////////////////////////////////////
 30//
 31// 一些函数
 32//
 33//////////////////////////////////////////////////////////
 34
 35//--------------------------------------------------------
 36// 指定窗口是否存在
 37//--------------------------------------------------------
 38function __winTree_isExistWin__(hdl){try{var ret=hdl && !hdl.closed}catch(e){var ret=false};return ret;}
 39
 40//--------------------------------------------------------
 41//////////////////////////////////////////////////////////
 42//
 43// 窗口控制
 44//
 45//////////////////////////////////////////////////////////
 46
 47//--------------------------------------------------------
 48// 构造窗口缺省名字
 49//--------------------------------------------------------
 50function __winTree_getDefaultWinName__()
 51{
 52    return "__wn" + (new Date().getTime()) + "__"; // 用当前时间构造窗口缺省名字
 53}
 54
 55//--------------------------------------------------------
 56// 打开子窗口,并添加到窗口目录树
 57//--------------------------------------------------------
 58function __winTree_openSubWin__(url, wname, property)
 59{
 60    var hdl = window.open(url, wname, property);
 61    __winTree_addSubWin__(wname, hdl); // 保存到子窗口对象集合
 62}
 63
 64//--------------------------------------------------------
 65// 保存到子窗口对象集合
 66//--------------------------------------------------------
 67function __winTree_addSubWin__(subWinName, sWin)
 68{
 69    var win = top ? top : window;  // 获取本窗口的最上层窗口
 70    var winTree = win.__winTree__;
 71
 72    winTree[subWinName] = sWin; // 将子窗口对象加入到集合中
 73    winTree["subWinNames"] += subWinName + ","; // 所有子窗口名称集合
 74}
 75
 76//--------------------------------------------------------
 77// 将指定窗口的子孙窗口对象,添加到指定窗口的父窗口中
 78//--------------------------------------------------------
 79// 使指定窗口的子孙窗口保持在目录树中的结构
 80// 否则指定窗口的子孙窗口将从目录树结构中断开,不能统一控制。
 81// (用于关闭指定窗口的操作时)
 82//--------------------------------------------------------
 83function __winTree_addSubWins2pWin__(thisWin)
 84{
 85    thisWin = thisWin || window; // 缺省为本窗口
 86
 87    var pWin = thisWin.__winParent__;
 88    var winTree = thisWin.__winTree__;
 89
 90    var arrSubWinNames = winTree.subWinNames.split(","); // 子窗口名字数组
 91    var intSubWinNamesLen = arrSubWinNames.length;
 92    for(var i=0; i<intSubWinNamesLen; i++)
 93    {
 94        var subWinName = arrSubWinNames[i]; // 指定窗口的子孙窗口名字
 95        if (!subWinName) continue;
 96
 97        var sWin = winTree[subWinName]; // 指定窗口的子孙窗口对象
 98
 99        // 为避免和父窗口中已有的子窗口的名称相同,因此要加上缺省的、以当前时间来构造的名称
100        pWin.__winTree_addSubWin__(subWinName + __winTree_getDefaultWinName__(), sWin);
101    }
102}
103
104//--------------------------------------------------------
105// 本窗口的所有下级子窗口执行指定动作
106//--------------------------------------------------------
107// funcName                    要执行的函数名称(例如 close ,即 window.close() ,或者其他自己定义的函数,例如 changeBgColor 等等)
108// argVals                    要执行的函数的参数值
109//--------------------------------------------------------
110function __winTree_doWithSubs__(win, funcName, argVals)
111{
112    if (!win || !funcName) return;
113
114    var winTree = win.__winTree__;
115    var arrSubWinNames = winTree.subWinNames.split(","); // 子窗口名字数组
116    var intSubWinNamesLen = arrSubWinNames.length;
117    for(var i=0; i<intSubWinNamesLen; i++)
118    {
119        var subWinName = arrSubWinNames[i]; // 子窗口名字
120        if (!subWinName) continue;
121
122        var sWin = winTree[subWinName]; // 子窗口对象
123        if (__winTree_isExistWin__(sWin))
124        {
125            sWin.__winTree_doWithSubs__(sWin, funcName, argVals); // 查找该子窗口的下级子窗口
126            sWin[funcName](argVals); // 执行指定的动作
127        }
128    }
129}
130
131//--------------------------------------------------------
132// 初始化窗口目录树
133//--------------------------------------------------------
134function __winTree_init__()
135{
136    if (__winTree_isExistWin__(opener)) // 如果存在父窗口
137    {
138        var pWin = opener.top; // 父窗口。有可能是在 iframe 中打开本窗体,因此父窗体应该是 opener 的顶级窗体
139        __winParent__ = pWin; // 祖先窗口
140        __winRoot__ = pWin;
141
142        var ppWin = pWin.opener;
143        if (__winTree_isExistWin__(ppWin)) // 修正祖先窗口
144        {
145            __winRoot__ = pWin.__winRoot__;
146        }
147    }
148    //alert([__winRoot__.document.title, __winParent__.document.title, window.document.title]); // for test only
149}
150
151//--------------------------------------------------------
152// 关闭当前窗口
153//--------------------------------------------------------
154function __winTree_closeWin__(win)
155{
156    win = win || window; // 缺省为关闭当前窗口
157    var pWin = win.__winParent__;
158    if (__winTree_isExistWin__(pWin)) // 如果指定窗口有父窗口,且未关闭
159    {
160        __winTree_addSubWins2pWin__(win); // 将指定窗口的子孙窗口对象,添加到指定窗口的父窗口中
161    }
162    win.opener = null; // 此语句用于取消“是否关闭此窗口”的提示
163    win.close(); // 关闭指定窗口
164    pWin.focus(); // 聚焦到父窗口
165}
166
167//--------------------------------------------------------
168// 关闭本窗口的所有下级子窗口
169//--------------------------------------------------------
170function __winTree_closeAllSubWins__(win)
171{
172    win = win || window; // 缺省为关闭当前窗口
173    __winTree_doWithSubs__(win, "close");
174}
175
176//--------------------------------------------------------
177// 初始化
178//--------------------------------------------------------
179__winTree_init__();
180


« 
» 
快速导航

Copyright © 2016 phpStudy | 豫ICP备2021030365号-3