RequireJS + PhoneGap + Backbone - backbone.js

I'm having problem with RequireJS giving me some 'Uncaught TypeError', all i have is the basic structure and when i test it in ripple i often get this.
Uncaught TypeError: Cannot call method 'local_data_exist' of undefined
Which is a function in one of my library.
Uncaught TypeError: Cannot read property 'jqmNavigator' of undefined
Or this.
So since the errors are not consistant they give me a hard time to debug. Wonder if anyone has face this before.
require.config({
deps:['main'],
baseUrl: "js",
paths:{
// Pointing to Main possible fix for random undefined
app: 'main',
// jQuery
jquery:'libs/jquery/jquery-1.9.1.min',
// jQuery Plugin for Dfp
dfp: 'libs/jquery/jquery.dfp.min',
// jQuery Mobile framework
jqm:'libs/jquery.mobile/jquery.mobile-1.3.0.min',
// Backbone.js library
Backbone:'libs/Backbone/Backbone',
// Backbone.js Adapter
localStorage: 'libs/Backbone/backbone.localStorage',
// RequireJS plugin
text:'libs/require/text',
// RequireJS plugin
domReady:'libs/require/domReady',
// underscore library
underscore:'libs/underscore/underscore',
// jQuery Mobile plugin for Backbone views navigation
jqmNavigator:'libs/jquery.mobile/jqmNavigator',
//TouchSwipe
touchSwipe: 'libs/jquery/jquery.touchSwipe.min',
//Moment (Date Plugin)
moment: 'libs/moment/moment',
// Language plugin
lang: 'libs/moment/langs.min',
// Utility Lib
utils: './utils'
},
shim:{
Backbone:{
deps:['underscore', 'jquery'],
exports:'Backbone'
},
app: {
deps:['jquery','Backbone','underscore'],
exports: "App"
},
underscore:{
exports:'_'
},
dfp : {
deps:['jquery']
},
jqm:{
deps:['jquery', 'jqm-config', 'jqmNavigator']
},
touchSwipe:{
deps:['jquery']
},
lang:{
deps:['moment']
},
utils:{
deps:['jquery']
}
},
waitSeconds: 200,
priority: ['jquery']
});
require(['jquery', 'domReady', 'Backbone', 'jqm-router', 'models/ApiModel', 'jqm', 'underscore', 'jqm-config', 'jqmNavigator'],
function ($, domReady, Backbone, AppRouter, Api) {
domReady(function(){
window.Api = Api;
$(this).router = new AppRouter();
});
}
);

Related

JST is undefined - Yeoman , Backbone - Template cannot be loaded

Am new to Yeoman and I generated a Backbone application using generator-backbone
This is my main.js ( require js config)
/*global require*/
'use strict';
require.config({
shim: {,
handlebars: {
exports: 'Handlebars'
}
},
paths: {
jquery: '../bower_components/jquery/dist/jquery',
backbone: '../bower_components/backbone/backbone',
underscore: '../bower_components/lodash/dist/lodash',
handlebars: '../bower_components/handlebars/handlebars'
}
});
require([
'backbone'
], function (Backbone) {
Backbone.history.start();
});
Now I created a view using yo backbone:view Login
This is the generated view
define([
'jquery',
'underscore',
'backbone',
'templates'
], function ($, _, Backbone, JST) {
'use strict';
var LoginViewView = Backbone.View.extend({
template: JST['app/scripts/templates/LoginView.hbs'],
tagName: 'div',
id: '',
className: '',
events: {},
initialize: function () {
this.listenTo(this.model, 'change', this.render);
},
render: function () {
this.$el.html(this.template(this.model.toJSON()));
}
});
return LoginView;
});
When I run the app with LoginView, i get an error
Error: Script error for: templates http://requirejs.org/docs/errors.html#scripterror
Apparently I see templates is no where defined in main.js. What am i missing while running the yeoman generator
If you did the same blunder mistake like m, just verify this
After generating the code, and if its shows template is undefined or u find the template.js missing, check the following steps
run grunt handlebars (include --force if you want to ignore any warning/errors)
This will pre compile the .hbs file make a single template.js file.
But the catch here is, it wont work out of the box, the template.js is written in the location app/.tmp/scripts/template.js location.
You can modify main require configure file accordingly, or open GruntFile.js and modify this function
grunt.registerTask('createDefaultTemplate', function () {
grunt.file.write('/your/custom/path/to/templates.js', 'this.JST = this.JST || {};');
});
Also verify if u have this line in GruntFile.js
grunt.loadNpmTasks('grunt-contrib-handlebars');
if not, add it at the very last (ofcourse not after the function block)

