how to show html contend in backbone.js - javascript

I am trying to load html file in backbone.js .but i am not able display view .could please tell where i did wrong ..i will share my code with u.
**code**: http://goo.gl/CcqYwX
$(document).ready(function(){
var ContactManager = new Marionette.Application();
ContactManager.addRegions({
mainRegion:"#contend"
})
ContactManager.on("start", function(){
console.log("ContactManager has started!");
});
ContactManager.start();
// router
var routers = Backbone.Router.extend({
routes: {
"": "showFirstPage"
},
showFirstPage:function(){
}
})
var ToolItemView = Backbone.Marionette.ItemView.extend({
template: 'template/test.html',
});
var toolItemview = new ToolItemView();
ContactManager.mainRegion.show(toolItemview);
})
i am trying to load test.html file but i am not able to do that..?

Marionette uses underscore templating by default. You'll need to either use some sort of external loader to load them in as variables, or you can place them in the DOM as script elements that you can then reference with your template property. See here:
So for instance if you put it in your html, the code would look like
<html>
<body>
<script type="text/template" id="example">
<div class="template-content-here">
<%=variable_here %>
<!-- probably more stuff here -->
</div>
</script>
<script src="myApp.js"></script>
</body>
</html>
then you could reference it in JavaScript as
var ToolItemView = Backbone.Marionette.ItemView.extend({
template: '#example',
});
That works nicely for small projects, for larger projects you'll want some sort of build/module system to pull in the precompiled templates and reference those directly.
Way more info here: http://marionettejs.com/docs/v2.3.1/marionette.renderer.html

Related

Create and Use a Custom HTML Component?

