My html template look like this:
<script type="text/template" id="players-template">
<table id="example" class="table table-striped table-bordered table-condensed table-hover">
<thead>
<tr>
<th>Name</th>
<th>group</th>
<th></th>
</tr>
</thead>
<tbody id="playersTable"></tbody>
</table>
</script>
<script type="text/template" id="player-list-item-template">
<td><#= name #></td>
<td>
<# _.each(hroups, function(group) { #>
<#= group.role #>
<# }); #>
</td>
</script>
My backbone view is as follows:
playerView = Backbone.View.extend({
template: _.template( $("#player-template").html() ),
initialize: function ()
if(this.collection){
this.collection.fetch();
},
render: function () {
this.$el.html( this.template );
this.collection.each(function(player) {
var itemView = new app.PlayerListItemView({ model: player });
itemView.render();
this.$el.find('#playersTable').append(itemView.$el);
},this
});
// view to generate each player for list of players
PlayerListItemView = Backbone.View.extend({
template: _.template($('#player-list-item-template').html()),
tagName: "tr",
render: function (eventName) {
this.$el.html( this.template(this.model.toJSON()) );
}
});
The above code works perfectly. Now, I want to use apply jquery datatable plugin wtih bootstrap support. You can find detail here :http://www.datatables.net/blog/Twitter_Bootstrap_2
So, I just added the line inside render as:
render: function () {
this.$el.html( this.template );
this.collection.each(function(player) {
var itemView = new app.PlayerListItemView({ model: player });
itemView.render();
this.$el.find('#playersTable').append(itemView.$el);
$('#example').dataTable( {
console.log('datatable');
"sDom": "<'row'<'span6'l><'span6'f>r>t<'row'<'span6'i> <'span6'p>>",
"sPaginationType": "bootstrap",
"oLanguage": {
"sLengthMenu": "_MENU_ records per page"
},
"aoColumnDefs": [
{ 'bSortable': false, 'aTargets': [ 2 ] }
]
} );
},this);
},
Now, the jquery datable is not initialized. They just diisplay normal table.
where should I intialized the table to apply jquery datatable?
they worked perfectly without backbone.
Most likely, the jQuery plugin needs the elements to be on the page to work. You don't show where you are calling render on that view, but I am going to assume you are doing something like this:
var view = new PlayerView();
$('#foo').html(view.render().el); // this renders, then adds to page
If this is true, then using the plugin inside render is too early, since the view's html is not yet added to the page.
You can try this:
var view = new PlayerView();
$('#foo').html(view.el); // add the view to page before rendering
view.render();
Or you can try this:
var view = new PlayerView();
$('#foo').html(view.render().el);
view.setupDataTable(); // setup the jQuery plugin after rendering and adding to page
Related
Ive created a simple backbone app that gets data from MySQL database about users to display in a view called LeaderBoardView.
Below is the HTML code for the view,
<body>
<div id="container"></div>
<h1>Leaderboard</h1>
<table class="table" id="modtable">
<tr>
<th>Username</th>
<th>Level</th>
</tr>
</table>
<div id="bbcontent"></div>
Im trying to get data and populate inside the div with bbcontent as the id.
Below is my Backbone model, collection and view,
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.3/jquery.min.js">
</script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/underscore.js/1.8.3/underscore-
min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/backbone.js/1.2.3/backbone-min.js">
</script>
<script language="javascript">
$(document).ready(function() {
alert("heyyyyyy")
//model
var User = Backbone.Model.extend({
idAttribute: "userId",
defaults: {
username: null,
userLevel: null
}
});
//collection
var Users = Backbone.Collection.extend({
model: User,
url: "/CW2/ASSWDCW2/cw2app/index.php/Leaderboard/leaderboard",
});
var usersC = new Users();
var LeaderboardDeetsView = Backbone.View.extend({
model: usersC,
el: $('#bbcontent'),
intialize: function() {
alert("asndasnxdjksa")
usersC.fetch({
async: false
})
this.render()
},
render: function() {
var self = this;
usersC.each(function(c) {
var block = "<div class='name'><h1>" + c.get('username') + "</h1></div>"
self.$el.append(block)
})
}
})
var leaderboardDeetsView = new LeaderboardDeetsView();
});
Problem with this code :
The LeaderboardDeetsView isn't being called hence the collection fetch function inside the initialize function of the LeaderboardDeetsView isn't being called.How can I correct my code? Please help
I have generated a data table using the Datatables jquery plugin. The table is populated with JSON.
I want to extract cell values when I make a selection to use in a URL but I can't get it to work.
#I'm using django
import json
#my list
users = [[1,26,'John','Smith'],[2,33,'Dave','Johnson'],[1,22,'Aaron','Jones']]
#my json
user_json = json.dumps(users)
<table class="table table-striped- table-bordered table-hover table-checkable" id="user-table">
<thead>
<tr>
<th>Age</th>
<th>Record ID</th>
<th>First Name</th>
<th>Last Name</th>
<th>Actions</th>
</tr>
</thead>
</table>
<script type="text/javascript">
var userData = {{user_json|safe}};
</script>
var SourceHtml = function() {
var dataJSONArray = userData;
var initTable1 = function() {
var table = $('#user-table');
// begin table
table.DataTable({
responsive: true,
data: dataJSONArray,
columnDefs: [
{
targets: -1,
title: 'Actions',
orderable: false,
render: function(data, type, full, meta) {
//this is where I need help. I need for each a-tag to link to a django url pattern such as href="{% url 'users:select-user' id=id_value %}"
return '<i class="la la-edit"></i>';
},
},
],
});
};
return {
//main function to initiate the module
init: function() {
initTable1();
}
};
}();
jQuery(document).ready(function() {
SourceHtml.init();
});
I need a href link to a django url pattern such as href="{% url 'users:select-user' id=id_value %}" in each a tag. however, I can't get the values from the cells.
Datatables columns.render option can be used to access full data source of current row.
By using columns.render as function type, we can use third (3)
parameter to access another column index form same row of data
source.
var userData = [[1,26,'John','Smith'],[2,33,'Dave','Johnson'],[1,22,'Aaron','Jones']];
$('#example').dataTable( {
"columnDefs": [ {
"targets": -1,
"data": null,
"title": 'Actions',
"render": function ( data, type, row, meta ) {
return 'Download';
}
} ]
} );
I tried using datatables for live data but my problem is, every time my data updates, I can't use searching and every time I use pagination, it goes back to first page. Can somebody knows what datatable plugin is compatible with angular?
Here is my code for realtime update of data:
angular.module('selectExample', [])
.controller('ExampleController', ['$scope','$interval', function($scope,$interval) {
$interval(function () {
$scope.register = {
regData: {
branch: {},
},
names: [
{name:"narquois"},{name:"vorpal"},{name:"keen"},
{name:"argol"},{name:"long"},{name:"propolis"},
{name:"bees"},{name:"film"},{name:"dipsetic"},
{name:"thirsty"},{name:"opacity"},{name:"simplex"},
{name:"jurel"},{name:"coastal "},{name:"fish"},
{name:"kraken"},{name:"woman"},{name:"limp"},
],
};
}, 1000);
}]);
<script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.7.5/angular.min.js"></script>
<div ng-app="selectExample" ng-controller="ExampleController">
<table id="example" width="100%">
<thead>
<tr align="center">
<th>Name</th>
</tr>
</thead>
<tbody>
<tr ng-repeat="person in register.names">
<td align="center">{{ person.name }}</td>
</tr>
</tbody>
</table>
</div>
Enable state saving and override state save/load handlers to use only the table's DOM id:
$('#example').dataTable( {
stateSave: true,
stateSaveCallback: function(settings,data) {
localStorage.setItem( 'DataTables_' + settings.sInstance, JSON.stringify(data) )
},
stateLoadCallback: function(settings) {
return JSON.parse( localStorage.getItem( 'DataTables_' + settings.sInstance ) )
}
} );
You have to initialize your DataTable with the option stateSave. It enables you to keep the pagination, filter values, and sorting of your table on page refresh. It uses HTML5's APIs localStorage and sessionStorage.
$('#example').dataTable( {
stateSave: true
});
I need help with my code, I'm trying to learn Backbone for my Social Project. I'm trying to render a view from a collection that I got from an API (deployd API)
Here is the HTML code for the table:
<div class="container-fluid">
<table id= "teachers">
<thead>
<tr>
<th>Name</th>
<th>Last Name</th>
<th>Code</th>
<th>Last time online</th>
</tr>
</thead>
<tbody id="table-body"></tbody>
</table>
</div>
<script type="text/template" id="teacher-template">
<td><%= name %></td>
<td><%= lastname %></td>
<td><%= code %></td>
<td><%= lastactivity %></td>
</script>
Here is the JS code:
var TeacherModel = Backbone.Model.extend({
defaults: {
id:'',
name: '',
lastname: '',
code: '',
lastactivity: ''
}
});
var TeacherCollection = Backbone.Collection.extend({
url: "/teachers",
model: TeacherModel
});
var teachercollection = new TeacherCollection();
teachercollection.url = '/teachers';
teachercollection.fetch({
success: function(collection, response) {
console.log("Done!!");
}, error: function(collection, response) {
alert(response);
}
});
var TeachersView = Backbone.View.extend({
el: '#table-body',
initialize: function() {
this.render();
},
render: function() {
this.$el.html('');
teachercollection.each(function(model) {
var teacher = new TeacherView({
model: model
});
this.$el.append(teacher.render().el);
}.bind(this));
return this;
}
});
var TeacherView = Backbone.View.extend({
tagName: 'tr',
template: _.template($('#teacher-template').html()),
render: function() {
this.$el.html(this.template(this.model.attributes));
return this;
}
});
// Launch app
var app = new TeachersView;
So my question is, how I can pass a collection to a view, or a model of the collection to a view? I want to render the data in each row from the table. The browser gets the collection, as you can see here:
I've been trying for days, and I just can't understand the logic, I have read the documentation, and a little of the Addy Osmani's book but just can't get my head on it, can someone explain it to me? Been looking for answers in this site but some on them include some "add models" stuff, which confuse me more.
(The parameters of the model in the image, differ from the code. I'd translate to make it more easy to understand.)
how I can pass a collection to a view, or a model of the collection to a view?
You are already doing that in your code:
var teacher = new TeacherView({
model: model
});
Here you're passing a model to view's constructor using model option.
You can pass a collection to view via it's constructor like:
var app = new TeachersView({
collection:teachercollection
});
Which you can access inside the view via this.collection and this.model respectively.
var TeachersView = Backbone.View.extend({
el: '#table-body',
initialize: function() {
this.render();
},
render: function() {
this.$el.html('');
this.collection.each(function(model) {
this.$el.append(new TeacherView({
model: model
}).el);
},this);
return this;
}
});
Note that fetch() is asynchronous, so you'll need to wait till it succeeds before rendering the view.
See the suggestions in this answer regarding the changes I made to your render method.
this answer might help understanding a thing or two.
I'm a little lost with my view rendering--first time trying to do this. I have my templates set up similar to this application.
So far I have it rendering the template for the CompositeView but it doesn't render any of the ItemViews. It doesn't even trigger the rendering method to try to debug so I'm not sure where I can log pieces to see where it's getting stuck... Here's the code:
This is my ItemView:
define([
'jquery',
'underscore',
'backbone',
'text!templates/service/item.ejs'
], function($, _, Backbone, template) {
ServiceItemView = Backbone.Marionette.ItemView.extend({
tagName: 'tr',
template: '#service-item-template'
});
}
);
This is my CompositeView: Update: Added in my requirejs code to show that ServiceItemView is loaded before ServiceTableView
define([
'jquery',
'underscore',
'backbone',
'views/service/item',
'text!templates/service/table.ejs'
], function($, _, Backbone, ServiceItemView, template) {
var ServiceTableView;
ServiceTableView = Backbone.Marionette.CompositeView.extend({
tagName: 'table',
id: 'service-table',
itemView: ServiceItemView,
itemViewContainer: 'tbody',
template: '#service-table-template',
appendHtml: function(collectionView, itemView){
console.log("here");
//collectionView.$("tbody").append(itemView.el);
}
});
}
);
Here's where I attempt to render it:
service_collection = new ServiceCollection([
new Service({
name: "Men's Cut",
length: 108000,
price: 2500
}),
new Service({
name: "Women's Cut",
length: 324000,
price: 5000
})
]);
service_table = new ServiceTableView({
collection: service_collection
});
App.main_region.show(service_table);
Update: Here are the two templates:
ServiceItemView Template:
<script type="text/html" id="service-item-template">
<td><%= name %></td>
<td><%= length %></td>
<td><%= price %></td>
<td class="actions">
<input type="button" class="icon" value="Delete" />
</td>
</script>
ServiceTableView Template:
<script type="text/html" id="service-table-template">
<thead>
<tr>
<th>Name</td>
<th>Time allotment</th>
<th>Pricing</th>
<th class="actions">Actions</th>
</tr>
</thead>
<tbody>
</tbody>
</script>
Again, the ServiceTableView template is rendered, but none of the Services are rendered underneath.
Any help is appreciated. Even pointers on where to stick log statements to get more information.
Thanks!
Turns out the Collections I had created were written:
Backbone.Model.extend instead of Backbone.Collection.extend. I must have copied the code from the model when creating the collection to speed up writing it.
Fixed now and working if anyone would like to use the above code for an example for their own projects.