|
|
(не показаны 24 промежуточные версии 4 участников) |
Строка 1: |
Строка 1: |
| {{DISPLAYTITLE: Демонстрационный стенд KNX }}
| | Статья в процессе наполнения. Информация может быть не полной или содержать не точности. |
| ==Описание ==
| | |
| {{note|info|Информация в статье устарела}}
| |
| Выставочный демо-стенд WB-KNX. Создан, как пример использования контроллера Wiren Board с модулем KNX. Стенд оснащен оборудованием с разными шинами и протоколами, объединяя их в одну систему через контроллер WB6. | | Выставочный демо-стенд WB-KNX. Создан, как пример использования контроллера Wiren Board с модулем KNX. Стенд оснащен оборудованием с разными шинами и протоколами, объединяя их в одну систему через контроллер WB6. |
| | | [[File:Knx_stand_2.png|250px|thumb|right|Демо-cтенд WB-KNX]] |
| <gallery mode="packed" heights="200px">
| | [[File:Knx_stand_1.png|250px|thumb|right|Демо-cтенд WB-KNX]] |
| Image: Knx_stand_2.png | Демо-cтенд WB-KNX
| | [[File:Knx_stand_3.png|250px|thumb|right|Диммер HDL M/D06.1, Релейный модуль GIRA 2152 00/I01 ]] |
| Image: Knx_stand_1.png | Демо-cтенд WB-KNX
| | [[File:Knx_stand_4.png|250px|thumb|right|Панельки HDL P03.2-A и MPT14.1]] |
| Image: Knx_stand_3.png | Диммер HDL M/D06.1, Релейный модуль GIRA 2152 00/I01
| | [[File:Knx_stand_5.png|250px|thumb|right|Контроллер WB6, релейный модуль WBIO-DO-R10A-8, модули входов WBIO-DI-DR-8 и WBIO-DI-HVD-8, датчик температуры DS18B20]] |
| Image: Knx_stand_4.png | Панельки HDL P03.2-A и MPT14.1
| | [[File:Knx_stand_6.png|250px|thumb|right|Modbus устройства WB-MDM2, WB-MR3LV/S, WB-MRGB]] |
| Image: Knx_stand_5.png | Контроллер WB6, релейный модуль WBIO-DO-R10A-8, модули входов WBIO-DI-DR-8 и WBIO-DI-HVD-8, датчик температуры DS18B20
| | [[File:Knx_stand_7.png|250px|thumb|right|Блок питания KNX Berker]] |
| Image: Knx_stand_6.png | Modbus устройства WB-MDM2, WB-MR3LV/S, WB-MRGB
| |
| Image: Knx_stand_7.png | Блок питания KNX Berker
| |
| </gallery>
| |
| == Состав == | | == Состав == |
|
| |
|
Строка 65: |
Строка 61: |
| == Описание == | | == Описание == |
|
| |
|
| Основная идея стенда - показать взаимодействие между устройствами с разными протоколами. И то, что контроллер [[Wiren Board 6]] может расширить уже существующую автоматизацию на KNX другими более дешевыми устройствами. | | Основная идея стенда - показать взаимодействие между устройствами с разными протоколами. И то что контроллер [[Wiren Board 6]] может расширить уже существующую автоматизацию на KNX другими более дешевыми устройствами. |
| Либо наоборот, если Вам захотелось добавить в проект красивую KNX панельку, при этом остальное оборудование работает по modbus. Далее подробно рассмотрим настройку стенда и написание правил. | | Либо наоборот, если Вам захотелось добавить в проект красивую KNX панельку, при этом остальное оборудование работает по modbus. Основную информацию по сетям KNX можно найти '''[https://www.ixbt.com/home/knx-intro.shtml в этой статье]'''. Далее подробно рассмотрим настройку стенда и написание правил. |
| [[File:Knx_stand_sch.png|450px|thumb|center|Схема Демо-Стенда WB-KNX]]
| |
| | |
| == Настройка контроллера ==
| |
| | |
| Для начала настроим модули Wirenboard. Для этого в web-интерфейсе переходим в раздел '''Configs → Hardware Modules Configuration''' И выбираем установленные модули. В нашем случаеː
| |
| | |
| Internal slot 1 - Вставлен [[KNX Module for WB6 (WBE2-I-KNX)]], выбираем "WBE2-I-KNX: KNX/EIB TP-UART"
| |
| | |
| External I/O module 1 - подключен модуль [[WBIO-DO-R10A-8 Relay Module]], выбираем "WBIO-DO-RxA-8: 8 Channel Relay I/O module"
| |
| | |
| External I/O module 2 - подключен модуль [[WBIO-DI-DR-8 I/O Module]], выбираем "WBIO-DI-DR-8: Digital inputs (dry contact) I/O module"
| |
| | |
| External I/O module 3 - подключен [[Модуль наличия 220В (WBIO-DI-HVD-8)]], выбираем "WBIO-DI-HVD-8: High Voltage Digital Inputs I/O module"
| |
| | |
| После этого нажимаем кнопку "Save".
| |
| [[File:Hwconf-knx1.PNG|250px|thumb|center|Настройка модуля WBE2-I-KNX]]
| |
| | |
| Настраиваем modbus устройства. Для этого в web-интерфейсе переходим в раздел '''Configs → Serial Device Driver Configuration''' и задаем нужные параметры. Как это сделать можно посмотреть в документации к устройствам, здесь подробно об этом писать не буду.
| |
| [[File:Mqtt-serial-knxStand.PNG|250px|thumb|center|Настройка modbus устройств]]
| |
| | |
| Следующим шагом будет установка и настройка программ для работы с KNX. А именноː '''[[Knxd]]''' - Для взаимодействия с шиной KNX, '''[[KnxTool]]''' - для отладки, '''[[WB-KNXD-CONFIG]]''' - для удобной настройки KNXD через веб-интерфейс контроллера, '''[[MQTT_KNX]]''' - для взаимодействия движка правил '''([[Движок правил wb-rules]])''' c '''[[Knxd]]'''. Для установки всех программ разом введите команду в консольː
| |
| | |
| <pre>$ apt-get update && apt-get install knxd knxd-tools wb-knxd-config wb-mqtt-knx</pre>
| |
| | |
| После установки программ в web-интерфейсе переходим в раздел '''Configs → KNXD Configuration''' для настройки KNXD.
| |
| | |
| "'''Driver (-b, --layer2)'''" - В этом поле нужно указать драйвер и путь к устройству. В нашем случае указываем '''ncn5120:/dev/ttyKNX1'''
| |
| | |
| "'''EIB address (-e, --eibaddr)'''" - задаем EIB адрес нашему контроллеру '''1.1.255'''
| |
| | |
| "'''Client-addrs (-E, --client-addrs)'''" - указываем диапазон адресов, которые будут выдаваться EIB клиентам '''1.1.5:50'''
| |
| | |
| "'''Discovery (-D, --Discovery)'''" - Ставим галку, что бы контроллер отвечал на запросы поиска.
| |
| | |
| "'''Tunnelling (-T, --Tunnelling)'''" - Ставим галку
| |
| | |
| "'''Routing (-R, --Routing)'''" - Ставим галку
| |
| | |
| "'''Server (-S, --Server)'''" - Тоже ставим галку, что бы включить EIBnet/IP multicast сервер на контроллере
| |
| | |
| "'''Custom name of the server'''" - Произвольное имя сервера. Впишем '''WirenboardKNX'''
| |
| | |
| "'''Server address'''" - Оставим именно этот адрес, что бы сервер автоматически определялся в ETS5ː '''224.0.23.12:3671'''
| |
| | |
| Остальные настройки на данный момент нам не интересны. Сохраняем изменения нажав кнопку "Save". На этом закончим настройку контроллера и перейдем к настройке KNX устройств через ETS5.
| |
| | |
| == Настройка KNX устройств через ETS5 ==
| |
| | |
| Для настройки KNX устройств нам понадобится программа ETS5. Для наших целей сойдет бесплатная демо-версия (до 5 устройств на проект). Скачать можно с '''[https://my.knx.org/en/shop/software сайта knx.org]'''. Устанавливаем, запускаем.
| |
| | |
| Далее нужно выбрать интерфейс. Заходим во вкладку '''Системная Шина → Соединения → Интерфейсы'''. Здесь во вкладке "Показать интерфейсы" отображаются автоматически найденные по бродкаст адресу интерфейсы. Если интерфейсы не определились автоматически, то во вкладке "Сконфигурированные интерфейсы" можно нажать кнопку '''"добавить" → "IP Tunneling"''' и справа ввести IP адрес контроллера с запущенным KNXD, указав порт 3671 и нажать кнопку "выбрать".
| |
| | |
| После этого возвращаемся в вкладку "Обзор" и создаем новый проект (или импортируем уже готовый, если имеется). В новом проекте создаем комнату и называем на пример "KNX стенд". Нажимаем на комнату '''→ Добавить → Устройство'''. Откроется вкладка каталога устройств. В нашем случае необходимых устройств в каталоге нет. Их нужно импортировать из специального файла, который распространяет производитель (HDL). Необходимые файлы можно найти '''[https://drive.google.com/drive/folders/1zZXMKCmfKpn-SUYXp7OrmiLE_DN772VW на гугл диске компании HDL]'''. Находим нужные файлы и импортируем их в ETS5, после чего добавляем нужные устройства в комнату '''KNX стенд'''.
| |
| | |
| Далее настраиваем каждое устройствоː задаем индивидуальный адрес, включаем необходимые функции и присваиваем им групповые адреса. Если необходимо связываем устройства групповыми адресами между собой. Полный процесс настройки описывать так же нет смысла. Для каждого устройства он индивидуальный. Ниже я оставлю ссылку на проект и все используемые для этого проекта файлы. | |
| | |
| Как только все устройства настроены, адреса заданы - выбираем в верхнем меню '''→ Ввод в эксплуатацию → Загрузка → Полная загрузка →''' Следуя указаниям на экране нажимайте на кнопки "Режима загрузки" на устройствах для загрузки программ.
| |
| | |
| <gallery mode="packed" heights="200px">
| |
| File:Knx stand ets1.PNG|Добавляем интерфейс в ручную.
| |
| File:Knx stand ets2.PNG|Конфигурирование устройств.
| |
| File:Knx stand ets3.PNG|Загрузка программ в устройства.
| |
| </gallery>
| |
| | |
| После того как проект успешно загружен можно переходить к написанию правил на контроллере WB6.
| |
| | |
| Скачать готовый ETS5 проект стенда можно [https://wirenboard.com/wiki/images/d/d1/Wb-knx.zip по ссылке]
| |
| | |
| == Правила wb-rules ==
| |
| | |
| Зайдите в веб интерфейс контроллера и создайте новое правило во вкладке "Scripts".
| |
| | |
| === Вспомогательное правило для KNX ===
| |
| | |
| Вспомогательное правило помогает избежать лишних действий при работе с KNX. При получении посылки в топик "knx/data" данные парсятся и раскладываются по топикам. Для каждого группового адреса создается отдельный контрол. При изменении этого контрола данные так же отправляются обратно в топик "knx/data" для отправки на шину KNX. В объекте knx_vdev_obj мы можем явно указать заранее известные групповые адреса и задать им необходимый тип.
| |
| | |
| <syntaxhighlight lang="ecmascript">
| |
| | |
| (function() {
| |
| var knx_vdev_obj = {
| |
| title: "KNX Group Addresses",
| |
| cells: {
| |
| "1-1-1": {
| |
| type: "value",
| |
| value: "0"
| |
| },
| |
| "1-1-2": {
| |
| type: "switch",
| |
| value: false
| |
| },
| |
| "1-1-3": {
| |
| type: "range",
| |
| max: 255,
| |
| value: 0,
| |
| knx_type: "wide"
| |
| },
| |
| "1-1-6": {
| |
| type: "switch",
| |
| value: false
| |
| },
| |
| "1-1-7": {
| |
| type: "value",
| |
| value: "0"
| |
| },
| |
| "1-1-8": {
| |
| type: "value",
| |
| value: "0"
| |
| },
| |
| "1-1-9": {
| |
| type: "value",
| |
| value: "0"
| |
| },
| |
| "1-1-10": {
| |
| type: "switch",
| |
| value: false
| |
| },
| |
| "1-1-11": {
| |
| type: "switch",
| |
| value: false
| |
| },
| |
| "1-1-12": {
| |
| type: "value",
| |
| value: "0"
| |
| },
| |
| "1-1-13": {
| |
| type: "value",
| |
| value: 0,
| |
| knx_type: "wide"
| |
| }
| |
| }
| |
| };
| |
| | |
| | |
| var vdev_when_changed = [];
| |
| var vdev_devid = "knx_group_addrs";
| |
| | |
| for (var control_id in knx_vdev_obj.cells) {
| |
| if (knx_vdev_obj.cells.hasOwnProperty(control_id)) {
| |
| vdev_when_changed.push("knx_group_addrs/" + control_id);
| |
| }
| |
| }
| |
| | |
| defineVirtualDevice(vdev_devid, knx_vdev_obj);
| |
| | |
| defineRule("knx_vdev_feedback", {
| |
| whenChanged: vdev_when_changed,
| |
| then: function(newValue, devName, cellName) {
| |
| var group_address = cellName.split("-").join("/");
| |
| var value = +newValue;
| |
| var write_str = "";
| |
| | |
| | |
| if (knx_vdev_obj.cells[cellName].knx_type == "wide") {
| |
| while (value > 0) {
| |
| var rem = value % 256;
| |
| value = Math.floor(value / 256);
| |
| write_str = rem + " " + write_str;
| |
| }
| |
| write_str = "0 " + write_str;
| |
| } else {
| |
| write_str = "" + value;
| |
| }
| |
| | |
| if (write_str) {
| |
| dev["knx/data"] = "g:{} GroupValueWrite {}".format(group_address, write_str);
| |
| }
| |
| }
| |
| });
| |
| | |
| defineRule("knx_vdev_incoming", {
| |
| whenChanged: "knx/data",
| |
| then: function(newValue, devName, cellName) {
| |
| var arr = newValue.split(/\s/);
| |
| var sourceAddr = arr[0].split(/i\:|\,/);
| |
| var groupAddr = arr[1].split(/g\:|\,/);
| |
| var arr1 = newValue.split(/GroupValueWrite/);
| |
| var value = arr1[1];
| |
| if ((sourceAddr[1] == "0/0/0") || (sourceAddr[1] == "1/1/255")) { // skip local echo
| |
| return;
| |
| }
| |
| dev[vdev_devid][groupAddr[1].split("/").join("-")] = !!parseInt(value, 16);
| |
| }
| |
| });
| |
| | |
| })()
| |
| | |
| | |
| | |
| function knxConvertToFloat16(value) {
| |
| var sign = 0;
| |
| var exp = 0;
| |
| if (value < 0) {
| |
| sign = 1;
| |
| }
| |
| | |
| var mant = Math.floor(value * 100);
| |
| while ((mant < -2048) || (mant > 2047)) {
| |
| mant = mant >> 1;
| |
| exp += 1
| |
| }
| |
| | |
| var data = (sign << 15) | (exp << 11) | (mant & 0x07ff);
| |
| return data;
| |
| };
| |
| </syntaxhighlight>
| |
| | |
| === Основное правило ===
| |
| | |
| Если предыдущее правило универсальное и может быть использовано почти в каждом проекте, то это правило написано специально для нашего стенда. Здесь уже нет сложных преобразований, мы просто следим за необходимыми нам топиками и реагируем на их изменения.
| |
| | |
| <syntaxhighlight lang="ecmascript">
| |
| | |
| (function() {
| |
| | |
| var channel_pairs = [
| |
| ["knx_group_addrs/1-1-10", "wb-gpio/EXT1_R3A1"], // По нажатию на KNX кнопку, к которой привязан групповой адрес 1/1/10 включать или выключать индикатор 2
| |
| ["knx_group_addrs/1-1-11", "wb-mr3_139/K1"]
| |
| ];
| |
| | |
| | |
| function makePairRules(chan1, chan2) {
| |
| defineRule("channel_pair_follow_" + chan1 + "_" + chan2, {
| |
| whenChanged: chan1,
| |
| then: function(newValue, devName, cellName) {
| |
| dev[chan2] = newValue;
| |
| }
| |
| });
| |
| };
| |
| | |
| for (var i = 0; i < channel_pairs.length; ++i) {
| |
| var chan1 = channel_pairs[i][0];
| |
| var chan2 = channel_pairs[i][1];
| |
| makePairRules(chan1, chan2);
| |
| makePairRules(chan2, chan1);
| |
| }
| |
| | |
| | |
| defineRule("hdl_panel_set_temp", {
| |
| whenChanged: "wb-w1/28-041643cee6ff",
| |
| then: function(newValue, devName, cellName) {
| |
| dev["knx_group_addrs/1-1-13"] = knxConvertToFloat16(newValue + 2); // Передаем на KNX панельку температуру с датчика DS18B20
| |
| }
| |
| });
| |
| | |
| defineRule("dimmer_chan1", {
| |
| whenChanged: "knx_group_addrs/1-1-7",
| |
| then: function(newValue, devName, cellName) {
| |
| if (newValue == 11) {
| |
| dev["wb-mdm2_1/Channel 1"] = Math.min(dev["wb-mdm2_1/Channel 1"] + 10, 100); // Если зажать KNX кнопку - увеличиваем яркость modbus диммера на 10 % единиц.
| |
| } else if (newValue == 3) {
| |
| dev["wb-mdm2_1/Channel 1"] = Math.max(dev["wb-mdm2_1/Channel 1"] - 10, 0);
| |
| }
| |
| }
| |
| });
| |
| | |
| defineRule("hdl_dimmer_chan1_on_off", {
| |
| whenChanged: "wb-gpio/EXT2_DR1",
| |
| then: function(newValue, devName, cellName) {
| |
| if (newValue) {
| |
| dev["knx_group_addrs/1-1-2"] = !dev["knx_group_addrs/1-1-2"]; // По нажатию на обычный выключатель звонкового типа переключаем KNX диммер
| |
| }
| |
| }
| |
| });
| |
| | |
| | |
| defineRule("dimmer_chan1_on_off", {
| |
| whenChanged: "wb-gpio/EXT2_DR2",
| |
| then: function(newValue, devName, cellName) {
| |
| if (newValue) {
| |
| dev["knx_group_addrs/1-1-6"] = !dev["knx_group_addrs/1-1-6"]
| |
| }
| |
| }
| |
| });
| |
| defineRule("dimmer_chan1_on_off_knx", {
| |
| whenChanged: "knx_group_addrs/1-1-6",
| |
| then: function(newValue, devName, cellName) {
| |
| if (newValue) {
| |
| dev["wb-mdm2_1/Channel 1"] = 70;
| |
| } else {
| |
| dev["wb-mdm2_1/Channel 1"] = 0;
| |
| }
| |
| }
| |
| });
| |
| | |
| })();
| |
| | |
| function knxConvertToFloat16(value) {
| |
| var sign = 0;
| |
| var exp = 0;
| |
| if (value < 0) {
| |
| sign = 1;
| |
| }
| |
| | |
| var mant = Math.floor(value * 100);
| |
| while ((mant < -2048) || (mant > 2047)) {
| |
| mant = mant >> 1;
| |
| exp += 1
| |
| }
| |
|
| |
|
| var data = (sign << 15) | (exp << 11) | (mant & 0x07ff);
| | == Настройка == |
| return data;
| |
| };
| |
| </syntaxhighlight>
| |