I have the following local html:
<html>
<head>
<link rel="import" href="https://mygithub.github.io/webcomponent/">
</head>
<body>
<!-- This is the custom html component I attempted to create -->
<img-slider></img-slider>
</body>
</html>
and the following attempt at a template:
<template>
<style>
.redColor{
background-color:red;
}
</style>
<div class = "redColor">The sky is blue</div>
</template>
<script>
// Grab our template full of slider markup and styles
var tmpl = document.querySelector('template');
// Create a prototype for a new element that extends HTMLElement
var ImgSliderProto = Object.create(HTMLElement.prototype);
// Setup our Shadow DOM and clone the template
ImgSliderProto.createdCallback = function() {
var root = this.createShadowRoot();
root.appendChild(document.importNode(tmpl.content, true));
};
// Register our new element
var ImgSlider = document.registerElement('img-slider', {
prototype: ImgSliderProto
});
</script>
As described in this article. When I run the code, I get:
Uncaught TypeError: Cannot read property 'content' of null
at HTMLElement.ImgSliderProto.createdCallback ((index):20)
In other words document.querySelector('template'); returns null. What gives?
My goal is to create custom html element and display it on the website that links the template code. I am 100% sure I am pulling the remote template code correctly (obviously, since I get the error in that code).
P.S. I am using latest Chrome, so I shouldn't need polyfills.
Try this:
var tmpl = (document.currentScript||document._currentScript).ownerDocument.querySelector('template');
The problem you ran into is that the template isn't really part of document but it is part of the currentScript. Due to polyfills and browser differences you need to check for currentScript and _currentScript to work correctly.
Also be aware that HTML Imports will never be fully cross browser. Most web components are moving to JavaScript based code and will be loaded using ES6 module loading.
There are things that help create templates in JS files. Using the backtick (`) is a reasonable way:
var tmpl = document.createElement('template');
tmpl.innerHTML = `<style>
.redColor{
background-color:red;
}
</style>
<div class = "redColor">The sky is blue</div>`;

Javascript ads in Angular templates

I'm trying to render a Javascript ad in my Angular template but it will not show up. I've found some solutions when they append the Javascript to the head tag but I want the ad to be placed in my Html (inside body).
Here is a Plunker: https://plnkr.co/edit/WHhQ95gS5HKSphmmirio
Here is a simple plain Html example that works.
<html>
<head>
</head>
<body>
<div class="ad">
<script src="http://media.affiliatelounge.com/data/nordicbet/ad_js/display_88.js?ad=ad_793270_88.html&size=300x250&clicktag=http://record.affiliatelounge.com/_sVuSoFFh4LK58VwA2IUESrKVVrME-Gsw/1&media=108786&campaign=1"></script>
</div>
</body>
</html>
But if I add the div inside an Angular template it will not render and the console says nothing.
I have some ads up and running here (http://www.odds.nu/erbjudanden), but they are either .gif or iframes. I want to be able to show Javascript ads instead. They are added to the Html but are not rendered (placed in the bottom of the page).
Can $sce or $compile help somehow?
My index.html
<div data-ng-view="" class="mainView"></div>
My app.js
$routeProvider.when("/erbjudanden", {
controller: "offerController",
templateUrl: "/app/templates/offers.html"
});
My offers.html
<div class="ad">
<script src="http://media.affiliatelounge.com/data/nordicbet/ad_js/display_88.js?ad=ad_793270_88.html&size=300x250&clicktag=http://record.affiliatelounge.com/_sVuSoFFh4LK58VwA2IUESrKVVrME-Gsw/1&media=108786&campaign=1"></script>
</div>
Any solution?
If you had inspected result of that url request(make sure adBlock is off)
https://wlbetclic.adsrv.eacdn.com/S.ashx?btag=a_17172b_14837c_&affid=12824&siteid=17172&adid=14837&c=
You will see the actual result
document.write('<script type="text/javascript" src="//wlbetclic.eacdn.com/TrafficOpt/s.5.4.min.js?t=1"></script>');
document.write('<script type="text/javascript" src="//wlbetclic.eacdn.com/wlbetclic/img/js/Affiliate_12824.js?t=20160224"></script>');
//other lines omitted for brevity
So this file is executing document.write which obviously will not work in angular, just because they are totally different (even though you could trigger digest cycle somehow, you still don't have access to modify that script file, as it's generated by 3rd party server and has own variables)
What i would do is - make a page like ad.html, just like index.html or 404.html, then request this file from angular (not as template, but like a view file) as an iframe src with custom attributes
And i would use custom DOM element, and populate contents with jQuery, or with angular, look at jQuery sample below
Also i would need krux/postscribe plugin, because you cannot use document.write in async html files
<!-- create multiple holders -->
<ad-holder url="https://wlbetclic.adsrv.eacdn.com/S.ashx?btag=a_17172b_14837c_&affid=12824&siteid=17172&adid=14837&c="></ad-holder>
<div class="black-widow">
<!-- with size attributes -->
<ad-holder url="http://google.com" width="100" height="40"></ad-holder>
</div>
<!-- jQuery population with iframe -->
<script>
//get all custom elements
$('ad-holder').each(function(){
//create iframe placeholder
var $iframe = $(document.createElement('iframe'));
//get url of custom element
var url = $(this).attr('url');
//request ad.html file with params, currently it's url param
$iframe.attr('src', 'ad.html?url=' + url);
//some stylings acceptable here
$iframe.width('100px');
//or get styles from custom-element
var heightValue = $(this).attr('height');
$iframe.height(heightValue || '50px');
//rebuild custom element with iframe
$(this).append($iframe);
});
</script>
<!-- angular populate with iframe directive -->
<scrip>
angular.module('app', []).directive('adHolder', function(){
return {
restrict: 'E',
scope: { url: '#' },
//you could also execute in compile-phase
link: function(scope, element, attribute){
var $iframe = angular.element(document.createElement('iframe'));
$iframe.attr('src', 'ad.html?url=' + scope.url);
element.html($iframe);
}
}
});
</script>
And ad.html would look like
<body>
<div id="ad"></div>
<script>
function getQueryVariable(variable) {
var query = window.location.search.substring(1);
//for the sake of simplicity we expect only 1 param (url)
return query.replace('url=', '');
}
var adUrl = getQueryVariable('url');
if (adUrl)
postscribe('#ad', '<script src="' + adUrl + '"><\/script>');
else {
var $h1 = $(document.createElement('h1'));
$h1.text('No ad available');
$(document.body).append($h1);
}
</script>
</body>
The best part of this solution is that you can reuse same custom-element with different url attribute for any other ads
Checkout jQuery real working demo
Although this demo heavily uses jQuery, it's easy to tweak for angular version, which i would suggest you to implement as homework =)
Short answer:
Angular does not perform compilation of Javascript in HTML templates. You either put the HTML manually in the page (instead of loading as template) or have another way to call it.
You can read more here

KnockoutJS with Sammy.js SPA suggestion

I am building a SPA app with the following structure:
<body>
<!-- Main Container for our application -->
<div id="main">
</div>
<!-- End Main Container -->
<!-- Vendor Libraries -->
<script src="js/vendor/jquery/jquery-1.11.0.min.js"></script>
<script src="js/vendor/knockout/knockout-3.1.0.js"></script>
<script src="js/vendor/sammy/sammy-latest.min.js"></script>
<!-- Models -->
<script src="js/models/model1.js"></script>
<!-- ViewModels -->
<script src="js/viewmodels/viewModel1.js"></script>
<script src="js/viewmodels/viewModel2.js"></script>
<!-- App scripts -->
<script src="js/routes.js"></script>
<script src="js/app.js"></script>
</body>
The html file has a div which will hold the html for each respective page handled by Sammy.js wit the following code:
Sammy('#main', function() {
this.get('#/', function(context) {
context.$element().load('views/main1.html', function() {
ko.applyBindings(new ViewModel1(), $("#home")[0]);
});
});
this.get('#/text', function(context) {
context.$element().load('views/text.html', function() {
ko.applyBindings(new ViewModel2(), $("#home")[0]);
});
});
this.get('', function(context) {
this.redirect('#/');
});
}).run();
Each time I am loading the markup found in each html file and then apply my viewmodel.
My questions are:
Can you suggest any other possible way to load the markup apart from using jquery load().
Are my old bindings being disposed each time a new route is being called?
1: This question is very 'open'. There are tons of way to do this that aren't jquery.load. But the real question is: do you NEED another way? Do you need some form of control that $.load isn't giving you?
If you do, consider switching to jquery.get or jquery.ajax, and handle the request yourself. At the bottom of this post is an example.
2: No, because you keep applying the bindings to the same element. What you instead want to do is apply bindings to the first element WITHIN the container with id 'home'. Then, when you switch views, you want to do ko.removeNode on the view that you're removing. Below is a code example that illustrates how you can gain some more control over the process and clean up your bindings behind you.
function loadView(url, viewModel) {
$.get(url, function (response) {
var $container = $('#home'),
$view = $container.find('.view'),
$newView = $('<div>').addClass('view').html(response);
if ($view.length) {
ko.removeNode($view[0]); // Clean up previous view
}
$container.append($newView);
ko.applyBindings(viewModel, $newView[0]);
});
}
this.get('#/', function(context) {
loadView('views/main1.html', new ViewModel1());
});
this.get('#/', function(context) {
loadView('views/text.html', new ViewModel2());
});
What I did in this example is using jquery.get so we gain control over the whole process of loading and displaying the HTML. I then refactored part of the logic out into a separate function that is generic enough to use on every view you have.
When a view is retrieved I store it in an element with class 'view'. The bindings are applied to this element and it is stored in your container element. When switching views I clean up and remove the old view before the new view is added to the DOM.
This is just the beginning: In the loadView function, you can now try to call generic methods that you can implement on your viewmodels, such as 'activate' and 'deactivate'. You can also show a spinner instead of a view when a new view is being retrieved, etc.

Kendo : How to render a kendo.View or a kendo.Layout from a separate file?

I would like to know if it is possible to load the content of a kendo.View(...) or kendo.layout(...) from a separate html file?
This is the example from Kendo Hello World Single Page Application :
<div id="app"></div>
<script id="index" type="text/x-kendo-template">
Hello <span data-bind="text: foo"></span>
</script>
<script>
var index = new kendo.View(
"index", // the id of the script element that contains the view markup
{ model: kendo.observable({ foo: "World!" }) }
);
var router = new kendo.Router();
router.route("/", function() {
index.render("#app");
});
$(function() {
router.start();
});
</script>
Is it possible to do somethink like this :
<div id="app"></div>
<script>
var index = new kendo.View(
"hello.html", // the path of the script element that contains the view markup
{ model: kendo.observable({ foo: "World!" }) }
);
var router = new kendo.Router();
router.route("/", function() {
index.render("#app");
});
$(function() {
router.start();
});
</script>
There is now a way to do it. Here is documentation on how to do it: Kendo Remote Templates
Here is the gist of it:
You need to make a template loader that basically reads html/string from a file. Kendo does not supply one in the box but this is the one that they use in their example.(templateLoader.js). Include it on the your html page.
Add your templates in a separate html file. You can store multiple templates in the same file. However you should only be putting templates there ideally. Let's say this is in file mytemplate.html
<script id="index" type="text/x-kendo-template">
Hello <span data-bind="text: foo"></span>
</script>
On your main html page, add a <script> block that calls your template loader with that template file. This will/should inject the templates onto your main page and then you should be able to use it as if it was a local template.
<script>
templateLoader.loadExtTemplate("mytemplate.html");
</script>
It can't be done this way atm. I'm not even sure if it should be doable.
Perhaps fetch the template beforehand using $.get() or .load()?
edit: using .load() you'd have to dynamically create script template and using $.get() append the script template somewhere in the document.

angular load template from url and compile inside div

As I'm new to Angular JS I was wondering how could I load an external template and compile it with some data into the targeted div.
For instance I have this template :
<script type="text/ng-template">
<img src="{{Thumb}}" />
<script>
The div that is supposed to contain the template :
<div data-ng-controller=" ... "></div>
The template is located somewhere in a folder /templates/test.php. Is there a build in way of doing the template loading like a directive would do and compile it against some data that would replace the key {{Thumb}} ( and many others of course ) ?
EDIT : What if I use $routes and load a template when I'm in the root of the website ? How could that be achieved ?
Using $templateRequest, you can load a template by it’s URL without having to embed it into your HTML page. If the template is already loaded, it will be taken from the cache.
app.controller('testCtrl', function($scope, $templateRequest, $sce, $compile){
// Make sure that no bad URLs are fetched. If you have a static string like in this
// example, you might as well omit the $sce call.
var templateUrl = $sce.getTrustedResourceUrl('nameOfTemplate.html');
$templateRequest(templateUrl).then(function(template) {
// template is the HTML template as a string
// Let's put it into an HTML element and parse any directives and expressions
// in the code. (Note: This is just an example, modifying the DOM from within
// a controller is considered bad style.)
$compile($("#my-element").html(template).contents())($scope);
}, function() {
// An error has occurred here
});
});
Be aware that this is the manual way to do it, and whereas in most cases the preferable way would be to define a directive that fetches the template using the templateUrl property.
in Angular there's 2 ways of using template (at least 2 ways that i know about):
the first using an inline template (in the same file) with this syntax:
<script type="text/ng-template">
<img ng-src="{{thumb}}">
</script>
the second one (what you want) is external template:
<img ng-src="{{thumb}}">
so what you need to do is to remove the script part from your template and then use the ng-include in the wanted div like this:
<div ng-include="'templates/test.php'"></div>
need to have double quotes and single quotes to work.
Hope this helps.
Let's say I have this index.html:
<!doctype html> <html lang="en" ng-app="myApp">
<body>
<script src="tpl/ng.menu.tpl" type="text/ng-template"></script>
<mainmenu></mainmenu>
<script src="lib/angular/angular.js"></script>
<script src="js/directives.js"></script>
</body>
</html>
And I have a template file "tpl/ng.menu.tpl" with only these 4 lines:
<ul class="menu">
<li>view1</li>
<li>view2</li>
</ul>
My directives mapping "js/directives.js":
angular.module('myApp',['myApp.directives']);
var myModule = angular.module('myApp.directives', []);
myModule.directive('mainmenu', function() {
return {
restrict:'E',
replace:true,
templateUrl:'tpl/ng.menu.tpl'
}
});

Categories

Resources