');
- $container.add($wrapper);
- _addItems(item.items, $wrapper);
- } else {
- var _item = _.copyObj(item);
- _item.clayId = _items.length;
+ } else if (utils.includesCapability(meta.activeWatchInfo, item.capabilities)) {
+ if (item.type === 'section') {
+ var $wrapper = HTML('
');
+ $container.add($wrapper);
+ _addItems(item.items, $wrapper);
+ } else {
+ var _item = _.copyObj(item);
+ _item.clayId = _items.length;
- var clayItem = new ClayItem(_item).initialize(self);
+ var clayItem = new ClayItem(_item).initialize(self);
- if (_item.id) {
- _itemsById[_item.id] = clayItem;
+ if (_item.id) {
+ _itemsById[_item.id] = clayItem;
+ }
+
+ if (_item.appKey) {
+ _itemsByAppKey[_item.appKey] = clayItem;
+ }
+
+ _items.push(clayItem);
+
+ // set the value of the item via the manipulator to ensure consistency
+ var value = typeof _settings[_item.appKey] !== 'undefined' ?
+ _settings[_item.appKey] :
+ (_item.defaultValue || '');
+
+ clayItem.set(value);
+
+ $container.add(clayItem.$element);
}
-
- if (_item.appKey) {
- _itemsByAppKey[_item.appKey] = clayItem;
- }
-
- _items.push(clayItem);
-
- // set the value of the item via the manipulator to ensure consistency
- var value = typeof _settings[_item.appKey] !== 'undefined' ?
- _settings[_item.appKey] :
- (_item.defaultValue || '');
-
- clayItem.set(value);
-
- $container.add(clayItem.$element);
}
}
diff --git a/src/scripts/lib/utils.js b/src/scripts/lib/utils.js
index 02079f3..2e2e54a 100644
--- a/src/scripts/lib/utils.js
+++ b/src/scripts/lib/utils.js
@@ -17,3 +17,112 @@ module.exports.updateProperties = function(obj, descriptor) {
Object.defineProperty(obj, prop, descriptor);
});
};
+
+module.exports.capabilityMap = {
+ APLITE: {
+ platforms: ['aplite'],
+ minFwMajor: 0,
+ minFwMinor: 0
+ },
+ BASALT: {
+ platforms: ['basalt'],
+ minFwMajor: 0,
+ minFwMinor: 0
+ },
+ CHALK: {
+ platforms: ['chalk'],
+ minFwMajor: 0,
+ minFwMinor: 0
+ },
+ DIORITE: {
+ platforms: ['diorite'],
+ minFwMajor: 0,
+ minFwMinor: 0
+ },
+ EMERY: {
+ platforms: ['emery'],
+ minFwMajor: 0,
+ minFwMinor: 0
+ },
+ BW: {
+ platforms: ['aplite', 'diorite'],
+ minFwMajor: 0,
+ minFwMinor: 0
+ },
+ COLOR: {
+ platforms: ['basalt', 'chalk', 'emery'],
+ minFwMajor: 0,
+ minFwMinor: 0
+ },
+ MICROPHONE: {
+ platforms: ['basalt', 'chalk', 'diorite', 'emery'],
+ minFwMajor: 0,
+ minFwMinor: 0
+ },
+ SMARTSTRAP: {
+ platforms: ['basalt', 'chalk', 'diorite', 'emery'],
+ minFwMajor: 3,
+ minFwMinor: 4
+ },
+ SMARTSTRAP_POWER: {
+ platforms: ['basalt', 'chalk', 'emery'],
+ minFwMajor: 3,
+ minFwMinor: 4
+ },
+ HEALTH: {
+ platforms: ['basalt', 'chalk', 'diorite', 'emery'],
+ minFwMajor: 3,
+ minFwMinor: 10
+ },
+ RECT: {
+ platforms: ['aplite', 'basalt', 'diorite', 'emery'],
+ minFwMajor: 0,
+ minFwMinor: 0
+ },
+ ROUND: {
+ platforms: ['chalk'],
+ minFwMajor: 3,
+ minFwMinor: 4
+ },
+ DISPLAY_144x168: {
+ platforms: ['aplite', 'basalt', 'diorite'],
+ minFwMajor: 0,
+ minFwMinor: 0
+ },
+ DISPLAY_180x180_ROUND: {
+ platforms: ['chalk'],
+ minFwMajor: 0,
+ minFwMinor: 0
+ },
+ DISPLAY_200x228: {
+ platforms: ['emery'],
+ minFwMajor: 0,
+ minFwMinor: 0
+ }
+};
+
+/**
+ * Checks if all of the provided capabilities are compatible with the watch
+ * @param {Object} activeWatchInfo
+ * @param {Array} [capabilities]
+ * @return {boolean}
+ */
+module.exports.includesCapability = function(activeWatchInfo, capabilities) {
+ if (!capabilities || !capabilities.length) {
+ return true;
+ }
+
+ for (var i = capabilities.length - 1; i >= 0; i--) {
+ var capability = capabilities[i];
+ var mapping = module.exports.capabilityMap[capability];
+ if (!mapping ||
+ mapping.platforms.indexOf(activeWatchInfo.platform) === -1 ||
+ mapping.minFwMajor > activeWatchInfo.firmware.major ||
+ mapping.minFwMajor === activeWatchInfo.firmware.major &&
+ mapping.minFwMinor > activeWatchInfo.firmware.minor
+ ) {
+ return false;
+ }
+ }
+ return true;
+};
diff --git a/test/spec/lib/clay-config.js b/test/spec/lib/clay-config.js
index a977935..eab242f 100644
--- a/test/spec/lib/clay-config.js
+++ b/test/spec/lib/clay-config.js
@@ -27,6 +27,177 @@ describe('ClayConfig', function() {
checkReadOnly(clayConfig, properties);
});
+ /**
+ * Tests if the provided capabilities of the platform match
+ * @param {string} platform
+ * @param {number} fwMajor
+ * @param {number} fwMinor
+ * @param {Array} capabilities
+ * @param {number} expected
+ * @return {void}
+ */
+ function testCapabilities(platform, fwMajor, fwMinor, capabilities, expected) {
+ it(platform + ' is' + (expected ? '' : ' not') + ' included on firmware ' +
+ fwMajor + '.' + fwMinor + ' for capabilities ' + JSON.stringify(capabilities),
+ function() {
+ var item = {
+ type: 'input',
+ capabilities: capabilities
+ };
+ var meta = {
+ activeWatchInfo: {
+ platform: platform,
+ model: 'qemu_platform_' + platform,
+ language: 'en_US',
+ firmware: {
+ major: fwMajor,
+ minor: fwMinor,
+ patch: 0,
+ suffix: ''
+ }
+ }
+ };
+ var clayConfig = fixtures.clayConfig([item], true, true, null, meta);
+
+ assert.strictEqual(clayConfig.getAllItems().length, expected);
+ });
+ }
+
+ describe('capability filtering', function() {
+ testCapabilities('aplite', 2, 9, ['BW'], 1);
+ testCapabilities('aplite', 2, 9, ['COLOR'], 0);
+ testCapabilities('aplite', 2, 9, ['MICROPHONE'], 0);
+ testCapabilities('aplite', 2, 9, ['SMARTSTRAP'], 0);
+ testCapabilities('aplite', 2, 9, ['SMARTSTRAP_POWER'], 0);
+ testCapabilities('aplite', 2, 9, ['HEALTH'], 0);
+ testCapabilities('aplite', 2, 9, ['RECT'], 1);
+ testCapabilities('aplite', 2, 9, ['ROUND'], 0);
+ testCapabilities('aplite', 2, 9, ['DISPLAY_144x168'], 1);
+ testCapabilities('aplite', 2, 9, ['DISPLAY_180x180_ROUND'], 0);
+ testCapabilities('aplite', 2, 9, ['DISPLAY_200x228'], 0);
+ testCapabilities('aplite', 2, 9, ['APLITE'], 1);
+ testCapabilities('aplite', 2, 9, ['BASALT'], 0);
+ testCapabilities('aplite', 2, 9, ['CHALK'], 0);
+ testCapabilities('aplite', 2, 9, ['DIORITE'], 0);
+ testCapabilities('aplite', 2, 9, ['EMERY'], 0);
+
+ testCapabilities('aplite', 3, 10, ['BW'], 1);
+ testCapabilities('aplite', 3, 10, ['COLOR'], 0);
+ testCapabilities('aplite', 3, 10, ['MICROPHONE'], 0);
+ testCapabilities('aplite', 3, 10, ['SMARTSTRAP'], 0);
+ testCapabilities('aplite', 3, 4, ['SMARTSTRAP'], 0);
+ testCapabilities('aplite', 3, 3, ['SMARTSTRAP'], 0);
+ testCapabilities('aplite', 3, 10, ['SMARTSTRAP_POWER'], 0);
+ testCapabilities('aplite', 3, 10, ['HEALTH'], 0);
+ testCapabilities('aplite', 3, 9, ['HEALTH'], 0);
+ testCapabilities('aplite', 3, 10, ['RECT'], 1);
+ testCapabilities('aplite', 3, 10, ['ROUND'], 0);
+ testCapabilities('aplite', 3, 10, ['DISPLAY_144x168'], 1);
+ testCapabilities('aplite', 3, 10, ['DISPLAY_180x180_ROUND'], 0);
+ testCapabilities('aplite', 3, 10, ['DISPLAY_200x228'], 0);
+ testCapabilities('aplite', 3, 10, ['APLITE'], 1);
+ testCapabilities('aplite', 3, 10, ['BASALT'], 0);
+ testCapabilities('aplite', 3, 10, ['CHALK'], 0);
+ testCapabilities('aplite', 3, 10, ['DIORITE'], 0);
+ testCapabilities('aplite', 3, 10, ['EMERY'], 0);
+
+ testCapabilities('basalt', 3, 10, ['BW'], 0);
+ testCapabilities('basalt', 3, 10, ['COLOR'], 1);
+ testCapabilities('basalt', 3, 10, ['MICROPHONE'], 1);
+ testCapabilities('basalt', 3, 10, ['SMARTSTRAP'], 1);
+ testCapabilities('basalt', 3, 4, ['SMARTSTRAP'], 1);
+ testCapabilities('basalt', 3, 3, ['SMARTSTRAP'], 0);
+ testCapabilities('basalt', 3, 10, ['SMARTSTRAP_POWER'], 1);
+ testCapabilities('basalt', 3, 4, ['SMARTSTRAP_POWER'], 1);
+ testCapabilities('basalt', 3, 3, ['SMARTSTRAP_POWER'], 0);
+ testCapabilities('basalt', 3, 10, ['HEALTH'], 1);
+ testCapabilities('basalt', 3, 9, ['HEALTH'], 0);
+ testCapabilities('basalt', 3, 10, ['RECT'], 1);
+ testCapabilities('basalt', 3, 10, ['ROUND'], 0);
+ testCapabilities('basalt', 3, 10, ['DISPLAY_144x168'], 1);
+ testCapabilities('basalt', 3, 10, ['DISPLAY_180x180_ROUND'], 0);
+ testCapabilities('basalt', 3, 10, ['DISPLAY_200x228'], 0);
+ testCapabilities('basalt', 3, 10, ['APLITE'], 0);
+ testCapabilities('basalt', 3, 10, ['BASALT'], 1);
+ testCapabilities('basalt', 3, 10, ['CHALK'], 0);
+ testCapabilities('basalt', 3, 10, ['DIORITE'], 0);
+ testCapabilities('basalt', 3, 10, ['EMERY'], 0);
+
+ testCapabilities('chalk', 3, 10, ['BW'], 0);
+ testCapabilities('chalk', 3, 10, ['COLOR'], 1);
+ testCapabilities('chalk', 3, 10, ['MICROPHONE'], 1);
+ testCapabilities('chalk', 3, 10, ['SMARTSTRAP'], 1);
+ testCapabilities('chalk', 3, 4, ['SMARTSTRAP'], 1);
+ testCapabilities('chalk', 3, 3, ['SMARTSTRAP'], 0);
+ testCapabilities('chalk', 3, 10, ['SMARTSTRAP_POWER'], 1);
+ testCapabilities('chalk', 3, 4, ['SMARTSTRAP_POWER'], 1);
+ testCapabilities('chalk', 3, 3, ['SMARTSTRAP_POWER'], 0);
+ testCapabilities('chalk', 3, 10, ['HEALTH'], 1);
+ testCapabilities('chalk', 3, 9, ['HEALTH'], 0);
+ testCapabilities('chalk', 3, 10, ['RECT'], 0);
+ testCapabilities('chalk', 3, 10, ['ROUND'], 1);
+ testCapabilities('chalk', 3, 10, ['DISPLAY_144x168'], 0);
+ testCapabilities('chalk', 3, 10, ['DISPLAY_180x180_ROUND'], 1);
+ testCapabilities('chalk', 3, 10, ['DISPLAY_200x228'], 0);
+ testCapabilities('chalk', 3, 10, ['APLITE'], 0);
+ testCapabilities('chalk', 3, 10, ['BASALT'], 0);
+ testCapabilities('chalk', 3, 10, ['CHALK'], 1);
+ testCapabilities('chalk', 3, 10, ['DIORITE'], 0);
+ testCapabilities('chalk', 3, 10, ['EMERY'], 0);
+
+ testCapabilities('diorite', 3, 10, ['BW'], 1);
+ testCapabilities('diorite', 3, 10, ['COLOR'], 0);
+ testCapabilities('diorite', 3, 10, ['MICROPHONE'], 1);
+ testCapabilities('diorite', 3, 10, ['SMARTSTRAP'], 1);
+ testCapabilities('diorite', 3, 4, ['SMARTSTRAP'], 1);
+ testCapabilities('diorite', 3, 3, ['SMARTSTRAP'], 0);
+ testCapabilities('diorite', 3, 10, ['SMARTSTRAP_POWER'], 0);
+ testCapabilities('diorite', 3, 4, ['SMARTSTRAP_POWER'], 0);
+ testCapabilities('diorite', 3, 3, ['SMARTSTRAP_POWER'], 0);
+ testCapabilities('diorite', 3, 10, ['HEALTH'], 1);
+ testCapabilities('diorite', 3, 9, ['HEALTH'], 0);
+ testCapabilities('diorite', 3, 10, ['RECT'], 1);
+ testCapabilities('diorite', 3, 10, ['ROUND'], 0);
+ testCapabilities('diorite', 3, 10, ['DISPLAY_144x168'], 1);
+ testCapabilities('diorite', 3, 10, ['DISPLAY_180x180_ROUND'], 0);
+ testCapabilities('diorite', 3, 10, ['DISPLAY_200x228'], 0);
+ testCapabilities('diorite', 3, 10, ['APLITE'], 0);
+ testCapabilities('diorite', 3, 10, ['BASALT'], 0);
+ testCapabilities('diorite', 3, 10, ['CHALK'], 0);
+ testCapabilities('diorite', 3, 10, ['DIORITE'], 1);
+ testCapabilities('diorite', 3, 10, ['EMERY'], 0);
+
+ testCapabilities('emery', 3, 10, ['BW'], 0);
+ testCapabilities('emery', 3, 10, ['COLOR'], 1);
+ testCapabilities('emery', 3, 10, ['MICROPHONE'], 1);
+ testCapabilities('emery', 3, 10, ['SMARTSTRAP'], 1);
+ testCapabilities('emery', 3, 4, ['SMARTSTRAP'], 1);
+ testCapabilities('emery', 3, 3, ['SMARTSTRAP'], 0);
+ testCapabilities('emery', 3, 10, ['SMARTSTRAP_POWER'], 1);
+ testCapabilities('emery', 3, 4, ['SMARTSTRAP_POWER'], 1);
+ testCapabilities('emery', 3, 3, ['SMARTSTRAP_POWER'], 0);
+ testCapabilities('emery', 3, 10, ['HEALTH'], 1);
+ testCapabilities('emery', 3, 9, ['HEALTH'], 0);
+ testCapabilities('emery', 3, 10, ['RECT'], 1);
+ testCapabilities('emery', 3, 10, ['ROUND'], 0);
+ testCapabilities('emery', 3, 10, ['DISPLAY_144x168'], 0);
+ testCapabilities('emery', 3, 10, ['DISPLAY_180x180_ROUND'], 0);
+ testCapabilities('emery', 3, 10, ['DISPLAY_200x228'], 1);
+ testCapabilities('emery', 3, 10, ['APLITE'], 0);
+ testCapabilities('emery', 3, 10, ['BASALT'], 0);
+ testCapabilities('emery', 3, 10, ['CHALK'], 0);
+ testCapabilities('emery', 3, 10, ['DIORITE'], 0);
+ testCapabilities('emery', 3, 10, ['EMERY'], 1);
+
+ testCapabilities('aplite', 3, 10, ['BW', 'HEALTH'], 0);
+ testCapabilities('emery', 3, 10, ['COLOR', 'HEALTH'], 1);
+ testCapabilities('emery', 3, 10, ['MICROPHONE'], 1);
+ testCapabilities('chalk', 3, 10, ['APLITE', 'BASALT', 'DIORITE'], 0);
+ testCapabilities('basalt', 3, 10, ['SMARTSTRAP', 'SMARTSTRAP_POWER'], 1);
+ testCapabilities('aplite', 3, 10, ['COLOR', 'APLITE'], 0);
+ testCapabilities('aplite', 3, 10, ['APLITE', 'COLOR'], 0);
+ });
+
describe('.meta', function() {
it('populates meta', function() {
var clayConfig = fixtures.clayConfig(['input']);