BackboneJS How to include MomentJS <locale> feature

I want to include the locale-feature from MomentJS into one of my Backbone Views. http://momentjs.com/docs/#/i18n/adding-locale/ - but I get an error:
Uncaught TypeError: undefined is not a function - and it refers to:
return moment.defineLocale('da', {
In my config.js I have:
require.config({
deps: ['main'],
paths: {
jquery : '../lib/jquery-2.1.1.min',
underscore : '../lib/lodash-2.4.1',
backbone : '../lib/backbone',
moment : '../lib/moment.min',
locale : '../lib/locale/da'
},
And in my View I have:
define([
'app',
'backbone',
'moment',
'locale'
],
function (App, Backbone, moment, locale) {
...
Does anyone know what the issue could be?
Here is the oficial documentation http://momentjs.com/docs/#/use-it/require-js/
seems to me that there is a little trick to work with requirejs

Using Angular with breeze and require

i am trying to use angular with breeze and requireJS
how ever i am getting error of
Uncaught Error: Module name "ko" has not been loaded yet for context: _. Use require([])
i have configured
define("breezeConfig", ["breeze"], function(breeze) {
// configure to use the model library for Angular
//breeze.config.initializeAdapterInstance({ dataService: "OData" });
breeze.config.initializeAdapterInstance("modelLibrary", "backingStore", true);
// configure to use camelCase
breeze.NamingConvention.camelCase.setAsDefault();
var serverAddress = "/odata/";
var manager = new breeze.EntityManager(serverAddress);
return breeze;
});
and in the main module
require.config({
baseUrl: "/app",
paths: {
"jQuery": "lib/jquery-1.8.2",
"angular": "lib/angular",
"angular-resource": "lib/angular-resource",
"text": "lib/text",
"Q": "lib/q",
"breeze": "lib/breeze.min"
and so on
at the end
require([
'jQuery',
'Q',
'breeze',
'angular',
'app',
'controllers',
'routes',
'breezeConfig'
], function ($, angular, app) {
angular.element(document).ready(function () {
angular.bootstrap(document, ['AMail']);
});
where am i wrong?
Yes ... we know. It's been reported on S.O. before. We have a fix on the way (next release).
Meanwhile, inside your main module do two things:
1) define a bogus knockout module
define('ko', function() {}); // do nothing
2) add a shim to your require.config function:
...
shim: {
jquery: { exports: '$' },
angular: { exports: 'angular' },
breeze: { deps: ['ko', 'jquery', 'Q'] }
}
...
You'll need the shim (minus the 'ko' dependency!) even after we fix the ko problem. Breeze depends on 'jquery' and 'Q' which must be loaded first. You may or may not need the other shim lines.

requirejs + backbonejs + optimizer = backbone undefined

Backbone doesn't get called in the indexview module.
using requirejs 2.1.5/2.1.4 and backbonejs 0.9.10
main.js after running r.js
...
// this is causing the backbone to return
// null/undefined in the next define call below
define("backbone", function(){});
define('views/index/IndexView', [
'underscore',
'backbone',
'text!templates/index/indexTemplate.html'
], function(_, Backbone, indexTemplate){
console.log(Backbone); // returns undefined
var IndexView = Backbone.View.extend({
...
BUT if I take out the first define call that registers backbone as a module, everything
works fine. but backbone-min.js gets loaded separately. but for now it's the only way
to make the script run. I am definitely missing something here.
main.js
require.config({
paths: {
underscore : 'libs/underscore/underscore-min',
backbone : 'libs/backbone/backbone-min'
templates : '../templates'
},
shim: {
'backbone': {
deps: ['jquery','underscore'],
exports: 'Backbone'
}
}
});
require(['app'], function(App){
App.initialize();
});
build.js
({
appDir: "../",
baseUrl: "js",
dir: "../../build",
optimize: "none",
paths: {
"jquery": "libs/requirejs/require-jquery",
"underscore" : 'libs/underscore/underscore-min',
"backbone": 'libs/backbone/backbone-min',
"templates": '../templates',
},
modules: [
{
name: "main",
exclude: ["jquery"]
}
]
})
I'm still getting my feet wet with backbone and requirejs.
any feedback is much appreciated.
First of all, you don't need that define('backbone',...). What is that part for anyways? You don't need to define Backbone as a module. Requirejs is doing the job of making Backbone available for you to use throughout your framework. As you can see in your code, by calling Backbone.View.extend(), Backbone already exists. If you want to inspect it, don't use console.log, use console.dir instead. In the chrome inspector it formats the output nicely.
Secondly, add underscore to the backbone deps array in your shim.
I've just had this issue, you need to add the 'shim' from your main.js to your build.js file, and will work like a charm ;)

Requirejs2: How to handle own files?

I have configured requirejs to load the core libs (jquery, underscore, backbone).
Now I would like to add my backbone models, controllers, views, etc to be loaded asyncronly
I found a lots of tutorials to this topic and lots of "ready" boilerplates unfortunatly I mentioned that most approaches are depreceated or rather complicated (even there are better approaches).
One example is how I configured requirejs for the main libs:
https://stackoverflow.com/a/10914666/1309847
So how do I load Backbone Views, Models, Collections, Routers, Controllers and Templates with a simple and valid Requirejs configuration?
I followed youre advice but get some strange error
main.js
require.config({
paths: {
jquery: 'vendors/jquery/jquery',
underscore: 'vendors/underscore/underscore',
backbone: 'vendors/backbone/backbone'
},
shim: {
underscore: {
exports: '_'
},
backbone: {
deps: ['underscore', 'jquery'],
exports: 'Backbone'
}
}
});
require(['app'], function(app){
});
app.js
define(['jquery', 'underscore', 'backbone'], function($, _, Backbone){
var Message = new Backbone.Model.extend({
//idAttribute: '_id',
//defaults: { body: '' }
//url: function(){ return this.id ? '/messages/' + this.id : '/messages'; }
});
var newMessage = new Message({ body: 'hi' });
newMessage.save();
});
The error occours in app.js:
Uncaught TypeError: Object [object Object] has no method 'apply'
When I comment the new Backbone.Model.extend part I don't get any error anymore.
in my experience, the best way to bootstrap your application is by creating a Backbone.Router. So you can associate urls with your application functionality.
If you are using RequireJS+Backbone, you probably have a main.js where RequireJS is configured (paths, shims, etc). The first call to "require" is used to load a initial script in order to bootstrap the whole app.
For example:
/**
* main.js - RequireJS bootstrap
*/
require.config({
paths: {
//your paths
},
shim: {
//your shims
}
});
require(
[
'app' //app.js is at the same directory as main.js
],
function(app) {
app.init();
}
);
then in app.js you can create a new Router instance, or you can just start creating Views and Models.
For further reference: http://addyosmani.github.com/backbone-fundamentals/
So as I have now understood right: You have to wrap a requirejs function around youre own custom js file.
The function is called define. The first parameter is an array of the dependencies which you have defined in the main.js file or a relative path to another custom js from you.
The second parameter is the callback which holds the original file. Important is that you return the object, function, array or variable which you want to share.
The whole thing looks like this:
define(
['underscore', 'backbone'], // the dependencies (either relative paths or shortcuts defined in main.js
function(_, Backbone){ // the return statement of the deps mapped to a var
var MessageModel = Backbone.Model.extend({ // the original code, file
defaults: { body: '' },
initialize: function(){}
});
return MessageModel; // the return statement, sharing the "final result", sometimes you return the initialize parameter
});
The same for a collection wrapping the models:
define(
['jquery', 'underscore', 'backbone', 'models/message_model'], // deps and the last one is the relative path
function($, _, Backbone,MessageModel){ // same as above explained
var MessageCollection = Backbone.Collection.extend({
model: MessageModel,
initialize: function(){}
});
return MessageCollection;
});
I now only have to figure out how I can bootstrap to whole application. But I think I need more knowledge of backbone to do this :)

Resources