Read 03: Flexbox and Templating - Ahmad-Sawalqeh/amman-301d1 GitHub Wiki
With Handlebars, you can separate the generation of HTML from the rest of your JavaScript and write cleaner code.
Just go to http://handlebarsjs.com/ , and click the download button to get the latest version. Now all you have to do is to include the library in your html with a regular <script> tag.
// From File
<script src="handlebars-v2.0.0.js"></script>
// From CDN
<script src="https://cdnjs.cloudflare.com/ajax/libs/handlebars.js/2.0.0/handlebars.js"></script>
The templates have an easy to grasp syntax. They can contain HTML and text, mixed with Handlebars expressions. Expressions are wrapped in double or triple curly braces {{}}. Expressions tell Handlebars to include the value of variables or to execute helper functions. Templates need to be compiled to a JavaScript function before use. You can see an example below.
<!--This is our template. -->
<!--Data will be inserted in its according place, replacing the brackets.-->
<script id="address-template" type="text/x-handlebars-template">
<p>You can find me in {{city}}. My address is {{number}} {{street}}.</p>
</script>
<!--Your new content will be displayed in here-->
<div class="content-placeholder"></div>
To build up from the previous example, any data that you print out in an {{ }} expression, will automatically get HTML escaped by handlebars. This is a great security feature, but some times you might wish to print raw HTML. In this case you will use the triple curly brace expression {{{ }}}.
Also, notice that the handlebars expressions support nested values which enables us to easily access any data from a JavaScript object.
<script id="expressions-template" type="text/x-handlebars-template">
{{description.escaped}}
{{example}}
<br><br>
{{description.unescaped}}
{{{example}}}
</script>
<div class="content-placeholder"></div>
Handlebars builds on the best features of Mustache. And one these is the concept of context - the object where properties you include in curly braces are looked up. Every template you write has a context. On the top level, this is the JavaScript object that you pass to the compiled template. But helpers like #each or #with modify it, so that you can access the properties of the iterated object directly. The next example will make things clearer.
<!-- The #each helper iterates over an array of items. -->
<script id="example-template" type="text/x-handlebars-template">
<!-- people is looked up on the global context, the one we pass to the compiled template -->
{{#each people}}
<!-- Here the context is each individual person. So we can access its properties directly: -->
<p>{{firstName}} {{lastName}}</p>
{{/each}}
</script>
we set a special value of display on the parent element of the elements you want to affect. In this case we want to lay out the <article> elements (flex items), so we set this on the <section> (which becomes a flex container):
section {
display: flex;
}
Flexbox provides a property called flex-direction that specifies what direction the main axis runs in (what direction the flexbox children are laid out in) — by default this is set to row, which causes them to be laid out in a row in the direction your browser's default language works in (left to right, in the case of an English browser).
section {
display: flex;
flex-direction: column;
}
You can also lay out flex items in a reverse direction using the row-reverse and column-reverse values.
adding the following declaration to your <section> rule:
section {
display: flex;
flex-direction: column;
flex-wrap: wrap;
}
Also, add the following declaration to your <article> rule:
article{
flex: 200px;
}
adding the following to the bottom of the example's CSS:
div {
display: flex;
align-items: center;
justify-content: space-around;
}
Flexbox also has a feature for changing the layout order of flex items, without affecting the source order. This is another thing that is impossible to do with traditional layout methods.
button:first-child {
order: 1;
}
button will move to the end of the main axis. Let's talk about how this works in a bit more detail:
- By default, all flex items have an order value of 0.
- Flex items with higher order values set on them will appear later in the display order than items with lower order values.
- Flex items with the same order value will appear in their source order. So if you have four items with order values of 2, 1, 1, and 0 set on them respectively, their display order would be 4th, 2nd, 3rd, then 1st.
- The 3rd item appears after the 2nd because it has the same order value and is after it in the source order.