Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[WIP] feature: support multiple fusion stereos #211

Open
wants to merge 2 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
259 changes: 259 additions & 0 deletions fusion/130820-new.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,259 @@
const camelCase = require('camelcase')

function prefix (key, n2k, state) {
return state.deviceName
? `entertainment.device.${state.deviceName}.${key}`
: null
}

function sourcePrefix (key, n2k, state) {
return state.currentFusionSource
? prefix(`avsource.source${state.currentFusionSource}.${key}`, n2k, state)
: null
}

module.exports = [
{
source: 'Name',
node: (n2k, state) => {
state.deviceName = camelCase(n2k.fields.Name)
return prefix('name', n2k, state)
},
filter: n2k => n2k.fields['Message ID'] == 'Unit Name'
},
{
node: (n2k, state) => {
return prefix('manufacturer', n2k, state)
},
value: () => "FUSION",
filter: n2k => n2k.fields['Message ID'] == 'Unit Name'
},
{
node: prefix.bind(null, 'state'),
filter: n2k => n2k.fields['Message ID'] == 'Power',
value: n2k => (n2k.fields['State'] === 'On' ? 'on' : 'off')
},
{
source: 'Artist',
node: sourcePrefix.bind(null, 'track.artistName'),
filter: (n2k, state) =>
n2k.fields['Message ID'] == 'Track Artist' && n2k.fields.Artist != 0
},
{
source: 'Album',
node: sourcePrefix.bind(null, 'track.albumName'),
filter: (n2k, state) =>
n2k.fields['Message ID'] == 'Track Album' && n2k.fields.Album != 0
},
{
source: 'Track',
node: sourcePrefix.bind(null, 'track.name'),
filter: (n2k, state) =>
n2k.fields['Message ID'] == 'Track Title' && n2k.fields.Track != 0
},
{
source: 'Progress',
node: sourcePrefix.bind(null, 'track.elapsedTime'),
filter: (n2k, state) => n2k.fields['Message ID'] == 'Track Progress'
},
{
source: 'Track Length',
node: sourcePrefix.bind(null, 'track.length'),
filter: (n2k, state) => n2k.fields['Message ID'] == 'Track Info'
},
{
source: 'Artist',
node: sourcePrefix.bind(null, 'track.artistName'),
filter: (n2k, state) => n2k.fields['Message ID'] == 'SiriusXM Artist'
},
{
source: 'Title',
node: sourcePrefix.bind(null, 'track.name'),
filter: (n2k, state) => n2k.fields['Message ID'] == 'SiriusXM Title'
},
{
source: 'Channel',
node: (n2k, state) => sourcePrefix.bind(null, 'tuner.stationName'),
filter: (n2k, state) => n2k.fields['Message ID'] == 'SiriusXM Channel'
},
{
source: 'Genre',
node: sourcePrefix.bind(null, 'track.genre'),
filter: n2k => n2k.fields['Message ID'] == 'SiriusXM Genre'
},
{
source: 'Track #',
node: sourcePrefix.bind(null, 'track.number'),
filter: (n2k, state) => n2k.fields['Message ID'] == 'Track Info'
},
{
source: 'Track Count',
node: sourcePrefix.bind(null, 'track.totalTracks'),
filter: (n2k, state) => n2k.fields['Message ID'] == 'Track Info'
},
{
node: prefix.bind(null, 'output.zone1.volume.master'),
source: 'Zone 1',
filter: (n2k, state) => n2k.fields['Message ID'] == 'Volume'
},
{
node: prefix.bind(null, 'output.zone2.volume.master'),
source: 'Zone 2',
filter: (n2k, state) => n2k.fields['Message ID'] == 'Volume'
},
{
node: prefix.bind(null, 'output.zone3.volume.master'),
source: 'Zone 3',
filter: (n2k, state) => n2k.fields['Message ID'] == 'Volume'
},
{
node: prefix.bind(null, 'output.zone4.volume.master'),
source: 'Zone 4',
filter: (n2k, state) => n2k.fields['Message ID'] == 'Volume'
},
{
node: (n2k, state) =>
prefix(
'output.zone' + (Number(n2k.fields.Number) + 1) + '.name',
n2k,
state
),
source: 'Name',
filter: (n2k, state) => n2k.fields['Message ID'] == 'Zone Name'
},
{
node: prefix.bind(null, 'output.zone1.source'),
value: (n2k, state) => {
state.currentFusionSource = n2k.fields['Current Source ID']
return prefix(
'avsource.source' + n2k.fields['Current Source ID'],
n2k,
state
)
},
filter: (n2k, state) => n2k.fields['Message ID'] == 'Source'
},
{
node: prefix.bind(null, 'output.zone2.source'),
value: (n2k, state) =>
prefix('avsource.source' + n2k.fields['Current Source ID'], n2k, state),
filter: (n2k, state) => n2k.fields['Message ID'] == 'Source'
},
{
node: prefix.bind(null, 'output.zone3.source'),
value: (n2k, state) =>
prefix('avsource.source' + n2k.fields['Current Source ID'], n2k, state),
filter: (n2k, state) => n2k.fields['Message ID'] == 'Source'
},
{
node: prefix.bind(null, 'output.zone4.source'),
value: (n2k, state) =>
prefix('avsource.source' + n2k.fields['Current Source ID'], n2k, state),
filter: (n2k, state) => n2k.fields['Message ID'] == 'Source'
},
{
source: 'Source',
node: (n2k, state) =>
prefix('avsource.source' + n2k.fields['Source ID'] + '.name', n2k, state),
filter: (n2k, state) => n2k.fields['Message ID'] == 'Source'
},
{
source: 'AM/FM',
node: sourcePrefix.bind(null, 'tuner.mode'),
filter: (n2k, state) => n2k.fields['Message ID'] == 'AM/FM Station'
},
{
source: 'Frequency',
node: sourcePrefix.bind(null, 'tuner.frequency'),
filter: (n2k, state) => n2k.fields['Message ID'] == 'AM/FM Station'
},
{
source: 'Track',
node: sourcePrefix.bind(null, 'track.name'),
filter: (n2k, state) => n2k.fields['Message ID'] == 'AM/FM Station' && n2k.fields['Track'] && n2k.fields['Track'].length > 0
},
{
node: sourcePrefix.bind(null, 'playbackState'),
value: (n2k, state) => {
var val = n2k.fields['Transport']
return val == 'Paused' ? 'Paused' : 'Playing'
},
filter: (n2k, state) => n2k.fields['Message ID'] == 'Track Info'
},
{
node: prefix.bind(null, 'output.zone1.isMuted'),
value: (n2k, state) => {
var val = n2k.fields['Mute']
return val == 'Muted' ? true : false
},
filter: (n2k, state) => n2k.fields['Message ID'] == 'Mute'
},
{
node: prefix.bind(null, 'output.zone2.isMuted'),
value: (n2k, state) => {
var val = n2k.fields['Mute']
return val == 'Muted' ? true : false
},
filter: (n2k, state) => n2k.fields['Message ID'] == 'Mute'
},
{
node: prefix.bind(null, 'output.zone3.isMuted'),
value: (n2k, state) => {
var val = n2k.fields['Mute']
return val == 'Muted' ? true : false
},
filter: (n2k, state) => n2k.fields['Message ID'] == 'Mute'
},
{
node: prefix.bind(null, 'output.zone4.isMuted'),
value: (n2k, state) => {
var val = n2k.fields['Mute']
return val == 'Muted' ? true : false
},
filter: (n2k, state) => n2k.fields['Message ID'] == 'Mute'
},
{
node: prefix.bind(null, 'output.zone1.equalizer'),
value: (n2k, state) => {
return {
bass: Number(n2k.fields.Bass),
mid: Number(n2k.fields.Mid),
treble: Number(n2k.fields.Treble)
}
},
filter: (n2k, state) => n2k.fields['Message ID'] == 'Tone'
},
{
node: prefix.bind(null, 'output.zone2.equalizer'),
value: (n2k, state) => {
return {
bass: Number(n2k.fields.Bass),
mid: Number(n2k.fields.Mid),
treble: Number(n2k.fields.Treble)
}
},
filter: (n2k, state) => n2k.fields['Message ID'] == 'Tone'
},
{
node: prefix.bind(null, 'output.zone3.equalizer'),
value: (n2k, state) => {
return {
bass: Number(n2k.fields.Bass),
mid: Number(n2k.fields.Mid),
treble: Number(n2k.fields.Treble)
}
},
filter: (n2k, state) => n2k.fields['Message ID'] == 'Tone'
},
{
node: prefix.bind(null, 'output.zone4.equalizer'),
value: (n2k, state) => {
return {
bass: Number(n2k.fields.Bass),
mid: Number(n2k.fields.Mid),
treble: Number(n2k.fields.Treble)
}
},
filter: (n2k, state) => n2k.fields['Message ID'] == 'Tone'
}
]
5 changes: 3 additions & 2 deletions fusion/index.js
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
module.exports = {
130820: require('./130820.js')
}
//130820: [ ...require('./130820.js'), ...require('./130820-new.js') ]
130820: require('./130820-new.js')
}
31 changes: 17 additions & 14 deletions n2kMapper.js
Original file line number Diff line number Diff line change
Expand Up @@ -243,23 +243,26 @@ var toValuesArray = function (theMappings, n2k, state) {
typeof theMapping.node === 'function'
? theMapping.node(n2k, state)
: theMapping.node
var value =
typeof theMapping.source === 'function'
? theMapping.source(n2k, state)
: getValue(n2k, theMapping, state)
var allowNull =
typeof theMapping.allowNull !== 'undefined' &&
theMapping.allowNull
if (!(value == null) || allowNull) {
// null or undefined
updates.push({
path: path,
value: value
})
if ( path !== null ) {
var value =
typeof theMapping.source === 'function'
? theMapping.source(n2k, state)
: getValue(n2k, theMapping, state)
var allowNull =
typeof theMapping.allowNull !== 'undefined' &&
theMapping.allowNull
if (!(value == null) || allowNull) {
// null or undefined
updates.push({
path: path,
value: value
})
}
}
}
} catch (ex) {
process.stderr.write(ex + ' ' + JSON.stringify(n2k))
process.stderr.write(JSON.stringify(n2k))
console.error(ex)
}
return updates
}, [])
Expand Down
1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
"dependencies": {
"@canboat/canboatjs": "^1.13.1",
"JSONStream": "~1.3.0",
"camelcase": "^6.2.0",
"debug": "^4.0.0",
"int64-buffer": "^0.99.1007",
"lodash": "^4.17.11",
Expand Down