How to display handlebars templates on two separate pages? - javascript

I have 2 HTML pages (page1.html and page2.html) and 1 data source. I'm able to display the handlebars data in page1.html by essentially making the entire page into a template
page1.html:
<body>
<div class="row" id="content-placeholder"></div>
<script id="some-template" type="text/x-handlebars-template">
<h1>{{Title}}</h1>
</script>
data.js
var source = $("#some-template").html();
var template = Handlebars.compile(source);
var gData = {
title: 'My Website'//,...
}
$("#content-placeholder").html(template(gData));
This works, but I'd like to display part of the same data object on the second html page.
page2.html
<body>
<div class="row" id="content-placeholder2"></div>
<script id="second-template" type="text/x-handlebars-template">
</script>
I tried using partials but I don't think that's the solution. How can I compile two templates?
Thanks!

Related

Add external Angular JS $scope.variable to HTML script tag variable

I am using AngularJS to retrieve some JSON data. Once the data is retrieved it should be accessible from the index.html page within <script> tags. Currently, I am able to print the $scope.article_names variable onto the body of the HTML page however I cannot understand why I am unable to retrieve that same Angular $scope variable within Javascript tags.
Here is the Angular code:
app.controller('dataCtrl', function($scope, $http) {
$http.get("http://127.0.0.1:8000/article_names")
.then(function(response) {
$scope.article_names = response.data;
});
console.log('test')
});
And the HTML is:
<body ng-app="myApp" ng-controller="dataCtrl">
<div >
<h1>This is a test</h1>
{{ collection_find }}
{{ article_names }}
<!--The below prints the result output gathered from angular -->
{$ article_names $}
<div id="chart"></div>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.5.8/angular.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.0rc1/angular-route.min.js"></script>
<script src="{% static 'javascript/angular.js' %}"></script>
<script>
var article_names = $scope.article_names;
// this does not print anything to the console
console.log(article_names);
</script>
How can I access that $scope.article_names variable into local <script tags? The thing I cannot understand the most is the fact that the $scope.article_names is accessible within the main body of the HTML, but does not work within <script tags

Handlebars template not displaying context data

I am trying to build a quiz application using Node express and Handlebars as the templating engine.
I have the following template:
<div id="quiz">
<div class="container">
<div class="row" id="quiz-header-row">
<div>
<div id="question-title"></div>
</div>
</div>
<div class="row" id="quiz-choices-row">
<div id="choices"></div>
</div>
<div class="row" id="quiz-footer-row">
<button id="quiz-next-btn" class="btn btn-success">Next</button>
</div>
</div>
</div>
<!-- Template -->
<script id="choices-template" type="text/x-handlebars-template">
<div>\{{choices}}</div>
<div>
{{#each choices}}
{{this}}
{{/each}}
</div>
</script>
If I do not use the backslash before curly braces, handlebars displays an empty string and thus I cannot write this:
<div>{{choices}}</div>
Found on handlebars official website that I have to use: \{{choices}}.
The javascript that fills the template with data:
renderChoices: function() {
var template = Handlebars.compile($('#choices-template').html());
var context = {
// array of quiz item choices
choices: Quiz.questions[Quiz.currentIndex].choices
};
$('#choices').html(template(context));
},
The issue I am facing is the #each block that does not display anything. The backslash before {{#each choices}} cannot be used as in the example above because the server throws "server internal error: 500".
This is the console logged context:
console log
The fiddle below works as needed and does not need the backslashes
fiddle.
But the exact same code I run in my project using Node does not display anything written inside the #each block.
I have Handlebars both on the server (express-handlebars) and on the client. Considering the results, I am doing something the wrong way.
Thank you in advance.
EDIT: Fixed by precompiling the templates in external files and including them as scripts in the view.
Try something like this:
{{#each choices as |choice|}}
{{choice}}
{{/each}}
And make sure choices is populated as you expect.
i just tried to execute your code it's printing the data, i have used jquery-2.2.1 and handlebars 2.0.0
<!DOCTYPE html>
<html>
<head>
<link rel="stylesheet" href="style.css">
<script src="script.js"></script>
</head>
<body>
<script id="address-template" type="text/x-handlebars-template">
<div>
{{#each choices}}
{{this}}
{{/each}}
</div>
</script>
<!--Your new content will be displayed in here-->
<div class="content-placeholder"></div>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.2.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/handlebars.js/2.0.0/handlebars.js">
</script>
<script>
$(function () {
// Grab the template script
var theTemplateScript = $("#address-template").html();
// Compile the template
var theTemplate = Handlebars.compile(theTemplateScript);
// Define our data object
var context={
choices: ["choice1","choice2","choice3"]
};
// Pass our data to the template
var theCompiledHtml = theTemplate(context);
// Add the compiled html to the page
$('.content-placeholder').html(theCompiledHtml);
});
</script>
</body>
</html>
Here is a link to plunker, i also tried with handlebars 4.0.3 and jquery 3.1.1 it's running fine.

abstracting handlebars templates into external files w/o AJAX

Is there any way to load handlebars templates more simply? Seems like an easy thing to be able to do. If I have the following code for index.html:
<body>
<h1>From the index.html</h1>
<div id="hbs"></div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/handlebars.js/4.0.5/handlebars.min.js"></script>
<script id="test" type="text/x-handlebars-template">
<h2>This is from HBS</h2>
<p>
hbs generated this p tag!
</p>
</script>
<script src="js/script.js"></script>
</body>
Here's the code for the script to compile the template in js/script.js:
var template = Handlebars.compile(document.querySelector("#test").innerHTML)
document.querySelector("#hbs").innerHTML = template({})
This works fine,but when I open the index.html I can see the header and p tag generated through the template. There has to be an easy way to abstract this template into a separate file!
You can put your template in a hbs file :
template.hbs:
<script type="text/x-handlebars-template">
<h2>This is from HBS</h2>
<p>
hbs generated this p tag!
</p>
</script>
And then use ajax to get your file instead of a querySelector to get your html
$document.ready(function(){
$.get( '/url/template.hbs', function( source ) {
var template = Handlebars.compile(source);
document.querySelector("#hbs").innerHTML = template({});
}
});

Handlebars.js wont compile/output my template/data

I'm playing around with Handlebars.js and trying to compile a small template. I am only using Handlebars.js and nothing more.
I am working locally on my computer, and not via any form of server.
my "html" looks like this. nothing special.
<!doctype html>
<html>
<head>
<script src="js/vendor/handlebars.min-4.0.4.js"></script>
</head>
<body>
<script id="menu-template" type="text/x-handlebars-template">
<h1>{{title}}</h1>
</script>
<section id="menu">
</section>
<script src="js/menu.js"></script>
</body>
</html>
And my JS is
var source = document.getElementById('menu-template').innerHTML;
var template = Handlebars.compile(source);
var data = {title: "test"};
document.getElementById('menu').innerHTML = template(data);
It seems that template() does not return anything, i don't get any result except what looks like a empty string.
And i have been playing around with this for a few hours and searching the internet for answers but no result.
Am i doing anything wrong here?
// Edit added the rest of the html page.
The code seems correct just make sure the Handlebars.js file is properly included before the existing script tag.
Ref for Handlebars CDN : https://cdnjs.cloudflare.com/ajax/libs/handlebars.js/4.0.4/handlebars.js

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.

Categories

Resources