Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

questions about pushState and history #456

Closed
imdonkey opened this issue Jul 4, 2011 · 11 comments
Closed

questions about pushState and history #456

imdonkey opened this issue Jul 4, 2011 · 11 comments
Labels

Comments

@imdonkey
Copy link

imdonkey commented Jul 4, 2011

hi,
I'm trying to upgrade Backbone in my project from 0.3.3 to 0.5.0 (d2082a5 ) and want to set pushState as true when call Backbone.history.start(), but ....

here is the code:

var router = Backbone.Router.extend({
routes: {                                                                            
        ""                                       : "home",                                                       
        ":uid"                                   : "profile",                                                                          
        "search/:query"                          : "search"                              
    }
})

and

new router();
Backbone.history.start({pushState: true});

The project is ok on IE678.. but can't work on pushState-capable browser such as FF and Chrome...
when I click any link on homepage, the URL has changed but can not trigger the correctly events that defined in router...

Is there someting wrong with my code or Backbone latest version?

Thanks~

@jashkenas
Copy link
Owner

when I click any link on homepage ...

Clicking HTML links certainly isn't compatible with pushState -- what would the link even be?

Use: http://documentcloud.github.com/backbone/#Router-navigate

@imdonkey
Copy link
Author

imdonkey commented Jul 7, 2011

ok thanks!
Now I replace tag 'a' with tag 'div' and bind 'click' event to trigger the router's and then call the navigate to update the URL.
It works for me.

but I can not use the 'Tab' to focus on the links.... I don't think that is a good user experience...

@threepointone
Copy link
Contributor

(this is quite ghetto/oldschool, but should solve your problem)

<a href="javascript:void(0);" onclick="triggerRouter()">whoopee</a>

(you can even the click handler elsewhere, this example is simply to show you how you could use it)

@Atinux
Copy link

Atinux commented Oct 10, 2011

Maybe too late but you can do like this :

$('a').click(function (e) {
    app.navigate($(this).attr('href'), true);
    return false;
});

And use links normally :

<a href="/help">Help me</a>

Like this, if the user doesn't have JavaScript, the link will be trigger by the server, otherwise by Backbone.

@pnbv
Copy link

pnbv commented Oct 28, 2011

Or, extending just a bit Atinux's example:

window.document.addEventListener('click', function(e) {
    e = e || window.event
    var target = e.target || e.srcElement
    if ( target.nodeName.toLowerCase() === 'a' ) {
        e.preventDefault()
        var uri = target.getAttribute('href')
        app_router.navigate(uri.substr(1), true)
    }
});
window.addEventListener('popstate', function(e) {
    app_router.navigate(location.pathname.substr(1), true);
}); 

if you want to have actions bound to not yet loaded views' routes and a working back button.
Please mind Backbone.history's root option.

@locomo
Copy link

locomo commented Nov 2, 2011

sorry.. noob here

where would i place this code by pnbv or Atinux?

@Atinux
Copy link

Atinux commented Nov 2, 2011

The code need to be executed after the document was loaded. So you can put anywhere in your page but it need to be in the Jquery ready event :

$(document).ready(function () {
// code to handle events here
});

@pnbv
Copy link

pnbv commented Nov 2, 2011

That's it.
But please take into account that using pushState only makes sense if you also have a server-side representation of each state at each location. That way you're covered when the user refreshes the page or makes a silly bookmark.
That being said you may not need to use event delegation for capturing link urls at all if your application uses a top/main view instead of a router.

@Atinux
Copy link

Atinux commented Nov 2, 2011

I'm not very sure that you need to have a server-side representation of each state. Indeed if Backbone JS catch the url when the page is loaded, there's no problem ?

@pnbv
Copy link

pnbv commented Nov 2, 2011

Yep, what I meant was that if you want urls instead of hashes then, in my opinion, it doesn't make sense to not have one.

But, on the other hand, if your application hides the address bar or lives inside a native app then it doesn't make sense to have different urls at all.

I think there may have been some confusion about the rational behind the history api.

@pnbv
Copy link

pnbv commented Nov 2, 2011

In my opinion there are two main use cases for Backbone.

  1. Stateful application
    a) In a webkit "webview" inside a native application. No address bar, refresh or back buttons. No need for hashes or urls.
    b) In a browser. Hiding or not the address bar. Only one entry point. Use hashes.
  2. Stateful application with server-side fallback (or stateless application with stateful mode)
    a) In a browser. Application state maps to urls. Multiple entry points ready :) Use urls, pushState and popstate.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

6 participants