Pass variable to #each in handlebars? - ember.js

I have template that looks like this:
calling it:
{{Gd-text-input label="Specify" name="Specify" key="entry.810220554" hideIf=true}}
The template:
<script type="text/x-handlebars" data-template-name='components/Gd-radio-input'>
{{log key}}
{{#each content}}
{{log key}}
<div class="radiobutton">
{{radio-button id=label value=label name=key }}
<label {{bind-attr for="label"}}>{{label}}</label>
</div>
{{/each}}
</script>
The first log key outputs asdf. The one inside the #each – loop is undefined. How can I tell the Each-loop about the variable or access it from outside the loop?

view.key is what is needed, so
{{log view.key}}
will output the variable-name

Related

Is it possible to pass some content to a {{partial}}?

Say I had a template that was like:
<script type="text/x-handlebars" id="something">
<div class="thisIsJustAnExample">Something I wanted in the template</div>
{{outlet}}
<div class="thisIsJustAnotherExample">Something else I wanted in the template</div>
</script>
And do the following in another template:
<script type="text/x-handlebars" id="thisThingPutsSomethingInSomething">
<span>
{{#partial "something"}}
<div>Some stuff I want to go into the outlet...</div>
{{/partial}}
</span>
</script>
So the result is:
<div class="thisIsJustAnExample">Something I wanted in the template</div>
<div>Some stuff I want to go into the outlet...</div>
<div class="thisIsJustAnotherExample">Something else I wanted in the template</div>
Is this possible?
Using a view this can be easily accomplished:
Parent Template and View
<script type="text/x-handlebars" data-template-name="foo">
hello {{yield}} world
</script>
App.FooView = Em.View.extend({
layoutName:'foo'
});
Usage
{{#view App.FooView}}
{{item}}
{{/view}}
Example
http://emberjs.jsbin.com/deluxaha/1/edit
Just load the {{partial}} at the place of your {{outlet}}. You can achieve the final output.
Jsbin - Link
Note: Your partial template-name should begin with a "_" refer the link - Partial_naming_convention

How to set itemController for instance variable in ember.js indexController?

I have a Ember.js page that displays a table of items and shows details of one of the items when it is selected. The controller looks like this:
CV.IndexController = Ember.ArrayController.extend({
itemController: "CurrVitae",
selectedCurrVitae: false,
actions: {
selectCurrVitae: function(currVitae) {
this.set('selectedCurrVitae', currVitae)
}
}
});
And the index controller is used in a template like this:
<div class="container">
<div class="curr-vitae-list">
{{#each curr_vitae in controller}}
<div class="curr-vitae-item row">
<div class="col-sm-2" {{action selectCurrVitae curr_vitae}}>
{{curr_vitae.name}}
</div>
<div class="col-sm-2">
<!-- NOTE: This method is defined on the item
controller (not the model) so the itemController is
available at this point. -->
{{curr_vitae.createdAtDisplay}}
</div>
<div class="col-sm-7">
<div class="embedded-cell">
{{curr_vitae.summary}}
</div>
<div class="embedded-cell">
{{curr_vitae.objective}}
</div>
</div>
</div>
{{/each}}
</div>
<div class="curr-vitae-view">
<h2>Details</h2>
<!-- EDIT: I have tried setting this
as {{#if selectedCurrVitae itemController="currVitae" }}
to match the way the #each handles item controllers but that did
not seem to work -->
{{#if selectedCurrVitae }}
<!-- NOTE: Down here, however, the item controller is not available
so I can't use methods defined on the item controller for the
currently selected instance. -->
{{ partial "cv_index_details" }}
{{/if}}
</div>
</div>
Question: The problem I'm running in to is that the itemController I've set in the index controller is not available when rendering the selectedCurrVitae in the cv_index_details.
More details:
Specifically, in the partial I want to reuse a editor component (taken from Noel Rappin's Ember.js book). So if the cv_index_details partial looks like this:
<h3 class="selected_cv">{{selectedCurrVitae.name}}</h3>
<div class="row selected_cv_summary">
<h4>Summary</h4>
{{block-editor emberObject=selectedCurrVitae propName="summary" action="itemChanged"}}
</div>
<div class="row selected_cv_experiences">
<h4>Experiences</h4>
{{#each experience in selectedCurrVitae.experiences itemController="experience"}}
{{ partial "experience_detail" }}
{{/each}}
</div>
So in this template, the itemChanged action is not found for the selectedCurrVitae instance. However, I use the same block-editor component for the experience instance and that works correctly; the itemChanged action defined on the ExperienceController is found.
selectedCurrVitae is outside of the itemController, the itemController is only applied inside the each (on each item, hence the name).
Probably the easiest way to accomplish this will be to reuse the item controller and use render.
Template
{{#if selectedCurrVitae }}
{{ render "cv_index_details" }}
{{/if}}
Controller
CV.CvIndexDetailsController = CV.CurrVitaeController.extend();
Or
Template
{{#if selectedCurrVitae }}
{{ render "currVitae" }}
{{/if}}
View
CV.CurrVitaeView = Ember.View.extend({
templateName: 'cv_index_details'
});

I can't loop an Object-Array with ember #each

<div class="nav-menu clearfix">
<ul class="list-unstyled list-inline">
{{#each MI in MB}}
<li id=""><span>{{ MI.MText }}</span></li>
{{else}}
{{MB}}
{{/each}}
</ul>
</div>
I want loop the MB with each.
but it dose not work and return the MB is empty.
but I get this for else.
[object Object],[object Object],[object Object],[object
Object],[object Object]
this is my route define
//application路由
App.ApplicationRoute = Ember.Route.extend(App.LazyLoadTemplate, {
model : function() {
return Ember.$.getJSON("/index/indexjson");
}
});
and get a json data is
{
'UIB':{...},
'MB':[{...},{...},...,{...}]
}
My English is not well ,Thanks for help!
As you already found, your scope of your property was incorrect. Just to set the record straight, Ember-Handlebars will not iterate over an object like it will over an Array. Additionally the else statement is totally legit, it will be triggered when the array being iterated across is empty (null/undefined/no elements)
{{#each item in model}}
{{item}}
{{else}}
No Items
{{/each}}
http://emberjs.jsbin.com/iWohUlE/1/edit
Edit as kingpin pointed out in his answer, this response is referencing the wrong version of handlebars.
Your misusing the block helper each in your template. Handlebars each will work similarly with objects and arrays. In addition you had an else outside of an if block. Rewrite your template as follows:
<div class="nav-menu clearfix">
<ul class="list-unstyled list-inline">
{{#each MB}}
<li id=""><span>{{ MText }}</span></li>
{{/each}}
</ul>
</div>
Fiddle example

How to remove the views while using the properties from the context of outerview in emberjs

I have a scenerio in which i wanted to render some properties in the child view with the properties of the parent view but on the basis of some properties. But when the properties evaluates to false the view should be destroyed but its giving error as:
cannot call unchain of undefined and some errors also related to this.
code:
Template
<script type="text/x-handlebars">
<h2>Welcome to Ember.js</h2>
{{outlet}}
</script>
<script type="text/x-handlebars" data-template-name="address">
{{item.Address.addressline1}}<br />
{{item.Address.addressLine2}}<br />
{{item.Address.city}}, {{item.Address.state}}<br />
</script>
<script type="text/x-handlebars" data-template-name="index">
{{#if addressVisible}}
<button {{action hideAddress}}> Hide Address </button>
{{else}}
<button {{action showAddress}}>Show Address</button>
{{/if}}
<ul>
{{#each item in model}}
<li>
{{item.name}}<br />
{{#if addressVisible}}
{{view App.AddressView}}
{{/if}}
</li>
{{/each}}
</ul>
</script>
I have created a fiddle to show my issue:
http://jsbin.com/inoroj/5/edit
When we click on showAddress it shows all the address views but when clicked on hide all views should hide, but instead it raises unchain error.
It looks like for some reason Ember did not like your property being capitalized. By changing Address to address the app worked as expected. I made a few other small changes as well.
http://jsbin.com/uquyuv/1/edit

Second argument (controller) to handlebars each helper. What does it mean?

I'm trying to analyse TodoMVC's Ember example. What does the second argument to the #each helper mean?
<ul id="todo-list">
{{#each filteredTodos itemController="todo"}}
<li {{bindAttr class="isCompleted:completed isEditing:editing"}}>
{{#if isEditing}}
{{view Todos.EditTodoView todoBinding="this"}}
{{else}}
{{view Ember.Checkbox checkedBinding="isCompleted" class="toggle"}}
<label {{action "editTodo" on="doubleClick"}}>{{title}}</label>
<button {{action "removeTodo"}} class="destroy"></button>
{{/if}}
</li>
{{/each}}
</ul>
It's supposed to be an option hash but I'm not sure.
It sets the itemController property of the current controller (TodosController I presume) to todo i.e the instance of the TodoController.
That means that every item (<li> element) will be binded not to the TodosController but to a TodoController instance.
isEditing looks for the property on the instance of TodoController and {{ action "removeTodo" }} will call removeTodo function on TodoController.