diff --git a/.claude/skills/form-compile/scripts/form-compile.ps1 b/.claude/skills/form-compile/scripts/form-compile.ps1 index 599564ac..b119988d 100644 --- a/.claude/skills/form-compile/scripts/form-compile.ps1 +++ b/.claude/skills/form-compile/scripts/form-compile.ps1 @@ -1,4 +1,4 @@ -# form-compile v1.12 — Compile 1C managed form from JSON or object metadata +# form-compile v1.13 — Compile 1C managed form from JSON or object metadata # Source: https://github.com/Nikolay-Shirokov/cc-1c-skills param( [string]$JsonPath, @@ -1926,10 +1926,34 @@ function Emit-CommonFlags { if ($el.readOnly -eq $true) { X "$indenttrue" } } +function Title-FromName { + param([string]$name) + if (-not $name) { return '' } + $s = [regex]::Replace($name, '([А-ЯA-Z])([А-ЯA-Z][а-яa-z])', '$1 $2') + $s = [regex]::Replace($s, '([а-яa-z0-9])([А-ЯA-Z])', '$1 $2') + $parts = $s -split ' ' + if ($parts.Count -eq 0) { return $s } + $out = New-Object System.Collections.ArrayList + [void]$out.Add($parts[0]) + for ($i = 1; $i -lt $parts.Count; $i++) { + $p = $parts[$i] + if ($p.Length -gt 1 -and $p -ceq $p.ToUpper()) { + [void]$out.Add($p) + } else { + [void]$out.Add($p.ToLower()) + } + } + return ($out -join ' ') +} + function Emit-Title { - param($el, [string]$name, [string]$indent) - if ($el.title) { - Emit-MLText -tag "Title" -text "$($el.title)" -indent $indent + param($el, [string]$name, [string]$indent, [switch]$auto) + $title = $el.title + if (-not $title -and $auto -and $name) { + $title = Title-FromName -name $name + } + if ($title) { + Emit-MLText -tag "Title" -text "$title" -indent $indent } } @@ -2001,7 +2025,7 @@ function Emit-Input { if ($el.path) { X "$inner$($el.path)" } - Emit-Title -el $el -name $name -indent $inner + Emit-Title -el $el -name $name -indent $inner -auto:(-not $el.path) Emit-CommonFlags -el $el -indent $inner if ($el.titleLocation) { @@ -2052,7 +2076,7 @@ function Emit-Check { if ($el.path) { X "$inner$($el.path)" } - Emit-Title -el $el -name $name -indent $inner + Emit-Title -el $el -name $name -indent $inner -auto:(-not $el.path) Emit-CommonFlags -el $el -indent $inner $tl = if ($el.titleLocation) { "$($el.titleLocation)" } else { "Right" } @@ -2073,12 +2097,13 @@ function Emit-Label { X "$indent" $inner = "$indent`t" - if ($el.title) { + $labelTitle = if ($el.title) { "$($el.title)" } else { Title-FromName -name $name } + if ($labelTitle) { $formatted = if ($el.hyperlink -eq $true) { "true" } else { "false" } X "$inner" X "$inner`t<v8:item>" X "$inner`t`t<v8:lang>ru</v8:lang>" - X "$inner`t`t<v8:content>$(Esc-Xml "$($el.title)")</v8:content>" + X "$inner`t`t<v8:content>$(Esc-Xml "$labelTitle")</v8:content>" X "$inner`t</v8:item>" X "$inner" } @@ -2108,7 +2133,7 @@ function Emit-LabelField { if ($el.path) { X "$inner$($el.path)" } - Emit-Title -el $el -name $name -indent $inner + Emit-Title -el $el -name $name -indent $inner -auto:(-not $el.path) Emit-CommonFlags -el $el -indent $inner if ($el.hyperlink -eq $true) { X "$innertrue" } @@ -2130,7 +2155,7 @@ function Emit-Table { if ($el.path) { X "$inner$($el.path)" } - Emit-Title -el $el -name $name -indent $inner + Emit-Title -el $el -name $name -indent $inner -auto:(-not $el.path) Emit-CommonFlags -el $el -indent $inner if ($el.representation) { @@ -2219,7 +2244,7 @@ function Emit-Page { X "$indent" $inner = "$indent`t" - Emit-Title -el $el -name $name -indent $inner + Emit-Title -el $el -name $name -indent $inner -auto Emit-CommonFlags -el $el -indent $inner if ($el.group) { @@ -2278,7 +2303,8 @@ function Emit-Button { } } - Emit-Title -el $el -name $name -indent $inner + $btnAuto = -not ($el.command -or $el.stdCommand) + Emit-Title -el $el -name $name -indent $inner -auto:$btnAuto Emit-CommonFlags -el $el -indent $inner if ($el.defaultButton -eq $true) { X "$innertrue" } @@ -2368,7 +2394,7 @@ function Emit-Calendar { if ($el.path) { X "$inner$($el.path)" } - Emit-Title -el $el -name $name -indent $inner + Emit-Title -el $el -name $name -indent $inner -auto:(-not $el.path) Emit-CommonFlags -el $el -indent $inner # Companions @@ -2408,7 +2434,7 @@ function Emit-Popup { X "$indent" $inner = "$indent`t" - Emit-Title -el $el -name $name -indent $inner + Emit-Title -el $el -name $name -indent $inner -auto Emit-CommonFlags -el $el -indent $inner if ($el.picture) { @@ -2449,8 +2475,9 @@ function Emit-Attributes { X "$indent`t" $inner = "$indent`t`t" - if ($attr.title) { - Emit-MLText -tag "Title" -text "$($attr.title)" -indent $inner + $attrTitle = if ($attr.title) { "$($attr.title)" } elseif ($attr.main -ne $true) { Title-FromName -name $attrName } else { '' } + if ($attrTitle) { + Emit-MLText -tag "Title" -text "$attrTitle" -indent $inner } # Type @@ -2542,8 +2569,9 @@ function Emit-Commands { X "$indent`t" $inner = "$indent`t`t" - if ($cmd.title) { - Emit-MLText -tag "Title" -text "$($cmd.title)" -indent $inner + $cmdTitle = if ($cmd.title) { "$($cmd.title)" } else { Title-FromName -name "$($cmd.name)" } + if ($cmdTitle) { + Emit-MLText -tag "Title" -text "$cmdTitle" -indent $inner } if ($cmd.action) { diff --git a/.claude/skills/form-compile/scripts/form-compile.py b/.claude/skills/form-compile/scripts/form-compile.py index f6d1f965..6682f143 100644 --- a/.claude/skills/form-compile/scripts/form-compile.py +++ b/.claude/skills/form-compile/scripts/form-compile.py @@ -1,5 +1,5 @@ #!/usr/bin/env python3 -# form-compile v1.12 — Compile 1C managed form from JSON or object metadata +# form-compile v1.13 — Compile 1C managed form from JSON or object metadata # Source: https://github.com/Nikolay-Shirokov/cc-1c-skills import argparse import copy @@ -1414,9 +1414,27 @@ def emit_common_flags(lines, el, indent): lines.append(f"{indent}true") -def emit_title(lines, el, name, indent): - if el.get('title'): - emit_mltext(lines, indent, 'Title', str(el['title'])) +def title_from_name(name): + """СуммаДокумента → 'Сумма документа'. НДСВключен → 'НДС включен'.""" + if not name: + return '' + s = re.sub(r'([А-ЯA-Z])([А-ЯA-Z][а-яa-z])', r'\1 \2', name) + s = re.sub(r'([а-яa-z0-9])([А-ЯA-Z])', r'\1 \2', s) + parts = s.split(' ') + if not parts: + return s + out = [parts[0]] + for p in parts[1:]: + out.append(p if (len(p) > 1 and p.isupper()) else p.lower()) + return ' '.join(out) + + +def emit_title(lines, el, name, indent, auto=False): + title = el.get('title') + if not title and auto and name: + title = title_from_name(name) + if title: + emit_mltext(lines, indent, 'Title', str(title)) # --- Type emitter --- @@ -1712,7 +1730,7 @@ def emit_input(lines, el, name, eid, indent): if el.get('path'): lines.append(f'{inner}{el["path"]}') - emit_title(lines, el, name, inner) + emit_title(lines, el, name, inner, auto=not el.get('path')) emit_common_flags(lines, el, inner) if el.get('titleLocation'): @@ -1768,7 +1786,7 @@ def emit_check(lines, el, name, eid, indent): if el.get('path'): lines.append(f'{inner}{el["path"]}') - emit_title(lines, el, name, inner) + emit_title(lines, el, name, inner, auto=not el.get('path')) emit_common_flags(lines, el, inner) tl = el.get('titleLocation') or 'Right' @@ -1787,12 +1805,13 @@ def emit_label(lines, el, name, eid, indent): lines.append(f'{indent}') inner = f'{indent}\t' - if el.get('title'): + label_title = el.get('title') or title_from_name(name) + if label_title: formatted = 'true' if el.get('hyperlink') is True else 'false' lines.append(f'{inner}') lines.append(f'{inner}\t<v8:item>') lines.append(f'{inner}\t\t<v8:lang>ru</v8:lang>') - lines.append(f'{inner}\t\t<v8:content>{esc_xml(str(el["title"]))}</v8:content>') + lines.append(f'{inner}\t\t<v8:content>{esc_xml(str(label_title))}</v8:content>') lines.append(f'{inner}\t</v8:item>') lines.append(f'{inner}') @@ -1825,7 +1844,7 @@ def emit_label_field(lines, el, name, eid, indent): if el.get('path'): lines.append(f'{inner}{el["path"]}') - emit_title(lines, el, name, inner) + emit_title(lines, el, name, inner, auto=not el.get('path')) emit_common_flags(lines, el, inner) if el.get('hyperlink') is True: @@ -1847,7 +1866,7 @@ def emit_table(lines, el, name, eid, indent): if el.get('path'): lines.append(f'{inner}{el["path"]}') - emit_title(lines, el, name, inner) + emit_title(lines, el, name, inner, auto=not el.get('path')) emit_common_flags(lines, el, inner) if el.get('representation'): @@ -1935,7 +1954,7 @@ def emit_page(lines, el, name, eid, indent): lines.append(f'{indent}') inner = f'{indent}\t' - emit_title(lines, el, name, inner) + emit_title(lines, el, name, inner, auto=True) emit_common_flags(lines, el, inner) if el.get('group'): @@ -1983,7 +2002,7 @@ def emit_button(lines, el, name, eid, indent): else: lines.append(f'{inner}Form.StandardCommand.{sc}') - emit_title(lines, el, name, inner) + emit_title(lines, el, name, inner, auto=not (el.get('command') or el.get('stdCommand'))) emit_common_flags(lines, el, inner) if el.get('defaultButton') is True: @@ -2071,7 +2090,7 @@ def emit_calendar(lines, el, name, eid, indent): if el.get('path'): lines.append(f'{inner}{el["path"]}') - emit_title(lines, el, name, inner) + emit_title(lines, el, name, inner, auto=not el.get('path')) emit_common_flags(lines, el, inner) # Companions @@ -2106,7 +2125,7 @@ def emit_popup(lines, el, name, eid, indent): lines.append(f'{indent}') inner = f'{indent}\t' - emit_title(lines, el, name, inner) + emit_title(lines, el, name, inner, auto=True) emit_common_flags(lines, el, inner) if el.get('picture'): @@ -2142,8 +2161,11 @@ def emit_attributes(lines, attrs, indent): lines.append(f'{indent}\t') inner = f'{indent}\t\t' - if attr.get('title'): - emit_mltext(lines, inner, 'Title', str(attr['title'])) + attr_title = attr.get('title') + if not attr_title and attr.get('main') is not True: + attr_title = title_from_name(attr_name) + if attr_title: + emit_mltext(lines, inner, 'Title', str(attr_title)) # Type if attr.get('type'): @@ -2223,8 +2245,9 @@ def emit_commands(lines, cmds, indent): lines.append(f'{indent}\t') inner = f'{indent}\t\t' - if cmd.get('title'): - emit_mltext(lines, inner, 'Title', str(cmd['title'])) + cmd_title = cmd.get('title') or title_from_name(str(cmd['name'])) + if cmd_title: + emit_mltext(lines, inner, 'Title', str(cmd_title)) if cmd.get('action'): lines.append(f'{inner}{cmd["action"]}') diff --git a/tests/skills/cases/form-compile/snapshots/attributes-types/DataProcessors/Типы/Forms/Форма/Ext/Form.xml b/tests/skills/cases/form-compile/snapshots/attributes-types/DataProcessors/Типы/Forms/Форма/Ext/Form.xml index ffa777f6..2916c692 100644 --- a/tests/skills/cases/form-compile/snapshots/attributes-types/DataProcessors/Типы/Forms/Форма/Ext/Form.xml +++ b/tests/skills/cases/form-compile/snapshots/attributes-types/DataProcessors/Типы/Forms/Форма/Ext/Form.xml @@ -38,6 +38,12 @@ true + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Строка</v8:content> + </v8:item> + xs:string @@ -47,6 +53,12 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Число</v8:content> + </v8:item> + xs:decimal @@ -57,6 +69,12 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Дата</v8:content> + </v8:item> + xs:dateTime @@ -65,6 +83,12 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Булево</v8:content> + </v8:item> + xs:boolean diff --git a/tests/skills/cases/form-compile/snapshots/auto-cmd-bar/Catalogs/Бригады/Forms/ФормаСписка/Ext/Form.xml b/tests/skills/cases/form-compile/snapshots/auto-cmd-bar/Catalogs/Бригады/Forms/ФормаСписка/Ext/Form.xml index 7691c445..ba549f33 100644 --- a/tests/skills/cases/form-compile/snapshots/auto-cmd-bar/Catalogs/Бригады/Forms/ФормаСписка/Ext/Form.xml +++ b/tests/skills/cases/form-compile/snapshots/auto-cmd-bar/Catalogs/Бригады/Forms/ФормаСписка/Ext/Form.xml @@ -51,6 +51,12 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Изменить выделенные</v8:content> + </v8:item> + ИзменитьВыделенные diff --git a/tests/skills/cases/form-compile/snapshots/commands/DataProcessors/Команды/Forms/Форма/Ext/Form.xml b/tests/skills/cases/form-compile/snapshots/commands/DataProcessors/Команды/Forms/Форма/Ext/Form.xml index 5db50871..85aec738 100644 --- a/tests/skills/cases/form-compile/snapshots/commands/DataProcessors/Команды/Forms/Форма/Ext/Form.xml +++ b/tests/skills/cases/form-compile/snapshots/commands/DataProcessors/Команды/Forms/Форма/Ext/Form.xml @@ -41,6 +41,12 @@ true + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Результат</v8:content> + </v8:item> + xs:string @@ -52,6 +58,12 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Выполнить</v8:content> + </v8:item> + ВыполнитьОбработка Ctrl+Enter diff --git a/tests/skills/cases/form-compile/snapshots/events/DataProcessors/События/Forms/Форма/Ext/Form.xml b/tests/skills/cases/form-compile/snapshots/events/DataProcessors/События/Forms/Форма/Ext/Form.xml index 820f90ab..4621a24e 100644 --- a/tests/skills/cases/form-compile/snapshots/events/DataProcessors/События/Forms/Форма/Ext/Form.xml +++ b/tests/skills/cases/form-compile/snapshots/events/DataProcessors/События/Forms/Форма/Ext/Form.xml @@ -50,6 +50,12 @@ true + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Организация</v8:content> + </v8:item> + xs:string @@ -59,6 +65,12 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Период</v8:content> + </v8:item> + xs:dateTime diff --git a/tests/skills/cases/form-compile/snapshots/file-dialog/DataProcessors/ЗагрузкаИзФайла/Forms/Форма/Ext/Form.xml b/tests/skills/cases/form-compile/snapshots/file-dialog/DataProcessors/ЗагрузкаИзФайла/Forms/Форма/Ext/Form.xml index dbc07f33..8a97cfdd 100644 --- a/tests/skills/cases/form-compile/snapshots/file-dialog/DataProcessors/ЗагрузкаИзФайла/Forms/Форма/Ext/Form.xml +++ b/tests/skills/cases/form-compile/snapshots/file-dialog/DataProcessors/ЗагрузкаИзФайла/Forms/Форма/Ext/Form.xml @@ -82,6 +82,12 @@ true + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Имя файла</v8:content> + </v8:item> + xs:string @@ -91,11 +97,23 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Первая строка заголовок</v8:content> + </v8:item> + xs:boolean + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Результат</v8:content> + </v8:item> + xs:string @@ -107,6 +125,12 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Загрузить</v8:content> + </v8:item> + ЗагрузитьОбработка Ctrl+Enter diff --git a/tests/skills/cases/form-compile/snapshots/groups/DataProcessors/СГруппами/Forms/Форма/Ext/Form.xml b/tests/skills/cases/form-compile/snapshots/groups/DataProcessors/СГруппами/Forms/Форма/Ext/Form.xml index ea8801a9..6215e9b1 100644 --- a/tests/skills/cases/form-compile/snapshots/groups/DataProcessors/СГруппами/Forms/Форма/Ext/Form.xml +++ b/tests/skills/cases/form-compile/snapshots/groups/DataProcessors/СГруппами/Forms/Форма/Ext/Form.xml @@ -74,6 +74,12 @@ true + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Поле1</v8:content> + </v8:item> + xs:string @@ -83,6 +89,12 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Поле2</v8:content> + </v8:item> + xs:decimal @@ -93,6 +105,12 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Поле3</v8:content> + </v8:item> + xs:dateTime diff --git a/tests/skills/cases/form-compile/snapshots/input-fields/DataProcessors/ПоляВвода/Forms/Форма/Ext/Form.xml b/tests/skills/cases/form-compile/snapshots/input-fields/DataProcessors/ПоляВвода/Forms/Форма/Ext/Form.xml index ce898f1c..fd2ea9fe 100644 --- a/tests/skills/cases/form-compile/snapshots/input-fields/DataProcessors/ПоляВвода/Forms/Форма/Ext/Form.xml +++ b/tests/skills/cases/form-compile/snapshots/input-fields/DataProcessors/ПоляВвода/Forms/Форма/Ext/Form.xml @@ -95,6 +95,12 @@ true + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Обычное поле</v8:content> + </v8:item> + xs:string @@ -104,6 +110,12 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Многострочное поле</v8:content> + </v8:item> + xs:string @@ -113,6 +125,12 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Поле пароля</v8:content> + </v8:item> + xs:string @@ -122,6 +140,12 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Поле с кнопками</v8:content> + </v8:item> + xs:string @@ -131,6 +155,12 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Поле подсказка</v8:content> + </v8:item> + xs:string @@ -140,6 +170,12 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Флаг</v8:content> + </v8:item> + xs:boolean diff --git a/tests/skills/cases/form-compile/snapshots/pages/DataProcessors/Мастер/Forms/Форма/Ext/Form.xml b/tests/skills/cases/form-compile/snapshots/pages/DataProcessors/Мастер/Forms/Форма/Ext/Form.xml index 7e55dee6..c5094674 100644 --- a/tests/skills/cases/form-compile/snapshots/pages/DataProcessors/Мастер/Forms/Форма/Ext/Form.xml +++ b/tests/skills/cases/form-compile/snapshots/pages/DataProcessors/Мастер/Forms/Форма/Ext/Form.xml @@ -83,6 +83,12 @@ true + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Параметр1</v8:content> + </v8:item> + xs:string @@ -92,6 +98,12 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Итог</v8:content> + </v8:item> + xs:string @@ -103,9 +115,21 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Назад</v8:content> + </v8:item> + НазадОбработка + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Далее</v8:content> + </v8:item> + ДалееОбработка diff --git a/tests/skills/cases/form-compile/snapshots/synonyms/DataProcessors/Тест/Forms/Форма/Ext/Form.xml b/tests/skills/cases/form-compile/snapshots/synonyms/DataProcessors/Тест/Forms/Форма/Ext/Form.xml index 8e01c701..3d2e6f3b 100644 --- a/tests/skills/cases/form-compile/snapshots/synonyms/DataProcessors/Тест/Forms/Форма/Ext/Form.xml +++ b/tests/skills/cases/form-compile/snapshots/synonyms/DataProcessors/Тест/Forms/Форма/Ext/Form.xml @@ -38,6 +38,12 @@ true + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Поле</v8:content> + </v8:item> + xs:string @@ -49,9 +55,21 @@ + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Кн1</v8:content> + </v8:item> + Кн1 + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Кн2</v8:content> + </v8:item> + Кн2 diff --git a/tests/skills/cases/form-compile/snapshots/table/DataProcessors/Таблица/Forms/Форма/Ext/Form.xml b/tests/skills/cases/form-compile/snapshots/table/DataProcessors/Таблица/Forms/Форма/Ext/Form.xml index 54a0b7a5..e6882c9d 100644 --- a/tests/skills/cases/form-compile/snapshots/table/DataProcessors/Таблица/Forms/Форма/Ext/Form.xml +++ b/tests/skills/cases/form-compile/snapshots/table/DataProcessors/Таблица/Forms/Форма/Ext/Form.xml @@ -44,6 +44,12 @@ true + + <v8:item> + <v8:lang>ru</v8:lang> + <v8:content>Данные</v8:content> + </v8:item> + v8:ValueTable