我正在使用Backbone,require和jQuery mobile作为技术堆栈构建HTML5移动应用程序。通过与后端Web服务的连接等,应用程序非常流畅。 要在页面之间切换,我使用jQuery changePage。 要实现Backbone视图,我使用以下策略:
$( document ).delegate("#card-delivery-address", "pageshow", function(){
require(["js/views/cardDeliveryAddressViews.js" ], function(cardDeliveryAddressViews) {
new cardDeliveryAddressViews();
});
});
$ .mobile.changePage('deliveryAddress.html')=>改变现状 页面使用jquery mobile
在#card-delivery-address 上触发名为“ pageshow ”的事件时 (这意味着我的页面已成功插入DOM中 渲染)=>创建骨干视图并将$ el绑定到 现有的DOM并使用骨干控制DOM事件 视图。
单向导航成功,假设我来自view1 - > view2(带有tempData)然后来自view2 - >视图3(覆盖相同的tempData)。现在,这是我的问题:如果我们想从视图3返回 - >在视图2中,我们将需要用于初始化和渲染视图的tmpData内容2.当我们想要返回view1时也是如此。
注意:我没有使用骨干路由器,但如果可以解决我的问题,我可以改用它。
任何想法的人?
答案 0 :(得分:2)
在页面转换期间,将从DOM中删除上一页
要保留DOM中所有以前访问过的网页,您可以添加以下属性:
<div data-role="page" id="card-delivery-address" data-dom-cache="true">
<!-- [...] -->
</div>
或初始化全局参数:
$.mobile.page.prototype.options.domCache = true;
答案 1 :(得分:2)
好的,让我们再试一次。我们将实现一个由页面路径键入的数据存储。
var pagesData = {};
// Let's assume we just switched to page '/my/page/1'
// Get a reference to the stored page data if it exists,
// or create it empty and return it.
var currentPageData = pagesData[window.location.pathname] ||
(pagesData[window.location.pathname] = {});
currentPageData.foo = 'bar';
console.log(pagesData['/my/page/1'].foo); // > "bar"
现在,您的所有页面都有一个“本地”数据存储区,允许它们在整个导航过程中保存状态/数据。
注意:如果您不使用pushState,则必须使用window.location.hash代替window.location.pathname作为PagesData中的键。
答案 2 :(得分:1)
为什么不将windows.tempData
作为对象?
windows.tempData = {};
存储页面数据:
window.tempData["id_of_page"] = your_data;
在pagebeforeshow
:
myDataForThisPage = window.tempData[this.id]; // assuming "this" being your page element
答案 3 :(得分:1)
使用堆栈可以解决您的问题。浏览器的内部历史记录处理使用它来处理导航和后退按钮。
使用Array
及其push()
和pop()
方法在Javascript中实现堆栈。它们允许您保存和恢复以前的状态。
var navigationStack = {...},
currentState = {...};
...
// When going to a new page, you push (or save) the current state on the stack
navigationStack.push(currentState);
...
...
// When going back to the previous page you pop the previous state from the stack
currentState = navigationStack.pop();
...
当然,如果您从view3导航到view2,如果类似于“后退”操作,则此方法有效。如果故意导航到之前已初始化的任何页面,则必须将页面状态保存在哈希中,并按页面名称(或完整路径)索引。
您的案例应符合这两种模式中的一种。如果没有,要么你的要求没有明确定义,要么我误解了你的问题。
答案 4 :(得分:1)
thibauts' answer似乎正朝着正确的方向发展。请给它一个阅读。
我理解你的问题的方式。在任何时候打开“page3a”取决于前一页。如果它是“page2a”它将以某种方式工作。如果它是“page2b”它将以不同的方式工作。这些信息保存在每个页面的tempData中。
骨干路由无法解决此问题。因为它们只提供将URL路由转换为执行序列的方法。您仍然需要管理tempData。 最终的解决方案取决于tempData的大小以及如何管理它。是否有一些共享数据可以从tempData结构中取出并保存在共享结构中。是否有一些数据可以单独保存,变化非常少,可以实现某种memento pattern。
有三种情况 -
tempData相对较小,您可以保留一些副本 - 在这种情况下,您可以在circular buffer中保留tempData的固定历史[比如说最后10页]。继续删除最旧的项目,并在每次访问时添加新项目。如果用户没有更改任何内容并专门尝试前进按钮/导航,这将为您提供后退导航,如thibauts所述和历史记录跳转以及后退导航后的导航。
1.1 编辑:如果您希望保留已经备份的转发操作,您仍然可以将其保留在循环队列中, 但是这样你就必须区分view2的两次访问 (看评论)。并将一切都视为前进和推进 历史(循环队列)。另一种方法是保持指针(数组 指数。如果可以,请参考缓冲区中的当前页面 当添加新页面(在某些动作上)缓冲移动指针时 那个。当做后退/前进动作时,只需移动点 缓冲和渲染。 [如果实施起来太复杂或太昂贵,那么 用户从中移回后,可以完全忽略视图/页面。 只需将其从历史记录中删除,以便用户无法再次使用fwd。或者回来 在回到新的后退后两次到达它。 backbone.router有办法 历史取代]
tempData很大足以让你只保留少量副本[假设小于5]。在这种情况下,请保留上一页的一个副本。并保留历史记录中特定关键页面的副本,用户返回的可能性很高。例如,在购物流程中,用户可以比地址页面更频繁地返回购物车。您将需要一个特殊的数据结构,您可以在其中保持每个页面的优先级。优先级取决于时间和一些偏差标准。最新获得高时间参数,最重要的是获得高偏置参数。每当您访问新页面时。删除优先级最低的tempData。
tempData具有可怕的大小 - 放弃后退导航。保留历史记录中的几个点,如重置点(如果可能),以及从头开始重新创建tempData的位置。
如果还有其他瓶颈而不是tempData。请评论。