Industry 4.0 · цифровые двойники станков и промышленной автоматики · отечественная R&D-разработка +7 925 353-56-35 info@synctwin.ru
Документация / Справочник / Механизм

Механизм — это данные, а не код

Чтобы платформа знала, как устроен ваш узел или станок, его не программируют — его описывают файлом. Формат описания — URDF: звенья, шарниры, пределы, точки датчиков. Мы такие модели потребляем: принять файл, связать имена, показать, питать позами с железа. Рисуете вы — в своём инструменте; мы проверяем принесённое и говорим, что не так.

Из чего состоит

Четыре понятия

ПонятиеЧто это у вас на железе
Звено (link)Твёрдое тело: рама, каретка, плечо, планшайба. Несёт видимую геометрию — примитив или меш.
Шарнир (joint)Подвижная связь двух звеньев: родитель, ребёнок, положение и направление оси. У шарнира есть имя — им его зовёт программа.
Пределы (limit)Границы хода, усилие и скорость. Границы — АБСОЛЮТНЫЕ координаты, а не длина хода.
Точка (frame)Место датчика или исполнителя. В URDF это звено без геометрии, прикреплённое неподвижным шарниром к тому звену, на котором оно физически сидит.

URDF — дерево: у каждого звена ровно один родитель, корень один. Из этого свойства следует всё остальное на этой странице, включая честную границу в конце.

Шарниры

Какие типы мы печатаем и читаем

ТипЧто значитУ насКогда
revoluteвращение с объявленными границамипечатаем · читаемПоворотный стол, ось-сустав. Требует <limit lower upper>.
prismaticпрямолинейный ход с границамипечатаем · читаемПортальная ось, толкатель, мачта, подъёмная колонна. Требует <limit lower upper>.
continuousвращение без границпечатаем · читаемЛента, шнек, шпиндель: паспортного хода у такой оси нет вовсе. Границы не объявляются — только усилие и скорость.
fixedнеподвижная связьпечатаем · читаемКожух на плече, точка датчика на каретке. Программой не зовётся.
floating · planarшесть / три свободных степенине печатаемПодвижным считается всё, что не fixed, — значит такой шарнир на входе потребует связи с каналом наравне с остальными. Обычно это признак, что модель описывает сцену, а не механизм.

continuous — не третий класс движения, а честная запись случая «вращение без объявленного предела». У ленты и шнека хода в паспорте нет вовсе, и revolute заставил бы выдумать границы либо запереть ось нулевым ходом.

Пределы — это абсолютные координаты хода, а не его длина. Ось, которая ходит от −150 до +150 мм, пишется как lower="-0.15" upper="0.15", а не как «300». Одно имя с двумя смыслами однажды сделало рабочий конверт станка вдвое шире реального.

Имена

Имя шарнира — то, чем его зовёт программа

Связка «механизм ↔ управление» держится на одном имени. Поэтому имя шарнира подвижной оси — не подпись для человека, а адрес.

Что этоНомерИмяГде в файле
серво узла автоматики0srv0<joint name="srv0">
серво узла автоматики2srv2<joint name="srv2">
дискретный вход1di1<link name="di1"> — точка датчика
дискретный выход0do0<link name="do0"> — точка исполнителя
аналоговый вход0ai0<link name="ai0"> — точка замера
ось станкаX · Y · Z · A · B · Cбуква оси: ею зовёт ось управляющая программа

Ведущих нулей нет. Подпись канала («зажим тисков») именем не является и меняется свободно — иначе переименование тихо переставляло бы шарнир под другой привод. Ваши собственные имена звеньев, материалов и неподвижных деталей — как хотите: договор касается только шарниров подвижных осей и точек каналов.

Сегодня файлом механизма описывается узел автоматики. Станок описывается шаблоном кинематики и паспортом осей — см. типы станков; общее у них одно и то же правило: имя, которым зовёт ось программа, и есть связка с механизмом.

Чужая модель

Таблица имён вместо переименования

Модель из ROS или от вендора несёт свои 7–36 имён. Переименовывать их руками — стена, а переименовать за вас мы не имеем права: порядок звеньев в дереве и номер привода — разные вещи, и однажды они разойдутся молча.

Поэтому файл приносится вместе с картой {канал: имя в файле}. Судить первый пункт договора будет карта, а не написание имён внутри файла.

{ "mechanism": "mechanism.urdf", "joints": { "srv0": "lift_lower_joint", "srv1": "lift_upper_joint" } }

