Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Browse files
Browse the repository at this point in the history
Add timezone-collection mega-component
Needs to be split into smaller components, and tested
- Loading branch information
Showing
6 changed files
with
105 additions
and
26 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,57 @@ | ||
import Ember from 'ember'; | ||
import TimezoneColumn from 'stz/models/timezone-column'; | ||
|
||
const secondsInHour = 3600; | ||
|
||
// FIXME: all these functions should be in utils so that they're testable | ||
|
||
function calculateTimezoneStart(offset) { | ||
// Finds the start of the hour window for the timezone containing offset. | ||
// 7200 -> 7200 | ||
// 9000 -> 7200 | ||
// -7200 -> -7200 | ||
// -9000 -> -10800 | ||
return Math.floor(offset / secondsInHour) * secondsInHour; | ||
} | ||
|
||
function calculateTimezoneStop(offset) { | ||
// Finds the end of the hour window for the timezone containing offset. | ||
// 7200 -> 7200 | ||
// 9000 -> 10800 | ||
// -7200 -> -7200 | ||
// -9000 -> -7200 | ||
return Math.ceil(offset / secondsInHour) * secondsInHour; | ||
} | ||
|
||
function nextTimezone(start) { | ||
return start + secondsInHour; | ||
} | ||
|
||
export default Ember.Component.extend({ | ||
classNames: ['timezone-container'], | ||
|
||
users: Ember.computed.alias('model'), | ||
offsets: Ember.computed.mapBy('users', 'tzOffset'), | ||
earliest: Ember.computed.min('offsets'), | ||
latest: Ember.computed.max('offsets'), | ||
|
||
columns: Ember.computed('users.@each.tzOffset', function() { | ||
let users = this.get('model'); | ||
let start = calculateTimezoneStart(this.get('earliest')); | ||
let stop = calculateTimezoneStop(this.get('latest')); | ||
let columns = Ember.A(); | ||
|
||
for (let tz = start; tz < stop; tz = nextTimezone(tz)) { | ||
let matches = users.filter(function(user) { | ||
let offset = user.get('tzOffset'); | ||
return offset >= tz && offset < nextTimezone(tz); | ||
}); | ||
columns.push(TimezoneColumn.create({ | ||
timezoneStart: tz, | ||
users: matches | ||
})); | ||
} | ||
|
||
return columns; | ||
}) | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,4 @@ | ||
import Ember from 'ember'; | ||
|
||
export default Ember.Controller.extend({ | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
import Ember from 'ember'; | ||
|
||
export default Ember.Object.extend({ | ||
timezoneStart: null, | ||
users: null, | ||
empty: Ember.computed.empty('users') | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,17 @@ | ||
{{#each columns as |column|}} | ||
<!-- FIXME: column should be a component --> | ||
<div class="timezone-column {{if column.empty 'timezone-column--empty'}}"> | ||
<!-- FIXME: users should be grouped by timezone (asc) --> | ||
<!-- FIXME: timezone should be displayed --> | ||
<!-- FIXME: current time should be displayed --> | ||
<!-- FIXME: item should be a component --> | ||
{{#each column.users as |user|}} | ||
<div class="timezone-column__item"> | ||
<div><img src={{user.image_72}}></div> | ||
<div>{{user.realName}}</div> | ||
<div>{{user.tz}}</div> | ||
<div>{{user.tzOffset}}</div> | ||
</div> | ||
{{/each}} | ||
</div> | ||
{{/each}} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,26 +1 @@ | ||
<h1>{{model.length}} Users</h1> | ||
|
||
<table> | ||
<thead> | ||
<tr> | ||
<th>Avatar</th> | ||
<th>User</th> | ||
<th>Real name</th> | ||
<th>Timezone</th> | ||
<th>Timezone Label</th> | ||
<th>Timezone Offset</th> | ||
</tr> | ||
</thead> | ||
<tbody> | ||
{{#each model as |user|}} | ||
<tr> | ||
<td><img src={{user.image_72}}></td> | ||
<td>{{user.username}}</td> | ||
<td>{{user.realName}}</td> | ||
<td>{{user.tz}}</td> | ||
<td>{{user.tzLabel}}</td> | ||
<td>{{user.tzOffset}}</td> | ||
</tr> | ||
{{/each}} | ||
</tbody> | ||
</table> | ||
{{timezone-collection users=model}} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,19 @@ | ||
import { moduleForComponent, test } from 'ember-qunit'; | ||
|
||
moduleForComponent('timezone-collection', 'Unit | Component | timezone collection', { | ||
// Specify the other units that are required for this test | ||
// needs: ['component:foo', 'helper:bar'], | ||
unit: true | ||
}); | ||
|
||
test('it renders', function(assert) { | ||
assert.expect(2); | ||
|
||
// Creates the component instance | ||
var component = this.subject(); | ||
assert.equal(component._state, 'preRender'); | ||
|
||
// Renders the component to the page | ||
this.render(); | ||
assert.equal(component._state, 'inDOM'); | ||
}); |