iobroker.artnet
Version:
The adapter allows to send and receive MQTT messages from ioBroker and to be a broker.
354 lines (314 loc) • 15 kB
HTML
<html>
<head>
<link rel="stylesheet" type="text/css" href="../../lib/css/themes/jquery-ui/redmond/jquery-ui.min.css"/>
<script type="text/javascript" src="../../lib/js/jquery-1.11.1.min.js"></script>
<script type="text/javascript" src="../../socket.io/socket.io.js"></script>
<script type="text/javascript" src="../../lib/js/jquery-ui-1.10.3.full.min.js"></script>
<link rel="stylesheet" type="text/css" href="../../css/adapter.css"/>
<script type="text/javascript" src="../../js/translate.js"></script>
<script type="text/javascript" src="words.js"></script>
<script type="text/javascript" src="../../js/adapter-settings.js"></script>
<style>
#grid-devices tr:nth-child(even) {
background: lightgray;
}
</style>
<script type="text/javascript">
var objects = {};
function addDevice(name, firstAddress, fixture, callback) {
if (typeof name === 'object') {
if (!name || !name.length) {
if (callback) callback();
return;
}
var _name = name.shift();
addDevice(_name, firstAddress, fixture, function () {
addDevice(name, firstAddress + fixture.native.length, fixture, callback);
});
} else {
var deviceObj = JSON.parse(JSON.stringify(fixture.native.channel));
var deviceId = 'artnet.' + instance + '.' + fixture._id.split('.').pop() + '.' + firstAddress;
deviceObj._id = deviceId;
deviceObj.common.name = name || deviceId;
deviceObj.native.address = firstAddress;
deviceObj.native.length = fixture.native.length;
deviceObj.native.interval = 0;
var objs = JSON.parse(JSON.stringify(fixture.native.states));
showDevice(deviceObj);
for (var i = 0; i < objs.length; i++) {
var dpType = objs[i].common.role.split('.').pop();
var id = deviceId + '.' + dpType;
objs[i].common.name = name ? name + ' ' + dpType : id;
objs[i].parent = deviceId;
objs[i]._id = id;
objs[i].native.channel = firstAddress++;
}
objs.push(deviceObj);
function insertObjs(_objs) {
if (!_objs || !_objs.length) {
console.log('done ' + deviceId);
callback && callback();
} else {
var obj = _objs.pop();
console.log('Add ' + obj._id);
socket.emit('setObject', obj._id, obj, function () {
insertObjs(_objs);
});
}
}
insertObjs(objs);
}
}
function load(settings, onChange) {
for (var key in settings) {
if (!settings.hasOwnProperty(key)) continue;
var $value = $('#' + key + '.value');
if ($value.attr('type') === 'checkbox') {
$value.prop('checked', settings[key]).change(function() {
onChange();
});
} else {
$value.val(settings[key]).change(function() {
onChange();
}).keyup(function () {
$(this).trigger('change');
})
}
}
onChange(false);
var fixtures = {};
socket.emit('getObjectView', 'system', 'meta', {startkey: 'artnet.meta.', endkey: 'artnet.meta.\u9999', include_docs: true}, function (err, res) {
var $fixture = $('#fixture');
for (var i = res.rows.length - 1; i >= 0; i--) {
var row = res.rows[i];
fixtures[row.id] = row.value;
$fixture.append('<option value="' + row.id + '">' + _(row.value.native.channel.common.role) + '</option>');
}
});
$('#tabs').tabs();
$('#dialog-fixture').dialog({
autoOpen: false,
width: 400,
height: 300,
modal: true,
title: _('choose fixture'),
buttons: [
{
text: _('Add device'),
click: function() {
var name = $('#name').val();
var firstAddress = parseInt($('#first-address').val(), 10);
var fixture = fixtures[$('#fixture').val()];
var count = parseInt($('#fixture-count').val(), 10);
if (count === 1) {
addDevice(name, firstAddress, fixture, function () {
$('#dialog-fixture').dialog('close');
});
} else {
var names = [];
for (var i = 0; i < count; i++) {
names.push(name + ' ' + (i + 1));
}
addDevice(names, firstAddress, fixture, function () {
$('#dialog-fixture').dialog('close');
});
}
}
},
{
text: _('Cancel'),
click: function () {
$(this).dialog('close');
}
}
]
});
$('#add').button({
label: _('Add device'),
icons: {
primary: 'ui-icon-plus'
}
}).on('click', function () {
// find next free address
var max = 1;
$('.device').each(function () {
var id = $(this).data('channel');
if (objects[id].native.address + objects[id].native.length > max) max = objects[id].native.address + objects[id].native.length;
});
$('#fixture-count').val(1);
$('#first-address').val(max);
$('#dialog-fixture').dialog('open');
});
socket.emit('getObjectView', 'system', 'channel', {startkey: 'artnet.' + instance + '.', endkey: 'artnet.' + instance + '.\u9999', include_docs: true}, function (err, res) {
res.rows.sort(function (a, b) {
if (a.value.native.address > b.value.native.address) return 1;
if (a.value.native.address < b.value.native.address) return -1;
return 0;
});
for (var i = 0; i < res.rows.length; i++) {
showDevice(res.rows[i].value);
}
});
}
function save(callback) {
var obj = {};
$('.value').each(function () {
var $this = $(this);
var id = $this.attr('id');
if ($this.attr('type') === 'checkbox') {
obj[id] = $this.prop('checked');
} else {
obj[id] = $this.val();
}
});
callback(obj);
}
function deleteState(id) {
socket.emit('delObject', id, function (err) {
socket.emit('delState', id, function (err) {
});
});
}
function showDevice(obj) {
objects[obj._id] = obj;
var text = '';
text += '<tr class="device" data-channel="' + obj._id + '">';
text += '<td style="text-align: right; width: 150px">' + obj.common.name + '</td>';
text += '<td style="text-align: center; width: 100px">' + obj.native.address + '</td>';
text += '<td style="text-align: center; width: 100px">' + _(obj.common.role) + '</td>';
text += '<td style="text-align: center; width: 100px"><select class="interval" data-id="' + obj._id + '">' +
'<option value="0" class="translate">none</option>' +
'<option value="100">100ms</option>' +
'<option value="200">200ms</option>' +
'<option value="300">300ms</option>' +
'<option value="400">400ms</option>' +
'<option value="500">500ms</option>' +
'<option value="600">600ms</option>' +
'<option value="700">700ms</option>' +
'<option value="800">800ms</option>' +
'<option value="900">900ms</option>' +
'<option value="1000">1s</option>' +
'<option value="1100">1s 100ms</option>' +
'<option value="1200">1s 200ms</option>' +
'<option value="1300">1s 300ms</option>' +
'<option value="1400">1s 400ms</option>' +
'<option value="1500">1s 500ms</option>' +
'<option value="1600">1s 600ms</option>' +
'<option value="1700">1s 700ms</option>' +
'<option value="1800">1s 800ms</option>' +
'<option value="1900">1s 900ms</option>' +
'<option value="2000">2s</option>' +
'<option value="2500">2.5s</option>' +
'<option value="3000">3s</option>' +
'<option value="3500">3.5s</option>' +
'<option value="4000">4s</option>' +
'<option value="4500">4.5s</option>' +
'<option value="5500">5.5s</option>' +
'<option value="6000">6s</option>' +
'<option value="7000">7s</option>' +
'<option value="8000">8s</option>' +
'<option value="9000">9s</option>' +
'<option value="10000">10s</option>' +
'<option value="12000">12s</option>' +
'<option value="15000">15s</option>' +
'<option value="17000">17s</option>' +
'<option value="20000">20s</option>' +
'<option value="25000">25s</option>' +
'<option value="30000">30s</option>' +
'</select></td>';
text += '<td style="text-align: center"><button class="del" data-id="' + obj._id + '"></button></td>';
text += '</tr>';
$('#grid-devices').append(text);
$('button[data-id="' + obj._id + '"]').button({
text: false,
icons: {
primary: 'ui-icon-trash'
}
}).css({width: 22, height: 22}).on('click', function () {
var id = $(this).data('id');
if (confirm(_('Are you sure?'))) {
socket.emit('delObject', id, function () {
socket.emit('getObjectView', 'system', 'state', {startkey: id + '.', endkey: id + '.\u9999', include_docs: true}, function (err, res) {
for (var i = 0; i < res.rows.length; i++) {
deleteState(res.rows[i].id);
}
$('tr[data-channel="' + id + '"]').remove();
delete objects[id];
});
});
}
});
$('.interval[data-id="' + obj._id + '"]').on('change', function () {
var $this = $(this);
var id = $this.data('id');
objects[id].native.interval = parseInt($this.val(), 10);
$(this).prop('disabled', true);
socket.emit('setObject', id, objects[id], function () {
$this.prop('disabled', false);
});
}).val(obj.native.interval || 0);
}
</script>
</head>
<body>
<div id="adapter-container">
<div id="tabs">
<ul>
<li><a href="#settings" class="translate">Art-Net node</a></li>
<li><a href="#devices" class="translate">DMX512 devices</a></li>
</ul>
<div id="settings">
<table><tr><td><img src="artnet.png" width="64" height="64"></td><td><h3 class="translate">Art-Net adapter settings</h3></td></tr></table>
<table>
<tr><td><label class="translate" for="host">Host</label></td><td><input class="value" type="text" id="host" size="20"></td></tr>
<tr><td><label class="translate" for="port">Port</label></td><td><input class="value" type="number" min="1" max="65565" id="port"></td></tr>
<tr><td><label class="translate" for="universe">DMX Universe</label></td><td><input class="value" type="number" min="0" max="512" id="universe"></td></tr>
</table>
</div>
<div id="devices">
<p class="translate">help</p>
<button id="add"></button>
<!--table id="grid-devices"></table>
<div id="pager-devices"></div-->
<table>
<thead>
<tr class="ui-widget-header">
<td style="width: 40px; text-align: center" class="translate">Name</td>
<td style="width: 40px; text-align: center" class="translate">Address</td>
<td style="width: 70px; text-align: center" class="translate">Type</td>
<td style="width: 70px; text-align: center" class="translate">Interval</td>
<td style="width: 30px; text-align: center" class="translate"></td>
</tr>
</thead>
<tbody id="grid-devices">
</tbody>
</table>
</div>
</div>
</div>
<div id="dialog-fixture">
<table>
<tr>
<td><label class="translate" for="name">Name</label></td>
<td><input id="name" type="text"></td>
</tr>
<tr>
<td><label class="translate" for="fixture">Fixture</label></td>
<td><select id="fixture">
</select></td>
</tr>
<tr>
<td><label class="translate" for="fixture-count">Count</label></td>
<td><input id="fixture-count" type="number"/></td>
</tr>
<tr>
<td><label class="translate" for="first-address">First address</label></td>
<td><input id="first-address" type="number"/></td>
</tr>
</table>
</div>
<div id="dialog-channel" title="setup channels">
<table id="table-channels"></table>
</div>
</body>
</html>