@rt-tools/ui-kit-v2 0.29.1 → 0.30.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/fesm2022/rt-tools-ui-kit-v2-autocomplete.mjs +23 -29
- package/fesm2022/rt-tools-ui-kit-v2-autocomplete.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-calendar.mjs +2 -2
- package/fesm2022/rt-tools-ui-kit-v2-calendar.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-core.mjs +223 -3
- package/fesm2022/rt-tools-ui-kit-v2-core.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-data-list.mjs +2 -2
- package/fesm2022/rt-tools-ui-kit-v2-data-list.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-draggable-tree.mjs +1 -2
- package/fesm2022/rt-tools-ui-kit-v2-draggable-tree.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-dynamic-list.mjs +2 -2
- package/fesm2022/rt-tools-ui-kit-v2-dynamic-list.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-dynamic-selector.mjs +277 -904
- package/fesm2022/rt-tools-ui-kit-v2-dynamic-selector.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-filter-control.mjs +2 -2
- package/fesm2022/rt-tools-ui-kit-v2-filter-control.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-hybrid-tree.mjs +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-hybrid-tree.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-multiselect.mjs +35 -48
- package/fesm2022/rt-tools-ui-kit-v2-multiselect.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-page-header.mjs +2 -2
- package/fesm2022/rt-tools-ui-kit-v2-pdf-viewer.mjs +2 -2
- package/fesm2022/rt-tools-ui-kit-v2-pdf-viewer.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-rich-editor.mjs +4 -4
- package/fesm2022/rt-tools-ui-kit-v2-rich-editor.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-select.mjs +37 -181
- package/fesm2022/rt-tools-ui-kit-v2-select.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-side-menu.mjs +5 -36
- package/fesm2022/rt-tools-ui-kit-v2-side-menu.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-tag.mjs +2 -3
- package/fesm2022/rt-tools-ui-kit-v2-tag.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-toolbar.mjs +2 -2
- package/fesm2022/rt-tools-ui-kit-v2-toolbar.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-tree-selector.mjs +8 -13
- package/fesm2022/rt-tools-ui-kit-v2-tree-selector.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-tree.mjs +12 -7
- package/fesm2022/rt-tools-ui-kit-v2-tree.mjs.map +1 -1
- package/fesm2022/rt-tools-ui-kit-v2-workspace.mjs +2 -2
- package/fesm2022/rt-tools-ui-kit-v2-workspace.mjs.map +1 -1
- package/package.json +1 -1
- package/src/lib/components/dynamic-selector/stories/component/test-dynamic-selector-popup-frame.component.scss +6 -0
- package/src/lib/components/page-header/rt-page-header.component.scss +4 -2
- package/src/lib/components/tree/CONTEXT.md +1 -1
- package/src/rich-editor/lib/components/ai-chat/CONTEXT.md +1 -1
- package/src/styles/_breakpoints.scss +37 -4
- package/src/styles/_index.scss +0 -4
- package/styles/tokens.css +0 -8
- package/types/rt-tools-ui-kit-v2-autocomplete.d.ts +4 -3
- package/types/rt-tools-ui-kit-v2-core.d.ts +155 -1
- package/types/rt-tools-ui-kit-v2-dynamic-selector.d.ts +51 -269
- package/types/rt-tools-ui-kit-v2-multiselect.d.ts +4 -3
- package/types/rt-tools-ui-kit-v2-select.d.ts +12 -74
- package/types/rt-tools-ui-kit-v2-side-menu.d.ts +5 -20
- package/types/rt-tools-ui-kit-v2-tag.d.ts +2 -3
- package/types/rt-tools-ui-kit-v2-tree-selector.d.ts +0 -2
- package/types/rt-tools-ui-kit-v2-tree.d.ts +7 -9
- package/src/styles/_place.scss +0 -7
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"rt-tools-ui-kit-v2-tree.mjs","names":[],"sources":["../../../projects/ui-kit-v2/src/lib/components/tree/rt-tree.directives.ts","../../../projects/ui-kit-v2/src/lib/components/tree/rt-tree.logic.ts","../../../projects/ui-kit-v2/src/lib/components/tree/rt-tree.component.ts","../../../projects/ui-kit-v2/src/lib/components/tree/rt-tree.component.html"],"sourcesContent":["import { inject, Directive, TemplateRef } from '@angular/core';\n\nimport { IRtTree } from './rt-tree.model';\n\n/**\n * Разметка приложения в конце каждой строки `rt-tree`. Узел строки приходит в контексте как\n * `$implicit`: дерево не заводит вход под каждый такой элемент.\n */\n@Directive({ selector: 'ng-template[rtTreeNodeEnd]' })\nexport class RtTreeNodeEndDirective<TValue> {\n public readonly templateRef: TemplateRef<IRtTree.NodeContext<TValue>> = inject<TemplateRef<IRtTree.NodeContext<TValue>>>(TemplateRef);\n}\n\n/**\n * Разметка приложения под подписью строки, в одной линии с метками узла. Узел строки приходит в\n * контексте как `$implicit`.\n */\n@Directive({ selector: 'ng-template[rtTreeNodeMeta]' })\nexport class RtTreeNodeMetaDirective<TValue> {\n public readonly templateRef: TemplateRef<IRtTree.NodeContext<TValue>> = inject<TemplateRef<IRtTree.NodeContext<TValue>>>(TemplateRef);\n}\n","import { rtTreeBranchState, rtTreeLeaves } from '@rt-tools/ui-kit-v2/select';\nimport { splitTitleByWords } from '@rt-tools/ui-kit-v2/side-menu';\nimport { IRtSideMenu } from '@rt-tools/ui-kit-v2/side-menu';\nimport { IRtTree } from './rt-tree.model';\n\n/**\n * Расчёт выбора `rt-tree` — чистые функции над неизменяемыми узлами.\n *\n * Строки, листья и отметки ветвей считает модуль дерева выбора из списка: здесь только то, чего у\n * выбора из списка нет — режим отметок, выключенный каскад и «выбрать всё». Узлы не меняются\n * никогда: каждая функция отвечает новым массивом выбора.\n */\n\ntype TNode<TValue> = IRtTree.Node<TValue>;\n\nfunction isBranch<TValue>(node: TNode<TValue>): boolean {\n return (node.children ?? []).length > 0;\n}\n\nfunction without<TValue>(value: ReadonlyArray<TValue>, drop: ReadonlyArray<TValue>): ReadonlyArray<TValue> {\n return value.filter((item: TValue): boolean => !drop.includes(item));\n}\n\nfunction withAll<TValue>(value: ReadonlyArray<TValue>, add: ReadonlyArray<TValue>): ReadonlyArray<TValue> {\n return [...value, ...add.filter((item: TValue): boolean => !value.includes(item))];\n}\n\n/**\n * Отметка строки. В каскаде ветка отмечена по своим листьям; без каскада и у листа — по тому,\n * лежит ли в выборе сам узел.\n */\nexport function rtTreeMark<TValue>(node: TNode<TValue>, value: ReadonlyArray<TValue>, cascade: boolean): IRtTree.Mark {\n if (cascade && isBranch(node)) {\n return rtTreeBranchState(node, value);\n }\n return value.includes(node.value) ? 'all' : 'none';\n}\n\n/**\n * Выбор после клика по узлу. Выключенный узел выбор не меняет. Одиночный режим держит один узел и\n * не снимает его повторным кликом. В каскаде ветка добавляет свои включённые листья или снимает\n * их, когда выбраны все; выключенные листья остаются как были.\n */\nexport function rtTreeChoose<TValue>(\n node: TNode<TValue>,\n value: ReadonlyArray<TValue>,\n mode: IRtTree.Mode,\n cascade: boolean\n): ReadonlyArray<TValue> {\n if (node.disabled || mode === 'none') {\n return value;\n }\n if (mode === 'single') {\n return [node.value];\n }\n if (cascade && isBranch(node)) {\n const leaves: ReadonlyArray<TValue> = rtTreeLeaves(node);\n return rtTreeBranchState(node, value) === 'all' ? without(value, leaves) : withAll(value, leaves);\n }\n return value.includes(node.value) ? without(value, [node.value]) : withAll(value, [node.value]);\n}\n\n/**\n * Включённые листья видимых строк. Раскрытая ветка отдаёт листья своими строками ниже, свёрнутая —\n * всеми листьями под собой: они видимы через неё.\n */\nexport function rtTreeVisibleLeaves<TValue>(rows: ReadonlyArray<IRtTree.Row<TValue>>): ReadonlyArray<TValue> {\n return rows.flatMap((row: IRtTree.Row<TValue>): ReadonlyArray<TValue> => (row.branch && row.open ? [] : rtTreeLeaves(row.option)));\n}\n\n/** Отметка «выбрать всё» по включённым листьям видимых строк. */\nexport function rtTreeSelectAllMark<TValue>(rows: ReadonlyArray<IRtTree.Row<TValue>>, value: ReadonlyArray<TValue>): IRtTree.Mark {\n const leaves: ReadonlyArray<TValue> = rtTreeVisibleLeaves(rows);\n const count: number = leaves.filter((leaf: TValue): boolean => value.includes(leaf)).length;\n if (count === 0) {\n return 'none';\n }\n return count === leaves.length ? 'all' : 'some';\n}\n\n/**\n * Выбор после клика по «выбрать всё»: включённые листья видимых строк добавляются, а когда выбраны\n * все — снимаются. Выключенные листья `rtTreeLeaves` не отдаёт, поэтому их состояние не меняется.\n */\nexport function rtTreeSelectAll<TValue>(rows: ReadonlyArray<IRtTree.Row<TValue>>, value: ReadonlyArray<TValue>): ReadonlyArray<TValue> {\n const leaves: ReadonlyArray<TValue> = rtTreeVisibleLeaves(rows);\n return rtTreeSelectAllMark(rows, value) === 'all' ? without(value, leaves) : withAll(value, leaves);\n}\n\n/**\n * Подпись, описание и метки узла, разрезанные по каждому слову запроса тем же резом, что у поиска\n * меню: приложение делит поиск по пробелам, и найденное слово видно там, где оно нашлось.\n */\nexport function rtTreeLabelParts<TValue>(node: TNode<TValue>, term: string): IRtTree.LabelParts {\n return {\n label: splitTitleByWords(node.label, term),\n description: splitTitleByWords(node.description ?? '', term),\n badges: (node.badges ?? []).map((badge: IRtTree.Badge): ReadonlyArray<IRtSideMenu.TitlePart> =>\n splitTitleByWords(badge.text, term)\n ),\n };\n}\n\n/** Значения узла и всех его потомков. */\nfunction covered<TValue>(node: TNode<TValue>): ReadonlyArray<TValue> {\n return [node.value, ...(node.children ?? []).flatMap((child: TNode<TValue>): ReadonlyArray<TValue> => covered(child))];\n}\n\n/** Значения выключенных узлов дерева: их состояние не меняет ни одно действие. */\nfunction disabledValues<TValue>(nodes: ReadonlyArray<TNode<TValue>>): ReadonlyArray<TValue> {\n return nodes.flatMap((node: TNode<TValue>): ReadonlyArray<TValue> => [\n ...(node.disabled ? [node.value] : []),\n ...disabledValues(node.children ?? []),\n ]);\n}\n\n/** Что остаётся от выбора перед кликом без Ctrl и Cmd: то, что покрывает сам узел, и выключенные узлы. */\nexport function rtTreeAloneBase<TValue>(\n nodes: ReadonlyArray<TNode<TValue>>,\n node: TNode<TValue>,\n value: ReadonlyArray<TValue>\n): ReadonlyArray<TValue> {\n const keep: ReadonlyArray<TValue> = [...covered(node), ...disabledValues(nodes)];\n return value.filter((item: TValue): boolean => keep.includes(item));\n}\n\n/**\n * Выбор после клика без Ctrl и Cmd в режиме, где клик выбирает один узел. Из выбора остаётся только\n * то, что покрывает сам узел, и выключенные узлы; дальше клик работает как обычно — поэтому\n * повторный клик по единственному выбранному снимает его.\n */\nexport function rtTreeChooseAlone<TValue>(\n nodes: ReadonlyArray<TNode<TValue>>,\n node: TNode<TValue>,\n value: ReadonlyArray<TValue>,\n cascade: boolean\n): ReadonlyArray<TValue> {\n if (node.disabled) {\n return value;\n }\n return rtTreeChoose(node, rtTreeAloneBase(nodes, node, value), 'multiple', cascade);\n}\n","import { NgTemplateOutlet } from '@angular/common';\nimport {\n booleanAttribute,\n computed,\n contentChild,\n inject,\n input,\n model,\n output,\n signal,\n ChangeDetectionStrategy,\n Component,\n InputSignal,\n InputSignalWithTransform,\n ModelSignal,\n OutputEmitterRef,\n Signal,\n TemplateRef,\n ViewEncapsulation,\n WritableSignal,\n} from '@angular/core';\n\nimport { FormsModule } from '@angular/forms';\n\nimport { BlockDirective, ElemDirective, ModDirective } from '@rt-tools/core';\n\nimport { IRtIcon, RT_KIT_LABELS, TRtKitLabelMap } from '@rt-tools/ui-kit-v2/core';\nimport { RtCheckboxComponent } from '@rt-tools/ui-kit-v2/checkbox';\nimport { RtIconComponent } from '@rt-tools/ui-kit-v2/icon';\nimport { RtRadioButtonComponent } from '@rt-tools/ui-kit-v2/radio-button';\nimport { RtTagComponent } from '@rt-tools/ui-kit-v2/tag';\nimport { RtTooltipDirective } from '@rt-tools/ui-kit-v2/tooltip';\nimport { rtTreeOpenFor, rtTreeRows, rtTreeSideKey, rtTreeToggle } from '@rt-tools/ui-kit-v2/select';\nimport { IRtSelect } from '@rt-tools/ui-kit-v2/select';\nimport { RtTreeNodeEndDirective, RtTreeNodeMetaDirective } from './rt-tree.directives';\nimport { rtTreeChoose, rtTreeChooseAlone, rtTreeLabelParts, rtTreeMark, rtTreeSelectAll, rtTreeSelectAllMark } from './rt-tree.logic';\nimport { IRtTree } from './rt-tree.model';\n\nconst BEM_BLOCK: string = 'rt-tree';\n\n/** Видимая строка с тем, что разметке нужно о ней знать. */\ninterface IRtTreeView<TValue> {\n readonly row: IRtTree.Row<TValue>;\n readonly mark: IRtTree.Mark;\n /** Рисуется ли у строки флажок или радио: у групп без отметок его нет. */\n readonly marked: boolean;\n /** Радио вместо флажка. */\n readonly radio: boolean;\n /** Строка выключена: свой `disabled` у узла или выключено всё дерево. */\n readonly disabled: boolean;\n /** Число выбранного под группой в конце строки; `null` — числа нет. */\n readonly count: number | null;\n readonly parts: IRtTree.LabelParts;\n readonly highlighted: boolean;\n}\n\n/**\n * Дерево выбора, стоящее на странице само по себе.\n *\n * Строки, листья, отметки ветвей, отбор по слову и боковые стрелки считает модуль дерева выбора\n * из списка — тот же, что у `rt-select` и `rt-multiselect`. Выбор живёт в `value`; узлы не\n * меняются. Раскрытые ветки и подсвеченная строка — состояние самого дерева.\n *\n * Клавиатура идёт через `handleKeydown`: его зовёт и само дерево с фокуса на себе, и приложение\n * со своего поля поиска. Ответ — взята ли клавиша: чужую дерево не трогает.\n */\n@Component({\n selector: 'rt-tree',\n templateUrl: './rt-tree.component.html',\n styleUrl: './rt-tree.component.scss',\n changeDetection: ChangeDetectionStrategy.OnPush,\n encapsulation: ViewEncapsulation.None,\n imports: [\n NgTemplateOutlet,\n FormsModule,\n RtCheckboxComponent,\n RtIconComponent,\n RtRadioButtonComponent,\n RtTagComponent,\n RtTooltipDirective,\n BlockDirective,\n ElemDirective,\n ModDirective,\n ],\n host: {\n class: BEM_BLOCK,\n role: 'tree',\n '[attr.tabindex]': 'disabled() ? -1 : 0',\n '[attr.aria-disabled]': 'disabled() || null',\n '[attr.aria-label]': 'ariaLabel()',\n '[attr.aria-multiselectable]': \"mode() === 'multiple'\",\n '(keydown)': 'handleKeydown($event)',\n },\n})\nexport class RtTreeComponent<TValue> {\n readonly #open: WritableSignal<ReadonlySet<TValue> | null> = signal<ReadonlySet<TValue> | null>(null);\n readonly #highlighted: WritableSignal<TValue | null> = signal<TValue | null>(null);\n\n protected readonly t: Signal<TRtKitLabelMap> = inject(RT_KIT_LABELS);\n\n protected readonly nodeEnd: Signal<RtTreeNodeEndDirective<TValue> | undefined> = contentChild(RtTreeNodeEndDirective);\n\n protected readonly nodeMeta: Signal<RtTreeNodeMetaDirective<TValue> | undefined> = contentChild(RtTreeNodeMetaDirective);\n\n /** Разметка в конце строки: вход раньше директивы — обёртка вроде селектора отдаёт её входом. */\n protected readonly endTemplate: Signal<TemplateRef<IRtTree.NodeContext<TValue>> | null> = computed(\n (): TemplateRef<IRtTree.NodeContext<TValue>> | null => this.nodeEndTemplate() ?? this.nodeEnd()?.templateRef ?? null\n );\n\n /** Разметка под подписью: вход раньше директивы. */\n protected readonly metaTemplate: Signal<TemplateRef<IRtTree.NodeContext<TValue>> | null> = computed(\n (): TemplateRef<IRtTree.NodeContext<TValue>> | null => this.nodeMetaTemplate() ?? this.nodeMeta()?.templateRef ?? null\n );\n\n /** Раскрытые ветки: до первого действия человека — ветки над выбранным. */\n protected readonly openBranches: Signal<ReadonlySet<TValue>> = computed(\n (): ReadonlySet<TValue> => this.#open() ?? rtTreeOpenFor(this.nodes(), this.value())\n );\n\n protected readonly rows: Signal<ReadonlyArray<IRtTree.Row<TValue>>> = computed((): ReadonlyArray<IRtTree.Row<TValue>> =>\n rtTreeRows(this.nodes(), this.openBranches(), this.filter() ? this.searchTerm() : '')\n );\n\n protected readonly views: Signal<ReadonlyArray<IRtTreeView<TValue>>> = computed((): ReadonlyArray<IRtTreeView<TValue>> => {\n const value: ReadonlyArray<TValue> = this.value();\n const cascade: boolean = this.cascade();\n const term: string = this.searchTerm();\n const highlighted: TValue | null = this.#highlighted();\n const mode: IRtTree.Mode = this.mode();\n const branchMarks: boolean = this.branchMarks();\n const treeDisabled: boolean = this.disabled();\n return this.rows().map((row: IRtTree.Row<TValue>): IRtTreeView<TValue> => {\n const marked: boolean = mode !== 'none' && (branchMarks || !row.branch);\n const state: IRtTree.RowState = this.rowState(row, value, cascade);\n return {\n row,\n marked,\n mark: state.mark,\n radio: state.radio,\n disabled: treeDisabled || !!row.option.disabled,\n count: marked ? null : state.count,\n parts: rtTreeLabelParts(row.option, term),\n highlighted: row.option.value === highlighted,\n };\n });\n });\n\n protected readonly selectAllMark: Signal<IRtTree.Mark> = computed((): IRtTree.Mark => this.selectAllMarkOf(this.rows(), this.value()));\n\n protected readonly isSelectAllShown: Signal<boolean> = computed(\n (): boolean => this.showSelectAll() && this.cascade() && this.mode() === 'multiple' && this.rows().length > 0\n );\n\n /** Отметка «выбрать всё» встаёт над отметкой первой строки; у строки без отметки — над стрелкой. */\n protected readonly isSelectAllUnderMark: Signal<boolean> = computed((): boolean => this.views()[0]?.marked ?? false);\n\n /** Первая строка — лист: там, где у листа нет места под стрелку, его нет и у «выбрать всё». */\n protected readonly isSelectAllOverLeaf: Signal<boolean> = computed((): boolean => this.views()[0]?.row.branch === false);\n\n protected readonly emptyText: Signal<string> = computed((): string =>\n this.nodes().length > 0 ? this.t().uiNothingFound : this.t().uiNoOptions\n );\n\n public readonly nodes: InputSignal<ReadonlyArray<IRtTree.Node<TValue>>> = input.required<ReadonlyArray<IRtTree.Node<TValue>>>();\n public readonly value: ModelSignal<ReadonlyArray<TValue>> = model<ReadonlyArray<TValue>>([]);\n public readonly mode: InputSignal<IRtTree.Mode> = input<IRtTree.Mode>('multiple');\n public readonly cascade: InputSignalWithTransform<boolean, unknown> = input<boolean, unknown>(true, { transform: booleanAttribute });\n public readonly searchTerm: InputSignal<string> = input<string>('');\n public readonly showSelectAll: InputSignalWithTransform<boolean, unknown> = input<boolean, unknown>(false, {\n transform: booleanAttribute,\n });\n public readonly ariaLabel: InputSignal<string | null> = input<string | null>(null);\n\n /** Отметки у групп. Без них клик, пробел и Enter по группе раскрывают и сворачивают её. */\n public readonly branchMarks: InputSignalWithTransform<boolean, unknown> = input<boolean, unknown>(true, {\n transform: booleanAttribute,\n });\n\n /** Клик без Ctrl и Cmd выбирает узел один; с Ctrl или Cmd добавляет к выбору. Только для флажков. */\n public readonly exclusive: InputSignalWithTransform<boolean, unknown> = input<boolean, unknown>(false, {\n transform: booleanAttribute,\n });\n\n /** Скрывает ли слово поиска строки. Без отбора строки отбирает приложение, а слово только отмечено. */\n public readonly filter: InputSignalWithTransform<boolean, unknown> = input<boolean, unknown>(true, {\n transform: booleanAttribute,\n });\n\n /** Выключенное дерево не меняет выбор ни кликом, ни клавишей, ни «выбрать всё»; ветки раскрываются стрелкой. */\n /** Значок кита над подписью пустого дерева. Без него пустое дерево — одна подпись. */\n public readonly emptyIcon: InputSignal<IRtIcon.Name | null> = input<IRtIcon.Name | null>(null);\n\n /**\n * Разметка в конце каждой строки, отданная входом. Нужна компоненту, который оборачивает дерево и\n * не может положить в него директиву `rtTreeNodeEnd`; вход сильнее директивы.\n */\n public readonly nodeEndTemplate: InputSignal<TemplateRef<IRtTree.NodeContext<TValue>> | null> = input<TemplateRef<\n IRtTree.NodeContext<TValue>\n > | null>(null);\n\n /** Разметка под подписью каждой строки, отданная входом; вход сильнее директивы `rtTreeNodeMeta`. */\n public readonly nodeMetaTemplate: InputSignal<TemplateRef<IRtTree.NodeContext<TValue>> | null> = input<TemplateRef<\n IRtTree.NodeContext<TValue>\n > | null>(null);\n\n public readonly disabled: InputSignalWithTransform<boolean, unknown> = input<boolean, unknown>(false, {\n transform: booleanAttribute,\n });\n\n public readonly picked: OutputEmitterRef<IRtTree.Node<TValue>> = output<IRtTree.Node<TValue>>();\n\n /**\n * Клавиша для дерева. Отвечает, взята ли она: не взятая идёт дальше нетронутой, поэтому\n * приложение может отдавать сюда каждую клавишу своего поля поиска.\n */\n public handleKeydown(event: KeyboardEvent): boolean {\n if (this.disabled()) {\n return false;\n }\n const taken: boolean = this.#takeKey(event.key, event.ctrlKey || event.metaKey);\n if (taken) {\n event.preventDefault();\n event.stopPropagation();\n }\n return taken;\n }\n\n public expandAll(): void {\n const all: Set<TValue> = new Set<TValue>();\n this.#collectBranches(this.nodes(), all);\n this.#open.set(all);\n }\n\n public collapseAll(): void {\n this.#open.set(new Set<TValue>());\n }\n\n public clearHighlight(): void {\n this.#highlighted.set(null);\n }\n\n protected onRowClick(row: IRtTree.Row<TValue>, event: MouseEvent): void {\n if (this.disabled()) {\n return;\n }\n this.#highlighted.set(row.option.value);\n if (row.option.disabled) {\n return;\n }\n if (this.#opensOnly(row)) {\n this.#toggleOrPick(row);\n return;\n }\n this.#choose(this.nextChoice(row.option, event.ctrlKey || event.metaKey));\n }\n\n protected onToggleClick(event: Event, value: TValue): void {\n event.stopPropagation();\n this.#toggle(value);\n }\n\n protected onSelectAll(): void {\n if (this.disabled()) {\n return;\n }\n this.#choose(this.selectAllChoice(this.rows(), this.value()));\n }\n\n /**\n * Отметка строки, её вид и число выбранного под ней. Дерево числа не рисует; наследник со своими\n * правилами выбора считает всё это по ним.\n */\n protected rowState(row: IRtTree.Row<TValue>, value: ReadonlyArray<TValue>, cascade: boolean): IRtTree.RowState {\n return { mark: rtTreeMark(row.option, value, cascade), radio: this.mode() === 'single', count: null };\n }\n\n protected selectAllMarkOf(rows: ReadonlyArray<IRtTree.Row<TValue>>, value: ReadonlyArray<TValue>): IRtTree.Mark {\n return rtTreeSelectAllMark(rows, value);\n }\n\n protected selectAllChoice(rows: ReadonlyArray<IRtTree.Row<TValue>>, value: ReadonlyArray<TValue>): ReadonlyArray<TValue> {\n return rtTreeSelectAll(rows, value);\n }\n\n /** Выбор после действия над узлом: в исключающем режиме без Ctrl и Cmd узел остаётся один. */\n protected nextChoice(node: IRtTree.Node<TValue>, additive: boolean): ReadonlyArray<TValue> {\n if (this.exclusive() && this.mode() === 'multiple' && !additive) {\n return rtTreeChooseAlone(this.nodes(), node, this.value(), this.cascade());\n }\n return rtTreeChoose(node, this.value(), this.mode(), this.cascade());\n }\n\n /** Строка, клик по которой ничего не отмечает: режим без отметок или группа без флажка. */\n #opensOnly(row: IRtTree.Row<TValue>): boolean {\n return this.mode() === 'none' || (row.branch && !this.branchMarks());\n }\n\n #toggleOrPick(row: IRtTree.Row<TValue>): void {\n if (row.branch) {\n this.#toggle(row.option.value);\n } else {\n this.picked.emit(row.option);\n }\n }\n\n #collectBranches(list: ReadonlyArray<IRtTree.Node<TValue>>, into: Set<TValue>): void {\n list.forEach((node: IRtTree.Node<TValue>): void => {\n if ((node.children ?? []).length > 0) {\n into.add(node.value);\n this.#collectBranches(node.children ?? [], into);\n }\n });\n }\n\n /**\n * Меняет выбор, не трогая раскрытие. Пока ветки никто не раскрывал руками, раскрытие считается из\n * выбора, и без этой фиксации отметка ветки сворачивала или раскрывала её саму.\n */\n #choose(next: ReadonlyArray<TValue>): void {\n this.#open.set(this.openBranches());\n this.value.set(next);\n }\n\n #toggle(value: TValue): void {\n this.#open.set(rtTreeToggle(this.openBranches(), value));\n }\n\n #highlightedIndex(): number {\n const highlighted: TValue | null = this.#highlighted();\n return this.rows().findIndex((row: IRtTree.Row<TValue>): boolean => row.option.value === highlighted);\n }\n\n #takeKey(key: string, additive: boolean): boolean {\n const rows: ReadonlyArray<IRtTree.Row<TValue>> = this.rows();\n const index: number = this.#highlightedIndex();\n if (key === 'ArrowDown' || key === 'ArrowUp') {\n return this.#move(rows, index, key === 'ArrowDown' ? 1 : -1);\n }\n if (index < 0) {\n return false;\n }\n if (key === 'ArrowRight' || key === 'ArrowLeft') {\n this.#side(rows, index, key);\n return true;\n }\n if (key === ' ') {\n this.#space(rows[index], additive);\n return true;\n }\n if (key === 'Enter') {\n this.#enter(rows[index], additive);\n return true;\n }\n return false;\n }\n\n #move(rows: ReadonlyArray<IRtTree.Row<TValue>>, index: number, step: number): boolean {\n if (rows.length === 0) {\n return false;\n }\n const next: number = index < 0 ? 0 : Math.min(rows.length - 1, Math.max(0, index + step));\n this.#highlighted.set(rows[next].option.value);\n return true;\n }\n\n #side(rows: ReadonlyArray<IRtTree.Row<TValue>>, index: number, key: string): void {\n const answer: IRtSelect.SideKeyAnswer<TValue> = rtTreeSideKey(rows, index, key);\n if (answer.toggle !== null) {\n this.#toggle(answer.toggle);\n }\n this.#highlighted.set(rows[answer.index].option.value);\n }\n\n #space(row: IRtTree.Row<TValue>, additive: boolean): void {\n if (this.#opensOnly(row) && row.branch) {\n this.#toggle(row.option.value);\n return;\n }\n if (!row.option.disabled && this.mode() !== 'none') {\n this.#choose(this.nextChoice(row.option, additive));\n }\n }\n\n #enter(row: IRtTree.Row<TValue>, additive: boolean): void {\n if (this.#opensOnly(row) && row.branch) {\n this.#toggle(row.option.value);\n return;\n }\n if (row.option.disabled) {\n return;\n }\n if (this.mode() !== 'none') {\n this.#choose(this.nextChoice(row.option, additive));\n }\n this.picked.emit(row.option);\n }\n}\n","<ng-container rtBlock=\"rt-tree\">\n <!--\n Строки выбираются мышью через (click); клавиатура — на самом дереве (handleKeydown), строки\n по отдельности фокус не берут: подсветка — третье состояние рядом с фокусом и выбором.\n -->\n <!-- eslint-disable @angular-eslint/template/click-events-have-key-events, @angular-eslint/template/interactive-supports-focus -->\n @if (isSelectAllShown()) {\n <div\n rtElem=\"select-all\"\n qa-dataid=\"tree-select-all\"\n role=\"presentation\"\n [rtMod]=\"{ disabled: disabled(), 'over-leaf': isSelectAllOverLeaf() }\"\n (click)=\"onSelectAll()\">\n @if (isSelectAllUnderMark()) {\n <span rtElem=\"toggle-space\"></span>\n }\n <rt-checkbox\n rtElem=\"check\"\n inert\n [disabled]=\"disabled()\"\n [indeterminate]=\"selectAllMark() === 'some'\"\n [ngModel]=\"selectAllMark() === 'all'\"\n [ngModelOptions]=\"{ standalone: true }\" />\n <span rtElem=\"label\">{{ t().uiSelectAll }}</span>\n </div>\n }\n\n @for (view of views(); track view.row.option.value) {\n <div\n rtElem=\"row\"\n qa-dataid=\"tree-row\"\n role=\"treeitem\"\n [attr.data-value]=\"view.row.option.value\"\n [attr.aria-level]=\"view.row.level + 1\"\n [attr.aria-expanded]=\"view.row.branch ? view.row.open : null\"\n [attr.aria-selected]=\"view.marked ? view.mark === 'all' : null\"\n [attr.aria-disabled]=\"view.disabled\"\n [style.--rt-tree-level]=\"view.row.level\"\n [rtMod]=\"{ highlighted: view.highlighted, disabled: view.disabled, chosen: view.mark === 'all' }\"\n (click)=\"onRowClick(view.row, $event)\">\n @if (view.row.branch) {\n <button\n rtElem=\"toggle\"\n qa-dataid=\"tree-row-toggle\"\n type=\"button\"\n tabindex=\"-1\"\n [attr.aria-label]=\"view.row.open ? t().uiCollapse : t().uiExpand\"\n (click)=\"onToggleClick($event, view.row.option.value)\">\n <rt-icon size=\"sm\" color=\"muted\" [name]=\"view.row.open ? 'chevron-down' : 'chevron-right'\" />\n </button>\n } @else {\n <span rtElem=\"toggle-space\"></span>\n }\n\n @if (view.marked && !view.radio) {\n <rt-checkbox\n rtElem=\"check\"\n qa-dataid=\"tree-row-checkbox\"\n inert\n [disabled]=\"view.disabled\"\n [indeterminate]=\"view.mark === 'some'\"\n [ngModel]=\"view.mark === 'all'\"\n [ngModelOptions]=\"{ standalone: true }\" />\n } @else if (view.marked) {\n <rt-radio-button\n rtElem=\"check\"\n qa-dataid=\"tree-row-radio\"\n inert\n [value]=\"view.row.option.value\"\n [checked]=\"view.mark === 'all'\"\n [disabled]=\"view.disabled\" />\n }\n\n <span rtElem=\"text\">\n <span rtElem=\"label\" qa-dataid=\"tree-row-label\" rtTooltipWhenTruncated [rtTooltip]=\"view.row.option.label\">\n @for (part of view.parts.label; track $index) {\n <span rtElem=\"part\" [rtMod]=\"{ match: part.matched }\">{{ part.text }}</span>\n }\n </span>\n @if (view.parts.description.length > 0) {\n <span\n rtElem=\"description\"\n qa-dataid=\"tree-row-description\"\n rtTooltipWhenTruncated\n [rtTooltip]=\"view.row.option.description\">\n @for (part of view.parts.description; track $index) {\n <span rtElem=\"part\" [rtMod]=\"{ match: part.matched }\">{{ part.text }}</span>\n }\n </span>\n }\n @if (view.row.option.badges?.length || metaTemplate()) {\n <span rtElem=\"meta\" qa-dataid=\"tree-row-meta\">\n @for (badge of view.row.option.badges; track $index) {\n <rt-tag size=\"sm\" [value]=\"badge.text\" [severity]=\"badge.severity ?? 'neutral'\" [highlight]=\"searchTerm()\" />\n }\n @if (metaTemplate(); as meta) {\n <ng-container [ngTemplateOutlet]=\"meta\" [ngTemplateOutletContext]=\"{ $implicit: view.row.option }\" />\n }\n </span>\n }\n </span>\n\n @if (view.count) {\n <span rtElem=\"count\" qa-dataid=\"tree-row-count\">{{ view.count }}</span>\n }\n\n @if (endTemplate(); as end) {\n <span rtElem=\"end\" qa-dataid=\"tree-row-end\">\n <ng-container [ngTemplateOutlet]=\"end\" [ngTemplateOutletContext]=\"{ $implicit: view.row.option }\" />\n </span>\n }\n </div>\n } @empty {\n <div rtElem=\"empty\" qa-dataid=\"tree-empty\" [rtMod]=\"{ 'with-icon': !!emptyIcon() }\">\n @if (emptyIcon(); as icon) {\n <rt-icon rtElem=\"empty-icon\" qa-dataid=\"tree-empty-icon\" size=\"lg\" [name]=\"icon\" />\n }\n {{ emptyText() }}\n </div>\n }\n</ng-container>\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"rt-tools-ui-kit-v2-tree.mjs","names":[],"sources":["../../../projects/ui-kit-v2/src/lib/components/tree/rt-tree.directives.ts","../../../projects/ui-kit-v2/src/lib/components/tree/rt-tree.logic.ts","../../../projects/ui-kit-v2/src/lib/components/tree/rt-tree.component.ts","../../../projects/ui-kit-v2/src/lib/components/tree/rt-tree.component.html"],"sourcesContent":["import { inject, Directive, TemplateRef } from '@angular/core';\n\nimport { IRtTree } from './rt-tree.model';\n\n/**\n * Разметка приложения в конце каждой строки `rt-tree`. Узел строки приходит в контексте как\n * `$implicit`: дерево не заводит вход под каждый такой элемент.\n */\n@Directive({ selector: 'ng-template[rtTreeNodeEnd]' })\nexport class RtTreeNodeEndDirective<TValue> {\n public readonly templateRef: TemplateRef<IRtTree.NodeContext<TValue>> = inject<TemplateRef<IRtTree.NodeContext<TValue>>>(TemplateRef);\n}\n\n/**\n * Разметка приложения под подписью строки, в одной линии с метками узла. Узел строки приходит в\n * контексте как `$implicit`.\n */\n@Directive({ selector: 'ng-template[rtTreeNodeMeta]' })\nexport class RtTreeNodeMetaDirective<TValue> {\n public readonly templateRef: TemplateRef<IRtTree.NodeContext<TValue>> = inject<TemplateRef<IRtTree.NodeContext<TValue>>>(TemplateRef);\n}\n","import { IRtMatchPart, rtMatchParts, rtTreeBranchState, rtTreeLeaves } from '@rt-tools/ui-kit-v2/core';\nimport { IRtTree } from './rt-tree.model';\n\n/**\n * Расчёт выбора `rt-tree` — чистые функции над неизменяемыми узлами.\n *\n * Строки, листья и отметки ветвей считает модуль дерева выбора из списка: здесь только то, чего у\n * выбора из списка нет — режим отметок, выключенный каскад и «выбрать всё». Узлы не меняются\n * никогда: каждая функция отвечает новым массивом выбора.\n */\n\ntype TNode<TValue> = IRtTree.Node<TValue>;\n\nfunction isBranch<TValue>(node: TNode<TValue>): boolean {\n return (node.children ?? []).length > 0;\n}\n\nfunction without<TValue>(value: ReadonlyArray<TValue>, drop: ReadonlyArray<TValue>): ReadonlyArray<TValue> {\n return value.filter((item: TValue): boolean => !drop.includes(item));\n}\n\nfunction withAll<TValue>(value: ReadonlyArray<TValue>, add: ReadonlyArray<TValue>): ReadonlyArray<TValue> {\n return [...value, ...add.filter((item: TValue): boolean => !value.includes(item))];\n}\n\n/**\n * Отметка строки. В каскаде ветка отмечена по своим листьям; без каскада и у листа — по тому,\n * лежит ли в выборе сам узел.\n */\nexport function rtTreeMark<TValue>(node: TNode<TValue>, value: ReadonlyArray<TValue>, cascade: boolean): IRtTree.Mark {\n if (cascade && isBranch(node)) {\n return rtTreeBranchState(node, value);\n }\n return value.includes(node.value) ? 'all' : 'none';\n}\n\n/**\n * Выбор после клика по узлу. Выключенный узел выбор не меняет. Одиночный режим держит один узел и\n * не снимает его повторным кликом. В каскаде ветка добавляет свои включённые листья или снимает\n * их, когда выбраны все; выключенные листья остаются как были.\n */\nexport function rtTreeChoose<TValue>(\n node: TNode<TValue>,\n value: ReadonlyArray<TValue>,\n mode: IRtTree.Mode,\n cascade: boolean\n): ReadonlyArray<TValue> {\n if (node.disabled || mode === 'none') {\n return value;\n }\n if (mode === 'single') {\n return [node.value];\n }\n if (cascade && isBranch(node)) {\n const leaves: ReadonlyArray<TValue> = rtTreeLeaves(node);\n return rtTreeBranchState(node, value) === 'all' ? without(value, leaves) : withAll(value, leaves);\n }\n return value.includes(node.value) ? without(value, [node.value]) : withAll(value, [node.value]);\n}\n\n/**\n * Включённые листья видимых строк. Раскрытая ветка отдаёт листья своими строками ниже, свёрнутая —\n * всеми листьями под собой: они видимы через неё.\n */\nexport function rtTreeVisibleLeaves<TValue>(rows: ReadonlyArray<IRtTree.Row<TValue>>): ReadonlyArray<TValue> {\n return rows.flatMap((row: IRtTree.Row<TValue>): ReadonlyArray<TValue> => (row.branch && row.open ? [] : rtTreeLeaves(row.option)));\n}\n\n/** Отметка «выбрать всё» по включённым листьям видимых строк. */\nexport function rtTreeSelectAllMark<TValue>(rows: ReadonlyArray<IRtTree.Row<TValue>>, value: ReadonlyArray<TValue>): IRtTree.Mark {\n const leaves: ReadonlyArray<TValue> = rtTreeVisibleLeaves(rows);\n const count: number = leaves.filter((leaf: TValue): boolean => value.includes(leaf)).length;\n if (count === 0) {\n return 'none';\n }\n return count === leaves.length ? 'all' : 'some';\n}\n\n/**\n * Выбор после клика по «выбрать всё»: включённые листья видимых строк добавляются, а когда выбраны\n * все — снимаются. Выключенные листья `rtTreeLeaves` не отдаёт, поэтому их состояние не меняется.\n */\nexport function rtTreeSelectAll<TValue>(rows: ReadonlyArray<IRtTree.Row<TValue>>, value: ReadonlyArray<TValue>): ReadonlyArray<TValue> {\n const leaves: ReadonlyArray<TValue> = rtTreeVisibleLeaves(rows);\n return rtTreeSelectAllMark(rows, value) === 'all' ? without(value, leaves) : withAll(value, leaves);\n}\n\n/**\n * Подпись, описание и метки узла, разрезанные по каждому слову запроса тем же резом, что у поиска\n * меню: приложение делит поиск по пробелам, и найденное слово видно там, где оно нашлось.\n */\nexport function rtTreeLabelParts<TValue>(node: TNode<TValue>, term: string): IRtTree.LabelParts {\n return {\n label: rtMatchParts(node.label, term),\n description: rtMatchParts(node.description ?? '', term),\n badges: (node.badges ?? []).map((badge: IRtTree.Badge): ReadonlyArray<IRtMatchPart> => rtMatchParts(badge.text, term)),\n };\n}\n\n/** Значения узла и всех его потомков. */\nfunction covered<TValue>(node: TNode<TValue>): ReadonlyArray<TValue> {\n return [node.value, ...(node.children ?? []).flatMap((child: TNode<TValue>): ReadonlyArray<TValue> => covered(child))];\n}\n\n/** Значения выключенных узлов дерева: их состояние не меняет ни одно действие. */\nfunction disabledValues<TValue>(nodes: ReadonlyArray<TNode<TValue>>): ReadonlyArray<TValue> {\n return nodes.flatMap((node: TNode<TValue>): ReadonlyArray<TValue> => [\n ...(node.disabled ? [node.value] : []),\n ...disabledValues(node.children ?? []),\n ]);\n}\n\n/** Что остаётся от выбора перед кликом без Ctrl и Cmd: то, что покрывает сам узел, и выключенные узлы. */\nexport function rtTreeAloneBase<TValue>(\n nodes: ReadonlyArray<TNode<TValue>>,\n node: TNode<TValue>,\n value: ReadonlyArray<TValue>\n): ReadonlyArray<TValue> {\n const keep: ReadonlyArray<TValue> = [...covered(node), ...disabledValues(nodes)];\n return value.filter((item: TValue): boolean => keep.includes(item));\n}\n\n/**\n * Выбор после клика без Ctrl и Cmd в режиме, где клик выбирает один узел. Из выбора остаётся только\n * то, что покрывает сам узел, и выключенные узлы; дальше клик работает как обычно — поэтому\n * повторный клик по единственному выбранному снимает его.\n */\nexport function rtTreeChooseAlone<TValue>(\n nodes: ReadonlyArray<TNode<TValue>>,\n node: TNode<TValue>,\n value: ReadonlyArray<TValue>,\n cascade: boolean\n): ReadonlyArray<TValue> {\n if (node.disabled) {\n return value;\n }\n return rtTreeChoose(node, rtTreeAloneBase(nodes, node, value), 'multiple', cascade);\n}\n","import { NgTemplateOutlet } from '@angular/common';\nimport {\n booleanAttribute,\n computed,\n contentChild,\n inject,\n input,\n model,\n output,\n signal,\n ChangeDetectionStrategy,\n Component,\n InputSignal,\n InputSignalWithTransform,\n ModelSignal,\n OutputEmitterRef,\n Signal,\n TemplateRef,\n ViewEncapsulation,\n WritableSignal,\n} from '@angular/core';\n\nimport { FormsModule } from '@angular/forms';\n\nimport { BlockDirective, ElemDirective, ModDirective } from '@rt-tools/core';\n\nimport { IRtIcon, RT_KIT_LABELS, TRtKitLabelMap } from '@rt-tools/ui-kit-v2/core';\nimport { RtCheckboxComponent } from '@rt-tools/ui-kit-v2/checkbox';\nimport { RtIconComponent } from '@rt-tools/ui-kit-v2/icon';\nimport { RtRadioButtonComponent } from '@rt-tools/ui-kit-v2/radio-button';\nimport { RtTagComponent } from '@rt-tools/ui-kit-v2/tag';\nimport { RtTooltipDirective } from '@rt-tools/ui-kit-v2/tooltip';\nimport { IRtOptionTree, rtTreeOpenFor, rtTreeRows, rtTreeSideKey, rtTreeToggle } from '@rt-tools/ui-kit-v2/core';\nimport { RtTreeNodeEndDirective, RtTreeNodeMetaDirective } from './rt-tree.directives';\nimport { rtTreeChoose, rtTreeChooseAlone, rtTreeLabelParts, rtTreeMark, rtTreeSelectAll, rtTreeSelectAllMark } from './rt-tree.logic';\nimport { IRtTree } from './rt-tree.model';\n\nconst BEM_BLOCK: string = 'rt-tree';\n\n/** Видимая строка с тем, что разметке нужно о ней знать. */\ninterface IRtTreeView<TValue> {\n readonly row: IRtTree.Row<TValue>;\n readonly mark: IRtTree.Mark;\n /** Рисуется ли у строки флажок или радио: у групп без отметок его нет. */\n readonly marked: boolean;\n /** Радио вместо флажка. */\n readonly radio: boolean;\n /** Строка выключена: свой `disabled` у узла или выключено всё дерево. */\n readonly disabled: boolean;\n /** Число выбранного под группой в конце строки; `null` — числа нет. */\n readonly count: number | null;\n readonly parts: IRtTree.LabelParts;\n readonly highlighted: boolean;\n}\n\n/**\n * Дерево выбора, стоящее на странице само по себе.\n *\n * Строки, листья, отметки ветвей, отбор по слову и боковые стрелки считает модуль дерева выбора\n * из списка — тот же, что у `rt-select` и `rt-multiselect`. Выбор живёт в `value`; узлы не\n * меняются. Раскрытые ветки и подсвеченная строка — состояние самого дерева.\n *\n * Клавиатура идёт через `handleKeydown`: его зовёт и само дерево с фокуса на себе, и приложение\n * со своего поля поиска. Ответ — взята ли клавиша: чужую дерево не трогает.\n */\n@Component({\n selector: 'rt-tree',\n templateUrl: './rt-tree.component.html',\n styleUrl: './rt-tree.component.scss',\n changeDetection: ChangeDetectionStrategy.OnPush,\n encapsulation: ViewEncapsulation.None,\n imports: [\n NgTemplateOutlet,\n FormsModule,\n RtCheckboxComponent,\n RtIconComponent,\n RtRadioButtonComponent,\n RtTagComponent,\n RtTooltipDirective,\n BlockDirective,\n ElemDirective,\n ModDirective,\n ],\n host: {\n class: BEM_BLOCK,\n role: 'tree',\n '[attr.tabindex]': 'disabled() ? -1 : 0',\n '[attr.aria-disabled]': 'disabled() || null',\n '[attr.aria-label]': 'ariaLabel()',\n '[attr.aria-multiselectable]': \"mode() === 'multiple'\",\n '(keydown)': 'handleKeydown($event)',\n },\n})\nexport class RtTreeComponent<TValue> {\n readonly #open: WritableSignal<ReadonlySet<TValue> | null> = signal<ReadonlySet<TValue> | null>(null);\n readonly #highlighted: WritableSignal<TValue | null> = signal<TValue | null>(null);\n\n protected readonly t: Signal<TRtKitLabelMap> = inject(RT_KIT_LABELS);\n\n protected readonly nodeEnd: Signal<RtTreeNodeEndDirective<TValue> | undefined> = contentChild(RtTreeNodeEndDirective);\n\n protected readonly nodeMeta: Signal<RtTreeNodeMetaDirective<TValue> | undefined> = contentChild(RtTreeNodeMetaDirective);\n\n /** Разметка в конце строки: вход раньше директивы — обёртка вроде селектора отдаёт её входом. */\n protected readonly endTemplate: Signal<TemplateRef<IRtTree.NodeContext<TValue>> | null> = computed(\n (): TemplateRef<IRtTree.NodeContext<TValue>> | null => this.nodeEndTemplate() ?? this.nodeEnd()?.templateRef ?? null\n );\n\n /** Разметка под подписью: вход раньше директивы. */\n protected readonly metaTemplate: Signal<TemplateRef<IRtTree.NodeContext<TValue>> | null> = computed(\n (): TemplateRef<IRtTree.NodeContext<TValue>> | null => this.nodeMetaTemplate() ?? this.nodeMeta()?.templateRef ?? null\n );\n\n /** Раскрытые ветки: до первого действия человека — ветки над выбранным. */\n protected readonly openBranches: Signal<ReadonlySet<TValue>> = computed(\n (): ReadonlySet<TValue> => this.#open() ?? rtTreeOpenFor(this.nodes(), this.value())\n );\n\n protected readonly rows: Signal<ReadonlyArray<IRtTree.Row<TValue>>> = computed((): ReadonlyArray<IRtTree.Row<TValue>> =>\n rtTreeRows(this.nodes(), this.openBranches(), this.filter() ? this.searchTerm() : '')\n );\n\n protected readonly views: Signal<ReadonlyArray<IRtTreeView<TValue>>> = computed((): ReadonlyArray<IRtTreeView<TValue>> => {\n const value: ReadonlyArray<TValue> = this.value();\n const cascade: boolean = this.cascade();\n const term: string = this.searchTerm();\n const highlighted: TValue | null = this.#highlighted();\n const mode: IRtTree.Mode = this.mode();\n const branchMarks: boolean = this.branchMarks();\n const treeDisabled: boolean = this.disabled();\n return this.rows().map((row: IRtTree.Row<TValue>): IRtTreeView<TValue> => {\n const marked: boolean = mode !== 'none' && (branchMarks || !row.branch);\n const state: IRtTree.RowState = this.rowState(row, value, cascade);\n return {\n row,\n marked,\n mark: state.mark,\n radio: state.radio,\n disabled: treeDisabled || !!row.option.disabled,\n count: marked ? null : state.count,\n parts: rtTreeLabelParts(row.option, term),\n highlighted: row.option.value === highlighted,\n };\n });\n });\n\n protected readonly selectAllMark: Signal<IRtTree.Mark> = computed((): IRtTree.Mark => this.selectAllMarkOf(this.rows(), this.value()));\n\n protected readonly isSelectAllShown: Signal<boolean> = computed(\n (): boolean => this.showSelectAll() && this.cascade() && this.mode() === 'multiple' && this.rows().length > 0\n );\n\n /** Отметка «выбрать всё» встаёт над отметкой первой строки; у строки без отметки — над стрелкой. */\n protected readonly isSelectAllUnderMark: Signal<boolean> = computed((): boolean => this.views()[0]?.marked ?? false);\n\n /** Первая строка — лист: там, где у листа нет места под стрелку, его нет и у «выбрать всё». */\n protected readonly isSelectAllOverLeaf: Signal<boolean> = computed((): boolean => this.views()[0]?.row.branch === false);\n\n protected readonly emptyText: Signal<string> = computed((): string =>\n this.nodes().length > 0 ? this.t().uiNothingFound : this.t().uiNoOptions\n );\n\n public readonly nodes: InputSignal<ReadonlyArray<IRtTree.Node<TValue>>> = input.required<ReadonlyArray<IRtTree.Node<TValue>>>();\n public readonly value: ModelSignal<ReadonlyArray<TValue>> = model<ReadonlyArray<TValue>>([]);\n public readonly mode: InputSignal<IRtTree.Mode> = input<IRtTree.Mode>('multiple');\n public readonly cascade: InputSignalWithTransform<boolean, unknown> = input<boolean, unknown>(true, { transform: booleanAttribute });\n public readonly searchTerm: InputSignal<string> = input<string>('');\n public readonly showSelectAll: InputSignalWithTransform<boolean, unknown> = input<boolean, unknown>(false, {\n transform: booleanAttribute,\n });\n public readonly ariaLabel: InputSignal<string | null> = input<string | null>(null);\n\n /** Отметки у групп. Без них клик, пробел и Enter по группе раскрывают и сворачивают её. */\n public readonly branchMarks: InputSignalWithTransform<boolean, unknown> = input<boolean, unknown>(true, {\n transform: booleanAttribute,\n });\n\n /** Клик без Ctrl и Cmd выбирает узел один; с Ctrl или Cmd добавляет к выбору. Только для флажков. */\n public readonly exclusive: InputSignalWithTransform<boolean, unknown> = input<boolean, unknown>(false, {\n transform: booleanAttribute,\n });\n\n /** Скрывает ли слово поиска строки. Без отбора строки отбирает приложение, а слово только отмечено. */\n public readonly filter: InputSignalWithTransform<boolean, unknown> = input<boolean, unknown>(true, {\n transform: booleanAttribute,\n });\n\n /** Выключенное дерево не меняет выбор ни кликом, ни клавишей, ни «выбрать всё»; ветки раскрываются стрелкой. */\n /** Значок кита над подписью пустого дерева. Без него пустое дерево — одна подпись. */\n public readonly emptyIcon: InputSignal<IRtIcon.Name | null> = input<IRtIcon.Name | null>(null);\n\n /**\n * Разметка в конце каждой строки, отданная входом. Нужна компоненту, который оборачивает дерево и\n * не может положить в него директиву `rtTreeNodeEnd`; вход сильнее директивы.\n */\n public readonly nodeEndTemplate: InputSignal<TemplateRef<IRtTree.NodeContext<TValue>> | null> = input<TemplateRef<\n IRtTree.NodeContext<TValue>\n > | null>(null);\n\n /** Разметка под подписью каждой строки, отданная входом; вход сильнее директивы `rtTreeNodeMeta`. */\n public readonly nodeMetaTemplate: InputSignal<TemplateRef<IRtTree.NodeContext<TValue>> | null> = input<TemplateRef<\n IRtTree.NodeContext<TValue>\n > | null>(null);\n\n public readonly disabled: InputSignalWithTransform<boolean, unknown> = input<boolean, unknown>(false, {\n transform: booleanAttribute,\n });\n\n public readonly picked: OutputEmitterRef<IRtTree.Node<TValue>> = output<IRtTree.Node<TValue>>();\n\n /**\n * Клавиша для дерева. Отвечает, взята ли она: не взятая идёт дальше нетронутой, поэтому\n * приложение может отдавать сюда каждую клавишу своего поля поиска.\n */\n public handleKeydown(event: KeyboardEvent): boolean {\n if (this.disabled()) {\n return false;\n }\n const taken: boolean = this.#takeKey(event.key, event.ctrlKey || event.metaKey);\n if (taken) {\n event.preventDefault();\n event.stopPropagation();\n }\n return taken;\n }\n\n public expandAll(): void {\n const all: Set<TValue> = new Set<TValue>();\n this.#collectBranches(this.nodes(), all);\n this.#open.set(all);\n }\n\n public collapseAll(): void {\n this.#open.set(new Set<TValue>());\n }\n\n public clearHighlight(): void {\n this.#highlighted.set(null);\n }\n\n protected onRowClick(row: IRtTree.Row<TValue>, event: MouseEvent): void {\n if (this.disabled()) {\n return;\n }\n this.#highlighted.set(row.option.value);\n if (row.option.disabled) {\n return;\n }\n if (this.#opensOnly(row)) {\n this.#toggleOrPick(row);\n return;\n }\n this.#choose(this.nextChoice(row.option, event.ctrlKey || event.metaKey));\n }\n\n protected onToggleClick(event: Event, value: TValue): void {\n event.stopPropagation();\n this.#toggle(value);\n }\n\n protected onSelectAll(): void {\n if (this.disabled()) {\n return;\n }\n this.#choose(this.selectAllChoice(this.rows(), this.value()));\n }\n\n /**\n * Отметка строки, её вид и число выбранного под ней. Дерево числа не рисует; наследник со своими\n * правилами выбора считает всё это по ним.\n */\n protected rowState(row: IRtTree.Row<TValue>, value: ReadonlyArray<TValue>, cascade: boolean): IRtTree.RowState {\n return { mark: rtTreeMark(row.option, value, cascade), radio: this.mode() === 'single', count: null };\n }\n\n protected selectAllMarkOf(rows: ReadonlyArray<IRtTree.Row<TValue>>, value: ReadonlyArray<TValue>): IRtTree.Mark {\n return rtTreeSelectAllMark(rows, value);\n }\n\n protected selectAllChoice(rows: ReadonlyArray<IRtTree.Row<TValue>>, value: ReadonlyArray<TValue>): ReadonlyArray<TValue> {\n return rtTreeSelectAll(rows, value);\n }\n\n /** Выбор после действия над узлом: в исключающем режиме без Ctrl и Cmd узел остаётся один. */\n protected nextChoice(node: IRtTree.Node<TValue>, additive: boolean): ReadonlyArray<TValue> {\n if (this.exclusive() && this.mode() === 'multiple' && !additive) {\n return rtTreeChooseAlone(this.nodes(), node, this.value(), this.cascade());\n }\n return rtTreeChoose(node, this.value(), this.mode(), this.cascade());\n }\n\n /** Строка, клик по которой ничего не отмечает: режим без отметок или группа без флажка. */\n #opensOnly(row: IRtTree.Row<TValue>): boolean {\n return this.mode() === 'none' || (row.branch && !this.branchMarks());\n }\n\n #toggleOrPick(row: IRtTree.Row<TValue>): void {\n if (row.branch) {\n this.#toggle(row.option.value);\n } else {\n this.picked.emit(row.option);\n }\n }\n\n #collectBranches(list: ReadonlyArray<IRtTree.Node<TValue>>, into: Set<TValue>): void {\n list.forEach((node: IRtTree.Node<TValue>): void => {\n if ((node.children ?? []).length > 0) {\n into.add(node.value);\n this.#collectBranches(node.children ?? [], into);\n }\n });\n }\n\n /**\n * Меняет выбор, не трогая раскрытие. Пока ветки никто не раскрывал руками, раскрытие считается из\n * выбора, и без этой фиксации отметка ветки сворачивала или раскрывала её саму.\n */\n #choose(next: ReadonlyArray<TValue>): void {\n this.#open.set(this.openBranches());\n this.value.set(next);\n }\n\n #toggle(value: TValue): void {\n this.#open.set(rtTreeToggle(this.openBranches(), value));\n }\n\n #highlightedIndex(): number {\n const highlighted: TValue | null = this.#highlighted();\n return this.rows().findIndex((row: IRtTree.Row<TValue>): boolean => row.option.value === highlighted);\n }\n\n #takeKey(key: string, additive: boolean): boolean {\n const rows: ReadonlyArray<IRtTree.Row<TValue>> = this.rows();\n const index: number = this.#highlightedIndex();\n if (key === 'ArrowDown' || key === 'ArrowUp') {\n return this.#move(rows, index, key === 'ArrowDown' ? 1 : -1);\n }\n return index >= 0 && this.#takeRowKey(rows, index, key, additive);\n }\n\n /** Клавиши, которым нужна подсвеченная строка. */\n #takeRowKey(rows: ReadonlyArray<IRtTree.Row<TValue>>, index: number, key: string, additive: boolean): boolean {\n if (key === 'Home' || key === 'End') {\n return this.#edge(rows, key);\n }\n if (key === 'ArrowRight' || key === 'ArrowLeft') {\n this.#side(rows, index, key);\n return true;\n }\n if (key === ' ') {\n this.#space(rows[index], additive);\n return true;\n }\n if (key === 'Enter') {\n this.#enter(rows[index], additive);\n return true;\n }\n return false;\n }\n\n #move(rows: ReadonlyArray<IRtTree.Row<TValue>>, index: number, step: number): boolean {\n if (rows.length === 0) {\n return false;\n }\n const next: number = index < 0 ? 0 : Math.min(rows.length - 1, Math.max(0, index + step));\n this.#highlighted.set(rows[next].option.value);\n return true;\n }\n\n /** Home и End ведут подсветку к первой и последней строке; без подсветки они остаются у курсора поля. */\n #edge(rows: ReadonlyArray<IRtTree.Row<TValue>>, key: string): boolean {\n this.#highlighted.set(rows[key === 'Home' ? 0 : rows.length - 1].option.value);\n return true;\n }\n\n #side(rows: ReadonlyArray<IRtTree.Row<TValue>>, index: number, key: string): void {\n const answer: IRtOptionTree.SideKeyAnswer<TValue> = rtTreeSideKey(rows, index, key);\n if (answer.toggle !== null) {\n this.#toggle(answer.toggle);\n }\n this.#highlighted.set(rows[answer.index].option.value);\n }\n\n #space(row: IRtTree.Row<TValue>, additive: boolean): void {\n if (this.#opensOnly(row) && row.branch) {\n this.#toggle(row.option.value);\n return;\n }\n if (!row.option.disabled && this.mode() !== 'none') {\n this.#choose(this.nextChoice(row.option, additive));\n }\n }\n\n #enter(row: IRtTree.Row<TValue>, additive: boolean): void {\n if (this.#opensOnly(row) && row.branch) {\n this.#toggle(row.option.value);\n return;\n }\n if (row.option.disabled) {\n return;\n }\n if (this.mode() !== 'none') {\n this.#choose(this.nextChoice(row.option, additive));\n }\n this.picked.emit(row.option);\n }\n}\n","<ng-container rtBlock=\"rt-tree\">\n <!--\n Строки выбираются мышью через (click); клавиатура — на самом дереве (handleKeydown), строки\n по отдельности фокус не берут: подсветка — третье состояние рядом с фокусом и выбором.\n -->\n <!-- eslint-disable @angular-eslint/template/click-events-have-key-events, @angular-eslint/template/interactive-supports-focus -->\n @if (isSelectAllShown()) {\n <div\n rtElem=\"select-all\"\n qa-dataid=\"tree-select-all\"\n role=\"presentation\"\n [rtMod]=\"{ disabled: disabled(), 'over-leaf': isSelectAllOverLeaf() }\"\n (click)=\"onSelectAll()\">\n @if (isSelectAllUnderMark()) {\n <span rtElem=\"toggle-space\"></span>\n }\n <rt-checkbox\n rtElem=\"check\"\n inert\n [disabled]=\"disabled()\"\n [indeterminate]=\"selectAllMark() === 'some'\"\n [ngModel]=\"selectAllMark() === 'all'\"\n [ngModelOptions]=\"{ standalone: true }\" />\n <span rtElem=\"label\">{{ t().uiSelectAll }}</span>\n </div>\n }\n\n @for (view of views(); track view.row.option.value) {\n <div\n rtElem=\"row\"\n qa-dataid=\"tree-row\"\n role=\"treeitem\"\n [attr.data-value]=\"view.row.option.value\"\n [attr.aria-level]=\"view.row.level + 1\"\n [attr.aria-expanded]=\"view.row.branch ? view.row.open : null\"\n [attr.aria-selected]=\"view.marked ? view.mark === 'all' : null\"\n [attr.aria-disabled]=\"view.disabled\"\n [style.--rt-tree-level]=\"view.row.level\"\n [rtMod]=\"{ highlighted: view.highlighted, disabled: view.disabled, chosen: view.mark === 'all' }\"\n (click)=\"onRowClick(view.row, $event)\">\n @if (view.row.branch) {\n <button\n rtElem=\"toggle\"\n qa-dataid=\"tree-row-toggle\"\n type=\"button\"\n tabindex=\"-1\"\n [attr.aria-label]=\"view.row.open ? t().uiCollapse : t().uiExpand\"\n (click)=\"onToggleClick($event, view.row.option.value)\">\n <rt-icon size=\"sm\" color=\"muted\" [name]=\"view.row.open ? 'chevron-down' : 'chevron-right'\" />\n </button>\n } @else {\n <span rtElem=\"toggle-space\"></span>\n }\n\n @if (view.marked && !view.radio) {\n <rt-checkbox\n rtElem=\"check\"\n qa-dataid=\"tree-row-checkbox\"\n inert\n [disabled]=\"view.disabled\"\n [indeterminate]=\"view.mark === 'some'\"\n [ngModel]=\"view.mark === 'all'\"\n [ngModelOptions]=\"{ standalone: true }\" />\n } @else if (view.marked) {\n <rt-radio-button\n rtElem=\"check\"\n qa-dataid=\"tree-row-radio\"\n inert\n [value]=\"view.row.option.value\"\n [checked]=\"view.mark === 'all'\"\n [disabled]=\"view.disabled\" />\n }\n\n <span rtElem=\"text\">\n <span rtElem=\"label\" qa-dataid=\"tree-row-label\" rtTooltipWhenTruncated [rtTooltip]=\"view.row.option.label\">\n @for (part of view.parts.label; track $index) {\n <span rtElem=\"part\" [rtMod]=\"{ match: part.matched }\">{{ part.text }}</span>\n }\n </span>\n @if (view.parts.description.length > 0) {\n <span\n rtElem=\"description\"\n qa-dataid=\"tree-row-description\"\n rtTooltipWhenTruncated\n [rtTooltip]=\"view.row.option.description\">\n @for (part of view.parts.description; track $index) {\n <span rtElem=\"part\" [rtMod]=\"{ match: part.matched }\">{{ part.text }}</span>\n }\n </span>\n }\n @if (view.row.option.badges?.length || metaTemplate()) {\n <span rtElem=\"meta\" qa-dataid=\"tree-row-meta\">\n @for (badge of view.row.option.badges; track $index) {\n <rt-tag size=\"sm\" [value]=\"badge.text\" [severity]=\"badge.severity ?? 'neutral'\" [highlight]=\"searchTerm()\" />\n }\n @if (metaTemplate(); as meta) {\n <ng-container [ngTemplateOutlet]=\"meta\" [ngTemplateOutletContext]=\"{ $implicit: view.row.option }\" />\n }\n </span>\n }\n </span>\n\n @if (view.count) {\n <span rtElem=\"count\" qa-dataid=\"tree-row-count\">{{ view.count }}</span>\n }\n\n @if (endTemplate(); as end) {\n <span rtElem=\"end\" qa-dataid=\"tree-row-end\">\n <ng-container [ngTemplateOutlet]=\"end\" [ngTemplateOutletContext]=\"{ $implicit: view.row.option }\" />\n </span>\n }\n </div>\n } @empty {\n <div rtElem=\"empty\" qa-dataid=\"tree-empty\" [rtMod]=\"{ 'with-icon': !!emptyIcon() }\">\n @if (emptyIcon(); as icon) {\n <rt-icon rtElem=\"empty-icon\" qa-dataid=\"tree-empty-icon\" size=\"lg\" [name]=\"icon\" />\n }\n {{ emptyText() }}\n </div>\n }\n</ng-container>\n"],"mappings":"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"}
|
|
@@ -448,7 +448,7 @@ var RtWorkspaceComponent = class RtWorkspaceComponent {
|
|
|
448
448
|
],
|
|
449
449
|
ngImport: i0,
|
|
450
450
|
template: "<ng-container rtBlock=\"rt-workspace\">\n @if (listSlot()) {\n <section rtElem=\"list\" qa-dataid=\"workspace-list\">\n <ng-container [ngTemplateOutlet]=\"listSlot()?.templateRef ?? null\" [ngTemplateOutletContext]=\"slotContext\" />\n </section>\n\n <div\n rtElem=\"handle\"\n qa-dataid=\"workspace-handle-list\"\n role=\"separator\"\n aria-orientation=\"vertical\"\n tabindex=\"0\"\n [attr.aria-label]=\"t().uiResizeList\"\n [rtMod]=\"{ list: true }\"\n [attr.aria-valuenow]=\"listWidth()\"\n [attr.aria-valuemin]=\"listMinWidth()\"\n [attr.aria-valuemax]=\"listMaxWidth()\"\n (pointerdown)=\"onHandlePointerDown($event, 'list')\"\n (dblclick)=\"onHandleReset('list')\"\n (keydown)=\"onHandleKeydown($event, 'list')\"></div>\n }\n\n <section rtElem=\"center\" qa-dataid=\"workspace-center\">\n @if (hasActive()) {\n <div rtElem=\"mobile-toolbar\">\n <rt-icon-button\n qa-dataid=\"workspace-back\"\n icon=\"arrow-left\"\n variant=\"secondary\"\n [ariaLabel]=\"t().uiBackToList\"\n [tooltip]=\"t().uiToList\"\n (clicked)=\"onBackClicked()\" />\n <rt-icon-button\n qa-dataid=\"workspace-open-details\"\n icon=\"info-circle\"\n variant=\"secondary\"\n [ariaLabel]=\"t().uiShowDetails\"\n [tooltip]=\"t().uiDetails\"\n (clicked)=\"openAside()\" />\n </div>\n }\n <ng-container [ngTemplateOutlet]=\"centerSlot()?.templateRef ?? null\" [ngTemplateOutletContext]=\"slotContext\" />\n </section>\n\n @if (asideSlot()) {\n <div\n rtElem=\"handle\"\n qa-dataid=\"workspace-handle-aside\"\n role=\"separator\"\n aria-orientation=\"vertical\"\n tabindex=\"0\"\n [attr.aria-label]=\"t().uiResizeDetails\"\n [rtMod]=\"{ aside: true }\"\n [attr.aria-valuenow]=\"asideWidth()\"\n [attr.aria-valuemin]=\"asideMinWidth()\"\n [attr.aria-valuemax]=\"asideMaxWidth()\"\n (pointerdown)=\"onHandlePointerDown($event, 'aside')\"\n (dblclick)=\"onHandleReset('aside')\"\n (keydown)=\"onHandleKeydown($event, 'aside')\"></div>\n\n <section rtElem=\"aside\" qa-dataid=\"workspace-aside\" [rtMod]=\"{ open: asideOpen() }\">\n <ng-container [ngTemplateOutlet]=\"asideSlot()?.templateRef ?? null\" [ngTemplateOutletContext]=\"slotContext\" />\n </section>\n }\n</ng-container>\n",
|
|
451
|
-
styles: ["@layer rt-kit.components{.rt-workspace{--rt-workspace-border-width: var(--rt-border-width-thin);--rt-workspace-handle-line-width: var(--rt-border-width-medium);--rt-workspace-handle-transition-duration: var(--rt-duration-fast);--rt-workspace-panel-transition-duration: var(--rt-duration-base);--rt-workspace-aside-shadow: var(--rt-shadow-md);position:relative;display:flex;flex-direction:row;block-size:calc(100dvh - var(--rt-header-height, 0px));min-block-size:0}.rt-workspace__list{display:flex;flex:0 0 var(--rt-workspace-list-size, 320px);flex-direction:column;border-inline-end:var(--rt-workspace-border-width) solid var(--rt-color-border-strong);min-inline-size:0}.rt-workspace__center{display:flex;flex:1 1 auto;flex-direction:column;min-block-size:0;min-inline-size:0;padding-inline:var(--rt-space-4)}.rt-workspace__mobile-toolbar{display:none}.rt-workspace__aside{display:flex;flex:0 0 var(--rt-workspace-aside-size, 360px);flex-direction:column;border-inline-start:var(--rt-workspace-border-width) solid var(--rt-color-border-strong);min-inline-size:0}.rt-workspace__handle{position:relative;z-index:1;flex:0 0 auto;background:transparent;cursor:col-resize;inline-size:var(--rt-space-2);margin-inline:calc(-1 * var(--rt-space-1));touch-action:none}.rt-workspace__handle:before{position:absolute;background:transparent;content:\"\";inline-size:var(--rt-workspace-handle-line-width);inset-block:0;inset-inline-start:50%;transform:translate(-50%);transition:background var(--rt-workspace-handle-transition-duration) ease}.rt-workspace__handle:hover:before,.rt-workspace__handle:focus-visible:before{background:var(--rt-color-border-strong)}.rt-workspace__handle:focus-visible{outline:none}.rt-workspace__handle:focus-visible:before{background:var(--rt-color-border-focus)}@container rt-place (width <= 1080px){.rt-workspace__desktop-only{display:none}}@container rt-place (width <= 1080px){.rt-workspace__mobile-toolbar{display:flex;justify-content:space-between;padding:var(--rt-space-2) var(--rt-space-4) 0}.rt-workspace__handle{display:none}.rt-workspace__aside{position:absolute;z-index:2;flex-basis:360px;background:var(--rt-color-bg-surface);box-shadow:var(--rt-workspace-aside-shadow);inset-block:0;inset-inline-end:0;max-inline-size:90%;transform:translate(100%);transition:transform var(--rt-workspace-panel-transition-duration) ease}.rt-workspace__aside--open{transform:translate(0)}}@container rt-place (width <= 768px){.rt-workspace__list{flex-basis:100%}}@container rt-place (width > 1080px){.rt-workspace__aside{overflow:hidden;transition:flex-basis var(--rt-workspace-panel-transition-duration) ease,border-inline-start-width var(--rt-workspace-panel-transition-duration) ease,opacity var(--rt-workspace-panel-transition-duration) ease;will-change:flex-basis}}@container rt-place (width <= 768px){.rt-workspace--has-active .rt-workspace__list{display:none}.rt-workspace--has-active .rt-workspace__center{flex-basis:100%}}@container rt-place (width > 1080px){.rt-workspace--aside-collapsed .rt-workspace__aside{flex-basis:0;border-inline-start-width:0;min-inline-size:0;opacity:0;pointer-events:none;transition:flex-basis var(--rt-workspace-panel-transition-duration) ease,border-inline-start-width var(--rt-workspace-panel-transition-duration) ease,opacity var(--rt-workspace-panel-transition-duration) ease,visibility 0s linear var(--rt-workspace-panel-transition-duration);visibility:hidden}.rt-workspace--aside-collapsed .rt-workspace__handle--aside{display:none}}.rt-workspace--resizing{cursor:col-resize;-webkit-user-select:none;user-select:none}.rt-workspace--resizing .rt-workspace__list,.rt-workspace--resizing .rt-workspace__aside{transition:none}@media(prefers-reduced-motion:reduce){.rt-workspace__aside{transition:none}}}\n"],
|
|
451
|
+
styles: ["@layer rt-kit.components{.rt-workspace{--rt-workspace-border-width: var(--rt-border-width-thin);--rt-workspace-handle-line-width: var(--rt-border-width-medium);--rt-workspace-handle-transition-duration: var(--rt-duration-fast);--rt-workspace-panel-transition-duration: var(--rt-duration-base);--rt-workspace-aside-shadow: var(--rt-shadow-md);position:relative;display:flex;flex-direction:row;block-size:calc(100dvh - var(--rt-header-height, 0px));min-block-size:0}.rt-workspace__list{display:flex;flex:0 0 var(--rt-workspace-list-size, 320px);flex-direction:column;border-inline-end:var(--rt-workspace-border-width) solid var(--rt-color-border-strong);min-inline-size:0}.rt-workspace__center{display:flex;flex:1 1 auto;flex-direction:column;min-block-size:0;min-inline-size:0;padding-inline:var(--rt-space-4)}.rt-workspace__mobile-toolbar{display:none}.rt-workspace__aside{display:flex;flex:0 0 var(--rt-workspace-aside-size, 360px);flex-direction:column;border-inline-start:var(--rt-workspace-border-width) solid var(--rt-color-border-strong);min-inline-size:0}.rt-workspace__handle{position:relative;z-index:1;flex:0 0 auto;background:transparent;cursor:col-resize;inline-size:var(--rt-space-2);margin-inline:calc(-1 * var(--rt-space-1));touch-action:none}.rt-workspace__handle:before{position:absolute;background:transparent;content:\"\";inline-size:var(--rt-workspace-handle-line-width);inset-block:0;inset-inline-start:50%;transform:translate(-50%);transition:background var(--rt-workspace-handle-transition-duration) ease}.rt-workspace__handle:hover:before,.rt-workspace__handle:focus-visible:before{background:var(--rt-color-border-strong)}.rt-workspace__handle:focus-visible{outline:none}.rt-workspace__handle:focus-visible:before{background:var(--rt-color-border-focus)}@container rt-place (width <= 1080px){.rt-workspace__desktop-only{display:none}}@media(width<=1080px){:where(html:not(:has(.rt-container))) .rt-workspace__desktop-only{display:none}}@container rt-place (width <= 1080px){.rt-workspace__mobile-toolbar{display:flex;justify-content:space-between;padding:var(--rt-space-2) var(--rt-space-4) 0}.rt-workspace__handle{display:none}.rt-workspace__aside{position:absolute;z-index:2;flex-basis:360px;background:var(--rt-color-bg-surface);box-shadow:var(--rt-workspace-aside-shadow);inset-block:0;inset-inline-end:0;max-inline-size:90%;transform:translate(100%);transition:transform var(--rt-workspace-panel-transition-duration) ease}.rt-workspace__aside--open{transform:translate(0)}}@media(width<=1080px){:where(html:not(:has(.rt-container))) .rt-workspace__mobile-toolbar{display:flex;justify-content:space-between;padding:var(--rt-space-2) var(--rt-space-4) 0}:where(html:not(:has(.rt-container))) .rt-workspace__handle{display:none}:where(html:not(:has(.rt-container))) .rt-workspace__aside{position:absolute;z-index:2;flex-basis:360px;background:var(--rt-color-bg-surface);box-shadow:var(--rt-workspace-aside-shadow);inset-block:0;inset-inline-end:0;max-inline-size:90%;transform:translate(100%);transition:transform var(--rt-workspace-panel-transition-duration) ease}:where(html:not(:has(.rt-container))) .rt-workspace__aside--open{transform:translate(0)}}@container rt-place (width <= 768px){.rt-workspace__list{flex-basis:100%}}@media(width<=768px){:where(html:not(:has(.rt-container))) .rt-workspace__list{flex-basis:100%}}@container rt-place (width > 1080px){.rt-workspace__aside{overflow:hidden;transition:flex-basis var(--rt-workspace-panel-transition-duration) ease,border-inline-start-width var(--rt-workspace-panel-transition-duration) ease,opacity var(--rt-workspace-panel-transition-duration) ease;will-change:flex-basis}}@media(width>1080px){:where(html:not(:has(.rt-container))) .rt-workspace__aside{overflow:hidden;transition:flex-basis var(--rt-workspace-panel-transition-duration) ease,border-inline-start-width var(--rt-workspace-panel-transition-duration) ease,opacity var(--rt-workspace-panel-transition-duration) ease;will-change:flex-basis}}@container rt-place (width <= 768px){.rt-workspace--has-active .rt-workspace__list{display:none}.rt-workspace--has-active .rt-workspace__center{flex-basis:100%}}@media(width<=768px){:where(html:not(:has(.rt-container))) .rt-workspace--has-active .rt-workspace__list{display:none}:where(html:not(:has(.rt-container))) .rt-workspace--has-active .rt-workspace__center{flex-basis:100%}}@container rt-place (width > 1080px){.rt-workspace--aside-collapsed .rt-workspace__aside{flex-basis:0;border-inline-start-width:0;min-inline-size:0;opacity:0;pointer-events:none;transition:flex-basis var(--rt-workspace-panel-transition-duration) ease,border-inline-start-width var(--rt-workspace-panel-transition-duration) ease,opacity var(--rt-workspace-panel-transition-duration) ease,visibility 0s linear var(--rt-workspace-panel-transition-duration);visibility:hidden}.rt-workspace--aside-collapsed .rt-workspace__handle--aside{display:none}}@media(width>1080px){:where(html:not(:has(.rt-container))) .rt-workspace--aside-collapsed .rt-workspace__aside{flex-basis:0;border-inline-start-width:0;min-inline-size:0;opacity:0;pointer-events:none;transition:flex-basis var(--rt-workspace-panel-transition-duration) ease,border-inline-start-width var(--rt-workspace-panel-transition-duration) ease,opacity var(--rt-workspace-panel-transition-duration) ease,visibility 0s linear var(--rt-workspace-panel-transition-duration);visibility:hidden}:where(html:not(:has(.rt-container))) .rt-workspace--aside-collapsed .rt-workspace__handle--aside{display:none}}.rt-workspace--resizing{cursor:col-resize;-webkit-user-select:none;user-select:none}.rt-workspace--resizing .rt-workspace__list,.rt-workspace--resizing .rt-workspace__aside{transition:none}@media(prefers-reduced-motion:reduce){.rt-workspace__aside{transition:none}}}\n"],
|
|
452
452
|
dependencies: [
|
|
453
453
|
{
|
|
454
454
|
kind: "directive",
|
|
@@ -535,7 +535,7 @@ i0.ɵɵngDeclareClassMetadata({
|
|
|
535
535
|
"[style.--rt-workspace-aside-size]": "asideWidth() + 'px'"
|
|
536
536
|
},
|
|
537
537
|
template: "<ng-container rtBlock=\"rt-workspace\">\n @if (listSlot()) {\n <section rtElem=\"list\" qa-dataid=\"workspace-list\">\n <ng-container [ngTemplateOutlet]=\"listSlot()?.templateRef ?? null\" [ngTemplateOutletContext]=\"slotContext\" />\n </section>\n\n <div\n rtElem=\"handle\"\n qa-dataid=\"workspace-handle-list\"\n role=\"separator\"\n aria-orientation=\"vertical\"\n tabindex=\"0\"\n [attr.aria-label]=\"t().uiResizeList\"\n [rtMod]=\"{ list: true }\"\n [attr.aria-valuenow]=\"listWidth()\"\n [attr.aria-valuemin]=\"listMinWidth()\"\n [attr.aria-valuemax]=\"listMaxWidth()\"\n (pointerdown)=\"onHandlePointerDown($event, 'list')\"\n (dblclick)=\"onHandleReset('list')\"\n (keydown)=\"onHandleKeydown($event, 'list')\"></div>\n }\n\n <section rtElem=\"center\" qa-dataid=\"workspace-center\">\n @if (hasActive()) {\n <div rtElem=\"mobile-toolbar\">\n <rt-icon-button\n qa-dataid=\"workspace-back\"\n icon=\"arrow-left\"\n variant=\"secondary\"\n [ariaLabel]=\"t().uiBackToList\"\n [tooltip]=\"t().uiToList\"\n (clicked)=\"onBackClicked()\" />\n <rt-icon-button\n qa-dataid=\"workspace-open-details\"\n icon=\"info-circle\"\n variant=\"secondary\"\n [ariaLabel]=\"t().uiShowDetails\"\n [tooltip]=\"t().uiDetails\"\n (clicked)=\"openAside()\" />\n </div>\n }\n <ng-container [ngTemplateOutlet]=\"centerSlot()?.templateRef ?? null\" [ngTemplateOutletContext]=\"slotContext\" />\n </section>\n\n @if (asideSlot()) {\n <div\n rtElem=\"handle\"\n qa-dataid=\"workspace-handle-aside\"\n role=\"separator\"\n aria-orientation=\"vertical\"\n tabindex=\"0\"\n [attr.aria-label]=\"t().uiResizeDetails\"\n [rtMod]=\"{ aside: true }\"\n [attr.aria-valuenow]=\"asideWidth()\"\n [attr.aria-valuemin]=\"asideMinWidth()\"\n [attr.aria-valuemax]=\"asideMaxWidth()\"\n (pointerdown)=\"onHandlePointerDown($event, 'aside')\"\n (dblclick)=\"onHandleReset('aside')\"\n (keydown)=\"onHandleKeydown($event, 'aside')\"></div>\n\n <section rtElem=\"aside\" qa-dataid=\"workspace-aside\" [rtMod]=\"{ open: asideOpen() }\">\n <ng-container [ngTemplateOutlet]=\"asideSlot()?.templateRef ?? null\" [ngTemplateOutletContext]=\"slotContext\" />\n </section>\n }\n</ng-container>\n",
|
|
538
|
-
styles: ["@layer rt-kit.components{.rt-workspace{--rt-workspace-border-width: var(--rt-border-width-thin);--rt-workspace-handle-line-width: var(--rt-border-width-medium);--rt-workspace-handle-transition-duration: var(--rt-duration-fast);--rt-workspace-panel-transition-duration: var(--rt-duration-base);--rt-workspace-aside-shadow: var(--rt-shadow-md);position:relative;display:flex;flex-direction:row;block-size:calc(100dvh - var(--rt-header-height, 0px));min-block-size:0}.rt-workspace__list{display:flex;flex:0 0 var(--rt-workspace-list-size, 320px);flex-direction:column;border-inline-end:var(--rt-workspace-border-width) solid var(--rt-color-border-strong);min-inline-size:0}.rt-workspace__center{display:flex;flex:1 1 auto;flex-direction:column;min-block-size:0;min-inline-size:0;padding-inline:var(--rt-space-4)}.rt-workspace__mobile-toolbar{display:none}.rt-workspace__aside{display:flex;flex:0 0 var(--rt-workspace-aside-size, 360px);flex-direction:column;border-inline-start:var(--rt-workspace-border-width) solid var(--rt-color-border-strong);min-inline-size:0}.rt-workspace__handle{position:relative;z-index:1;flex:0 0 auto;background:transparent;cursor:col-resize;inline-size:var(--rt-space-2);margin-inline:calc(-1 * var(--rt-space-1));touch-action:none}.rt-workspace__handle:before{position:absolute;background:transparent;content:\"\";inline-size:var(--rt-workspace-handle-line-width);inset-block:0;inset-inline-start:50%;transform:translate(-50%);transition:background var(--rt-workspace-handle-transition-duration) ease}.rt-workspace__handle:hover:before,.rt-workspace__handle:focus-visible:before{background:var(--rt-color-border-strong)}.rt-workspace__handle:focus-visible{outline:none}.rt-workspace__handle:focus-visible:before{background:var(--rt-color-border-focus)}@container rt-place (width <= 1080px){.rt-workspace__desktop-only{display:none}}@container rt-place (width <= 1080px){.rt-workspace__mobile-toolbar{display:flex;justify-content:space-between;padding:var(--rt-space-2) var(--rt-space-4) 0}.rt-workspace__handle{display:none}.rt-workspace__aside{position:absolute;z-index:2;flex-basis:360px;background:var(--rt-color-bg-surface);box-shadow:var(--rt-workspace-aside-shadow);inset-block:0;inset-inline-end:0;max-inline-size:90%;transform:translate(100%);transition:transform var(--rt-workspace-panel-transition-duration) ease}.rt-workspace__aside--open{transform:translate(0)}}@container rt-place (width <= 768px){.rt-workspace__list{flex-basis:100%}}@container rt-place (width > 1080px){.rt-workspace__aside{overflow:hidden;transition:flex-basis var(--rt-workspace-panel-transition-duration) ease,border-inline-start-width var(--rt-workspace-panel-transition-duration) ease,opacity var(--rt-workspace-panel-transition-duration) ease;will-change:flex-basis}}@container rt-place (width <= 768px){.rt-workspace--has-active .rt-workspace__list{display:none}.rt-workspace--has-active .rt-workspace__center{flex-basis:100%}}@container rt-place (width > 1080px){.rt-workspace--aside-collapsed .rt-workspace__aside{flex-basis:0;border-inline-start-width:0;min-inline-size:0;opacity:0;pointer-events:none;transition:flex-basis var(--rt-workspace-panel-transition-duration) ease,border-inline-start-width var(--rt-workspace-panel-transition-duration) ease,opacity var(--rt-workspace-panel-transition-duration) ease,visibility 0s linear var(--rt-workspace-panel-transition-duration);visibility:hidden}.rt-workspace--aside-collapsed .rt-workspace__handle--aside{display:none}}.rt-workspace--resizing{cursor:col-resize;-webkit-user-select:none;user-select:none}.rt-workspace--resizing .rt-workspace__list,.rt-workspace--resizing .rt-workspace__aside{transition:none}@media(prefers-reduced-motion:reduce){.rt-workspace__aside{transition:none}}}\n"]
|
|
538
|
+
styles: ["@layer rt-kit.components{.rt-workspace{--rt-workspace-border-width: var(--rt-border-width-thin);--rt-workspace-handle-line-width: var(--rt-border-width-medium);--rt-workspace-handle-transition-duration: var(--rt-duration-fast);--rt-workspace-panel-transition-duration: var(--rt-duration-base);--rt-workspace-aside-shadow: var(--rt-shadow-md);position:relative;display:flex;flex-direction:row;block-size:calc(100dvh - var(--rt-header-height, 0px));min-block-size:0}.rt-workspace__list{display:flex;flex:0 0 var(--rt-workspace-list-size, 320px);flex-direction:column;border-inline-end:var(--rt-workspace-border-width) solid var(--rt-color-border-strong);min-inline-size:0}.rt-workspace__center{display:flex;flex:1 1 auto;flex-direction:column;min-block-size:0;min-inline-size:0;padding-inline:var(--rt-space-4)}.rt-workspace__mobile-toolbar{display:none}.rt-workspace__aside{display:flex;flex:0 0 var(--rt-workspace-aside-size, 360px);flex-direction:column;border-inline-start:var(--rt-workspace-border-width) solid var(--rt-color-border-strong);min-inline-size:0}.rt-workspace__handle{position:relative;z-index:1;flex:0 0 auto;background:transparent;cursor:col-resize;inline-size:var(--rt-space-2);margin-inline:calc(-1 * var(--rt-space-1));touch-action:none}.rt-workspace__handle:before{position:absolute;background:transparent;content:\"\";inline-size:var(--rt-workspace-handle-line-width);inset-block:0;inset-inline-start:50%;transform:translate(-50%);transition:background var(--rt-workspace-handle-transition-duration) ease}.rt-workspace__handle:hover:before,.rt-workspace__handle:focus-visible:before{background:var(--rt-color-border-strong)}.rt-workspace__handle:focus-visible{outline:none}.rt-workspace__handle:focus-visible:before{background:var(--rt-color-border-focus)}@container rt-place (width <= 1080px){.rt-workspace__desktop-only{display:none}}@media(width<=1080px){:where(html:not(:has(.rt-container))) .rt-workspace__desktop-only{display:none}}@container rt-place (width <= 1080px){.rt-workspace__mobile-toolbar{display:flex;justify-content:space-between;padding:var(--rt-space-2) var(--rt-space-4) 0}.rt-workspace__handle{display:none}.rt-workspace__aside{position:absolute;z-index:2;flex-basis:360px;background:var(--rt-color-bg-surface);box-shadow:var(--rt-workspace-aside-shadow);inset-block:0;inset-inline-end:0;max-inline-size:90%;transform:translate(100%);transition:transform var(--rt-workspace-panel-transition-duration) ease}.rt-workspace__aside--open{transform:translate(0)}}@media(width<=1080px){:where(html:not(:has(.rt-container))) .rt-workspace__mobile-toolbar{display:flex;justify-content:space-between;padding:var(--rt-space-2) var(--rt-space-4) 0}:where(html:not(:has(.rt-container))) .rt-workspace__handle{display:none}:where(html:not(:has(.rt-container))) .rt-workspace__aside{position:absolute;z-index:2;flex-basis:360px;background:var(--rt-color-bg-surface);box-shadow:var(--rt-workspace-aside-shadow);inset-block:0;inset-inline-end:0;max-inline-size:90%;transform:translate(100%);transition:transform var(--rt-workspace-panel-transition-duration) ease}:where(html:not(:has(.rt-container))) .rt-workspace__aside--open{transform:translate(0)}}@container rt-place (width <= 768px){.rt-workspace__list{flex-basis:100%}}@media(width<=768px){:where(html:not(:has(.rt-container))) .rt-workspace__list{flex-basis:100%}}@container rt-place (width > 1080px){.rt-workspace__aside{overflow:hidden;transition:flex-basis var(--rt-workspace-panel-transition-duration) ease,border-inline-start-width var(--rt-workspace-panel-transition-duration) ease,opacity var(--rt-workspace-panel-transition-duration) ease;will-change:flex-basis}}@media(width>1080px){:where(html:not(:has(.rt-container))) .rt-workspace__aside{overflow:hidden;transition:flex-basis var(--rt-workspace-panel-transition-duration) ease,border-inline-start-width var(--rt-workspace-panel-transition-duration) ease,opacity var(--rt-workspace-panel-transition-duration) ease;will-change:flex-basis}}@container rt-place (width <= 768px){.rt-workspace--has-active .rt-workspace__list{display:none}.rt-workspace--has-active .rt-workspace__center{flex-basis:100%}}@media(width<=768px){:where(html:not(:has(.rt-container))) .rt-workspace--has-active .rt-workspace__list{display:none}:where(html:not(:has(.rt-container))) .rt-workspace--has-active .rt-workspace__center{flex-basis:100%}}@container rt-place (width > 1080px){.rt-workspace--aside-collapsed .rt-workspace__aside{flex-basis:0;border-inline-start-width:0;min-inline-size:0;opacity:0;pointer-events:none;transition:flex-basis var(--rt-workspace-panel-transition-duration) ease,border-inline-start-width var(--rt-workspace-panel-transition-duration) ease,opacity var(--rt-workspace-panel-transition-duration) ease,visibility 0s linear var(--rt-workspace-panel-transition-duration);visibility:hidden}.rt-workspace--aside-collapsed .rt-workspace__handle--aside{display:none}}@media(width>1080px){:where(html:not(:has(.rt-container))) .rt-workspace--aside-collapsed .rt-workspace__aside{flex-basis:0;border-inline-start-width:0;min-inline-size:0;opacity:0;pointer-events:none;transition:flex-basis var(--rt-workspace-panel-transition-duration) ease,border-inline-start-width var(--rt-workspace-panel-transition-duration) ease,opacity var(--rt-workspace-panel-transition-duration) ease,visibility 0s linear var(--rt-workspace-panel-transition-duration);visibility:hidden}:where(html:not(:has(.rt-container))) .rt-workspace--aside-collapsed .rt-workspace__handle--aside{display:none}}.rt-workspace--resizing{cursor:col-resize;-webkit-user-select:none;user-select:none}.rt-workspace--resizing .rt-workspace__list,.rt-workspace--resizing .rt-workspace__aside{transition:none}@media(prefers-reduced-motion:reduce){.rt-workspace__aside{transition:none}}}\n"]
|
|
539
539
|
}]
|
|
540
540
|
}],
|
|
541
541
|
ctorParameters: () => [],
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"rt-tools-ui-kit-v2-workspace.mjs","names":[],"sources":["../../../projects/ui-kit-v2/src/lib/components/workspace/rt-workspace.directives.ts","../../../projects/ui-kit-v2/src/lib/components/workspace/rt-workspace.component.ts","../../../projects/ui-kit-v2/src/lib/components/workspace/rt-workspace.component.html"],"sourcesContent":["import { Directive, inject, TemplateRef } from '@angular/core';\n\nimport { IRtWorkspace } from './rt-workspace.model';\n\n@Directive({\n selector: '[rtWorkspaceDesktopOnly]',\n host: {\n class: 'rt-workspace__desktop-only',\n },\n})\nexport class RtWorkspaceDesktopOnlyDirective {}\n\n@Directive({\n selector: '[rtWorkspaceList]',\n})\nexport class RtWorkspaceListDirective {\n public readonly templateRef: TemplateRef<IRtWorkspace.SlotContext> = inject<TemplateRef<IRtWorkspace.SlotContext>>(TemplateRef);\n\n // eslint-disable-next-line @typescript-eslint/no-unused-vars -- второй довод стража контекста шаблона стоит только в типе-предикате; убрать его нечем, подпись задаёт каркас\n public static ngTemplateContextGuard(_directive: RtWorkspaceListDirective, context: unknown): context is IRtWorkspace.SlotContext {\n return true;\n }\n}\n\n@Directive({\n selector: '[rtWorkspaceCenter]',\n})\nexport class RtWorkspaceCenterDirective {\n public readonly templateRef: TemplateRef<IRtWorkspace.SlotContext> = inject<TemplateRef<IRtWorkspace.SlotContext>>(TemplateRef);\n\n // eslint-disable-next-line @typescript-eslint/no-unused-vars -- второй довод стража контекста шаблона стоит только в типе-предикате; убрать его нечем, подпись задаёт каркас\n public static ngTemplateContextGuard(_directive: RtWorkspaceCenterDirective, context: unknown): context is IRtWorkspace.SlotContext {\n return true;\n }\n}\n\n@Directive({\n selector: '[rtWorkspaceAside]',\n})\nexport class RtWorkspaceAsideDirective {\n public readonly templateRef: TemplateRef<IRtWorkspace.SlotContext> = inject<TemplateRef<IRtWorkspace.SlotContext>>(TemplateRef);\n\n // eslint-disable-next-line @typescript-eslint/no-unused-vars -- второй довод стража контекста шаблона стоит только в типе-предикате; убрать его нечем, подпись задаёт каркас\n public static ngTemplateContextGuard(_directive: RtWorkspaceAsideDirective, context: unknown): context is IRtWorkspace.SlotContext {\n return true;\n }\n}\n","import { BooleanInput } from '@angular/cdk/coercion';\nimport { NgTemplateOutlet } from '@angular/common';\nimport {\n booleanAttribute,\n ChangeDetectionStrategy,\n Component,\n computed,\n contentChild,\n DestroyRef,\n effect,\n ElementRef,\n inject,\n input,\n InputSignal,\n InputSignalWithTransform,\n numberAttribute,\n output,\n OutputEmitterRef,\n Renderer2,\n signal,\n Signal,\n untracked,\n ViewEncapsulation,\n WritableSignal,\n} from '@angular/core';\n\nimport { StorageService } from '@rt-tools/core';\nimport { BlockDirective, ElemDirective, ModDirective } from '@rt-tools/core';\n\nimport { RT_KIT_LABELS, TRtKitLabelMap } from '@rt-tools/ui-kit-v2/core';\nimport { RtIconButtonComponent } from '@rt-tools/ui-kit-v2/icon-button';\nimport { RtWorkspaceAsideDirective, RtWorkspaceCenterDirective, RtWorkspaceListDirective } from './rt-workspace.directives';\nimport { IRtWorkspace } from './rt-workspace.model';\n\nconst BEM_BLOCK: string = 'rt-workspace';\nconst STORAGE_PREFIX: string = 'rt-workspace:';\nconst KEYBOARD_STEP: number = 16;\n\ninterface IDragState {\n kind: IRtWorkspace.PanelKind;\n startX: number;\n startWidth: number;\n}\n\n@Component({\n selector: 'rt-workspace',\n templateUrl: './rt-workspace.component.html',\n styleUrls: ['./rt-workspace.component.scss'],\n changeDetection: ChangeDetectionStrategy.OnPush,\n encapsulation: ViewEncapsulation.None,\n imports: [\n // Angular\n NgTemplateOutlet,\n\n // standalone components / directives\n RtIconButtonComponent,\n BlockDirective,\n ElemDirective,\n ModDirective,\n ],\n host: {\n class: BEM_BLOCK,\n '[class.rt-workspace--has-active]': 'hasActive()',\n '[class.rt-workspace--aside-collapsed]': 'asideCollapsed()',\n '[class.rt-workspace--resizing]': 'resizing()',\n '[style.--rt-workspace-list-size]': \"listWidth() + 'px'\",\n '[style.--rt-workspace-aside-size]': \"asideWidth() + 'px'\",\n },\n})\nexport class RtWorkspaceComponent implements IRtWorkspace.PanelApi {\n readonly #storage: StorageService = inject(StorageService);\n\n readonly #renderer: Renderer2 = inject(Renderer2);\n\n readonly #hostRef: ElementRef<HTMLElement> = inject(ElementRef);\n\n readonly #destroyRef: DestroyRef = inject(DestroyRef);\n\n readonly #listWidthOverride: WritableSignal<number | null> = signal<number | null>(null);\n\n readonly #asideWidthOverride: WritableSignal<number | null> = signal<number | null>(null);\n\n readonly #asideCollapsed: WritableSignal<boolean> = signal<boolean>(false);\n\n readonly #asideOpen: WritableSignal<boolean> = signal<boolean>(false);\n\n readonly #resizing: WritableSignal<boolean> = signal<boolean>(false);\n\n #restoredKey: string | null = null;\n\n #dragState: IDragState | null = null;\n\n #detachDragListeners: (() => void) | null = null;\n\n protected readonly t: Signal<TRtKitLabelMap> = inject(RT_KIT_LABELS);\n\n protected readonly listSlot: Signal<RtWorkspaceListDirective | undefined> = contentChild(RtWorkspaceListDirective);\n\n protected readonly centerSlot: Signal<RtWorkspaceCenterDirective | undefined> = contentChild(RtWorkspaceCenterDirective);\n\n protected readonly asideSlot: Signal<RtWorkspaceAsideDirective | undefined> = contentChild(RtWorkspaceAsideDirective);\n\n protected readonly resizing: Signal<boolean> = this.#resizing.asReadonly();\n\n protected readonly slotContext: IRtWorkspace.SlotContext = { $implicit: this };\n\n public readonly storageKey: InputSignal<string | null> = input<string | null>(null);\n\n public readonly hasActive: InputSignalWithTransform<boolean, BooleanInput> = input<boolean, BooleanInput>(false, {\n transform: booleanAttribute,\n });\n\n public readonly listMinWidth: InputSignalWithTransform<number, number | string> = input<number, number | string>(240, {\n transform: numberAttribute,\n });\n\n public readonly listMaxWidth: InputSignalWithTransform<number, number | string> = input<number, number | string>(480, {\n transform: numberAttribute,\n });\n\n public readonly listDefaultWidth: InputSignalWithTransform<number, number | string> = input<number, number | string>(320, {\n transform: numberAttribute,\n });\n\n public readonly asideMinWidth: InputSignalWithTransform<number, number | string> = input<number, number | string>(280, {\n transform: numberAttribute,\n });\n\n public readonly asideMaxWidth: InputSignalWithTransform<number, number | string> = input<number, number | string>(560, {\n transform: numberAttribute,\n });\n\n public readonly asideDefaultWidth: InputSignalWithTransform<number, number | string> = input<number, number | string>(360, {\n transform: numberAttribute,\n });\n\n public readonly centerMinWidth: InputSignalWithTransform<number, number | string> = input<number, number | string>(360, {\n transform: numberAttribute,\n });\n\n public readonly backClicked: OutputEmitterRef<void> = output<void>();\n\n public readonly listWidth: Signal<number> = computed((): number => this.#listWidthOverride() ?? this.listDefaultWidth());\n\n public readonly asideWidth: Signal<number> = computed((): number => this.#asideWidthOverride() ?? this.asideDefaultWidth());\n\n public readonly asideCollapsed: Signal<boolean> = this.#asideCollapsed.asReadonly();\n\n public readonly asideOpen: Signal<boolean> = this.#asideOpen.asReadonly();\n\n constructor() {\n effect((): void => {\n const key: string | null = this.storageKey();\n if (key === null || key === this.#restoredKey) {\n return;\n }\n this.#restoredKey = key;\n untracked((): void => this.#restoreFromStorage(key));\n });\n\n this.#destroyRef.onDestroy((): void => this.#stopDragging());\n }\n\n public toggleAsideCollapsed(): void {\n this.#asideCollapsed.update((collapsed: boolean): boolean => !collapsed);\n this.#persist();\n }\n\n public openAside(): void {\n this.#asideOpen.set(true);\n }\n\n public closeAside(): void {\n this.#asideOpen.set(false);\n }\n\n public toggleAside(): void {\n this.#asideOpen.update((open: boolean): boolean => !open);\n }\n\n protected onBackClicked(): void {\n this.closeAside();\n this.backClicked.emit();\n }\n\n protected onHandlePointerDown(event: PointerEvent, kind: IRtWorkspace.PanelKind): void {\n if (event.button !== 0) {\n return;\n }\n event.preventDefault();\n this.#dragState = {\n kind,\n startX: event.clientX,\n startWidth: kind === 'list' ? this.listWidth() : this.asideWidth(),\n };\n this.#resizing.set(true);\n\n const detachMove: () => void = this.#renderer.listen('document', 'pointermove', (moveEvent: PointerEvent): void =>\n this.#onDragMove(moveEvent)\n );\n const detachUp: () => void = this.#renderer.listen('document', 'pointerup', (): void => {\n this.#persist();\n this.#stopDragging();\n });\n this.#detachDragListeners = (): void => {\n detachMove();\n detachUp();\n };\n }\n\n protected onHandleKeydown(event: KeyboardEvent, kind: IRtWorkspace.PanelKind): void {\n let delta: number;\n if (event.key === 'ArrowRight') {\n delta = kind === 'list' ? KEYBOARD_STEP : -KEYBOARD_STEP;\n } else if (event.key === 'ArrowLeft') {\n delta = kind === 'list' ? -KEYBOARD_STEP : KEYBOARD_STEP;\n } else {\n return;\n }\n event.preventDefault();\n const current: number = kind === 'list' ? this.listWidth() : this.asideWidth();\n this.#applyWidth(kind, current + delta);\n this.#persist();\n }\n\n protected onHandleReset(kind: IRtWorkspace.PanelKind): void {\n const override: WritableSignal<number | null> = kind === 'list' ? this.#listWidthOverride : this.#asideWidthOverride;\n override.set(null);\n this.#persist();\n }\n\n #onDragMove(event: PointerEvent): void {\n const drag: IDragState | null = this.#dragState;\n if (drag === null) {\n return;\n }\n const dx: number = event.clientX - drag.startX;\n const rawWidth: number = drag.kind === 'list' ? drag.startWidth + dx : drag.startWidth - dx;\n this.#applyWidth(drag.kind, rawWidth);\n }\n\n #applyWidth(kind: IRtWorkspace.PanelKind, rawWidth: number): void {\n const override: WritableSignal<number | null> = kind === 'list' ? this.#listWidthOverride : this.#asideWidthOverride;\n override.set(this.#clampWidth(kind, rawWidth));\n }\n\n #clampWidth(kind: IRtWorkspace.PanelKind, rawWidth: number): number {\n const min: number = kind === 'list' ? this.listMinWidth() : this.asideMinWidth();\n const configMax: number = kind === 'list' ? this.listMaxWidth() : this.asideMaxWidth();\n // Место соседней панели вычитается, только когда она объявлена: без её слота ширина\n // соседки — число из умолчаний, а места она не занимает вовсе.\n const otherWidth: number = this.#occupiedWidth(kind === 'list' ? 'aside' : 'list');\n const hostWidth: number = this.#hostRef.nativeElement.clientWidth;\n const available: number = hostWidth > 0 ? hostWidth - otherWidth - this.centerMinWidth() : Number.POSITIVE_INFINITY;\n const max: number = Math.max(min, Math.min(configMax, available));\n return Math.round(Math.min(max, Math.max(min, rawWidth)));\n }\n\n /** Сколько ширины занимает панель: необъявленная не занимает ничего. */\n #occupiedWidth(kind: IRtWorkspace.PanelKind): number {\n if (kind === 'list') {\n return this.listSlot() ? this.listWidth() : 0;\n }\n\n return this.asideSlot() ? this.asideWidth() : 0;\n }\n\n #stopDragging(): void {\n this.#detachDragListeners?.();\n this.#detachDragListeners = null;\n this.#dragState = null;\n this.#resizing.set(false);\n }\n\n #restoreFromStorage(key: string): void {\n const stored: IRtWorkspace.PersistedState | null =\n this.#storage.getItem<IRtWorkspace.PersistedState>(`${STORAGE_PREFIX}${key}`) ?? null;\n if (stored === null || typeof stored !== 'object') {\n return;\n }\n if (typeof stored.listWidth === 'number') {\n this.#listWidthOverride.set(this.#clampWidth('list', stored.listWidth));\n }\n if (typeof stored.asideWidth === 'number') {\n this.#asideWidthOverride.set(this.#clampWidth('aside', stored.asideWidth));\n }\n this.#asideCollapsed.set(stored.asideCollapsed === true);\n }\n\n #persist(): void {\n const key: string | null = this.storageKey();\n if (key === null) {\n return;\n }\n const state: IRtWorkspace.PersistedState = {\n listWidth: this.listWidth(),\n asideWidth: this.asideWidth(),\n asideCollapsed: this.asideCollapsed(),\n };\n this.#storage.setItem(`${STORAGE_PREFIX}${key}`, state);\n }\n}\n","<ng-container rtBlock=\"rt-workspace\">\n @if (listSlot()) {\n <section rtElem=\"list\" qa-dataid=\"workspace-list\">\n <ng-container [ngTemplateOutlet]=\"listSlot()?.templateRef ?? null\" [ngTemplateOutletContext]=\"slotContext\" />\n </section>\n\n <div\n rtElem=\"handle\"\n qa-dataid=\"workspace-handle-list\"\n role=\"separator\"\n aria-orientation=\"vertical\"\n tabindex=\"0\"\n [attr.aria-label]=\"t().uiResizeList\"\n [rtMod]=\"{ list: true }\"\n [attr.aria-valuenow]=\"listWidth()\"\n [attr.aria-valuemin]=\"listMinWidth()\"\n [attr.aria-valuemax]=\"listMaxWidth()\"\n (pointerdown)=\"onHandlePointerDown($event, 'list')\"\n (dblclick)=\"onHandleReset('list')\"\n (keydown)=\"onHandleKeydown($event, 'list')\"></div>\n }\n\n <section rtElem=\"center\" qa-dataid=\"workspace-center\">\n @if (hasActive()) {\n <div rtElem=\"mobile-toolbar\">\n <rt-icon-button\n qa-dataid=\"workspace-back\"\n icon=\"arrow-left\"\n variant=\"secondary\"\n [ariaLabel]=\"t().uiBackToList\"\n [tooltip]=\"t().uiToList\"\n (clicked)=\"onBackClicked()\" />\n <rt-icon-button\n qa-dataid=\"workspace-open-details\"\n icon=\"info-circle\"\n variant=\"secondary\"\n [ariaLabel]=\"t().uiShowDetails\"\n [tooltip]=\"t().uiDetails\"\n (clicked)=\"openAside()\" />\n </div>\n }\n <ng-container [ngTemplateOutlet]=\"centerSlot()?.templateRef ?? null\" [ngTemplateOutletContext]=\"slotContext\" />\n </section>\n\n @if (asideSlot()) {\n <div\n rtElem=\"handle\"\n qa-dataid=\"workspace-handle-aside\"\n role=\"separator\"\n aria-orientation=\"vertical\"\n tabindex=\"0\"\n [attr.aria-label]=\"t().uiResizeDetails\"\n [rtMod]=\"{ aside: true }\"\n [attr.aria-valuenow]=\"asideWidth()\"\n [attr.aria-valuemin]=\"asideMinWidth()\"\n [attr.aria-valuemax]=\"asideMaxWidth()\"\n (pointerdown)=\"onHandlePointerDown($event, 'aside')\"\n (dblclick)=\"onHandleReset('aside')\"\n (keydown)=\"onHandleKeydown($event, 'aside')\"></div>\n\n <section rtElem=\"aside\" qa-dataid=\"workspace-aside\" [rtMod]=\"{ open: asideOpen() }\">\n <ng-container [ngTemplateOutlet]=\"asideSlot()?.templateRef ?? null\" [ngTemplateOutletContext]=\"slotContext\" />\n </section>\n }\n</ng-container>\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"rt-tools-ui-kit-v2-workspace.mjs","names":[],"sources":["../../../projects/ui-kit-v2/src/lib/components/workspace/rt-workspace.directives.ts","../../../projects/ui-kit-v2/src/lib/components/workspace/rt-workspace.component.ts","../../../projects/ui-kit-v2/src/lib/components/workspace/rt-workspace.component.html"],"sourcesContent":["import { Directive, inject, TemplateRef } from '@angular/core';\n\nimport { IRtWorkspace } from './rt-workspace.model';\n\n@Directive({\n selector: '[rtWorkspaceDesktopOnly]',\n host: {\n class: 'rt-workspace__desktop-only',\n },\n})\nexport class RtWorkspaceDesktopOnlyDirective {}\n\n@Directive({\n selector: '[rtWorkspaceList]',\n})\nexport class RtWorkspaceListDirective {\n public readonly templateRef: TemplateRef<IRtWorkspace.SlotContext> = inject<TemplateRef<IRtWorkspace.SlotContext>>(TemplateRef);\n\n // eslint-disable-next-line @typescript-eslint/no-unused-vars -- второй довод стража контекста шаблона стоит только в типе-предикате; убрать его нечем, подпись задаёт каркас\n public static ngTemplateContextGuard(_directive: RtWorkspaceListDirective, context: unknown): context is IRtWorkspace.SlotContext {\n return true;\n }\n}\n\n@Directive({\n selector: '[rtWorkspaceCenter]',\n})\nexport class RtWorkspaceCenterDirective {\n public readonly templateRef: TemplateRef<IRtWorkspace.SlotContext> = inject<TemplateRef<IRtWorkspace.SlotContext>>(TemplateRef);\n\n // eslint-disable-next-line @typescript-eslint/no-unused-vars -- второй довод стража контекста шаблона стоит только в типе-предикате; убрать его нечем, подпись задаёт каркас\n public static ngTemplateContextGuard(_directive: RtWorkspaceCenterDirective, context: unknown): context is IRtWorkspace.SlotContext {\n return true;\n }\n}\n\n@Directive({\n selector: '[rtWorkspaceAside]',\n})\nexport class RtWorkspaceAsideDirective {\n public readonly templateRef: TemplateRef<IRtWorkspace.SlotContext> = inject<TemplateRef<IRtWorkspace.SlotContext>>(TemplateRef);\n\n // eslint-disable-next-line @typescript-eslint/no-unused-vars -- второй довод стража контекста шаблона стоит только в типе-предикате; убрать его нечем, подпись задаёт каркас\n public static ngTemplateContextGuard(_directive: RtWorkspaceAsideDirective, context: unknown): context is IRtWorkspace.SlotContext {\n return true;\n }\n}\n","import { BooleanInput } from '@angular/cdk/coercion';\nimport { NgTemplateOutlet } from '@angular/common';\nimport {\n booleanAttribute,\n ChangeDetectionStrategy,\n Component,\n computed,\n contentChild,\n DestroyRef,\n effect,\n ElementRef,\n inject,\n input,\n InputSignal,\n InputSignalWithTransform,\n numberAttribute,\n output,\n OutputEmitterRef,\n Renderer2,\n signal,\n Signal,\n untracked,\n ViewEncapsulation,\n WritableSignal,\n} from '@angular/core';\n\nimport { StorageService } from '@rt-tools/core';\nimport { BlockDirective, ElemDirective, ModDirective } from '@rt-tools/core';\n\nimport { RT_KIT_LABELS, TRtKitLabelMap } from '@rt-tools/ui-kit-v2/core';\nimport { RtIconButtonComponent } from '@rt-tools/ui-kit-v2/icon-button';\nimport { RtWorkspaceAsideDirective, RtWorkspaceCenterDirective, RtWorkspaceListDirective } from './rt-workspace.directives';\nimport { IRtWorkspace } from './rt-workspace.model';\n\nconst BEM_BLOCK: string = 'rt-workspace';\nconst STORAGE_PREFIX: string = 'rt-workspace:';\nconst KEYBOARD_STEP: number = 16;\n\ninterface IDragState {\n kind: IRtWorkspace.PanelKind;\n startX: number;\n startWidth: number;\n}\n\n@Component({\n selector: 'rt-workspace',\n templateUrl: './rt-workspace.component.html',\n styleUrls: ['./rt-workspace.component.scss'],\n changeDetection: ChangeDetectionStrategy.OnPush,\n encapsulation: ViewEncapsulation.None,\n imports: [\n // Angular\n NgTemplateOutlet,\n\n // standalone components / directives\n RtIconButtonComponent,\n BlockDirective,\n ElemDirective,\n ModDirective,\n ],\n host: {\n class: BEM_BLOCK,\n '[class.rt-workspace--has-active]': 'hasActive()',\n '[class.rt-workspace--aside-collapsed]': 'asideCollapsed()',\n '[class.rt-workspace--resizing]': 'resizing()',\n '[style.--rt-workspace-list-size]': \"listWidth() + 'px'\",\n '[style.--rt-workspace-aside-size]': \"asideWidth() + 'px'\",\n },\n})\nexport class RtWorkspaceComponent implements IRtWorkspace.PanelApi {\n readonly #storage: StorageService = inject(StorageService);\n\n readonly #renderer: Renderer2 = inject(Renderer2);\n\n readonly #hostRef: ElementRef<HTMLElement> = inject(ElementRef);\n\n readonly #destroyRef: DestroyRef = inject(DestroyRef);\n\n readonly #listWidthOverride: WritableSignal<number | null> = signal<number | null>(null);\n\n readonly #asideWidthOverride: WritableSignal<number | null> = signal<number | null>(null);\n\n readonly #asideCollapsed: WritableSignal<boolean> = signal<boolean>(false);\n\n readonly #asideOpen: WritableSignal<boolean> = signal<boolean>(false);\n\n readonly #resizing: WritableSignal<boolean> = signal<boolean>(false);\n\n #restoredKey: string | null = null;\n\n #dragState: IDragState | null = null;\n\n #detachDragListeners: (() => void) | null = null;\n\n protected readonly t: Signal<TRtKitLabelMap> = inject(RT_KIT_LABELS);\n\n protected readonly listSlot: Signal<RtWorkspaceListDirective | undefined> = contentChild(RtWorkspaceListDirective);\n\n protected readonly centerSlot: Signal<RtWorkspaceCenterDirective | undefined> = contentChild(RtWorkspaceCenterDirective);\n\n protected readonly asideSlot: Signal<RtWorkspaceAsideDirective | undefined> = contentChild(RtWorkspaceAsideDirective);\n\n protected readonly resizing: Signal<boolean> = this.#resizing.asReadonly();\n\n protected readonly slotContext: IRtWorkspace.SlotContext = { $implicit: this };\n\n public readonly storageKey: InputSignal<string | null> = input<string | null>(null);\n\n public readonly hasActive: InputSignalWithTransform<boolean, BooleanInput> = input<boolean, BooleanInput>(false, {\n transform: booleanAttribute,\n });\n\n public readonly listMinWidth: InputSignalWithTransform<number, number | string> = input<number, number | string>(240, {\n transform: numberAttribute,\n });\n\n public readonly listMaxWidth: InputSignalWithTransform<number, number | string> = input<number, number | string>(480, {\n transform: numberAttribute,\n });\n\n public readonly listDefaultWidth: InputSignalWithTransform<number, number | string> = input<number, number | string>(320, {\n transform: numberAttribute,\n });\n\n public readonly asideMinWidth: InputSignalWithTransform<number, number | string> = input<number, number | string>(280, {\n transform: numberAttribute,\n });\n\n public readonly asideMaxWidth: InputSignalWithTransform<number, number | string> = input<number, number | string>(560, {\n transform: numberAttribute,\n });\n\n public readonly asideDefaultWidth: InputSignalWithTransform<number, number | string> = input<number, number | string>(360, {\n transform: numberAttribute,\n });\n\n public readonly centerMinWidth: InputSignalWithTransform<number, number | string> = input<number, number | string>(360, {\n transform: numberAttribute,\n });\n\n public readonly backClicked: OutputEmitterRef<void> = output<void>();\n\n public readonly listWidth: Signal<number> = computed((): number => this.#listWidthOverride() ?? this.listDefaultWidth());\n\n public readonly asideWidth: Signal<number> = computed((): number => this.#asideWidthOverride() ?? this.asideDefaultWidth());\n\n public readonly asideCollapsed: Signal<boolean> = this.#asideCollapsed.asReadonly();\n\n public readonly asideOpen: Signal<boolean> = this.#asideOpen.asReadonly();\n\n constructor() {\n effect((): void => {\n const key: string | null = this.storageKey();\n if (key === null || key === this.#restoredKey) {\n return;\n }\n this.#restoredKey = key;\n untracked((): void => this.#restoreFromStorage(key));\n });\n\n this.#destroyRef.onDestroy((): void => this.#stopDragging());\n }\n\n public toggleAsideCollapsed(): void {\n this.#asideCollapsed.update((collapsed: boolean): boolean => !collapsed);\n this.#persist();\n }\n\n public openAside(): void {\n this.#asideOpen.set(true);\n }\n\n public closeAside(): void {\n this.#asideOpen.set(false);\n }\n\n public toggleAside(): void {\n this.#asideOpen.update((open: boolean): boolean => !open);\n }\n\n protected onBackClicked(): void {\n this.closeAside();\n this.backClicked.emit();\n }\n\n protected onHandlePointerDown(event: PointerEvent, kind: IRtWorkspace.PanelKind): void {\n if (event.button !== 0) {\n return;\n }\n event.preventDefault();\n this.#dragState = {\n kind,\n startX: event.clientX,\n startWidth: kind === 'list' ? this.listWidth() : this.asideWidth(),\n };\n this.#resizing.set(true);\n\n const detachMove: () => void = this.#renderer.listen('document', 'pointermove', (moveEvent: PointerEvent): void =>\n this.#onDragMove(moveEvent)\n );\n const detachUp: () => void = this.#renderer.listen('document', 'pointerup', (): void => {\n this.#persist();\n this.#stopDragging();\n });\n this.#detachDragListeners = (): void => {\n detachMove();\n detachUp();\n };\n }\n\n protected onHandleKeydown(event: KeyboardEvent, kind: IRtWorkspace.PanelKind): void {\n let delta: number;\n if (event.key === 'ArrowRight') {\n delta = kind === 'list' ? KEYBOARD_STEP : -KEYBOARD_STEP;\n } else if (event.key === 'ArrowLeft') {\n delta = kind === 'list' ? -KEYBOARD_STEP : KEYBOARD_STEP;\n } else {\n return;\n }\n event.preventDefault();\n const current: number = kind === 'list' ? this.listWidth() : this.asideWidth();\n this.#applyWidth(kind, current + delta);\n this.#persist();\n }\n\n protected onHandleReset(kind: IRtWorkspace.PanelKind): void {\n const override: WritableSignal<number | null> = kind === 'list' ? this.#listWidthOverride : this.#asideWidthOverride;\n override.set(null);\n this.#persist();\n }\n\n #onDragMove(event: PointerEvent): void {\n const drag: IDragState | null = this.#dragState;\n if (drag === null) {\n return;\n }\n const dx: number = event.clientX - drag.startX;\n const rawWidth: number = drag.kind === 'list' ? drag.startWidth + dx : drag.startWidth - dx;\n this.#applyWidth(drag.kind, rawWidth);\n }\n\n #applyWidth(kind: IRtWorkspace.PanelKind, rawWidth: number): void {\n const override: WritableSignal<number | null> = kind === 'list' ? this.#listWidthOverride : this.#asideWidthOverride;\n override.set(this.#clampWidth(kind, rawWidth));\n }\n\n #clampWidth(kind: IRtWorkspace.PanelKind, rawWidth: number): number {\n const min: number = kind === 'list' ? this.listMinWidth() : this.asideMinWidth();\n const configMax: number = kind === 'list' ? this.listMaxWidth() : this.asideMaxWidth();\n // Место соседней панели вычитается, только когда она объявлена: без её слота ширина\n // соседки — число из умолчаний, а места она не занимает вовсе.\n const otherWidth: number = this.#occupiedWidth(kind === 'list' ? 'aside' : 'list');\n const hostWidth: number = this.#hostRef.nativeElement.clientWidth;\n const available: number = hostWidth > 0 ? hostWidth - otherWidth - this.centerMinWidth() : Number.POSITIVE_INFINITY;\n const max: number = Math.max(min, Math.min(configMax, available));\n return Math.round(Math.min(max, Math.max(min, rawWidth)));\n }\n\n /** Сколько ширины занимает панель: необъявленная не занимает ничего. */\n #occupiedWidth(kind: IRtWorkspace.PanelKind): number {\n if (kind === 'list') {\n return this.listSlot() ? this.listWidth() : 0;\n }\n\n return this.asideSlot() ? this.asideWidth() : 0;\n }\n\n #stopDragging(): void {\n this.#detachDragListeners?.();\n this.#detachDragListeners = null;\n this.#dragState = null;\n this.#resizing.set(false);\n }\n\n #restoreFromStorage(key: string): void {\n const stored: IRtWorkspace.PersistedState | null =\n this.#storage.getItem<IRtWorkspace.PersistedState>(`${STORAGE_PREFIX}${key}`) ?? null;\n if (stored === null || typeof stored !== 'object') {\n return;\n }\n if (typeof stored.listWidth === 'number') {\n this.#listWidthOverride.set(this.#clampWidth('list', stored.listWidth));\n }\n if (typeof stored.asideWidth === 'number') {\n this.#asideWidthOverride.set(this.#clampWidth('aside', stored.asideWidth));\n }\n this.#asideCollapsed.set(stored.asideCollapsed === true);\n }\n\n #persist(): void {\n const key: string | null = this.storageKey();\n if (key === null) {\n return;\n }\n const state: IRtWorkspace.PersistedState = {\n listWidth: this.listWidth(),\n asideWidth: this.asideWidth(),\n asideCollapsed: this.asideCollapsed(),\n };\n this.#storage.setItem(`${STORAGE_PREFIX}${key}`, state);\n }\n}\n","<ng-container rtBlock=\"rt-workspace\">\n @if (listSlot()) {\n <section rtElem=\"list\" qa-dataid=\"workspace-list\">\n <ng-container [ngTemplateOutlet]=\"listSlot()?.templateRef ?? null\" [ngTemplateOutletContext]=\"slotContext\" />\n </section>\n\n <div\n rtElem=\"handle\"\n qa-dataid=\"workspace-handle-list\"\n role=\"separator\"\n aria-orientation=\"vertical\"\n tabindex=\"0\"\n [attr.aria-label]=\"t().uiResizeList\"\n [rtMod]=\"{ list: true }\"\n [attr.aria-valuenow]=\"listWidth()\"\n [attr.aria-valuemin]=\"listMinWidth()\"\n [attr.aria-valuemax]=\"listMaxWidth()\"\n (pointerdown)=\"onHandlePointerDown($event, 'list')\"\n (dblclick)=\"onHandleReset('list')\"\n (keydown)=\"onHandleKeydown($event, 'list')\"></div>\n }\n\n <section rtElem=\"center\" qa-dataid=\"workspace-center\">\n @if (hasActive()) {\n <div rtElem=\"mobile-toolbar\">\n <rt-icon-button\n qa-dataid=\"workspace-back\"\n icon=\"arrow-left\"\n variant=\"secondary\"\n [ariaLabel]=\"t().uiBackToList\"\n [tooltip]=\"t().uiToList\"\n (clicked)=\"onBackClicked()\" />\n <rt-icon-button\n qa-dataid=\"workspace-open-details\"\n icon=\"info-circle\"\n variant=\"secondary\"\n [ariaLabel]=\"t().uiShowDetails\"\n [tooltip]=\"t().uiDetails\"\n (clicked)=\"openAside()\" />\n </div>\n }\n <ng-container [ngTemplateOutlet]=\"centerSlot()?.templateRef ?? null\" [ngTemplateOutletContext]=\"slotContext\" />\n </section>\n\n @if (asideSlot()) {\n <div\n rtElem=\"handle\"\n qa-dataid=\"workspace-handle-aside\"\n role=\"separator\"\n aria-orientation=\"vertical\"\n tabindex=\"0\"\n [attr.aria-label]=\"t().uiResizeDetails\"\n [rtMod]=\"{ aside: true }\"\n [attr.aria-valuenow]=\"asideWidth()\"\n [attr.aria-valuemin]=\"asideMinWidth()\"\n [attr.aria-valuemax]=\"asideMaxWidth()\"\n (pointerdown)=\"onHandlePointerDown($event, 'aside')\"\n (dblclick)=\"onHandleReset('aside')\"\n (keydown)=\"onHandleKeydown($event, 'aside')\"></div>\n\n <section rtElem=\"aside\" qa-dataid=\"workspace-aside\" [rtMod]=\"{ open: asideOpen() }\">\n <ng-container [ngTemplateOutlet]=\"asideSlot()?.templateRef ?? null\" [ngTemplateOutletContext]=\"slotContext\" />\n </section>\n }\n</ng-container>\n"],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -210,8 +210,10 @@
|
|
|
210
210
|
@include bp.place-max(1380px) {
|
|
211
211
|
/* Селектор из двух классов, а не одного: `.rt-icon` задаёт иконке
|
|
212
212
|
`display`, и порядок стилей двух компонентов кита между собой не
|
|
213
|
-
закреплён ничем.
|
|
214
|
-
|
|
213
|
+
закреплён ничем. Второй класс записан буквами: `&` внутри порога несёт
|
|
214
|
+
запасное условие страницы без каркаса, и второе `&` повторило бы его
|
|
215
|
+
внутри ссылки, где оно не совпадает никогда. */
|
|
216
|
+
&__link .rt-page-header__icon {
|
|
215
217
|
display: none;
|
|
216
218
|
}
|
|
217
219
|
}
|
|
@@ -28,7 +28,7 @@
|
|
|
28
28
|
## Главное, что нужно знать
|
|
29
29
|
|
|
30
30
|
**Дерево считает тот же модуль, что дерево вариантов у `rt-select` и `rt-multiselect`.** Строки,
|
|
31
|
-
листья, отметки ветвей, отбор по слову и боковые стрелки — функции `rt-
|
|
31
|
+
листья, отметки ветвей, отбор по слову и боковые стрелки — функции `rt-option-tree.ts` в ядре кита. Свою копию
|
|
32
32
|
логики дерево не держит: две копии разошлись бы на первой правке.
|
|
33
33
|
|
|
34
34
|
**Узлы не меняются никогда.** Выбор живёт в `value`, каждый клик даёт новый массив. В каскаде
|
|
@@ -56,7 +56,7 @@
|
|
|
56
56
|
- `--rt-ai-chat-content-max-width` (по умолчанию `100%`) становится боковым отступом `feed`,
|
|
57
57
|
`composer` и `disclaimer`: колонка стоит по центру беседы, полоса прокрутки ленты остаётся у её
|
|
58
58
|
края. `max-inline-size` на самой ленте увёл бы полосу прокрутки внутрь колонки.
|
|
59
|
-
- Подсветка совпадений поиска по беседам — `
|
|
59
|
+
- Подсветка совпадений поиска по беседам — `rtMatchParts` из ядра кита.
|
|
60
60
|
- Строки-превью пустого списка бесед — `emptyPreviewIcons`, по умолчанию `sparkle`, `bot`, `sparkle`:
|
|
61
61
|
беседы идут с ассистентом, а не с людьми. Вход уходит в `rt-thread-list` как есть.
|
|
62
62
|
- Ответ рисует внутренний `rt-ai-chat-answer` (папка `answer/`): без него шаблон организма
|
|
@@ -6,16 +6,30 @@ $rt-bp-md: 768px !default;
|
|
|
6
6
|
$rt-bp-lg: 1080px !default;
|
|
7
7
|
$rt-bp-xl: 1380px !default;
|
|
8
8
|
|
|
9
|
-
// Место страницы — контейнер с именем `rt-place
|
|
10
|
-
//
|
|
11
|
-
//
|
|
9
|
+
// Место страницы — контейнер с именем `rt-place`, его объявляет `rt-container`. Компонент внутри
|
|
10
|
+
// каркаса считает порог от его ширины. На странице без каркаса порог считается от окна: запасной
|
|
11
|
+
// `@media` стоит под предком `html:not(:has(.rt-container))`. Условие стоит предком, а не на самом
|
|
12
|
+
// узле, чтобы вложенные `&__элемент` в `@content` строились как раньше. Корень документа местом не
|
|
13
|
+
// объявляется: контейнер на корне или на `body` не даёт фону `body` растечься на всё окно. Имя
|
|
14
|
+
// записано буквами: линтер стилей не читает имя из переменной.
|
|
15
|
+
|
|
16
|
+
// Страница без каркаса: `:where` не добавляет условию специфичности.
|
|
17
|
+
$-no-place: ':where(html:not(:has(.rt-container)))';
|
|
12
18
|
|
|
13
19
|
// Порог по ширине места: `@include bp.place-max(bp.$rt-bp-md) { … }`. Окна и панели поверх
|
|
14
|
-
// экрана сюда не идут: они лежат вне места страницы и остаются на `@media`.
|
|
20
|
+
// экрана сюда не идут: они лежат вне места страницы и остаются на `@media`. Внутри порога `&`
|
|
21
|
+
// встречается в селекторе один раз: каждое `&` несёт запасное условие, и второе повторяет его
|
|
22
|
+
// внутри первого узла, где оно не совпадает никогда.
|
|
15
23
|
@mixin place-max($width) {
|
|
16
24
|
@container rt-place (width <= #{$width}) {
|
|
17
25
|
@content;
|
|
18
26
|
}
|
|
27
|
+
|
|
28
|
+
@media (width <= #{$width}) {
|
|
29
|
+
@include -on-page-without-place {
|
|
30
|
+
@content;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
19
33
|
}
|
|
20
34
|
|
|
21
35
|
// Шире порога по месту — пара к `place-max`.
|
|
@@ -23,4 +37,23 @@ $rt-bp-xl: 1380px !default;
|
|
|
23
37
|
@container rt-place (width > #{$width}) {
|
|
24
38
|
@content;
|
|
25
39
|
}
|
|
40
|
+
|
|
41
|
+
@media (width > #{$width}) {
|
|
42
|
+
@include -on-page-without-place {
|
|
43
|
+
@content;
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
// Внутри селектора условие встаёт предком родителя, в слое без селектора — предком содержимого.
|
|
49
|
+
@mixin -on-page-without-place {
|
|
50
|
+
@if & {
|
|
51
|
+
#{$-no-place} & {
|
|
52
|
+
@content;
|
|
53
|
+
}
|
|
54
|
+
} @else {
|
|
55
|
+
#{$-no-place} {
|
|
56
|
+
@content;
|
|
57
|
+
}
|
|
58
|
+
}
|
|
26
59
|
}
|
package/src/styles/_index.scss
CHANGED
|
@@ -43,10 +43,6 @@
|
|
|
43
43
|
// раскладку у себя, ради чего словарь и переехал в кит.
|
|
44
44
|
@forward './form';
|
|
45
45
|
|
|
46
|
-
// Запасное место страницы на корне документа: без него порог по месту у компонента вне
|
|
47
|
-
// `rt-container` не нашёл бы контейнера и не сработал.
|
|
48
|
-
@forward './place';
|
|
49
|
-
|
|
50
46
|
// Стили директивы кнопки: своего представления у директивы нет, поэтому её `.scss` не
|
|
51
47
|
// подключён ни одним `styleUrl`. Без этой строки потребитель, взявший `tokens.css` по
|
|
52
48
|
// инструкции README, получает `rtButton`, нарисованный браузерной кнопкой.
|
package/styles/tokens.css
CHANGED
|
@@ -6799,14 +6799,6 @@ html.rt-theme-dark.rt-preset-material {
|
|
|
6799
6799
|
}
|
|
6800
6800
|
}
|
|
6801
6801
|
}
|
|
6802
|
-
/* Корень документа — запасное место страницы. Компонент кита считает пороги от ближайшего
|
|
6803
|
-
места по имени: внутри `rt-container` от его ширины, вне его от корня, а ширина корня равна
|
|
6804
|
-
окну. Так потребитель без контейнера видит пороги окна, как раньше. Объявление стоит вне
|
|
6805
|
-
слоя, как и свойства на корне: потребитель перебивает его порядком. */
|
|
6806
|
-
:root {
|
|
6807
|
-
container: rt-place/inline-size;
|
|
6808
|
-
}
|
|
6809
|
-
|
|
6810
6802
|
@layer rt-kit.components {
|
|
6811
6803
|
.rt-button {
|
|
6812
6804
|
/* Высота приходит общей шкалой контролов, а не своим числом: кнопка, поле и
|