Карта проверяется целиком: непокрытый подвижный шарнир и канал, чьё имя ни к чему в файле не ведёт, — это названные отказы. Карта едет на бокс отдельным файлом рядом с механизмом, потому что пакет обязан быть самодостаточным: бокс, получив чужой файл, должен знать, какой шарнир двигает srv0.

Геометрия

Меши: что принимаем и что показываем

ФорматХранилищеЭкранЗамечание
.glbдадапредпочтительный формат: одно тело, материалы внутри
.gltfдадавезёт с собой буфер .bin и текстуры .png / .jpg
.stlдадаголая сетка, без материалов
.daeданетхранилище примет, экран назовёт отказ «формат .dae не читаем»
.objданетто же: принимается, но не рисуется
.bin · .png · .jpgдаспутники glTF: URDF их не называет, тело тянет их само

Путь меша указывается ровно так, как он написан внутри URDF (meshes/frame.stl): файлы приезжают тем же запросом, что и текст механизма, — одна транзакция, один владелец записи. Общий предел на комплект геометрии — 30 МБ.

Принимаются меши только подвижных звеньев. «Подвижное» — это вывод, а не список исключений: звено подвижно, если путь от корня до него содержит хотя бы один не-fixed шарнир (кожух, прикрученный fixed к плечу, едет вместе с плечом и потому подвижен). Не принесённый меш подвижного звена — отказ; меш неподвижной рамы не кладётся, и об этом говорится строкой предупреждения, а не молчанием.

На бокс уезжают три вещи: текст механизма, таблица имён и принятые меши.

Не требуем

Что мы принимаем и игнорируем

ТегЧто с ним
<collision>Принимаем и игнорируем: столкновений мы не считаем. Меш, названный только в <collision>, не требуется — платить десятками мегабайт за данные, которые никто не читает, мы не просим.
<inertial>Динамики мы не считаем: копия питается позами с железа, а не решает уравнения движения.
<mimic>НЕ поддержан: сцепленную пару (гантри, параллельный захват, пантограф) покажем как два независимых шарнира. Если в вашей модели ведомый вал идёт за ведущим — на картинке он будет стоять.

Не тратьте время на подготовку столкновительной геометрии и на массы с тензорами инерции: мы их не читаем. Копия питается позами, приходящими с железа, а не решает физику.

Импорт

Что проверяет дверь

Порядок жёсткий: судья → отказ либо запись. Молчаливого приёма нет, правки принесённого текста нет — ни отступов, ни единиц. Отказ приходит целиком, со всеми замечаниями сразу, а не по одному на попытку.

1

Имена

Шарнир подвижной оси зовётся по договору (srv0, srv1, …) — либо приносится таблица имён. Имя, похожее на адрес, но написанное иначе (servo_0, SRV0, joint3), отвергается с подсказкой точного имени. За вас не переименовываем.

проверяется
2

Дерево

У звена ровно один родитель, корень один, циклов нет.

проверяется
3

Пределы

<limit lower upper> объявлены у revolute и prismatic и заданы абсолютными координатами хода, а не его длиной.

проверяется
4

Единицы

Метры и радианы: URDF — это СИ. Объявить единицы в файле нечем, поэтому проверяется правдоподобие величины — так ловятся миллиметры и градусы, положенные в СИ-поле.

проверяется
5

Внутри нет железа

Ни пина, ни слейва, ни шины (lcec, slave, cia402, din-, dout-, ain-). URDF описывает механику; чем канал является электрически (роль, профиль движения) — знает passport.json рядом с механизмом. Куда он подключён на конкретном стенде — не знает и паспорт: узел в каталоге один, стендов много.

проверяется

Файлы xacro принимаются. Реальные модели ROS почти всегда приходят макросами и включениями — разворачивание идёт до того же единственного судьи. Вместе с файлом механизма присылаются его соседи (включения, макросы, параметры). Аргументы xacro на этом шаге не задаются: берутся умолчания, а объявленные файлом аргументы называются в ответе — у файла с $(arg …) разворачиваний несколько, и мы взяли одно.

Пока свой файл не принесён, механизм — наш черновик, напечатанный по паспорту узла: цепочка по порядку приводов, схематичные звенья, и каждое додуманное число названо и в предупреждениях, и комментарием в самом XML. После импорта механизм — ваш файл, и генератор в него больше не пишет; вернуться к черновику можно одним движением.

Паспорт

Четвёртый файл каталога — passport.json

