我应该使用哪个?Backbone.js Router.navigate和window.location.hash。

11

最近我通过阅读一本书开始学习Backbonejs,但是对这个问题感到有些困惑。下面是一个Router:

define(['views/index', 'views/login'], function(indexView, loginView) {

    var SelinkRouter = Backbone.Router.extend({

        currentView: null,

        routes: {
            'home': 'home',
            'login': 'login'
        },

        changeView: function(view) {
            if(null != this.currentView)
                this.currentView.undelegateEvents();
            this.currentView = view;
            this.currentView.render();
        },

        home: function() {
            this.changeView(indexView);
        },

        login: function() {
            this.changeView(loginView);
        }
    });

    return new SelinkRouter();
});

这是一个应用程序的引导方法:

define(['router'], function(router) {

    var initialize = function() {
        // Require home page from server
        $.ajax({
            url: '/home',          // page url
            type: 'GET',           // method is get
            dataType: 'json',      // use json format
            success: function() {  // success handler
                runApplicaton(true);
            },
            error: function() {    // error handler
                runApplicaton(false);
            }
        });
    };

    var runApplicaton = function(authenticated) {

        // Authenticated user move to home page
        if(authenticated) window.location.hash='home';
                          //router.navigate('home', true); -> not work

        // Unauthed user move to login page
        else window.location.hash='login';
             //router.navigate('login', true); -> not work

        // Start history
        Backbone.history.start();
    }

    return {
        initialize: initialize
    };
});
我的问题与runApplication相关。我读过的书中的示例仅将路由器传递到模块中,就像这样使用window.location.hash = "XXX",并且根本没有触及路由器。

我认为"navigate"方法应该会使浏览器跳转到我指定的页面,但是没有任何反应。为什么?

另外,为了最佳实践考虑,什么是在页面或视图之间进行移动的最佳方法?

感谢任何想法。

2个回答

18

你也可以使用静态方法来避免路由器依赖(例如在使用requirejs时)。

Backbone.history.navigate(fragment, options)

这样,你只需要:

// Start history
Backbone.history.start();

// Authenticated user move to home page
if(authenticated)
  Backbone.history.navigate('home', true);
// Unauthed user move to login page
else
  Backbone.history.navigate('login', true);

仅 URL 发生了变化,内容部分未改变。 - albert Jegani

12

根据文档显示,如果你想调用特定路由的函数,你需要传递选项trigger: true

当你到达应用程序中想要保存为URL的点时,请调用navigate以更新URL。 如果你还想调用路由函数,则将触发选项设置为true。 要更新URL而不在浏览器的历史记录中创建条目,请将replace选项设置为true。

你的代码应该像这样:

if(authenticated)
    router.navigate('home', {trigger: true});

创建路由器后,您还需要调用它

Backbone.history.start();

Backbone.history.start([options])

在创建所有 Router 并设置所有路由正确后,调用 Backbone.history.start() 开始监控 hashchange 事件并分派路由。

最终的 runApplication 逻辑将类似于以下内容:

var runApplicaton = function(authenticated) {

    var router = new SelinkRouter();
    // Start history
    Backbone.history.start();

    // Authenticated user move to home page
    if(authenticated)
        router.navigate('home', true);
    // Unauthed user move to login page
    else
        router.navigate('login', true);
}

谢谢,akoskm。像你说的那样,我尝试将Backbone.history.start()放在router.navigate()之前,它起作用了。所以我必须在导航到某个地方之前启动历史记录,对吗? - Hetfield Joe
@HetfieldJoe,要开始监视哈希更改事件(导航),您必须启动Backbone.history,请参见上面文档中的引用。 - Akos K

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接