easyui修复浏览器刷新后,tab页全部关闭的问题
一.问题描述
使用easyui搭建的上左右页面布局,当我们在右侧打开了tab页,发现点击浏览器的刷新按钮后,整个页面会被重新渲染,导致所有打开的tab页都被关闭,回到初始状态的问题。
这个问题虽然不影响业务,但对用户操作造成了一定的困扰。因为浏览器刷新后,tab页全部被关闭,那么用户又需要打开刚才正在使用的tab页,甚至有可能,用户会忘记打开过哪些tab页。
二.解决思路
因为浏览器刷新后,页面重新渲染,所有tab页都不存在了,其实并不是关闭了tab,只是页面回到了初始状态。所以要解决这个问题,我们可以使用一个变量来保存已经打开的tab页的信息,这样即使页面刷新,我们也可以通过这个变量来恢复到原来的状态。
三.解决步骤
1.使用cookie来保存这个变量
//从cookie中读取treeNodes的值,其中保存着处于打开状态的tab页的信息 treeNodes = $.cookie("treeNodes"); if(treeNodes == null){ //如果为空,则表示没有打开的tab页 treeNodes = []; }else{ //如果不为空,则表示加载这个页面之前,存在已经打开的tab页 //注意:cookie中存放的是string类型,需要转化为json数组对象 treeNodes = $.parseJSON(treeNodes); }
2.为菜单树添加onLoadSuccess事件,用来恢复原来已经打开的tab页的状态;菜单树的onClick事件中,每次打开一个tab,增加一个对应的值
/* * 获取左侧菜单树,并为其节点指定单击事件 */ $("#home-west-tree").tree({ url: "${ctx }/tree.do", method: "get", animate: true, //当tree加载成功后,检查是否之前存在已经打开的tab页 //如果存在,则打开对应的tab页 onLoadSuccess: function(){ for(var i = 0; i<treeNodes.length; i++){ var treeNode = treeNodes[i]; //通过节点的id来找到node var node = $("#home-west-tree").tree("find",treeNode.id); addTab({ url: "${ctx }/" + node.attributes.url, title: node.text }); } }, onClick: function(node){ if(node.attributes && node.attributes.url){ addTab({ url: "${ctx }/" + node.attributes.url, title: node.text }); //当用户点击tree打开tab页时记录到treeNodes中 //因为tree和tabs相关的属性就只有text和title,所以必须保存这一个属性, //后来发现tree只有一个find方法(通过id查找node)能方便的找到对应的node,所以只好将id也保存下来 treeNodes.push({ "id":node.id, "text":node.text }); //每次对treeNodes的操作都要保存到cookie中 //注意:treeNodes需要转化为string才能保存到cookie中 $.cookie("treeNodes",JSON.stringify(treeNodes)); } } });
3.为tabs组件添加onClose事件,每次关闭一个tab,删除一个对应的值
/* * 初始化内容区的tabs */ $("#home-tabs").tabs({ fit : true, border : false, //为其附加鼠标右键事件 onContextMenu: function(e, title, index){ e.preventDefault(); var mm = $("#home-tabs-menu"); //显示右键菜单 mm.menu("show",{ top: e.pageY, left: e.pageX }).data("tabTitle",title); //为右键菜单选项绑定事件 mm.menu({ onClick: function(item){ closeTab(this, item.name); } }); }, //每次关闭tab页时,删除treeNodes中对应的值 onClose: function(title, index){ for(var i=0; ; i++){ if(treeNodes[i].text == title){ treeNodes.splice(i,1); $.cookie("treeNodes",JSON.stringify(treeNodes)); break; } } } });
四.总结与说明
在修复过程中,引用了jquery.cookie.js来操作cookie。
这个变量应该和页面无关,只和会话有关,所以可以有两种方式来处理,一种是发送到后台,保存到session中,另一种是保存到cookie中,我这里使用的是后面一种方法。
其中最容易出问题的就是json对象和string的转换,我们在程序中,treeNodes是json数组对象,而cookie保存的只能是string对象,所以这两者之间的转换一定要注意,而我就在这里折腾了好久好久。。。
五.后记
#2016-03-14
在使用过程中,发现了一个bug。在多选项卡类型的浏览器中,如果只关闭选项卡而不完全关闭浏览器,则会造成再次打开网页后,tab页会恢复到原来的状态,即关闭选项卡再打开,相当于刷新页面。
我也尝试过js监听网页关闭和刷新,可是最终发现,只能区分只有一个选项卡的浏览器关闭和刷新事件,对于多选项卡则无能为力。