URDF описывает МЕХАНИКУ узла — звенья, шарниры, пределы хода. Всё, что механикой не является — роль канала, чем он физически исполнен, профиль его движения, адресное пространство ячеек, имя и описание узла для человека, — несёт отдельный файл рядом с механизмом: passport.json. Узел заводится каталогом из пяти файлов, и ни строкой кода:

  • mechanism.urdf — механика: звенья, шарниры, пределы хода.
  • меши — видимая геометрия звеньев.
  • mechanism_map.json — имена чужого донора, если файл принесён не наш.
  • passport.json — роли каналов, электрика, ячейки, имя и описание узла.
  • program.plc — логика: что узел делает.

Разграничение владения записи жёсткое: поле, которое КРУГ URDF выводит сам (тип шарнира, ход, порядок каналов), в паспорте не дублируется — это была бы вторая правда о том же. Паспорт несёт ровно то, чего URDF не может сказать в принципе.

РазделПоляПочему не в URDF
servosrole (ось · сустав · вращение · затяжка), kind (физический механизм: лента, мачта, вилка, шнек…), max_velocity, max_acceleration, max_deceleration, max_torque, rated_torque_nm, lead_mm (ход винта, мм/об), gear_num / gear_den шарнир задаёт ТИП движения и пределы хода, но не режим привода и не физику передачи — continuous из файла читается одинаково что у ленты, что у шпинделя завинчивания
outputsrole: grip, clamp, gate, valve, marker, applicator, diverter, vacuum, glue, part_feed точка исполнителя в URDF есть, а того, ЧТО она делает, файл не говорит — дискретных выходов в дереве звеньев нет вовсе
inputsrole: presence, at_position, trigger, verdict, fill_level, force_ok, grip_ok, label_gap то же для входов: точка датчика есть, смысл сигнала — нет
analogsquantity, units аналоговых каналов URDF не несёт вовсе
gridcols, rows, levels (адрес: буква A,B,… → X, число 1.. → Y, .N → Z), pitch [dx,dy,dz] мм (без умолчания), origin [x,y,z] мм — координата ячейки A1 ячеек в URDF нет по определению: стеллаж — не звено и не шарнир, вывести «восемь столбцов с шагом 700» из механизма не из чего. Именованные точки (exit1 / home / input) сюда НЕ попадают — у точки есть родитель-звено, она остаётся <link>-маркером cell_<имя> в самом механизме; сами ячейки A1…H5 нигде не хранятся — считаются из шага и начала
name / descriptionдве строки, ровно два поля <robot name=…> в URDF — идентификатор механизма, а не подпись узла для человека; описания в файле нет вовсе
{ "version": 1, "name": "Кран-штабелёр (склад)", "description": "Рельсовый ASRS-кран: рельс + мачта + вилка + захват.", "servos": [ { "channel": "srv0", "label": "нижняя ступень", "role": "linear_axis", "kind": "mast" }, { "channel": "srv1", "label": "верхняя ступень", "role": "linear_axis", "kind": "mast" } ], "outputs": [], "inputs": [], "analogs": [], "grid": { "cols": 8, "rows": 5, "levels": 1, "pitch": [700.0, 400.0, 0.0], "origin": [0.0, 0.0, 0.0] } }

lead_mm умолчания не имеет. Ход винта — свойство ЭКЗЕМПЛЯРА оборудования, не механики. Не назван в паспорте — прямая ось честно остаётся без хода винта (в 3D не поедет, и это видно) вместо того, чтобы поехать по придуманному числу. Образец галереи ewellix_lift ровно в этом положении: программа-пример для него не собрана, потому что lead_mm паспортом не назван.

Чего в паспорте нет и быть не должно — фактов КОНКРЕТНОГО СТЕНДА: слейв, пин, шарнир привода, датум нуля. Узел в каталоге один, стендов, куда его поставят, много; эти числа называет наладчик у железа, а не карточка образца.

Ключ канала паспорта — его ИМЯ (srv0, di0), то же самое, которым его зовут URDF и программа; отдельного порядкового номера паспорт не хранит.

Программа

Пятый файл каталога — program.plc

URDF описывает механику, паспорт — роли и электрику, а что узел делает называет отдельный текстовый файл рядом с ними: program.plc. Внутри — ТЕЛО программы на языке лаборатории PLC (том же, на котором пишутся программы рода motion в /programs/plc): состояния, переходы, движения по дорожкам.

Объявления оборудования в файле нет. Пролог rig({ axes, outputs, inputs }) — вторая запись состава узла — платформа ПЕЧАТАЕТ сама из паспорта и механизма, на место метки // @rig в начале файла. Написать этот пролог рукой нельзя: состав узла жил бы в двух местах сразу и расходился бы молча, как только один из них поправят. Метка бывает и в форме // @rig inline — печать входит прямо в неё, без переноса строки.

