2013-02-05 24 views
1

我在当用户想要预览它由路线叫做发票的功能做表单验证回应按钮(实际上,按钮和一个href)的形式:骨干路由点击并不会不第2次尝试

<div class="span8 alignRight"> 
    <button id="saveInvoiceDraft" type="submit" class="btn btn-warning">Save Draft</button> 
    <a id="previewInvoice" class="btn btn-primary">Preview &amp; Send</a> 
</div> 

当创建该发票,对于标签的URL被设定为:

var url = '#preview'; 
$('#previewInvoice').attr('href',url); 

最后,当我点击“预览&发送”按钮时,下面的previewInvoice(invoiceid)函数将运行,正确捕获缺少的一个表单域并显示错误消息。在这一点上,即使我填写表单字段,该按钮已经死了,不再回应。但是,“保存草稿”按钮完美地工作,并且与previewInvoice()函数中的模拟代码相同。

我知道可能有更好的方法来做到这一点,但我是按照这种方式,它是在我继承的应用程序的另一部分完成的。其实,当我输入这个时,我想知道,因为sendDraft()函数工作,它的按钮和previewInvoice()函数没有,它是一个href的事实可能与它有关。

function previewInvoice(invoiceid) { 
    var invoice = new Invoice({"invoiceid": invoiceid}); 
    invoice.set({"invoiceid": invoiceid,"invoicestatus": "draft"}); 
    formGetter(invoice); 
    validateInvoiceForm(invoice); 

    if (window.errors.length == 0) { 
     //business logic here 

     if (window.panel == undefined) { 
      // business logic here 
     } 
     else { 
      //save business logic here 
     } 
    } 
    else { 
     showInvoiceErrors(); 
    } 
} 

任何想法为什么按钮不再响应?我在控制台中看不到任何错误。我在函数中添加了一个consol.log以显示不同表单元素的值,并且它在控制台中首次显示,但是如果我更改数据并再次单击该按钮,那么该日志不会更新,对我而言是另一个线索,它只是不开火。

回答

1

Backbone.History收听hashchange事件以触发导航到路线。当您首次单击previewInvoice按钮时,URL散列片段被设置为#preview,并且匹配的路由被触发。

当你第二次点击同一个按钮时,哈希值实际上并没有改变,因此路由器没有收到它。

我很难推荐一个很好的解决方案来解决这个问题。通常我会建议捕捉点击事件并手动呼叫router.navigate("preview", {trigger:true});。但是,根据您的代码示例,它看起来像您的应用程序围绕Router构建,并且没有用于DOM事件处理的View图层,正如您在大多数Backbone应用程序中所期望的那样。

在路由器层面上,这有点难以解决。在执行preview路由后,您可以使用router.navigate设置虚拟散列。这会导致链接第二次触发hashchange。不幸的是,这意味着preview页面不可收藏,并且由于您未使用pushState,因此会留下无关的历史记录条目。

恐怕这个问题将不得不用hacky修复(如上所述)或重大重构来解决。

+0

谢谢。这有助于我更多地理解它。奇怪的是,此页面上的另一个按钮用于保存草稿按我希望的方式工作,并且没有散列更改。我会尝试你的建议,并让你知道它是如何发生的。我们也在使用视图。 – Dan

1

我有这个相同的问题,我的解决方案是放入一个处理程序,做一个假的“中间”路线,从历史中隐藏,以便Backbone.history将注册导航作为更改并触发行动。

放在你所需要的路由操作,无论触发链接类,如果该URL是相同的:

<a href="/someaction" class="js-ensureNav">do it</a> 

在你的骨干视图,放在一个事件处理程序:

events: { 
    "click .js-ensureNav": "_ensureNav", 
}, 

实际处理程序:

_ensureNav: function (event) { 
    var route_name = $(event.target).attr('href').slice(1); 
    Backbone.history.navigate("fake"); 
    Backbone.history.navigate(route_name, {trigger: true, replace: true}); 
}, 
1

而不是

var url ='#preview';

$('#previewInvoice')。attr('href',url);

试试这个

VAR日期=新的日期();

var url ='#preview?date:'+ date;

$('#previewInvoice')。attr('href',url);

所以每次都会产生新的请求,这将解决您的问题。