oxjs/examples/ui/audio_player/js/example.js
2012-12-11 16:38:44 +01:00

1129 lines
39 KiB
JavaScript

/*
Demo application using Ox.AudioPlayer.
*/
'use strict';
Ox.load('UI', function() {
var app = {
$ui: {},
data: {},
site: {
listColumns: [
{
format: function(value, data) {
return Ox.Element('<img>')
.addClass('symbol')
.attr({src: Ox.UI.getImageURL(
'symbol' + Ox.toTitleCase(
value || (data.query ? 'find ': 'click')
)
)});
},
id: 'icon',
title: 'icon',
visible: true,
width: 16
},
{
id: 'title',
title: 'Title',
visible: true,
width: 136
},
{
align: 'right',
id: 'items',
title: 'Items',
visible: true,
width: 40
}
],
lists: [
{icon: 'audio', id: 'Music', index: 0, items: 3, title: 'Music'},
{icon: 'playlist', id: 'Playing', index: 1, items: 0, title: 'Playing'}
],
sort: [
{key: 'artist', operator: '+'},
{key: 'year', operator: '+'},
{key: 'disc', operator: '+'},
{key: 'track', operator: '+'}
],
sums: ['duration', 'size'],
trackColumns: [
{
format: function(value) {
return value
? Ox.Element('<img>')
.addClass('symbol')
.attr({src: Ox.UI.getImageURL(
app.user.ui.paused
? 'symbolUnmute' : 'symbolMute'
)})
: Ox.Element();
},
id: 'playing',
removable: false,
title: 'Playing',
titleImage: 'mute',
visible: true,
width: 16
},
{
format: function(value) {
return value
? Ox.Element('<img>')
.addClass('symbol')
.attr({src: Ox.UI.getImageURL(
'symbolCheck'
)})
: Ox.Element();
},
id: 'checked',
removable: false,
title: 'Checked',
titleImage: 'check',
visible: true,
width: 16
},
{
format: function(value) {
return value
? Ox.Element('<img>')
.addClass('image')
.attr({src: value})
: Ox.Element()
},
id: 'artwork',
operator: '+',
title: 'Artwork',
titleImage: 'icon',
visible: true,
width: 16
},
{
align: 'right',
id: 'disc',
operator: '+',
title: 'Disc',
titleImage: 'circle',
width: 32
},
{
align: 'right',
id: 'track',
operator: '+',
title: 'Track',
titleImage: 'square',
width: 32
},
{
id: 'title',
operator: '+',
removable: false,
title: 'Title',
visible: true,
width: 192
},
{
id: 'artist',
operator: '+',
removable: false,
title: 'Artist',
visible: true,
width: 192
},
{
id: 'album',
operator: '+',
removable: false,
title: 'Album',
visible: true,
width: 192
},
{
align: 'right',
id: 'year',
operator: '+',
title: 'Year',
visible: true,
width: 64
},
{
align: 'right',
format: function(value) {
return Ox.formatDuration(value).substr(4);
},
id: 'duration',
operator: '-',
title: 'Time',
visible: true,
width: 64
},
{
align: 'right',
format: function(value) {
return Ox.formatValue(value, 'B');
},
id: 'size',
operator: '-',
title: 'Size',
visible: true,
width: 64
},
{
align: 'right',
format: function(value) {
return Math.round(value) + ' kbps'
},
id: 'bitrate',
operator: '-',
title: 'Bitrate',
visible: true,
width: 64
},
{
id: 'genre',
operator: '+',
title: 'Genre',
visible: true,
width: 128
}
]
},
ui: {},
user: {
lists: [
{
id: 'favorites',
index: 0,
items: 0,
title: 'Favorites',
type: 'static'
},
{
id: 'hip-hop',
index: 1,
items: 1,
query: {
conditions: [
{key: 'genre', operator: '==', value: 'Hip-Hop'}
],
operator: '&'
},
title: 'Hip-Hop'
}
],
ui: {
artwork: 'selected',
coverSize: 64,
list: 'Music',
paused: true,
query: {
conditions: [],
operator: '&',
},
selectedAlbum: [],
selectedArtist: [],
selectedTrack: [],
showSidebar: true,
sidebarSize: 192,
track: 0,
tracklistSize: 256,
view: 'tracks'
}
},
utils: {}
};
app.user.ui.sort = Ox.clone(app.site.sort, true);
app.load = function() {
Ox.getJSON('json/music.json', function(data) {
app.data.tracks = data;
app.data.artists = app.utils.getArtists();
app.data.albums = app.utils.getAlbums();
app.$ui.appPanel = app.ui.appPanel().appendTo(Ox.$body);
Ox.$window.bind({resize: app.utils.resizeWindow});
});
};
app.UI = (function() {
var that = {};
that.set = function() {
var args = Ox.makeObject(arguments),
keys = [],
previousUI = Ox.clone(app.user.ui, true);
Ox.forEach(args, function(value, key) {
if (!Ox.isEqual(value, previousUI[key])) {
app.user.ui[key] = value;
keys.push(key);
}
});
keys.forEach(function(key) {
var data = {
previousValue: previousUI[key],
value: app.user.ui[key]
}
Ox.print('ui_' + key.toLowerCase(), JSON.stringify(app.user.ui[key]))
Ox.forEach(app.$ui, function($elements) {
Ox.makeArray($elements).forEach(function($element) {
$element.triggerEvent('ui_' + key.toLowerCase(), data);
});
});
});
};
return that;
}());
app.ui.appPanel = function() {
return Ox.SplitPanel({
elements: [
{element: app.$ui.mainMenu = app.ui.mainMenu(), size: 20},
{element: app.$ui.mainPanel = app.ui.mainPanel()}
],
orientation: 'vertical'
});
};
app.ui.mainMenu = function() {
return Ox.MainMenu({
menus: [
{
id: '0xcd',
title: '0xCD',
items: [
{id: 'about', title: 'About 0xCD'}
]
}
]
})
.bindEvent({
click: function(data) {
if (data.id == 'about') {
app.$ui.aboutDialog = (
app.$ui.aboutDialog || app.ui.aboutDialog()
).open();
}
}
});
};
app.ui.aboutDialog = function() {
var $element = Ox.Dialog({
buttons: [
Ox.Button({
id: 'close',
title: 'Close'
})
.bindEvent({
click: function() {
$element.close();
}
})
],
content: Ox.Element()
.html('Audio Player Example'),
height: 256,
keys: {enter: 'close', escape: 'close'},
title: 'About 0xCD',
width: 512
});
return $element;
};
app.ui.mainPanel = function() {
return Ox.SplitPanel({
elements: [
{element: app.ui.$toolbar = app.ui.toolbar(), size: 39},
{element: app.ui.$bothPanel = app.ui.bothPanel()}
],
orientation: 'vertical'
});
};
app.ui.toolbar = function() {
return Ox.Bar({size: 39})
.attr({id: 'toolbar'})
.append(app.$ui.audioPlayer = app.ui.audioPlayer())
.append(app.$ui.viewLabel = app.ui.viewLabel())
.append(app.$ui.viewButtons = app.ui.viewButtons())
.append(app.$ui.findSelect = app.ui.findSelect())
.append(app.$ui.findLabel = app.ui.findLabel())
.append(app.$ui.findInput = app.ui.findInput());
};
app.ui.audioPlayer = function() {
return Ox.AudioPlayer({
audio: app.data.tracks,
paused: true,
width: window.innerWidth - 190
})
.css({left: '4px', top: '4px'})
.bindEvent({
paused: function(data) {
var id = app.data.tracks[app.user.ui.track].file
app.user.ui.paused = data.paused;
app.$ui.trackList.value(id, 'playing', false);
app.$ui.trackList.value(id, 'playing', true);
},
track: function(data) {
var id = app.data.tracks[app.user.ui.track].file
app.$ui.trackList.value(id, 'playing', false);
app.user.ui.track = data.track;
$app.$ui.trackList.value(id, 'playing', true);
}
});
};
app.ui.viewLabel = function() {
return Ox.Label({
textAlign: 'center',
title: 'Tracks',
width: 50
})
.attr({id: 'viewLabel'});
};
app.ui.viewButtons = function() {
return Ox.ButtonGroup({
buttons: [
{id: 'tracks', title: 'list', tooltip: 'View Tracks'},
{id: 'albums', title: 'grid', tooltip: 'View Albums'},
{id: 'artists', title: 'columns', tooltip: 'View Artists'}
],
max: 1,
min: 1,
selectable: true,
type: 'image'
})
.attr({id: 'viewButtons'})
.css({
position: 'absolute',
right: '136px',
top: '19px'
})
.bindEvent({
change: function(data) {
app.user.ui.view = data.value;
app.$ui.viewLabel.options({title: Ox.toTitleCase(app.user.ui.view)});
app.$ui.rightPanel.replaceElement(0, app.$ui.musicPanel = app.ui.musicPanel());
}
});
};
app.ui.findSelect = function() {
return Ox.Select({
items: [
{id: 'all', title: 'Find: All'},
{id: 'tracks', title: 'Find: Tracks'},
{id: 'artists', title: 'Find: Artists'},
{id: 'albums', title: 'Find: Albums'}
],
overlap: 'left',
type: 'image'
})
.attr({id: 'findSelect'})
.bindEvent({
change: function(data) {
$findLabel.options({title: data.title});
}
});
};
app.ui.findLabel = function() {
return Ox.Label({
title: 'Find: All',
width: 112
})
.attr({id: 'findLabel'});
};
app.ui.findInput = function() {
return Ox.Input({
clear: true,
width: 128
})
.attr({id: 'findInput'});
};
app.ui.bothPanel = function() {
return Ox.SplitPanel({
elements: [
{
collapsible: true,
element: app.$ui.leftPanel = app.ui.leftPanel(),
resizable: true,
resize: [128, 192, 256, 320, 384],
size: app.user.ui.sidebarSize
},
{
element: app.$ui.rightPanel = app.ui.rightPanel()
}
],
orientation: 'horizontal'
});
}
app.ui.leftPanel = function() {
return Ox.SplitPanel({
elements: [
{
element: app.$ui.listsPanel = app.ui.listsPanel()
},
{
collapsible: true,
element: app.$ui.artworkPanel = app.ui.artworkPanel(),
size: app.user.ui.sidebarSize + 16
}
],
orientation: 'vertical'
})
.bindEvent({
resize: function(data) {
app.user.ui.sidebarSize = data.size;
[app.$ui.siteLists, app.$ui.userLists].forEach(function($list) {
$list.setColumnWidth('title', app.user.ui.sidebarSize - 56);
});
app.$ui.listsList
app.$ui.leftPanel.size(1, app.user.ui.sidebarSize + 16);
app.$ui.artwork.css({
width: app.user.ui.sidebarSize + 'px',
height: app.user.ui.sidebarSize + 'px'
});
//$musicList.size();
}
})
};
app.ui.listsPanel = function() {
return Ox.SplitPanel({
elements: [
{
element: app.$ui.siteLists = app.ui.siteLists(),
size: app.site.lists.length * 16
},
{
element: app.$ui.userLists = app.ui.userLists()
}
],
orientation: 'vertical'
});
};
app.ui.siteLists = function() {
var $element = Ox.TableList({
columns: app.site.listColumns,
items: app.site.lists,
max: 1,
selected: [app.user.ui.list],
sort: [{key: 'index', operator: '+'}],
unique: 'id'
})
.bindEvent({
select: function(data) {
app.UI.set({list: data.ids[0] || app.site.lists[0].id});
},
selectafter: function() {
app.UI.set({list: app.user.lists[0].id});
app.$ui.userLists.gainFocus();
},
ui_list: function(data) {
$element.options({
selected: data.value[0] == data.value[0].toUpperCase()
? [data.value] : []
});
}
});
$element.update = function() {
return $element.setColumnWidth('title', app.user.ui.sidebarSize - 56);
};
return $element.update();
};
app.ui.userLists = function() {
var $element = Ox.TableList({
columns: app.site.listColumns,
items: app.user.lists,
max: 1,
selected: [app.user.ui.list],
sort: [{key: 'index', operator: '+'}],
sortable: true,
unique: 'id'
})
.bindEvent({
move: function(data) {
Ox.print('MOVE:', data);
},
select: function(data) {
app.UI.set({list: data.ids[0] || app.site.lists[0].id});
},
selectbefore: function() {
app.UI.set({list: Ox.last(app.site.lists).id});
app.$ui.siteLists.gainFocus();
},
ui_list: function(data) {
$element.options({
selected: data.value[0] == data.value[0].toLowerCase()
? [data.value] : []
});
}
});
$element.update = function() {
return $element.setColumnWidth('title', app.user.ui.sidebarSize - 56);
};
return $element.update();
};
app.ui.artworkPanel = function() {
return Ox.SplitPanel({
elements: [
{element: app.$ui.artworkbar = app.ui.artworkbar(), size: 16},
{element: app.$ui.artwork = app.ui.artwork()}
],
orientation: 'vertical'
});
};
app.ui.artworkbar = function() {
return Ox.Bar({size: 16})
.append(app.$ui.artworkText = app.ui.artworkText())
.bindEvent({
anyclick: function() {
app.UI.set({
artwork: app.user.ui.artwork == 'playing'
? 'selected' : 'playing'
});
}
});
};
app.ui.artworkText = function() {
var $element = Ox.Element()
.attr({id: 'artworkText'})
.bindEvent({
ui_artwork: function() {
$element.update();
}
});
$element.update = function() {
$element.html(
app.user.ui.artwork == 'playing'
? 'Now Playing' : 'Selected Item'
);
return $element;
};
return $element.update();
};
app.ui.artwork = function() {
var $element = Ox.Element('<img>')
.attr({src: app.data.tracks[0].artwork})
.bindEvent({
ui_selectedalbum: function(data) {
if (app.user.ui.artwork == 'selected') {
$element.attr({
src: data.value.length
? Ox.getObjectById(app.data.albums, data.value[0]).artwork
: ''
});
}
},
ui_selectedartist: function(data) {
if (app.user.ui.artwork == 'selected') {
$element.attr({
src: data.value.length
? Ox.getObjectById(app.data.artists, data.value[0]).artwork
: ''
});
}
},
ui_selectedtrack: function(data) {
if (app.user.ui.artwork == 'selected') {
$element.attr({
src: data.value.length
? Ox.getObjectById(app.data.tracks, data.value[0]).artwork
: ''
});
}
}
});
$element.update = function() {
$element.css({
width: app.user.ui.sidebarSize + 'px',
height: app.user.ui.sidebarSize + 'px'
});
return $element;
};
return $element.update();
};
app.ui.rightPanel = function() {
return Ox.SplitPanel({
elements: [
{element: app.$ui.musicPanel = app.ui.musicPanel()},
{element: app.$ui.statusbar = app.ui.statusbar(), size: 16}
],
orientation: 'vertical'
});
};
app.ui.musicPanel = function() {
return app.ui[app.user.ui.view + 'Panel']();
};
app.ui.tracksPanel = function() {
return Ox.SplitPanel({
elements: [
{
collapsible: true,
element: app.$ui.albumBrowser = app.ui.albumBrowser(),
size: 112 + Ox.UI.SCROLLBAR_SIZE
},
{
element: app.$ui.trackList = app.ui.trackList()
}
],
orientation: 'vertical'
});
};
app.ui.albumBrowser = function() {
var $element = Ox.IconList({
fixedRatio: 1,
item: function(data, sort, size) {
return {
height: size,
id: data.id,
info: data.year,
title: [data.artist, data.title].join(' &mdash; '),
url: data.artwork,
width: size
};
},
items: app.data.albums,
max: 1,
orientation: 'horizontal',
pageLength: 100,
query: {conditions: [], operator: '&'},
selected: [],
size: 64,
sort: [{key: 'index', operator: '+'}],
unique: 'id'
})
.bindEvent({
ui_sort: function() {
$element.update();
}
});
$element.update = function() {
app.utils.getTrackAlbums(function(albums) {
Ox.print('ALBUMS::::', albums)
$element.options({items: albums});
});
return $element;
}
return $element;
};
app.ui.trackList = function() {
return Ox.TableList({
columns: app.site.trackColumns,
columnsMovable: true,
columnsRemovable: true,
columnsResizable: true,
columnsVisible: true,
items: app.data.tracks,
scrollbarVisible: true,
sort: Ox.clone(app.user.ui.sort, true),
sums: app.site.sums,
unique: 'id'
})
.bindEvent({
init: function(data) {
app.$ui.statusText.update(data);
app.utils.getTrackAlbums(function(data) {
Ox.print('::::', data);
});
},
open: function(data) {
var file = data.ids[0],
id = app.data.tracks[app.user.ui.track].id,
index = Ox.getIndexById(app.data.tracks, id);
if (index == app.user.ui.track) {
app.$ui.trackList.value(id, 'playing', true);
app.$ui.audioPlayer.options({paused: false, position: 0});
} else {
app.$ui.trackList.value(id, 'playing', false);
app.user.ui.track = index;
app.$ui.audioPlayer.options({paused: false, track: app.user.ui.track});
app.$ui.trackList.value(id, 'playing', true);
}
},
openpreview: function(data) {
app.user.ui.paused = !app.user.ui.paused;
app.$ui.audioPlayer.options({paused: app.user.ui.paused});
app.$ui.trackList.closePreview();
},
select: function(data) {
app.UI.set({selectedTrack: data.ids});
},
sort: function(data) {
Ox.print('DDD', data);
app.UI.set({sort: [data]});
}
});
};
app.ui.albumsPanel = function() {
return Ox.SplitPanel({
elements: [
{
element: app.$ui.albumList = app.ui.albumList()
},
{
element: app.$ui.trackBrowser = app.ui.trackBrowser(),
resizable: true,
resize: [192, 256, 320],
size: app.user.ui.tracklistSize
}
],
orientation: 'horizontal'
});
};
app.ui.albumList = function() {
return Ox.IconList({
fixedRatio: 1,
item: function(data, sort, size) {
var key = Ox.contains(['artist', 'title'], sort[0].key)
? 'year' : sort[0].key,
column = Ox.getObjectById(app.site.trackColumns, key),
info = (column.format || Ox.identity)(data[key]);
return {
height: size,
id: data.id,
info: info,
title: [data.artist, data.title].join(' &mdash; '),
url: data.artwork,
width: size
};
},
items: app.data.albums,
pageLength: 120,
query: {conditions: [], operator: '&'},
selected: [],
size: 128,
sort: Ox.clone(app.user.ui.sort, true),
unique: 'id'
})
.bindEvent({
select: function(data) {
app.UI.set({selectedAlbum: data.ids});
},
openpreview: function() {
}
});
};
app.ui.trackBrowser = function() {
return Ox.TableList({
columns: [
Ox.getObjectById(app.site.trackColumns, 'playing'),
Ox.getObjectById(app.site.trackColumns, 'checked'),
Ox.getObjectById(app.site.trackColumns, 'artwork'),
Ox.extend(
Ox.getObjectById(app.site.trackColumns, 'track'),
{visible: true}
),
Ox.extend(
Ox.getObjectById(app.site.trackColumns, 'title'),
{width: app.user.ui.tracklistSize - 144 - Ox.UI.SCROLLBAR_SIZE}
),
Ox.getObjectById(app.site.trackColumns, 'duration')
],
items: app.data.tracks,
query: {conditions: [], operator: '&'},
scrollbarVisible: true,
selected: [],
sort: Ox.clone(app.site.sort, true),
unique: 'id'
})
.bindEvent({
resize: function(data) {
app.user.ui.tracklistSize = data.size;
app.$ui.trackBrowser.setColumnWidth(
'title', app.user.ui.tracklistSize - 144 - Ox.UI.SCROLLBAR_SIZE
);
},
ui_selectedalbum: function(data) {
app.$ui.trackBrowser.options({
items: data.value.length ? Ox.flatten(
data.value.map(function(id) {
return Ox.getObjectById(app.data.albums, id).items;
})
) : []
});
}
});
};
app.ui.artistsPanel = function() {
return Ox.ColumnList({
columns: [
{
id: 'artists',
item: function(data, width) {
data.artwork = data.artwork || '';
data.years = data.years || [];
var $item = $('<div>')
.addClass('item')
.css({width: width + 'px'});
$('<img>')
.addClass('itemIcon')
.attr({src: data.artwork})
.appendTo($item);
$('<div>')
.addClass('itemTitle')
.css({width: width - 36 + 'px'})
.html(data.name ? data.name : '')
.appendTo($item);
$('<div>')
.addClass('itemInfo OxLight')
.css({width: width - 36 + 'px'})
.html(
[
data.years.join('-'),
Ox.formatCount(data.albums, 'album'),
Ox.formatCount(data.tracks, 'track'),
Ox.formatDuration(data.duration),
Ox.formatValue(data.size, 'B')
].join(' &mdash; ')
)
.appendTo($item);
return $item;
},
itemHeight: 32,
keys: ['albums', 'artwork', 'duration', 'name', 'size', 'tracks', 'years']
},
{
id: 'albums',
item: function(data, width) {
data.artwork = data.artwork || '';
data.tracks = data.tracks || [{duration: 0}];
data.year = data.year || '????';
var $item = $('<div>')
.addClass('item')
.css({width: width + 'px'});
$('<img>')
.addClass('itemIcon')
.attr({src: data.artwork})
.appendTo($item);
$('<div>')
.addClass('itemTitle')
.css({width: width - 36 + 'px'})
.html(data.title ? data.title : '')
.appendTo($item);
$('<div>')
.addClass('itemInfo OxLight')
.css({width: width - 36 + 'px'})
.html(
[
data.year,
Ox.formatCount(data.tracks, 'track'),
Ox.formatDuration(data.duration),
Ox.formatValue(data.size, 'B')
].join(' &mdash; ')
)
.appendTo($item);
return $item;
},
itemHeight: 32,
keys: ['artwork', 'duration', 'size', 'title', 'tracks', 'year']
},
{
id: 'tracks',
item: function(data, width) {
var $item = $('<div>')
.addClass('item')
.css({width: width + 'px'});
$('<img>')
.addClass('itemIcon')
.attr({src: data.artwork})
.appendTo($item);
$('<div>')
.addClass('itemTitle')
.css({width: width - 36 + 'px'})
.html(data.title ? data.title : '')
.appendTo($item);
$('<div>')
.addClass('itemInfo OxLight')
.css({width: width - 36 + 'px'})
.html(
[
Ox.formatDuration(data.duration),
Ox.formatValue(data.size, 'B'),
Math.round(data.bitrate) + ' kbps'
].join(' &mdash; ')
)
.appendTo($item);
return $item;
},
itemHeight: 32,
keys: ['artwork', 'bitrate', 'checked', 'duration', 'playing', 'size', 'title']
}
],
items: app.data.artists,
list: 'custom',
width: window.innerWidth - app.user.ui.sidebarSize - 1
})
.bindEvent({
resize: function(data) {
$panel.options({width: data.size})
},
select: function(data) {
Ox.print('SELECT::', data)
app.UI.set(
'selected' + Ox.toTitleCase(data.id.slice(0, -1)),
data.ids
);
}
});
};
app.ui.statusbar = function() {
return Ox.Bar({size: 16})
.append(app.$ui.statusText = app.ui.statusText());
};
app.ui.statusText = function() {
var $element = Ox.Element().attr({id: 'statusText'});
$element.update = function(data) {
return $element.html(
data ? [
Ox.formatCount(data.items, 'track'),
Ox.formatDuration(data.duration),
Ox.formatValue(data.size, 'B')
].join(' &mdash; ') : 'Loading...'
);
};
return $element.update();
};
app.utils.getAlbums = function() {
var albums = []
app.data.artists.forEach(function(artist) {
artist.items.forEach(function(album) {
albums.push(Ox.extend(album, {artist: artist.name}));
});
});
return albums;
};
app.utils.getArtists = function() {
var artists = [], tree = {};
app.data.tracks.forEach(function(track, index) {
var artist = track.artist,
album = track.year + ' ' + track.album,
title = Ox.pad(track.disc, 2) + '\n' + Ox.pad(track.track, 2)
+ '\n' + track.title;
if (!tree[artist]) {
tree[artist] = {};
}
if (!tree[artist][album]) {
tree[artist][album] = {};
}
if (!tree[artist][album][title]) {
tree[artist][album][title] = track;
}
});
Ox.forEach(tree, function(albums, artist) {
artist = {
albums: Ox.len(albums),
artwork: 'mp3/' + artist + '/artwork.png',
id: artist,
items: [],
name: artist
};
Ox.forEach(albums, function(tracks, id) {
var title = id.substr(5),
year = id.substr(0, 4);
artist.items.push({
artwork: tracks[Object.keys(tracks)[0]].artwork,
duration: Ox.values(tracks).reduce(function(r, v, i) {
return r + v.duration;
}, 0),
id: [artist.id, year + ' ' + title].join('\n'),
items: [],
size: Ox.values(tracks).reduce(function(r, v, i) {
return r + v.size;
}, 0),
title: title,
tracks: Ox.len(tracks),
year: year
});
Ox.forEach(tracks, function(track, id) {
artist.items[artist.items.length - 1].items.push({
artist: track.artist,
artwork: track.artwork,
bitrate: track.bitrate,
checked: track.checked,
disc: track.disc,
duration: track.duration,
id: id,
genre: track.genre,
playing: track.playing,
size: track.size,
title: track.title,
track: track.track
});
});
});
['duration', 'size', 'tracks'].forEach(function(key) {
artist[key] = artist.items.reduce(function(r, v, i) {
return r + v[key];
}, 0);
})
artist.years = Ox.unique(artist.items.map(function(item) {
return item.year;
})).sort();
artist.years = [artist.years[0]].concat(
artist.years.length > 1
? [artist.years[artist.years.length - 1]]
: []
);
artists.push(artist);
});
return artists;
};
app.utils.getTrackAlbums = function(callback) {
app.$ui.trackList.api({
keys: ['id'],
query: app.user.ui.query,
sort: app.user.ui.sort
}, function(result) {
callback(result.data.items.reduce(function(r, v, i) {
var albumId = v.id.split('\n').slice(0, 2).join('\n'),
last = Ox.last(r);
return last && last.albumId == albumId ? r : r.concat(
Ox.extend(
Ox.clone(Ox.getObjectById(app.data.albums, albumId)),
{albumId: albumId, id: v.id, index: r.length}
)
);
}, []));
});
};
app.utils.resizeWindow = function() {
};
app.load();
window.app = app;
});