Файла нет — программы у узла нет. Не подставляется ни пустой шаблон, ни программа по умолчанию: логика не объявлена, и вывести её из механизма с паспортом не из чего. Это видно строкой на экране узла, а не молчанием.

// @rig machine({ title: 'Конвейер — счёт деталей', initial: 'ход', states: { 'ход': { lanes: { лента: [spin(1, 30)] }, on: { 'счётчик ↑': 'посчитали' }, }, 'посчитали': { wait: 0.4, on: { done: 'ход' }, }, }, })

Файлом программу можно принести не у всякого узла. У образцов, чья программа-пример ВЫЧИСЛЯЕТСЯ из <limit> принесённого механизма (motopos_d500, flir_ptu_d46, ewellix_lift), она остаётся вычисляемой, а не файлом: замените механизм — программа обязана поехать за новыми пределами хода, а статический текст файла этого не умеет. Это граница формата, а не недоделанная функция.

Граница формата

Что URDF не выражает — и мы это не скрываем

Параллельные кинематики в URDF невыразимы. У гексапода подвижная платформа держится на шести штангах — это шесть родителей у одного звена, тогда как дерево допускает ровно одного. Сферических шарниров в URDF нет вовсе. То же у трипода и линейной дельты. Ожидаемое поведение — названный отказ, а не молчание и не картинка, которая врёт. Второй формат входа для замкнутых цепей — ниже, в разделе «Готовится».

Токарный станок, наоборот, ложится на дерево отлично — двумя ветвями от станины:

станина ├── каретка Z (prismatic) → салазки X (prismatic) → резцедержка └── шпиндель (continuous) → патрон → заготовка

Осторожно, если шпиндель работает и как ось C. Тип шарнира называется один раз: шпиндель — это continuous, вращение без границ. Пределы и подача оси C живут отдельным полем паспорта, а не вторым шарниром на том же валу. Иначе получится одно имя с двумя смыслами — и разъедется не значение, а смысл.

Готовится

Вход из STEP и второй формат

в работе

Механизм из STEP

Интеграторы приносят STEP и чертежи, а не робо-описания. STEP даёт точную геометрию, дерево сборки и имена, но не даёт осей. Планируемый договор: структура сборки совпадает с кинематическим деревом — подсборка становится звеном, её трансформация — положением шарнира; человеку остаются тип шарнира, ось и пределы. Ось размечается кликом по грани, а точные числа берутся из математики B-rep.

в работе

SDF — для замкнутых цепей

Формат входа сменный: внутренняя модель наша, а формат — это парсер. Второй на очереди — SDF (SDFormat): он умеет замкнутые цепи и закрывает ровно ту дыру, где URDF отказывает, — гексапод, трипод, дельту.

Оба пункта в разработке прямо сейчас. Сроков здесь не публикуем; сегодняшний рабочий вход — URDF и xacro.

Образцы

Галерея готовых механизмов

Девять образцов, которые можно взять и посмотреть, как выглядит правильно описанный узел. Учебные: паспортом оборудования они не являются, числа из них цитировать как замер нельзя.

ОбразецПроисхождениеЧто показывает
Конвейернаш черновиклента одним серво; геометрии нет — учит договору имён
Портал 3 оси + захватнаш черновикцепочка X→Y→Z и точки каналов
Поворотный делительный столнаш черновикодна поворотная ось
Конвейер с рамойгибридчужой меш рамы (Gazebo Fuel, CC-BY 4.0) + наш подвижный барабан
Ewellix TLTдонор ROSтелескопическая подъёмная колонна, две ступени на призматических шарнирах
FLIR PTU-D46донор ROSповоротная голова: поворот + наклон
Yaskawa MotoPos D500донор ROSсварочный позиционер: наклон + вращение планшайбы
Robotiq 2F-85донор ROSдвухпальцевый схват: один мотор, ход губок 85 мм
Стеллаж-краннаш черновикединственный образец с ЯЧЕЙКАМИ: три оси и адресное пространство 8×5 в паспорте, точки exit1/home/input — link-маркерами в механизме

Доноры взяты из открытых репозиториев ROS с зафиксированным коммитом и датой загрузки; лицензия и источник указаны рядом с каждым. Все образцы проходят ту же дверь, что и ваш файл: образец, не проходящий её, означает ошибку либо в образце, либо в правиле.

Дальше — типы станков и кинематики: какая порода что умеет и почему гексапод программируется движениями, но не режет по G-code.