Note that there are some explanatory texts on larger screens.

plurals
  1. POBackbone JS multiple level navigation example
    primarykey
    data
    text
    <p>I'm trying to construct a solid Backbone JS experiment, where I have a local JSON data file which contains my pages (a project I'm doing has this sort of requirement anyhow). And I've coded this example so I can have endless nested subpages in the pages data. It seems to be working great. But when it comes to the URLs, I'm a little stuck.</p> <p>How do I approach giving this multiple level navigation example totally dynamic URLs? What I mean is, correctly using the url property of the models and collections to construct the right URLs for all the top level and nested elements. Is it even possible? I just can't think how to do it.</p> <p>See a live demo of where I am now: <a href="http://littlejim.co.uk/code/backbone/multiple-level-navigation-experiment/" rel="nofollow">http://littlejim.co.uk/code/backbone/multiple-level-navigation-experiment/</a></p> <p>Just so it's easier, the source code is below...</p> <p>index.html</p> <pre><code>&lt;!DOCTYPE html&gt; &lt;html lang="en"&gt; &lt;head&gt; &lt;meta http-equiv="Content-Type" content="text/html; charset=utf-8"&gt; &lt;title&gt;Multiple Level Navigation Experiment&lt;/title&gt; &lt;script type="text/javascript" src="../../media/scripts/jquery-1.5.1.min.js"&gt;&lt;/script&gt; &lt;script type="text/javascript" src="../../media/scripts/underscore-min.js"&gt;&lt;/script&gt; &lt;script type="text/javascript" src="../../media/scripts/backbone-min.js"&gt;&lt;/script&gt; &lt;script type="text/javascript" src="application.js"&gt;&lt;/script&gt; &lt;script type="text/javascript"&gt; // wait for the DOM to load $(document).ready(function() { App.initialize(); }); &lt;/script&gt; &lt;/head&gt; &lt;body&gt; &lt;div id="header"&gt; &lt;h1&gt;Multiple Level Navigation Experiment&lt;/h1&gt; &lt;p&gt;Want to get this page structure pulled from JSON locally and have a fully functional multiple level nested navigation with correct anchors.&lt;/p&gt; &lt;/div&gt; &lt;div id="article"&gt; &lt;!-- dynamic content here --&gt; &lt;/div&gt; &lt;/body&gt; &lt;/html&gt; </code></pre> <p>content.json</p> <pre><code>{ "pages": [ { "id": 1, "title": "Home", "slug": "home" }, { "id": 2, "title": "Services", "slug": "services", "subpages": [ { "id": 1, "title": "Details", "slug": "details", "subpages": [ { "id": 1, "title": "This", "slug": "this" }, { "id": 2, "title": "That", "slug": "that" } ] }, { "id": 2, "title": "Honest Service", "slug": "honest-service" }, { "id": 3, "title": "What We Do", "slug": "what-we-do" } ] }, { "id": 3, "title": "Contact Us", "slug": "contact-us" } ] } </code></pre> <p>application.js</p> <pre><code>// global app class window.App = { Data: {}, Controller: {}, Model: {}, Collection: {}, View: {}, initialize : function () { $.ajax({ url: "data/content.json", dataType: "json", success: function(json) { App.Data.Pages = json.pages; new App.Controller.Main(); }, error: function (XMLHttpRequest, textStatus, errorThrown) { console.log(errorThrown); } }); } } // main controller class // when called it should have 'data' in JSON format passed to it App.Controller.Main = Backbone.Controller.extend({ initialize: function() { var pagesCollection = new App.Collection.Pages(App.Data.Pages); var pagesView = new App.View.Pages({collection: pagesCollection}); $('#article').html(pagesView.render().el); } }); // pages model class App.Model.Page = Backbone.Model.extend({ initialize: function() { if (!_.isUndefined(this.get("subpages"))) { this.subpages = new App.Collection.Pages(this.get("subpages")); } // end if this.view = new App.View.Page({model: this}); }, }); // page collection class App.Collection.Pages = Backbone.Collection.extend({ model: App.Model.Page }); // single page view class App.View.Page = Backbone.View.extend({ tagName: "li", initialize: function() { _.bindAll(this, "render"); }, render: function() { $(this.el).html(_.template("&lt;%=title%&gt;", {title: this.model.get("title")})); return this; } }); // multiple pages view class App.View.Pages = Backbone.View.extend({ tagName: "ul", initialize: function() { _.bindAll(this, "render"); }, render: function() { var that = this; this.collection.each(function(page) { $(that.el).append(page.view.render().el); if (!_.isUndefined(page.subpages)) { var subpagesView = new App.View.Pages({collection: page.subpages}); $(that.el).append(subpagesView.render().el); } // end if }); return that; } }); </code></pre> <p>I'm just needing so right direction on how to do the URLs properly. The idea I'm wanting is that I can setup my controller for routes so it can expect any page of any nested level. The models, collections and nested collections should be able to generate their URLs on their own, but the hash URL must reflect the level.</p> <p>Ideally, this navigation would go to URLs like these:</p> <ul> <li><a href="http://example.com/#pages/services" rel="nofollow">http://example.com/#pages/services</a></li> <li><a href="http://example.com/#pages/services/details" rel="nofollow">http://example.com/#pages/services/details</a></li> <li><a href="http://example.com/#pages/services/details/this" rel="nofollow">http://example.com/#pages/services/details/this</a></li> </ul> <p>...the URLs using the "slug" from the content.json data. Does any of this make sense? I'm pretty new to Backbone JS and just want to do things right. Thanks, James</p>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload