Ember.js binding a css style in a template - ember.js

This is solved since Ember 1.8 with the HTMLBars engine.
I would like to bind a css style in a template. What would be the
solution ?
I tried this:
<div class="bar" style="width:{{barWidth}}px"></div>
but DOM element look like this after its been rendered:
<div class="bar" style="width:<script id='metamorph-28-start' type='text/x-placeholder'></script>5.000000000000002<script
id='metamorph-28-end' type='text/x-placeholder'>px">
Obviously here we can see that the tag for metamorph was
added within the style attribute...
I'm wondering what is the best way to achieve such things with
Ember.js
There is something i don't get yet.
I have a template as follow:
<script type="text/x-handlebars" data-template-name="listTemplate">
<ul id="list">
{{#each App.list}}
<li {{bindAttr data-item-id="itemId"}}>
<div>
<span class="label">{{itemName}}</span>
<div class="barContainer">
<div class="bar" {{bindAttr style="barWidth"}}></div>
<div class="barCap"></div>
</div>
</div>
</li>
{{/each}}
</ul>
i'm in a for each loop that loops thru my ArrayProxy content... and the bar width vary depending of the value of each item in the list. Your solution here will not work as the view is the UL and i need a barWidth per model item. and I do not want to polute my Model with css related things like "width: ###px"
Is there any other elegant way to solve what i try to do ? maybe it would be radically different. I'm very new to ember.js and try to discover the best-practices yet:)

Set a string on your view that looks like "width: 100px" and then bind it to your div with the bind-attr helper like so: <div {{bind-attr style="divStyle"}}>Test</div>
http://jsfiddle.net/tomwhatmore/rearT/1/

To simplify all that, I created a tiny handlebars helper for emberjs that allows you to bind any style properties. You can look at https://github.com/yderidde/bindstyle-ember-helper

Add unbound:
<div class="bar" style="width:{{unbound barWidth}}px"></div>

In Ember 2.0:
<div class="bar" style="width:{{barWidth}}px"></div>
will just work.

Related

Ember passing multiple list items in template

Is it possible to pass multiple list of items in template using {{each}}
Can someone guide me on what I am doing,
in my sales-orders.hbs below is my currenet code.
{{#each model as |detail|}}
<li>{{sales-orders-grid detail=detail}}</li>
{{else}}
Blank
{{/each}}
</ul>
Then calling the sales-orders-grid component
Shipping Method
<div class="col-xs-12 col-md-12 col-sm-12 products-item-products border-left padding10">
<ul>
{{#each shippingMethod as |sm|}}
{{sales-orders-grid-shipping-method sm=sm}}
{{/each}}
</ul>
</div>
In my sales-orders-grid-shipping-method component calling is this:
sm.shippingMethodName
What I'm trying to achieve here is to pass list of items in {{each}} in my main template. Is it possible?
To change scope you can use the "with" helper.
http://emberjs.com/api/classes/Ember.Templates.helpers.html#method_with
{{#with user.posts as |blogPosts|}}
<div class="notice">
There are {{blogPosts.length}} blog posts written by {{user.name}}.
</div>
{{#each blogPosts as |post|}}
<li>{{post.title}}</li>
{{/each}}
{{/with}}
I think you can nest multiple "with" helper.
I think the way to go is to restructure your data as:model.list1,model.list2,etc.
Then pass the model and use as necessary.And use nested each to acheive the grid.
Iam only posting this as an answer because I can't comment yet.
So, do get back to me for Clarifications.

How do you bind-attr and action on the same element in handlebars?

Can you actually use two handlebar statements for the same element? for example, I have:
<div class="resultRow" {{action 'didClickResultDefault' this}}>
But I also need to bind an id to it like this:
<div class="resultRow" {{bind-attr id="testID"}}>
Can you do both? If so, how?
Most certainly! What you would do is this:
<div class="resultRow" {{bind-attr id="testID" }}
{{action 'didClickResultDefault' this on='click'}}>
{{testID}}
</div>
Ember allows you to bind attributes and actions to the same element. Here's a JSBIN showing what would happen if you click it.

Ember.js View without Wrapping Div?

I have a 3 column layout in my app. I'm using Semantic UI. So, the layout is:
<div class='ui celled grid'>
<div class='left column'>...</div>
<div class='middle column'>...</div>
<div class='right column'>...</div>
</div>
So, straightforward.
In my application.hbs it is simply:
<div class='ui celled grid'>
<div class='left column'><!-- menu --></div>
{{outlet}}
</div>
And the other 2 columns are in my sub-controller/templates. And this works fine until I need a View. If I need a View, then Ember makes the HTML layout become:
<div class='ui celled grid'>
<div class='left column'><!-- menu --></div>
<div class='ember-view'>
<div class='middle column'><!-- content --></div>
<div class='right column'><!-- content --></div>
</div>
</div>
And the wrapping <div class='ember-view'> breaks my layout. Because I don't always need a View I need a way to make the HTML the same for with or without a View.
At this point, I see 2 solutions. I'll either have to rework my layout in some way (that I'm yet to work out). Or I can get rid of the wrapping div.
But is it possible to get rid of the wrapping div? I tried this:
export default Ember.View.extend({
tagName: null
});
But that doesn't work. I also tried a span, but that still breaks my layout.
Any ideas?
Thanks.
Try using
tagName:''
The empty string as the tagName's value on your view.
Update:
When I brought this to the attention of ember.js contributors, they suggested inheriting the view from
Ember._MetamorphView
https://github.com/emberjs/ember.js/pull/4790

What is the recommended way of adding selection behavior to an Ember.js CollectionView?

I need basically a Select view, but I would like something a bit more visually appealing. My hunch is that I can use a CollectionView to do this, but that I'll have to implement selection of elements within the collection myself. Is this a common practice? Is there a recommended way to do this? Are there any good examples?
Assuming I'm reading this correctly you just want something that's prettier than your basic select list. I don't know your constraints, but I really like the bootstrap dropdowns for these types of things
Easy: Try and style your <select>'s to your liking
{{view Ember.Select
contentBinding="App.content"
optionLabelBinding="content.text"
optionValueBinding="content.value"
selectionBinding="App.selection"
prompt="Choose ...."}}
If you go with Bootstrap, something like this should work
<div class="dropdown">
<a class="dropdown-toggle" data-toggle="dropdown" href="#">Dropdown trigger</a>
<ul class="dropdown-menu" role="menu" aria-labelledby="dLabel">
{{#each App.content}}
{{#view App.SelectView contentBinding="this"}}{{label}}{{/view}}
{{/each}}
</ul>
</div>
Javascript:
App.SelectView = Em.View.extend({
tagName: 'li',
click:function(){
App.set('selected', this.get('content'));
// then hide the dropdown
}
});
This link was recommended to me on #emberjs on Freenode:
https://gist.github.com/1626943
It extends CollectionView to allow selecting items.

Handling dynamic nested views with Ember + Handlebars

I'm using Ember.js 1.0 pre release and Handlebars 1.0.0 and want to represent a list of comments to a post.
My comment object is this:
// COMMENT ITEM
HaBlog.Comment = Em.Object.extend({
user:null,
text:null,
created: moment().subtract('years', 100),
createdAgo: function(){
return (this.get('created').fromNow());
}.property('created'),
rating:null,
replies:[]
});
And this is my template for the view:
<div id="postComments" class="span10">
<h1>Comments</h1>
{{#each comments}}
<div class="comment">
<small>
<span class="commentDate">
{{createdAgo}}
</span>
</small>
<span class="commentText">
{{text}}
</span>
</div>
{{#each comments.replies}}
<div class="comment">
<small>
<span class="commentDate">
{{createdAgo}}
</span>
</small>
<span class="commentText">
{{text}}
</span>
</div>
{{/each}}
</div>
My problem is that each comment can have a number of replies, which are comments on their own, so they can have more replies.
I have check the nested views in Ember.js and Handlebars, but don't seem to find any way to make it loop through all the replies in a recursive way displaying all the comments in a "tree" way...
I'm having a little trouble understanding exactly what falls under comment vs reply based on your question but I think you should still be able to solve this based on what I suggest below.
What you'll want to do is use an Ember.CollectionView and define a view class that you'll use as the itemViewClass on the collection view. So your itemViewClass would be something like CommentView, and what have a template like:
Comment Text: {{text}}
Replies: {{view Ember.CollectionView content=replies itemViewClass=HaBlog.CommentView}}
This is the only way to handle the problem of recursion, which, like you said, can't really be handled with Handlebars only.