jQuery mobile – 关于历史记录的关闭面板
我有一个jQuery移动面板从侧面滑入,它工作得很好。 但是,假设您有一个登录页面,该页面会重定向到带有面板的主页面。 现在,如果用户打开面板,然后单击后退按钮,他希望面板关闭。 但是浏览器会导航回登录页面。
我试过在url上添加一些内容:
window.location.hash = "panelOpen";
但这只是弄乱了jQuery移动历史状态模式。 我也尝试过监听导航事件,并在面板打开时阻止它:
$(window).on('navigate', function (e, hans) { var panels = $('[data-role="panel"].ui-panel-open'); if (panels&&panels.length>0) { e.preventDefault(); e.stopPropagation(); $('#' + panels[0].id).panel('close'); return false; } });
这种工作,除了更改url,我不能抓住更改url的事件。 此外,它还会混淆jQuery移动历史模式。
那么人们如何通过jQuery移动面板实现这种预期的’app-like’行为; 打开面板>历史记录>关闭面板。 就是这样。
非常感谢!
更新
不是从jQuery Mobile的历史记录中检索当前URL,而是从hashchange
事件event.originalEvent.newURL
检索它更安全,然后将其传递给popstate
事件,使其成为具有该URL的replaceState()
。
而不是听navigate
,听听之前激发的popstate
。 这里的技巧是通过replaceState()
操纵浏览器的历史记录和jQuery Mobile的历史记录,并重新加载相同的页面而不进行转换 。
var newUrl; $(window).on("hashchange", function (e) { /* retrieve URL */ newUrl = e.originalEvent.newURL; }).on("popstate", function (e) { var direction = e.historyState.direction == "back" ? true : false, activePanel = $(".ui-panel-open").length > 0 ? true : false, url = newUrl, title = document.title; if (direction && activePanel) { $(".ui-panel-open").panel("close"); $(".ui-header .ui-btn-active").removeClass("ui-btn-active"); /* reload same page to maintain jQM's history */ $.mobile.pageContainer.pagecontainer("change", url, { allowSamePageTransition: true }); /* replace state to maintain browsers history */ window.history.replaceState({}, title, url); /* prevent navigating into history */ return false; } });
此部分旨在维护先前使用的相同转换,因为在重新加载相同页面时transition
设置为none
。
$(document).on("pagebeforechange", function (e, data) { if (data.options && data.options.allowSamePageTransition) { data.options.transition = "none"; } else { data.options.transition = $.mobile.defaultPageTransition; } });
演示 – 代码
我在派对上有点迟,但我最近有相同的要求,我想分享我是如何做到的。 所以,我将原始问题的要求扩展到Panels
, Popups
和Pages
:
…预期的’app-like’行为,历史回归> close whaterver是开放的。 就是这样。
在.on("panelopen")
.on("popupafteropen")
和.on("popupafteropen")
,我只需使用HTML5 API将另一个条目添加到窗口历史记录中( https://developer.mozilla.org/ en-US / docs / Web / API / History_API )(我相信没有必要使用JQM导航浏览器怪癖):
window.history.pushState({}, window.document.title, window.location.href);
在那之后,我正在使用或多或少的Omar函数来拦截popstate
事件:
$(window).on("popstate", function (e) { var pageId = $(":mobile-pagecontainer").pagecontainer("getActivePage").prop("id"); var pageOpen = (pageId != "page-home"); var panelOpen = $(".ui-panel-open").length > 0; var popupOpen = $(".ui-popup-active").length > 0; if(pageOpen) { $.mobile.pageContainer.pagecontainer("change", "#page-home", {reverse: true}); return false; } if(panelOpen) { $(".ui-panel-open").panel("close"); return false; } if(popupOpen) { $(".ui-popup-active .ui-popup").popup("close") return false; } });
如您所见,主页只是一个级别,但通过使用JQM历史记录实现来获取上一页,可以轻松扩展它:
var activeId = $.mobile.navigate.history.activeIndex; var jqmHistory = $.mobile.navigate.history.stack; // array of pages
并使用pagecontainer
更改为活动条目 – 1。
最后一点,通过完全禁用内置的JQM Ajax导航系统,这也很有效:
/* Completely disable navigation for mobile app */ $.mobile.ajaxEnabled = false; $.mobile.loadingMessage = false; $.mobile.pushStateEnabled = false; $.mobile.hashListeningEnabled = false; $.mobile.changePage.defaults.changeHash = false; $.mobile.popup.prototype.options.history = false;
(在浏览器中测试,在真实的Android和iOS设备上)