Skip to content

Commit

Permalink
Switch to subject last
Browse files Browse the repository at this point in the history
  • Loading branch information
XiphiasUvella committed Feb 23, 2016
1 parent 485b8a6 commit d78e7dd
Show file tree
Hide file tree
Showing 23 changed files with 95 additions and 51 deletions.
50 changes: 35 additions & 15 deletions README.md
Expand Up @@ -37,6 +37,26 @@ except: ['pipe'] // imports all helpers except `pipe`
only: ['pipe'] // imports only `pipe`
```
## Argument ordering
This addon is built with _composability_ in mind, and in order to faciliate that,
the ordering of arguments is somewhat different then you might be used to.
For all non-unary helpers, the subject of the helper function will always be the last argument.
This way the arguments are better readable if you compose together multiple helpers:
```hbs
{{take 5 (sort "lastName" "firstName" (filter-by "active" array))}}
```
For action helpers, this will mean better currying semantics:
```hbs
<button {{action (pipe (action "closePopover") (toggle "isExpanded")) this}}>
{{if isExpanded "I am expanded" "I am not"}}
</button>
```
## Available helpers
* [Action](#action-helpers)
Expand Down Expand Up @@ -92,7 +112,7 @@ The square of 4 is {{compute (action "square") 4}}
Toggles a boolean value.
```hbs
<button {{action (toggle this "isExpanded")}}>
<button {{action (toggle "isExpanded" this)}}>
{{if isExpanded "I am expanded" "I am not"}}
</button>
```
Expand Down Expand Up @@ -133,7 +153,7 @@ See also: [Ember `w` documentation](http://emberjs.com/api/classes/Ember.String.
Maps an array on a property.
```hbs
{{#each (map-by users "fullName") as |fullName|}}
{{#each (map-by "fullName" users) as |fullName|}}
{{fullName}}
{{/each}}
```
Expand All @@ -144,15 +164,15 @@ Maps an array on a property.
Sort an array by given properties.
```hbs
{{#each (sort-by users "lastName" "firstName") as |user|}}
{{#each (sort-by "lastName" "firstName" users) as |user|}}
{{user.lastName}}, {{user.firstName}}
{{/each}}
```
You can append `:desc` to properties to sort in reverse order.
```hbs
{{#each (sort-by users "age:desc") as |user|}}
{{#each (sort-by "age:desc" users) as |user|}}
{{user.firstName}} {{user.lastName}} ({{user.age}})
{{/each}}
```
Expand All @@ -163,23 +183,23 @@ You can append `:desc` to properties to sort in reverse order.
Filters an array by a property.
```hbs
{{#each (filter-by users "isActive" true) as |user|}}
{{#each (filter-by "isActive" true users) as |user|}}
{{user.name}} is active!
{{/each}}
```
If you omit the third argument it will test if the property is truthy.
```hbs
{{#each (filter-by users "address") as |user|}}
{{#each (filter-by "address" users) as |user|}}
{{user.name}} has an address specified!
{{/each}}
```
You can also pass an action as third argument:
```hbs
{{#each (filter-by users age (action "olderThan" 18)) as |user|}}
{{#each (filter-by "age" (action "olderThan" 18) users) as |user|}}
{{user.name}} is older than eighteen!
{{/each}}
```
Expand Down Expand Up @@ -214,7 +234,7 @@ Returns the first `n` entries of a given array.
```hbs
<h3>Top 3:</h3>
{{#each (take contestants 3) as |contestant|}}
{{#each (take 3 contestants) as |contestant|}}
{{contestant.rank}}. {{contestant.name}}
{{/each}}
```
Expand All @@ -226,7 +246,7 @@ Returns an array with the first `n` entries omitted.
```hbs
<h3>Other contestants:</h3>
{{#each (drop contestants 3) as |contestant|}}
{{#each (drop 3 contestants) as |contestant|}}
{{contestant.rank}}. {{contestant.name}}
{{/each}}
```
Expand Down Expand Up @@ -283,13 +303,13 @@ And works with a negative range:
Joins the given array with an optional separator into a string.
```hbs
{{join categories ', '}}
{{join ', ' categories}}
```
**[⬆️ back to top](#available-helpers)**
#### `compact`
Removes blank items from an array.
Removes blank items from an array.
```hbs
{{#each (compact arrayWithBlanks) as |notBlank|}}
Expand All @@ -311,15 +331,15 @@ Checks if a given value or sub-array is contained within an array.
**[⬆️ back to top](#available-helpers)**
---
---
### Object helpers
#### `group-by`
Returns an object where the keys are the unique values of the given property, and the values are an array with all items of the array that have the same value of that property.
```hbs
{{#each-in (group-by artists "category") as |category artists|}}
{{#each-in (group-by "category" artists) as |category artists|}}
<h3>{{category}}</h3>
<ul>
{{#each artists as |artist|}}
Expand All @@ -340,7 +360,7 @@ Increments by `1` or `step`.
```hbs
{{inc numberOfPeople}}
{{inc numberOfPeople 2}}
{{inc 2 numberOfPeople}}
```
**[⬆️ back to top](#available-helpers)**
Expand All @@ -350,7 +370,7 @@ Decrements by `1` or `step`.
```hbs
{{dec numberOfPeople}}
{{dec numberOfPeople 2}}
{{dec 2 numberOfPeople}}
```
**[⬆️ back to top](#available-helpers)**
Expand Down
9 changes: 7 additions & 2 deletions addon/helpers/dec.js
@@ -1,8 +1,13 @@
import Ember from 'ember';

const { Helper: { helper } } = Ember;
const { Helper: { helper }, isEmpty } = Ember;

export function dec([step, val]) {
if (isEmpty(val)) {
val = step;
step = undefined;
}

export function dec([val, step]) {
step = step || 1;
return val - step;
}
Expand Down
2 changes: 1 addition & 1 deletion addon/helpers/drop.js
Expand Up @@ -7,7 +7,7 @@ const {
} = Ember;

export default Helper.extend({
compute([array, dropAmount]) {
compute([dropAmount, array]) {
set(this, 'array', array);
return array.slice(dropAmount);
},
Expand Down
8 changes: 7 additions & 1 deletion addon/helpers/filter-by.js
Expand Up @@ -13,7 +13,13 @@ const {
} = Ember;

export default Helper.extend({
compute([array, byPath, value]) {
compute([byPath, value, array]) {

if (!isArray(array) && isArray(value)) {
array = value;
value = undefined;
}

set(this, 'array', array);
set(this, 'byPath', byPath);
set(this, 'value', value);
Expand Down
2 changes: 1 addition & 1 deletion addon/helpers/group-by.js
Expand Up @@ -32,7 +32,7 @@ const groupFunction = function() {
};

export default Helper.extend({
compute([array, byPath]) {
compute([byPath, array]) {
set(this, 'array', array);
set(this, 'byPath', byPath);

Expand Down
9 changes: 7 additions & 2 deletions addon/helpers/inc.js
@@ -1,8 +1,13 @@
import Ember from 'ember';

const { Helper: { helper } } = Ember;
const { Helper: { helper }, isEmpty } = Ember;

export function inc([step, val]) {
if (isEmpty(val)) {
val = step;
step = undefined;
}

export function inc([val, step]) {
step = step || 1;
return val + step;
}
Expand Down
8 changes: 7 additions & 1 deletion addon/helpers/join.js
Expand Up @@ -3,11 +3,17 @@ import Ember from 'ember';
const {
Helper,
observer,
isArray,
set
} = Ember;

export default Helper.extend({
compute([array, separator = ',']) {
compute([separator, array]) {
if (isArray(separator)) {
array = separator;
separator = ',';
}

set(this, 'array', array);
return array.join(separator);
},
Expand Down
2 changes: 1 addition & 1 deletion addon/helpers/map-by.js
Expand Up @@ -12,7 +12,7 @@ const {
} = Ember;

export default Helper.extend({
compute([array, byPath]) {
compute([byPath, array]) {
set(this, 'array', array);
set(this, 'byPath', byPath);

Expand Down
4 changes: 3 additions & 1 deletion addon/helpers/sort-by.js
Expand Up @@ -13,7 +13,9 @@ const {
} = Ember;

export default Helper.extend({
compute([array, ...sortProps]) {
compute(sortProps) {
let array = sortProps.pop();

set(this, 'array', array);
set(this, 'sortProps', sortProps);

Expand Down
2 changes: 1 addition & 1 deletion addon/helpers/take.js
Expand Up @@ -7,7 +7,7 @@ const {
} = Ember;

export default Helper.extend({
compute([array, takeAmount]) {
compute([takeAmount, array]) {
set(this, 'array', array);
return array.slice(0, takeAmount);
},
Expand Down
2 changes: 1 addition & 1 deletion addon/helpers/toggle.js
Expand Up @@ -2,7 +2,7 @@ import Ember from 'ember';

const { Helper: { helper }, get, set } = Ember;

export function toggle([obj, prop]) {
export function toggle([prop, obj]) {
return function() {
set(obj, prop, !get(obj, prop));
};
Expand Down
2 changes: 1 addition & 1 deletion tests/integration/helpers/dec-test.js
Expand Up @@ -12,7 +12,7 @@ test('it decrements a value', function(assert) {
});

test('it decrements a value', function(assert) {
this.render(hbs`{{dec 5 2}}`);
this.render(hbs`{{dec 2 5}}`);

assert.equal(this.$().text().trim(), '3', 'should decrement by 2');
});
4 changes: 2 additions & 2 deletions tests/integration/helpers/drop-test.js
Expand Up @@ -12,7 +12,7 @@ test('It drops the first N entries of array', function(assert) {
this.set('array', emberArray([1, 2, 3, 4, 5]));

this.render(hbs`
{{~#each (drop array 2) as |n|~}}
{{~#each (drop 2 array) as |n|~}}
{{n}}
{{~/each~}}
`);
Expand All @@ -25,7 +25,7 @@ test('It watches for changes', function(assert) {
this.set('array', array);

this.render(hbs`
{{~#each (drop array 2) as |n|~}}
{{~#each (drop 2 array) as |n|~}}
{{n}}
{{~/each~}}
`);
Expand Down
10 changes: 5 additions & 5 deletions tests/integration/helpers/filter-by-test.js
Expand Up @@ -16,7 +16,7 @@ test('It filters by value', function(assert) {
]));

this.render(hbs`
{{~#each (filter-by array 'foo' true) as |item|~}}
{{~#each (filter-by 'foo' true array) as |item|~}}
{{~item.name~}}
{{~/each~}}
`);
Expand All @@ -34,7 +34,7 @@ test('It filters by truthiness', function(assert) {
]));

this.render(hbs`
{{~#each (filter-by array 'foo') as |item|~}}
{{~#each (filter-by 'foo' array) as |item|~}}
{{~item.name~}}
{{~/each~}}
`);
Expand All @@ -52,7 +52,7 @@ test('It recomputes the filter if array changes', function(assert) {
this.set('array', array);

this.render(hbs`
{{~#each (filter-by array 'foo' true) as |item|~}}
{{~#each (filter-by 'foo' true array) as |item|~}}
{{~item.name~}}
{{~/each~}}
`);
Expand All @@ -72,7 +72,7 @@ test('It recomputes the filter if a value under given path changes', function(as
this.set('array', array);

this.render(hbs`
{{~#each (filter-by array 'foo' true) as |item|~}}
{{~#each (filter-by 'foo' true array) as |item|~}}
{{~item.name~}}
{{~/each~}}
`);
Expand All @@ -92,7 +92,7 @@ test('It can be passed an action', function(assert) {
this.on('isOdd', (value) => value % 2 === 1);

this.render(hbs`
{{~#each (filter-by array 'foo' (action 'isOdd')) as |item|~}}
{{~#each (filter-by 'foo' (action 'isOdd') array) as |item|~}}
{{~item.name~}}
{{~/each~}}
`);
Expand Down
4 changes: 2 additions & 2 deletions tests/integration/helpers/group-by-test.js
Expand Up @@ -17,7 +17,7 @@ test('It groups by given property', function(assert) {
]));

this.render(hbs`
{{~#each-in (group-by array 'category') as |category entries|~}}
{{~#each-in (group-by 'category' array) as |category entries|~}}
{{~category~}}
{{~#each entries as |entry|~}}{{~entry.name~}}{{~/each~}}
{{~/each-in~}}
Expand All @@ -37,7 +37,7 @@ test('It watches for changes', function(assert) {
this.set('array', array);

this.render(hbs`
{{~#each-in (group-by array 'category') as |category entries|~}}
{{~#each-in (group-by 'category' array) as |category entries|~}}
{{~category~}}
{{~#each entries as |entry|~}}{{~entry.name~}}{{~/each~}}
{{~/each-in~}}
Expand Down
2 changes: 1 addition & 1 deletion tests/integration/helpers/inc-test.js
Expand Up @@ -12,7 +12,7 @@ test('it increments a value', function(assert) {
});

test('it increments a value', function(assert) {
this.render(hbs`{{inc 1 2}}`);
this.render(hbs`{{inc 2 1}}`);

assert.equal(this.$().text().trim(), '3', 'should increment by 2');
});
4 changes: 2 additions & 2 deletions tests/integration/helpers/join-test.js
Expand Up @@ -11,7 +11,7 @@ moduleForComponent('join', 'Integration | Helper | {{join}}', {
test('It joins the words with given separator', function(assert) {
this.set('array', emberArray(['foo', 'bar', 'baz']));

this.render(hbs`{{join array ', '}}`);
this.render(hbs`{{join ', ' array}}`);

assert.equal(this.$().text().trim(), 'foo, bar, baz', 'words are joined with a comma and a space');
});
Expand All @@ -28,7 +28,7 @@ test('It watches for changes', function(assert) {
let array = emberArray(['foo', 'bar', 'baz']);
this.set('array', array);

this.render(hbs`{{join array ', '}}`);
this.render(hbs`{{join ', ' array}}`);

run(() => array.pushObject('quux'));

Expand Down

0 comments on commit d78e7dd

Please sign in to comment.