@oicl/openbridge-webcomponents 2.0.0-next.170 → 2.0.0-next.172

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.
Files changed (100) hide show
  1. package/bundle/openbridge-webcomponents.bundle.js +974 -511
  2. package/bundle/openbridge-webcomponents.bundle.js.map +1 -1
  3. package/custom-elements.json +1853 -377
  4. package/dist/ar/poi/poi-aton.d.ts +1 -0
  5. package/dist/ar/poi/poi-aton.d.ts.map +1 -1
  6. package/dist/ar/poi/poi-aton.js +1 -0
  7. package/dist/ar/poi/poi-aton.js.map +1 -1
  8. package/dist/ar/poi/poi-base.d.ts +39 -5
  9. package/dist/ar/poi/poi-base.d.ts.map +1 -1
  10. package/dist/ar/poi/poi-base.js +108 -37
  11. package/dist/ar/poi/poi-base.js.map +1 -1
  12. package/dist/ar/poi/poi-data.d.ts +1 -0
  13. package/dist/ar/poi/poi-data.d.ts.map +1 -1
  14. package/dist/ar/poi/poi-data.js +1 -0
  15. package/dist/ar/poi/poi-data.js.map +1 -1
  16. package/dist/ar/poi/poi-vessel.d.ts +1 -0
  17. package/dist/ar/poi/poi-vessel.d.ts.map +1 -1
  18. package/dist/ar/poi/poi-vessel.js +1 -0
  19. package/dist/ar/poi/poi-vessel.js.map +1 -1
  20. package/dist/ar/poi/poi.d.ts +4 -12
  21. package/dist/ar/poi/poi.d.ts.map +1 -1
  22. package/dist/ar/poi/poi.js +6 -72
  23. package/dist/ar/poi/poi.js.map +1 -1
  24. package/dist/ar/poi-button/poi-button.d.ts +6 -2
  25. package/dist/ar/poi-button/poi-button.d.ts.map +1 -1
  26. package/dist/ar/poi-button/poi-button.js +10 -1
  27. package/dist/ar/poi-button/poi-button.js.map +1 -1
  28. package/dist/ar/poi-card/poi-card.d.ts +12 -1
  29. package/dist/ar/poi-card/poi-card.d.ts.map +1 -1
  30. package/dist/ar/poi-card/poi-card.js +4 -1
  31. package/dist/ar/poi-card/poi-card.js.map +1 -1
  32. package/dist/ar/poi-controller/poi-controller.d.ts +45 -1
  33. package/dist/ar/poi-controller/poi-controller.d.ts.map +1 -1
  34. package/dist/ar/poi-controller/poi-controller.js +72 -14
  35. package/dist/ar/poi-controller/poi-controller.js.map +1 -1
  36. package/dist/ar/poi-group/poi-group.d.ts +28 -5
  37. package/dist/ar/poi-group/poi-group.d.ts.map +1 -1
  38. package/dist/ar/poi-group/poi-group.js +50 -7
  39. package/dist/ar/poi-group/poi-group.js.map +1 -1
  40. package/dist/ar/poi-layer/poi-layer.css.js +69 -18
  41. package/dist/ar/poi-layer/poi-layer.css.js.map +1 -1
  42. package/dist/ar/poi-layer/poi-layer.d.ts +64 -5
  43. package/dist/ar/poi-layer/poi-layer.d.ts.map +1 -1
  44. package/dist/ar/poi-layer/poi-layer.js +173 -39
  45. package/dist/ar/poi-layer/poi-layer.js.map +1 -1
  46. package/dist/ar/poi-layer-stack/poi-layer-stack.d.ts +82 -7
  47. package/dist/ar/poi-layer-stack/poi-layer-stack.d.ts.map +1 -1
  48. package/dist/ar/poi-layer-stack/poi-layer-stack.js +172 -100
  49. package/dist/ar/poi-layer-stack/poi-layer-stack.js.map +1 -1
  50. package/dist/ar/poi-projection/poi-projection.d.ts +88 -0
  51. package/dist/ar/poi-projection/poi-projection.d.ts.map +1 -0
  52. package/dist/ar/poi-projection/poi-projection.js +90 -0
  53. package/dist/ar/poi-projection/poi-projection.js.map +1 -0
  54. package/dist/automation/automation-button/abstract-automation-button-motorized.d.ts +11 -1
  55. package/dist/automation/automation-button/abstract-automation-button-motorized.d.ts.map +1 -1
  56. package/dist/automation/automation-button/abstract-automation-button-motorized.js +14 -4
  57. package/dist/automation/automation-button/abstract-automation-button-motorized.js.map +1 -1
  58. package/dist/automation/automation-button/abstract-automation-button-squared.d.ts +25 -1
  59. package/dist/automation/automation-button/abstract-automation-button-squared.d.ts.map +1 -1
  60. package/dist/automation/automation-button/abstract-automation-button-squared.js +27 -3
  61. package/dist/automation/automation-button/abstract-automation-button-squared.js.map +1 -1
  62. package/dist/automation/automation-button/abstract-automation-button-storybook-helpers.d.ts +12 -0
  63. package/dist/automation/automation-button/abstract-automation-button-storybook-helpers.d.ts.map +1 -1
  64. package/dist/automation/automation-button/abstract-automation-button-storybook-helpers.js +8 -0
  65. package/dist/automation/automation-button/abstract-automation-button-storybook-helpers.js.map +1 -1
  66. package/dist/automation/bipolar-transistor/bipolar-transistor.js +4 -4
  67. package/dist/automation/bipolar-transistor/bipolar-transistor.js.map +1 -1
  68. package/dist/automation/capacitor/capacitor.js +4 -4
  69. package/dist/automation/capacitor/capacitor.js.map +1 -1
  70. package/dist/automation/converter/converter.js +4 -4
  71. package/dist/automation/converter/converter.js.map +1 -1
  72. package/dist/automation/damper/damper.js +1 -1
  73. package/dist/automation/damper/damper.js.map +1 -1
  74. package/dist/automation/diodes/diodes.js +6 -6
  75. package/dist/automation/diodes/diodes.js.map +1 -1
  76. package/dist/automation/fan/fan.js +1 -1
  77. package/dist/automation/fan/fan.js.map +1 -1
  78. package/dist/automation/filter/filter.js +4 -4
  79. package/dist/automation/filter/filter.js.map +1 -1
  80. package/dist/automation/ground/ground.js +3 -3
  81. package/dist/automation/ground/ground.js.map +1 -1
  82. package/dist/automation/logic/logic.js +6 -6
  83. package/dist/automation/logic/logic.js.map +1 -1
  84. package/dist/automation/mosfet/mosfet.js +8 -8
  85. package/dist/automation/mosfet/mosfet.js.map +1 -1
  86. package/dist/automation/motor/motor.js +2 -2
  87. package/dist/automation/motor/motor.js.map +1 -1
  88. package/dist/automation/pump/pump.js +2 -2
  89. package/dist/automation/pump/pump.js.map +1 -1
  90. package/dist/automation/resistor/resistor.js +5 -5
  91. package/dist/automation/resistor/resistor.js.map +1 -1
  92. package/dist/automation/router/router.js +2 -2
  93. package/dist/automation/router/router.js.map +1 -1
  94. package/dist/automation/source/source.js +5 -5
  95. package/dist/automation/source/source.js.map +1 -1
  96. package/dist/automation/switch/switch.js +4 -4
  97. package/dist/automation/switch/switch.js.map +1 -1
  98. package/dist/automation/transformer/transformer.js +2 -2
  99. package/dist/automation/transformer/transformer.js.map +1 -1
  100. package/package.json +2 -2
@@ -1 +1 @@
1
- {"version":3,"file":"poi-button.js","names":[],"sources":["../../../src/ar/poi-button/poi-button.ts"],"sourcesContent":["import {LitElement, html, nothing, unsafeCSS} from 'lit';\nimport {property} from 'lit/decorators.js';\nimport compentStyle from './poi-button.css?inline';\nimport {classMap} from 'lit/directives/class-map.js';\nimport {customElement} from '../../decorator.js';\nimport '../building-blocks/poi-header/poi-header.js';\nimport {\n ObcPoiHeaderType,\n ObcPoiHeaderState,\n} from '../building-blocks/poi-header/poi-header.js';\nimport {\n ObcPoiObjectState,\n ObcPoiObjectStyle,\n ObcPoiObjectType,\n} from '../poi-object/poi-object.js';\nimport {\n ObcPoiSelectionFrameState,\n ObcPoiSelectionFrameType,\n} from '../building-blocks/poi-selection-frame/poi-selection-frame.js';\nimport '../building-blocks/poi-selection-frame/poi-selection-frame.js';\n\nexport enum ObcPoiButtonType {\n Button = 'button',\n Enhanced = 'enhanced',\n}\n\nexport enum ObcPoiButtonLayout {\n Anchored = 'anchored',\n Inline = 'inline',\n}\n\nexport enum ObcPoiButtonState {\n Enabled = 'enabled',\n Caution = 'caution',\n Warning = 'warning',\n Alarm = 'alarm',\n LevelCritical = 'level-critical',\n LevelHigh = 'level-high',\n LevelMedium = 'level-medium',\n LevelLow = 'level-low',\n LevelDiagnostic = 'level-diagnostic',\n}\n\nexport enum PoiButtonVisualState {\n Unchecked = 'unchecked',\n Checked = 'checked',\n Activated = 'activated',\n Overlapped = 'overlapped',\n}\n\nconst BUTTON_TOUCH_TARGET_PX = 48;\nconst ENHANCED_TOUCH_TARGET_PX = 64;\nconst DEFAULT_ENHANCED_BOX_AREA_THRESHOLD_PX =\n (BUTTON_TOUCH_TARGET_PX * BUTTON_TOUCH_TARGET_PX +\n ENHANCED_TOUCH_TARGET_PX * ENHANCED_TOUCH_TARGET_PX) /\n 2;\n\nexport function resolvePoiButtonTypeFromBoxSize(\n boxWidthPx: number | null | undefined,\n boxHeightPx: number | null | undefined,\n enhancedAreaThresholdPx: number = DEFAULT_ENHANCED_BOX_AREA_THRESHOLD_PX\n): ObcPoiButtonType {\n const width = Number(boxWidthPx);\n const height = Number(boxHeightPx);\n if (\n !Number.isFinite(width) ||\n !Number.isFinite(height) ||\n width <= 0 ||\n height <= 0\n ) {\n return ObcPoiButtonType.Button;\n }\n\n const area = width * height;\n return area >= enhancedAreaThresholdPx\n ? ObcPoiButtonType.Enhanced\n : ObcPoiButtonType.Button;\n}\n\nexport interface ObcPoiButtonDataItem {\n value: string;\n label: string;\n unit: string;\n}\n\n/**\n * `<obc-poi-button>` - Marker button component that renders an icon target with optional header and data rows.\n *\n * ## Overview\n * Use this component when you need a button-style marker that can show stateful framing and optional metric rows.\n * Keywords/synonyms: marker button, target button, icon target, POI button.\n *\n * ## Features/Variants\n * - `type` (default `button`): `button` or `enhanced` size.\n * - `layout` (default `anchored`): `anchored` or `inline`.\n * - `value` (default `unchecked`): `unchecked`, `checked`, `activated`, `overlapped`.\n * - `overlapOpaque` (default `false`): controls overlapped opacity mode (`false` = translucent, `true` = opaque).\n * - `state` (default `enabled`): `enabled`, `caution`, `warning`, `alarm`, `level-critical`, `level-high`, `level-medium`, `level-low`, `level-diagnostic`.\n * - `selected` (default `false`): shows selection frame in anchored layout.\n * - `relativeDirection` (default `0`): rotates default-slot icon content in degrees.\n * - `data` (default `[]`): when non-empty, renders value/label/unit rows.\n * - `hasHeader` + `header` slot: renders a header area and syncs slotted `obc-poi-header` state.\n * - `hasRelation` (default `false`): enables optional relation content in data mode.\n * - `inExpandedGroup` (default `false`): applies `expanded` CSS class.\n * - TODO(designer): Confirm intended UX semantics for `inExpandedGroup` beyond styling.\n *\n * ## Usage Guidelines\n * - Use `layout=\"anchored\"` for standalone marker buttons.\n * - Use `layout=\"inline\"` when this component is embedded in a larger marker composition.\n * - Provide `data` for metric display variants.\n * - Enable `hasRelation` only when relation slot content is provided.\n *\n * ## Slots/Content\n * - Default slot: Icon/content rendered inside `obc-poi-object`.\n * - `header`: Optional header content rendered above the marker body.\n * - `relation`: Optional relation icon/content rendered when `hasRelation` is true in data mode.\n *\n * ## Events\n * This component emits no custom events. A standard `click` bubbles from the\n * internal `<button>` (`onClick` in the framework wrappers).\n *\n * ## Best Practices\n * - Keep `value`, `state`, and `selected` synchronized to avoid conflicting visual states.\n * - Prefer enum values for `type`, `layout`, `state`, and `value`.\n *\n * ## Example\n * ```html\n * <obc-poi-button type=\"button\" layout=\"anchored\" value=\"checked\" selected>\n * <obi-placeholder></obi-placeholder>\n * <obc-poi-header slot=\"header\" content=\"1\"></obc-poi-header>\n * </obc-poi-button>\n * ```\n *\n * @slot - Icon/content rendered inside `obc-poi-object`.\n * @slot header - Optional header content rendered above the marker body.\n * @slot relation - Optional relation icon/content in data mode when `hasRelation` is true.\n * @fires click - Fired when the marker is clicked.\n * @experimental\n */\n@customElement('obc-poi-button')\nexport class ObcPoiButton extends LitElement {\n @property({type: Number}) relativeDirection = 0;\n @property({type: Boolean}) selected = false;\n @property({type: String}) layout: ObcPoiButtonLayout =\n ObcPoiButtonLayout.Anchored;\n @property({type: Boolean})\n hasHeader = false;\n @property({type: String})\n state: ObcPoiButtonState = ObcPoiButtonState.Enabled;\n @property({type: String})\n value: PoiButtonVisualState = PoiButtonVisualState.Unchecked;\n @property({type: Boolean})\n overlapOpaque = false;\n @property({type: String}) type = ObcPoiButtonType.Button;\n @property({type: Boolean}) inExpandedGroup = false;\n @property({type: Array, attribute: false}) data: ObcPoiButtonDataItem[] = [];\n @property({type: Boolean}) hasRelation = false;\n @property({type: String, attribute: 'header-content'}) headerContent = '';\n private headerContentObserver?: MutationObserver;\n\n override connectedCallback() {\n super.connectedCallback();\n this.setupHeaderContentObserver();\n }\n\n override disconnectedCallback() {\n super.disconnectedCallback();\n this.headerContentObserver?.disconnect();\n this.headerContentObserver = undefined;\n }\n\n private setupHeaderContentObserver() {\n this.headerContentObserver?.disconnect();\n this.headerContentObserver = new MutationObserver((mutations) => {\n for (const mutation of mutations) {\n if (mutation.type === 'childList') {\n this.requestUpdate();\n return;\n }\n if (\n mutation.type === 'attributes' &&\n mutation.target instanceof HTMLElement &&\n mutation.target.getAttribute('slot') === 'header'\n ) {\n this.requestUpdate();\n return;\n }\n }\n });\n this.headerContentObserver.observe(this, {\n childList: true,\n subtree: true,\n attributes: true,\n attributeFilter: ['slot'],\n });\n }\n\n get hasData(): boolean {\n return this.data.length > 0;\n }\n\n private get alertClassSuffix(): string {\n if (this.state === ObcPoiButtonState.Enabled) {\n return 'none';\n }\n return this.state;\n }\n\n private get resolvedHeaderState(): ObcPoiHeaderState {\n switch (this.state) {\n case ObcPoiButtonState.Caution:\n return ObcPoiHeaderState.Caution;\n case ObcPoiButtonState.Warning:\n return ObcPoiHeaderState.Warning;\n case ObcPoiButtonState.Alarm:\n return ObcPoiHeaderState.Alarm;\n case ObcPoiButtonState.LevelCritical:\n return ObcPoiHeaderState.LevelCritical;\n case ObcPoiButtonState.LevelHigh:\n return ObcPoiHeaderState.LevelHigh;\n case ObcPoiButtonState.LevelMedium:\n return ObcPoiHeaderState.LevelMedium;\n case ObcPoiButtonState.LevelLow:\n return ObcPoiHeaderState.LevelLow;\n case ObcPoiButtonState.LevelDiagnostic:\n return ObcPoiHeaderState.LevelDiagnostic;\n case ObcPoiButtonState.Enabled:\n default:\n return ObcPoiHeaderState.Selected;\n }\n }\n\n private get hasHeaderContent(): boolean {\n return this.querySelector('[slot=\"header\"]') !== null;\n }\n\n private get hasGeneratedHeaderContent(): boolean {\n return this.headerContent.trim().length > 0;\n }\n\n private syncSlottedHeaderState() {\n const headerSlot = this.renderRoot.querySelector(\n 'slot[name=\"header\"]'\n ) as HTMLSlotElement | null;\n if (!headerSlot) {\n return;\n }\n\n const state = this.resolvedHeaderState;\n const assigned = headerSlot.assignedElements({flatten: true});\n const headers = new Set<HTMLElement>();\n\n for (const element of assigned) {\n if (element.matches('obc-poi-header')) {\n headers.add(element as HTMLElement);\n }\n for (const nested of element.querySelectorAll('obc-poi-header')) {\n headers.add(nested as HTMLElement);\n }\n }\n\n for (const header of headers) {\n (header as {state?: string}).state = state;\n header.setAttribute('state', state);\n }\n }\n\n private handleHeaderSlotChange = () => {\n this.syncSlottedHeaderState();\n };\n\n protected override updated(_changedProperties: Map<string, unknown>) {\n this.syncSlottedHeaderState();\n }\n\n protected renderHeader() {\n if (\n !this.hasHeader ||\n (!this.hasHeaderContent && !this.hasGeneratedHeaderContent)\n ) {\n return nothing;\n }\n\n return html`\n <div class=\"id-label\">\n ${\n this.hasHeaderContent\n ? html`<slot\n name=\"header\"\n @slotchange=${this.handleHeaderSlotChange}\n ></slot>`\n : html`<obc-poi-header\n .content=${this.headerContent}\n .state=${this.resolvedHeaderState}\n .type=${ObcPoiHeaderType.Id}\n ></obc-poi-header>`\n }\n </div>\n `;\n }\n\n protected get poiObjectType(): ObcPoiObjectType {\n return this.type === ObcPoiButtonType.Enhanced\n ? ObcPoiObjectType.Large\n : ObcPoiObjectType.Regular;\n }\n\n protected get poiObjectState(): ObcPoiObjectState {\n if (this.value === PoiButtonVisualState.Overlapped) {\n return ObcPoiObjectState.Overlapped;\n }\n\n if (this.hasData) {\n if (this.value === PoiButtonVisualState.Activated) {\n return ObcPoiObjectState.Activated;\n }\n if (this.value === PoiButtonVisualState.Checked) {\n return ObcPoiObjectState.StaticChecked;\n }\n return ObcPoiObjectState.StaticUnchecked;\n }\n\n if (this.value === PoiButtonVisualState.Activated) {\n return ObcPoiObjectState.Activated;\n }\n if (this.value === PoiButtonVisualState.Checked) {\n return ObcPoiObjectState.Checked;\n }\n\n return ObcPoiObjectState.Unchecked;\n }\n\n override render() {\n if (this.hasData) {\n return this.renderWithData();\n }\n return this.renderButton();\n }\n\n protected renderPoiObject() {\n return html`\n <obc-poi-object\n class=\"poi-object\"\n .type=${this.poiObjectType}\n .objectStyle=${ObcPoiObjectStyle.Regular}\n .state=${this.poiObjectState}\n .interactive=${false}\n >\n <span\n class=\"icon\"\n style=\"transform: rotate(${this.relativeDirection}deg);\"\n >\n <slot></slot>\n </span>\n </obc-poi-object>\n `;\n }\n\n protected renderButton() {\n return html`\n <button\n type=\"button\"\n class=${classMap({\n wrapper: true,\n selected: this.selected,\n [`alert-${this.alertClassSuffix}`]: true,\n [`type-${this.type}`]: true,\n [`value-${this.value}`]: true,\n [`layout-${this.layout}`]: true,\n 'overlap-opaque': this.overlapOpaque,\n expanded: this.inExpandedGroup,\n })}\n >\n ${this.renderHeader()}\n <div class=\"button-wrapper\">\n ${this.renderSelectionFrame()} ${this.renderPoiObject()}\n <div class=\"alert-ring\"></div>\n </div>\n </button>\n `;\n }\n\n protected renderWithData() {\n return html`\n <button\n type=\"button\"\n class=${classMap({\n wrapper: true,\n 'has-data': true,\n selected: this.selected,\n 'has-header':\n this.hasHeader &&\n (this.hasHeaderContent || this.hasGeneratedHeaderContent),\n [`alert-${this.alertClassSuffix}`]: true,\n [`type-${this.type}`]: true,\n [`value-${this.value}`]: true,\n [`layout-${this.layout}`]: true,\n 'overlap-opaque': this.overlapOpaque,\n expanded: this.inExpandedGroup,\n })}\n >\n <div class=\"visible-wrapper\"></div>\n ${this.renderHeader()}\n <div class=\"data-wrapper\">\n ${this.data.map(\n (item) =>\n html`<div class=\"data\">\n <div class=\"value\">${item.value}</div>\n <div class=\"label\">${item.label}</div>\n <div class=\"unit\">${item.unit}</div>\n </div>`\n )}\n </div>\n <div class=\"button-wrapper\">\n ${this.renderSelectionFrame()} ${this.renderPoiObject()}\n </div>\n ${\n this.hasRelation\n ? html`<div class=\"relation-wrapper\" part=\"relation-wrapper\">\n <slot name=\"relation\" class=\"relation\" part=\"relation\"></slot>\n </div>`\n : nothing\n }\n <div class=\"alert-ring\"></div>\n </button>\n `;\n }\n\n protected get selectionFrameType(): ObcPoiSelectionFrameType {\n return this.type === ObcPoiButtonType.Enhanced\n ? ObcPoiSelectionFrameType.Enhanced\n : ObcPoiSelectionFrameType.Button;\n }\n\n protected get selectionFrameState(): ObcPoiSelectionFrameState {\n return this.state === ObcPoiButtonState.Enabled\n ? ObcPoiSelectionFrameState.Regular\n : ObcPoiSelectionFrameState.Alert;\n }\n\n protected renderSelectionFrame() {\n if (!this.selected || this.layout === ObcPoiButtonLayout.Inline) {\n return nothing;\n }\n\n return html`\n <obc-poi-selection-frame\n class=\"selection-frame\"\n .type=${this.selectionFrameType}\n .state=${this.selectionFrameState}\n ></obc-poi-selection-frame>\n `;\n }\n\n static override styles = unsafeCSS(compentStyle);\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'obc-poi-button': ObcPoiButton;\n }\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"poi-button.js","names":[],"sources":["../../../src/ar/poi-button/poi-button.ts"],"sourcesContent":["import {LitElement, html, nothing, unsafeCSS} from 'lit';\nimport {property} from 'lit/decorators.js';\nimport compentStyle from './poi-button.css?inline';\nimport {classMap} from 'lit/directives/class-map.js';\nimport {customElement} from '../../decorator.js';\nimport '../building-blocks/poi-header/poi-header.js';\nimport {\n ObcPoiHeaderType,\n ObcPoiHeaderState,\n} from '../building-blocks/poi-header/poi-header.js';\nimport {\n ObcPoiObjectState,\n ObcPoiObjectStyle,\n ObcPoiObjectType,\n} from '../poi-object/poi-object.js';\nimport {\n ObcPoiSelectionFrameState,\n ObcPoiSelectionFrameType,\n} from '../building-blocks/poi-selection-frame/poi-selection-frame.js';\nimport '../building-blocks/poi-selection-frame/poi-selection-frame.js';\n\nexport enum ObcPoiButtonType {\n Button = 'button',\n Enhanced = 'enhanced',\n}\n\nexport enum ObcPoiButtonLayout {\n Anchored = 'anchored',\n Inline = 'inline',\n}\n\nexport enum ObcPoiButtonState {\n Enabled = 'enabled',\n Caution = 'caution',\n Warning = 'warning',\n Alarm = 'alarm',\n LevelCritical = 'level-critical',\n LevelHigh = 'level-high',\n LevelMedium = 'level-medium',\n LevelLow = 'level-low',\n LevelDiagnostic = 'level-diagnostic',\n}\n\nexport enum PoiButtonVisualState {\n Unchecked = 'unchecked',\n Checked = 'checked',\n Activated = 'activated',\n Overlapped = 'overlapped',\n}\n\nconst BUTTON_TOUCH_TARGET_PX = 48;\nconst ENHANCED_TOUCH_TARGET_PX = 64;\nconst DEFAULT_ENHANCED_BOX_AREA_THRESHOLD_PX =\n (BUTTON_TOUCH_TARGET_PX * BUTTON_TOUCH_TARGET_PX +\n ENHANCED_TOUCH_TARGET_PX * ENHANCED_TOUCH_TARGET_PX) /\n 2;\n\nexport function resolvePoiButtonTypeFromBoxSize(\n boxWidthPx: number | null | undefined,\n boxHeightPx: number | null | undefined,\n enhancedAreaThresholdPx: number = DEFAULT_ENHANCED_BOX_AREA_THRESHOLD_PX\n): ObcPoiButtonType {\n const width = Number(boxWidthPx);\n const height = Number(boxHeightPx);\n if (\n !Number.isFinite(width) ||\n !Number.isFinite(height) ||\n width <= 0 ||\n height <= 0\n ) {\n return ObcPoiButtonType.Button;\n }\n\n const area = width * height;\n return area >= enhancedAreaThresholdPx\n ? ObcPoiButtonType.Enhanced\n : ObcPoiButtonType.Button;\n}\n\nexport interface ObcPoiButtonDataItem {\n value: string;\n label: string;\n unit: string;\n}\n\n/**\n * `<obc-poi-button>` - Marker button component that renders an icon target with optional header and data rows.\n *\n * ## Overview\n * Use this component when you need a button-style marker that can show stateful framing and optional metric rows.\n * Keywords/synonyms: marker button, target button, icon target, POI button.\n *\n * ## Features/Variants\n * - `type` (default `button`): `button` or `enhanced` size.\n * - `layout` (default `anchored`): `anchored` or `inline`.\n * - `value` (default `unchecked`): `unchecked`, `checked`, `activated`, `overlapped`.\n * - `overlapOpaque` (default `false`): controls overlapped opacity mode (`false` = translucent, `true` = opaque).\n * - `state` (default `enabled`): `enabled`, `caution`, `warning`, `alarm`, `level-critical`, `level-high`, `level-medium`, `level-low`, `level-diagnostic`.\n * - `selected` (default `false`): shows selection frame in anchored layout.\n * - `relativeDirection` (default `0`): rotates default-slot icon content in degrees.\n * - `data` (default `[]`): when non-empty, renders value/label/unit rows.\n * - `hasHeader` + `header` slot: renders a header area and syncs slotted `obc-poi-header` state.\n * - `hasRelation` (default `false`): enables optional relation content in data mode.\n * - `inExpandedGroup` (default `false`): expanded-group presentation state, applied by the owning group composition during expand/collapse orchestration; consumers should not set it directly.\n *\n * ## Usage Guidelines\n * - Use `layout=\"anchored\"` for standalone marker buttons.\n * - Use `layout=\"inline\"` when this component is embedded in a larger marker composition.\n * - Provide `data` for metric display variants.\n * - Enable `hasRelation` only when relation slot content is provided.\n *\n * ## Slots/Content\n * - Default slot: Icon/content rendered inside `obc-poi-object`.\n * - `header`: Optional header content rendered above the marker body.\n * - `relation`: Optional relation icon/content rendered when `hasRelation` is true in data mode.\n *\n * ## Events\n * This component emits no custom events. A standard `click` bubbles from the\n * internal `<button>` (`onClick` in the framework wrappers).\n *\n * ## Best Practices\n * - Keep `value`, `state`, and `selected` synchronized to avoid conflicting visual states.\n * - Prefer enum values for `type`, `layout`, `state`, and `value`.\n *\n * ## Example\n * ```html\n * <obc-poi-button type=\"button\" layout=\"anchored\" value=\"checked\" selected>\n * <obi-placeholder></obi-placeholder>\n * <obc-poi-header slot=\"header\" content=\"1\"></obc-poi-header>\n * </obc-poi-button>\n * ```\n *\n * @property inExpandedGroup - Expanded-group presentation state, applied by the owning group composition\n * while the button is shown inside an expanded `obc-poi-group` and during\n * its collapse animations. Consumers should not set it directly.\n * @slot - Icon/content rendered inside `obc-poi-object`.\n * @slot header - Optional header content rendered above the marker body.\n * @slot relation - Optional relation icon/content in data mode when `hasRelation` is true.\n * @fires click - Fired when the marker is clicked.\n * @experimental\n */\n@customElement('obc-poi-button')\nexport class ObcPoiButton extends LitElement {\n @property({type: Number}) relativeDirection = 0;\n @property({type: Boolean}) selected = false;\n @property({type: String}) layout: ObcPoiButtonLayout =\n ObcPoiButtonLayout.Anchored;\n @property({type: Boolean})\n hasHeader = false;\n @property({type: String})\n state: ObcPoiButtonState = ObcPoiButtonState.Enabled;\n @property({type: String})\n value: PoiButtonVisualState = PoiButtonVisualState.Unchecked;\n @property({type: Boolean})\n overlapOpaque = false;\n @property({type: String}) type = ObcPoiButtonType.Button;\n @property({type: Boolean}) inExpandedGroup = false;\n @property({type: Array, attribute: false}) data: ObcPoiButtonDataItem[] = [];\n @property({type: Boolean}) hasRelation = false;\n @property({type: String, attribute: 'header-content'}) headerContent = '';\n private headerContentObserver?: MutationObserver;\n\n // Forwarding slots from an outer shadow tree (`<slot name=\"header\"\n // slot=\"header\">` rendered by obc-poi / PoiBase variants) fire\n // `slotchange` that bubbles through this element; re-render so\n // `hasHeaderContent` re-evaluates the forwarded assignment.\n private handleLightSlotChange = () => {\n this.requestUpdate();\n this.syncSlottedHeaderState();\n };\n\n override connectedCallback() {\n super.connectedCallback();\n this.addEventListener('slotchange', this.handleLightSlotChange);\n this.setupHeaderContentObserver();\n }\n\n override disconnectedCallback() {\n super.disconnectedCallback();\n this.removeEventListener('slotchange', this.handleLightSlotChange);\n this.headerContentObserver?.disconnect();\n this.headerContentObserver = undefined;\n }\n\n private setupHeaderContentObserver() {\n this.headerContentObserver?.disconnect();\n this.headerContentObserver = new MutationObserver((mutations) => {\n for (const mutation of mutations) {\n if (mutation.type === 'childList') {\n this.requestUpdate();\n return;\n }\n if (\n mutation.type === 'attributes' &&\n mutation.target instanceof HTMLElement &&\n mutation.target.getAttribute('slot') === 'header'\n ) {\n this.requestUpdate();\n return;\n }\n }\n });\n this.headerContentObserver.observe(this, {\n childList: true,\n subtree: true,\n attributes: true,\n attributeFilter: ['slot'],\n });\n }\n\n get hasData(): boolean {\n return this.data.length > 0;\n }\n\n private get alertClassSuffix(): string {\n if (this.state === ObcPoiButtonState.Enabled) {\n return 'none';\n }\n return this.state;\n }\n\n private get resolvedHeaderState(): ObcPoiHeaderState {\n switch (this.state) {\n case ObcPoiButtonState.Caution:\n return ObcPoiHeaderState.Caution;\n case ObcPoiButtonState.Warning:\n return ObcPoiHeaderState.Warning;\n case ObcPoiButtonState.Alarm:\n return ObcPoiHeaderState.Alarm;\n case ObcPoiButtonState.LevelCritical:\n return ObcPoiHeaderState.LevelCritical;\n case ObcPoiButtonState.LevelHigh:\n return ObcPoiHeaderState.LevelHigh;\n case ObcPoiButtonState.LevelMedium:\n return ObcPoiHeaderState.LevelMedium;\n case ObcPoiButtonState.LevelLow:\n return ObcPoiHeaderState.LevelLow;\n case ObcPoiButtonState.LevelDiagnostic:\n return ObcPoiHeaderState.LevelDiagnostic;\n case ObcPoiButtonState.Enabled:\n default:\n return ObcPoiHeaderState.Selected;\n }\n }\n\n private get hasHeaderContent(): boolean {\n for (const child of this.querySelectorAll('[slot=\"header\"]')) {\n if (child instanceof HTMLSlotElement) {\n if (child.assignedElements({flatten: true}).length > 0) {\n return true;\n }\n } else {\n return true;\n }\n }\n return false;\n }\n\n private get hasGeneratedHeaderContent(): boolean {\n return this.headerContent.trim().length > 0;\n }\n\n private syncSlottedHeaderState() {\n const headerSlot = this.renderRoot.querySelector(\n 'slot[name=\"header\"]'\n ) as HTMLSlotElement | null;\n if (!headerSlot) {\n return;\n }\n\n const state = this.resolvedHeaderState;\n const assigned = headerSlot.assignedElements({flatten: true});\n const headers = new Set<HTMLElement>();\n\n for (const element of assigned) {\n if (element.matches('obc-poi-header')) {\n headers.add(element as HTMLElement);\n }\n for (const nested of element.querySelectorAll('obc-poi-header')) {\n headers.add(nested as HTMLElement);\n }\n }\n\n for (const header of headers) {\n (header as {state?: string}).state = state;\n header.setAttribute('state', state);\n }\n }\n\n private handleHeaderSlotChange = () => {\n this.syncSlottedHeaderState();\n };\n\n protected override updated(_changedProperties: Map<string, unknown>) {\n this.syncSlottedHeaderState();\n }\n\n protected renderHeader() {\n if (\n !this.hasHeader ||\n (!this.hasHeaderContent && !this.hasGeneratedHeaderContent)\n ) {\n return nothing;\n }\n\n return html`\n <div class=\"id-label\">\n ${\n this.hasHeaderContent\n ? html`<slot\n name=\"header\"\n @slotchange=${this.handleHeaderSlotChange}\n ></slot>`\n : html`<obc-poi-header\n .content=${this.headerContent}\n .state=${this.resolvedHeaderState}\n .type=${ObcPoiHeaderType.Id}\n ></obc-poi-header>`\n }\n </div>\n `;\n }\n\n protected get poiObjectType(): ObcPoiObjectType {\n return this.type === ObcPoiButtonType.Enhanced\n ? ObcPoiObjectType.Large\n : ObcPoiObjectType.Regular;\n }\n\n protected get poiObjectState(): ObcPoiObjectState {\n if (this.value === PoiButtonVisualState.Overlapped) {\n return ObcPoiObjectState.Overlapped;\n }\n\n if (this.hasData) {\n if (this.value === PoiButtonVisualState.Activated) {\n return ObcPoiObjectState.Activated;\n }\n if (this.value === PoiButtonVisualState.Checked) {\n return ObcPoiObjectState.StaticChecked;\n }\n return ObcPoiObjectState.StaticUnchecked;\n }\n\n if (this.value === PoiButtonVisualState.Activated) {\n return ObcPoiObjectState.Activated;\n }\n if (this.value === PoiButtonVisualState.Checked) {\n return ObcPoiObjectState.Checked;\n }\n\n return ObcPoiObjectState.Unchecked;\n }\n\n override render() {\n if (this.hasData) {\n return this.renderWithData();\n }\n return this.renderButton();\n }\n\n protected renderPoiObject() {\n return html`\n <obc-poi-object\n class=\"poi-object\"\n .type=${this.poiObjectType}\n .objectStyle=${ObcPoiObjectStyle.Regular}\n .state=${this.poiObjectState}\n .interactive=${false}\n >\n <span\n class=\"icon\"\n style=\"transform: rotate(${this.relativeDirection}deg);\"\n >\n <slot></slot>\n </span>\n </obc-poi-object>\n `;\n }\n\n protected renderButton() {\n return html`\n <button\n type=\"button\"\n class=${classMap({\n wrapper: true,\n selected: this.selected,\n [`alert-${this.alertClassSuffix}`]: true,\n [`type-${this.type}`]: true,\n [`value-${this.value}`]: true,\n [`layout-${this.layout}`]: true,\n 'overlap-opaque': this.overlapOpaque,\n expanded: this.inExpandedGroup,\n })}\n >\n ${this.renderHeader()}\n <div class=\"button-wrapper\">\n ${this.renderSelectionFrame()} ${this.renderPoiObject()}\n <div class=\"alert-ring\"></div>\n </div>\n </button>\n `;\n }\n\n protected renderWithData() {\n return html`\n <button\n type=\"button\"\n class=${classMap({\n wrapper: true,\n 'has-data': true,\n selected: this.selected,\n 'has-header':\n this.hasHeader &&\n (this.hasHeaderContent || this.hasGeneratedHeaderContent),\n [`alert-${this.alertClassSuffix}`]: true,\n [`type-${this.type}`]: true,\n [`value-${this.value}`]: true,\n [`layout-${this.layout}`]: true,\n 'overlap-opaque': this.overlapOpaque,\n expanded: this.inExpandedGroup,\n })}\n >\n <div class=\"visible-wrapper\"></div>\n ${this.renderHeader()}\n <div class=\"data-wrapper\">\n ${this.data.map(\n (item) =>\n html`<div class=\"data\">\n <div class=\"value\">${item.value}</div>\n <div class=\"label\">${item.label}</div>\n <div class=\"unit\">${item.unit}</div>\n </div>`\n )}\n </div>\n <div class=\"button-wrapper\">\n ${this.renderSelectionFrame()} ${this.renderPoiObject()}\n </div>\n ${\n this.hasRelation\n ? html`<div class=\"relation-wrapper\" part=\"relation-wrapper\">\n <slot name=\"relation\" class=\"relation\" part=\"relation\"></slot>\n </div>`\n : nothing\n }\n <div class=\"alert-ring\"></div>\n </button>\n `;\n }\n\n protected get selectionFrameType(): ObcPoiSelectionFrameType {\n return this.type === ObcPoiButtonType.Enhanced\n ? ObcPoiSelectionFrameType.Enhanced\n : ObcPoiSelectionFrameType.Button;\n }\n\n protected get selectionFrameState(): ObcPoiSelectionFrameState {\n return this.state === ObcPoiButtonState.Enabled\n ? ObcPoiSelectionFrameState.Regular\n : ObcPoiSelectionFrameState.Alert;\n }\n\n protected renderSelectionFrame() {\n if (!this.selected || this.layout === ObcPoiButtonLayout.Inline) {\n return nothing;\n }\n\n return html`\n <obc-poi-selection-frame\n class=\"selection-frame\"\n .type=${this.selectionFrameType}\n .state=${this.selectionFrameState}\n ></obc-poi-selection-frame>\n `;\n }\n\n static override styles = unsafeCSS(compentStyle);\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'obc-poi-button': ObcPoiButton;\n }\n}\n"],"mappings":"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"}
@@ -51,6 +51,13 @@ export declare enum PointerDirection {
51
51
  *
52
52
  * ## Events
53
53
  * - `card-click`: Fired when the card surface is activated in interactive mode.
54
+ * - `close-click`: Fired when the header close button is pressed (`hasCloseButton` with the detailed header variant).
55
+ *
56
+ * ## CSS Parts
57
+ * - `wrapper`: Outer layout wrapper holding the pointer arrows and the card surface.
58
+ * - `content-box`: Card surface with background, border, and rounded corners.
59
+ * - `header`: The `obc-poi-card-header` element, rendered when `showHeader` is true.
60
+ * - `content`: Body area wrapping the default slot.
54
61
  *
55
62
  * ## Best Practices
56
63
  * - Keep `index` stable so event payloads remain predictable.
@@ -83,8 +90,12 @@ export declare enum PointerDirection {
83
90
  * @slot - Main card body content.
84
91
  * @slot leading-icon - Optional icon used by the regular header variant.
85
92
  * @slot poi-icon - Optional icon used by the detailed header variant.
93
+ * @csspart wrapper - Outer layout wrapper holding the pointer arrows and the card surface.
94
+ * @csspart content-box - Card surface with background, border, and rounded corners.
95
+ * @csspart header - The `obc-poi-card-header` element, rendered when `showHeader` is true.
96
+ * @csspart content - Body area wrapping the default slot.
86
97
  * @fires {CustomEvent<PoiCardClickDetail>} card-click - Fired when the card is activated in interactive mode.
87
- * @fires {CustomEvent<void>} close-click - Passed on from the header when its close button is pressed (`hasCloseButton`).
98
+ * @fires {CustomEvent<void>} close-click - Passed on from the header when its close button is pressed (`hasCloseButton` with the detailed header variant).
88
99
  * @experimental
89
100
  */
90
101
  export declare class ObcPoiCard extends LitElement {
@@ -1 +1 @@
1
- {"version":3,"file":"poi-card.d.ts","sourceRoot":"","sources":["../../../src/ar/poi-card/poi-card.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,UAAU,EAA2B,MAAM,KAAK,CAAC;AAKzD,OAAO,uCAAuC,CAAC;AAC/C,OAAO,EAAC,uBAAuB,EAAC,MAAM,uCAAuC,CAAC;AAE9E,OAAO,EAAC,uBAAuB,EAAC,CAAC;AAEjC,MAAM,WAAW,kBAAkB;IACjC,KAAK,EAAE,MAAM,CAAC;CACf;AAED,MAAM,MAAM,iBAAiB,GAAG,WAAW,CAAC,kBAAkB,CAAC,CAAC;AAEhE;;;;;;;GAOG;AACH,oBAAY,gBAAgB;IAC1B,IAAI,SAAS;IACb,GAAG,QAAQ;IACX,MAAM,WAAW;IACjB,IAAI,SAAS;IACb,KAAK,UAAU;CAChB;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAiEG;AACH,qBACa,UAAW,SAAQ,UAAU;IACd,gBAAgB,EAAE,gBAAgB,CACpC;IAEG,SAAS,UAAS;IAEA,UAAU,UAAQ;IAErC,aAAa,EAAE,uBAAuB,CAC5B;IAEV,KAAK,SAAO;IAEZ,SAAS,SAAM;IAEf,WAAW,SAAM;IAEjB,MAAM,SAAM;IAEZ,SAAS,SAAM;IAEd,cAAc,UAAS;IAEvB,cAAc,UAAS;IAEvB,WAAW,UAAS;IAEpB,QAAQ,UAAS;IAE5C,OAAO,CAAC,eAAe;IAYvB,OAAO,CAAC,aAAa;IAWrB,OAAO,CAAC,WAAW;IASnB,OAAO,CAAC,gBAAgB;IA4BxB,OAAO,CAAC,gBAAgB;IAOxB,OAAO,CAAC,mBAAmB;IAS3B,OAAO,CAAC,iBAAiB;IAOzB,OAAO,CAAC,kBAAkB;IAS1B,OAAO,CAAC,YAAY;IAmBpB,OAAO,CAAC,gBAAgB;IAYf,MAAM;IAmCf,OAAgB,MAAM,0BAA6B;CACpD;AAED,OAAO,CAAC,MAAM,CAAC;IACb,UAAU,qBAAqB;QAC7B,cAAc,EAAE,UAAU,CAAC;KAC5B;CACF"}
1
+ {"version":3,"file":"poi-card.d.ts","sourceRoot":"","sources":["../../../src/ar/poi-card/poi-card.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,UAAU,EAA2B,MAAM,KAAK,CAAC;AAKzD,OAAO,uCAAuC,CAAC;AAC/C,OAAO,EAAC,uBAAuB,EAAC,MAAM,uCAAuC,CAAC;AAE9E,OAAO,EAAC,uBAAuB,EAAC,CAAC;AAEjC,MAAM,WAAW,kBAAkB;IACjC,KAAK,EAAE,MAAM,CAAC;CACf;AAED,MAAM,MAAM,iBAAiB,GAAG,WAAW,CAAC,kBAAkB,CAAC,CAAC;AAEhE;;;;;;;GAOG;AACH,oBAAY,gBAAgB;IAC1B,IAAI,SAAS;IACb,GAAG,QAAQ;IACX,MAAM,WAAW;IACjB,IAAI,SAAS;IACb,KAAK,UAAU;CAChB;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA4EG;AACH,qBACa,UAAW,SAAQ,UAAU;IACd,gBAAgB,EAAE,gBAAgB,CACpC;IAEG,SAAS,UAAS;IAEA,UAAU,UAAQ;IAErC,aAAa,EAAE,uBAAuB,CAC5B;IAEV,KAAK,SAAO;IAEZ,SAAS,SAAM;IAEf,WAAW,SAAM;IAEjB,MAAM,SAAM;IAEZ,SAAS,SAAM;IAEd,cAAc,UAAS;IAEvB,cAAc,UAAS;IAEvB,WAAW,UAAS;IAEpB,QAAQ,UAAS;IAE5C,OAAO,CAAC,eAAe;IAYvB,OAAO,CAAC,aAAa;IAWrB,OAAO,CAAC,WAAW;IASnB,OAAO,CAAC,gBAAgB;IA4BxB,OAAO,CAAC,gBAAgB;IAOxB,OAAO,CAAC,mBAAmB;IAS3B,OAAO,CAAC,iBAAiB;IAOzB,OAAO,CAAC,kBAAkB;IAS1B,OAAO,CAAC,YAAY;IAoBpB,OAAO,CAAC,gBAAgB;IAYf,MAAM;IAqCf,OAAgB,MAAM,0BAA6B;CACpD;AAED,OAAO,CAAC,MAAM,CAAC;IACb,UAAU,qBAAqB;QAC7B,cAAc,EAAE,UAAU,CAAC;KAC5B;CACF"}
@@ -121,6 +121,7 @@ var ObcPoiCard = class ObcPoiCard extends LitElement {
121
121
  if (!this.showHeader) return nothing;
122
122
  return html`
123
123
  <obc-poi-card-header
124
+ part="header"
124
125
  variant=${this.headerVariant}
125
126
  index=${this.index}
126
127
  cardTitle=${this.cardTitle}
@@ -148,6 +149,7 @@ var ObcPoiCard = class ObcPoiCard extends LitElement {
148
149
  render() {
149
150
  return html`
150
151
  <div
152
+ part="wrapper"
151
153
  class=${classMap({
152
154
  wrapper: true,
153
155
  "hug-content": !this.fixedSize,
@@ -159,6 +161,7 @@ var ObcPoiCard = class ObcPoiCard extends LitElement {
159
161
  <div class="center">
160
162
  ${this.renderLeftPointer()}
161
163
  <div
164
+ part="content-box"
162
165
  class="content-box"
163
166
  role=${this.interactive ? "button" : nothing}
164
167
  tabindex=${this.interactive ? "0" : nothing}
@@ -168,7 +171,7 @@ var ObcPoiCard = class ObcPoiCard extends LitElement {
168
171
  @keyup=${this.handleKeyUp}
169
172
  >
170
173
  ${this.renderHeader()}
171
- <div class="content">
174
+ <div part="content" class="content">
172
175
  <slot></slot>
173
176
  </div>
174
177
  ${this.renderAlertLayer()}
@@ -1 +1 @@
1
- {"version":3,"file":"poi-card.js","names":[],"sources":["../../../src/ar/poi-card/poi-card.ts"],"sourcesContent":["import {LitElement, html, nothing, unsafeCSS} from 'lit';\nimport {property} from 'lit/decorators.js';\nimport componentStyle from './poi-card.css?inline';\nimport {classMap} from 'lit/directives/class-map.js';\nimport {customElement} from '../../decorator.js';\nimport '../poi-card-header/poi-card-header.js';\nimport {ObcPoiCardHeaderVariant} from '../poi-card-header/poi-card-header.js';\n\nexport {ObcPoiCardHeaderVariant};\n\nexport interface PoiCardClickDetail {\n index: string;\n}\n\nexport type PoiCardClickEvent = CustomEvent<PoiCardClickDetail>;\n\n/**\n * Direction of the arrow pointer anchoring the card.\n * - `none`: No pointer shown.\n * - `top`: Arrow points up from the card.\n * - `bottom`: Arrow points down from the card.\n * - `left`: Arrow points left from the card.\n * - `right`: Arrow points right from the card.\n */\nexport enum PointerDirection {\n None = 'none',\n Top = 'top',\n Bottom = 'bottom',\n Left = 'left',\n Right = 'right',\n}\n\n/**\n * `<obc-poi-card>` - Content card container with optional pointer arrow, header variants, and interactive click handling.\n *\n * ## Overview\n * Use this component to wrap contextual marker details in a card with optional directional anchoring.\n * Keywords/synonyms: detail card, marker card, anchored card, popover card.\n *\n * ## Features/Variants\n * - `pointerDirection` (default `none`): `none`, `top`, `bottom`, `left`, `right`.\n * - `fixedSize` (default `false`): toggles fixed `256x256` sizing instead of content-based sizing.\n * - Header options:\n * - `showHeader` controls whether the header area is visible.\n * - `headerVariant` controls header layout (`tag`, `condensed`, `regular`, `detailed`).\n * - `index`, `cardTitle`, `description`, `source`, `timestamp` are forwarded to `obc-poi-card-header`.\n * - `hasLeadingIcon` and `hasCloseButton` gate header affordances.\n * - `interactive` (default `false`): enables keyboard activation and `card-click` dispatch.\n * - `hasAlert` (default `false`): shows alert ring layer when `interactive` is enabled.\n *\n * ## Usage Guidelines\n * - Use `pointerDirection` when the card should visually point to an anchor target.\n * - Keep `interactive` off for read-only cards.\n * - Use the header slots only when the selected `headerVariant` renders them.\n *\n * ## Slots/Content\n * - Default slot: Main card body content.\n * - `leading-icon`: Optional icon used by the regular header variant.\n * - `poi-icon`: Optional icon used by the detailed header variant.\n *\n * ## Events\n * - `card-click`: Fired when the card surface is activated in interactive mode.\n *\n * ## Best Practices\n * - Keep `index` stable so event payloads remain predictable.\n * - Pair `hasAlert` with meaningful alert state in surrounding UI logic.\n *\n * ## Example\n * ```html\n * <obc-poi-card pointerDirection=\"bottom\" index=\"1\" cardTitle=\"Target\" interactive>\n * <obi-placeholder slot=\"leading-icon\"></obi-placeholder>\n * <div>Custom card content</div>\n * </obc-poi-card>\n * ```\n *\n * @property fixedSize - When true, uses fixed 256x256px size; otherwise sizes to content.\n * @availableWhen headerVariant showHeader==true\n * @availableWhen cardTitle showHeader==true && headerVariant!=tag\n * @property description - Passed to header (detailed variant only).\n * @availableWhen description showHeader==true && headerVariant==detailed\n * @property source - Source badge text (e.g., \"AIS\", \"RADAR\"). Hidden when empty.\n * @availableWhen source showHeader==true && headerVariant!=tag\n * @property timestamp - Passed to header (detailed variant only).\n * @availableWhen timestamp showHeader==true && headerVariant==detailed\n * @property hasLeadingIcon - Enables the leading-icon slot (regular header variant only).\n * @availableWhen hasLeadingIcon showHeader==true && headerVariant==regular\n * @property hasCloseButton - Enables the close button (detailed header variant only).\n * @availableWhen hasCloseButton showHeader==true && headerVariant==detailed\n * @property interactive - Enables click events, keyboard focus, and alert border support.\n * @property hasAlert - Shows alert/caution border rings. Requires `interactive` to be true.\n * @availableWhen hasAlert interactive==true\n * @slot - Main card body content.\n * @slot leading-icon - Optional icon used by the regular header variant.\n * @slot poi-icon - Optional icon used by the detailed header variant.\n * @fires {CustomEvent<PoiCardClickDetail>} card-click - Fired when the card is activated in interactive mode.\n * @fires {CustomEvent<void>} close-click - Passed on from the header when its close button is pressed (`hasCloseButton`).\n * @experimental\n */\n@customElement('obc-poi-card')\nexport class ObcPoiCard extends LitElement {\n @property({type: String}) pointerDirection: PointerDirection =\n PointerDirection.None;\n\n @property({type: Boolean}) fixedSize = false;\n\n @property({type: Boolean, attribute: false}) showHeader = true;\n\n @property({type: String}) headerVariant: ObcPoiCardHeaderVariant =\n ObcPoiCardHeaderVariant.Condensed;\n\n @property({type: String}) index = '1';\n\n @property({type: String}) cardTitle = '';\n\n @property({type: String}) description = '';\n\n @property({type: String}) source = '';\n\n @property({type: String}) timestamp = '';\n\n @property({type: Boolean}) hasLeadingIcon = false;\n\n @property({type: Boolean}) hasCloseButton = false;\n\n @property({type: Boolean}) interactive = false;\n\n @property({type: Boolean}) hasAlert = false;\n\n private handleCardClick() {\n if (!this.interactive) return;\n\n this.dispatchEvent(\n new CustomEvent<PoiCardClickDetail>('card-click', {\n detail: {index: this.index},\n bubbles: true,\n composed: true,\n })\n );\n }\n\n private handleKeyDown(e: KeyboardEvent) {\n if (!this.interactive) return;\n if (e.target !== e.currentTarget) return;\n if (e.key === ' ') {\n e.preventDefault();\n } else if (e.key === 'Enter' && !e.repeat) {\n e.preventDefault();\n this.handleCardClick();\n }\n }\n\n private handleKeyUp(e: KeyboardEvent) {\n if (!this.interactive) return;\n if (e.target !== e.currentTarget) return;\n if (e.key === ' ') {\n e.preventDefault();\n this.handleCardClick();\n }\n }\n\n private renderPointerSvg(direction: 'top' | 'bottom' | 'left' | 'right') {\n const paths = {\n top: 'M6 0L12 6H0L6 0Z',\n bottom: 'M6 6L0 0H12L6 6Z',\n left: 'M0 6L6 0V12L0 6Z',\n right: 'M6 6L0 0V12L6 6Z',\n };\n\n const isVertical = direction === 'top' || direction === 'bottom';\n const width = isVertical ? 12 : 6;\n const height = isVertical ? 6 : 12;\n\n return html`\n <svg\n width=\"${width}\"\n height=\"${height}\"\n viewBox=\"0 0 ${width} ${height}\"\n fill=\"none\"\n xmlns=\"http://www.w3.org/2000/svg\"\n >\n <path\n d=\"${paths[direction]}\"\n fill=\"var(--overlay-border-outline-color)\"\n />\n </svg>\n `;\n }\n\n private renderTopPointer() {\n if (this.pointerDirection !== PointerDirection.Top) return nothing;\n return html`\n <div class=\"pointer-container top\">${this.renderPointerSvg('top')}</div>\n `;\n }\n\n private renderBottomPointer() {\n if (this.pointerDirection !== PointerDirection.Bottom) return nothing;\n return html`\n <div class=\"pointer-container bottom\">\n ${this.renderPointerSvg('bottom')}\n </div>\n `;\n }\n\n private renderLeftPointer() {\n if (this.pointerDirection !== PointerDirection.Left) return nothing;\n return html`\n <div class=\"pointer-container left\">${this.renderPointerSvg('left')}</div>\n `;\n }\n\n private renderRightPointer() {\n if (this.pointerDirection !== PointerDirection.Right) return nothing;\n return html`\n <div class=\"pointer-container right\">\n ${this.renderPointerSvg('right')}\n </div>\n `;\n }\n\n private renderHeader() {\n if (!this.showHeader) return nothing;\n return html`\n <obc-poi-card-header\n variant=${this.headerVariant}\n index=${this.index}\n cardTitle=${this.cardTitle}\n description=${this.description}\n source=${this.source}\n timestamp=${this.timestamp}\n ?hasLeadingIcon=${this.hasLeadingIcon}\n ?hasCloseButton=${this.hasCloseButton}\n >\n <slot name=\"leading-icon\" slot=\"leading-icon\"></slot>\n <slot name=\"poi-icon\" slot=\"poi-icon\"></slot>\n </obc-poi-card-header>\n `;\n }\n\n private renderAlertLayer() {\n if (!this.interactive || !this.hasAlert) return nothing;\n\n return html`\n <div class=\"alert-layer\">\n <div class=\"ring-outer\"></div>\n <div class=\"ring-middle alert\"></div>\n <div class=\"ring-inner\"></div>\n </div>\n `;\n }\n\n override render() {\n return html`\n <div\n class=${classMap({\n wrapper: true,\n 'hug-content': !this.fixedSize,\n 'fixed-size': this.fixedSize,\n interactive: this.interactive,\n })}\n >\n ${this.renderTopPointer()}\n <div class=\"center\">\n ${this.renderLeftPointer()}\n <div\n class=\"content-box\"\n role=${this.interactive ? 'button' : nothing}\n tabindex=${this.interactive ? '0' : nothing}\n aria-disabled=${this.interactive ? 'false' : nothing}\n @click=${this.handleCardClick}\n @keydown=${this.handleKeyDown}\n @keyup=${this.handleKeyUp}\n >\n ${this.renderHeader()}\n <div class=\"content\">\n <slot></slot>\n </div>\n ${this.renderAlertLayer()}\n </div>\n ${this.renderRightPointer()}\n </div>\n ${this.renderBottomPointer()}\n </div>\n `;\n }\n\n static override styles = unsafeCSS(componentStyle);\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'obc-poi-card': ObcPoiCard;\n }\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"poi-card.js","names":[],"sources":["../../../src/ar/poi-card/poi-card.ts"],"sourcesContent":["import {LitElement, html, nothing, unsafeCSS} from 'lit';\nimport {property} from 'lit/decorators.js';\nimport componentStyle from './poi-card.css?inline';\nimport {classMap} from 'lit/directives/class-map.js';\nimport {customElement} from '../../decorator.js';\nimport '../poi-card-header/poi-card-header.js';\nimport {ObcPoiCardHeaderVariant} from '../poi-card-header/poi-card-header.js';\n\nexport {ObcPoiCardHeaderVariant};\n\nexport interface PoiCardClickDetail {\n index: string;\n}\n\nexport type PoiCardClickEvent = CustomEvent<PoiCardClickDetail>;\n\n/**\n * Direction of the arrow pointer anchoring the card.\n * - `none`: No pointer shown.\n * - `top`: Arrow points up from the card.\n * - `bottom`: Arrow points down from the card.\n * - `left`: Arrow points left from the card.\n * - `right`: Arrow points right from the card.\n */\nexport enum PointerDirection {\n None = 'none',\n Top = 'top',\n Bottom = 'bottom',\n Left = 'left',\n Right = 'right',\n}\n\n/**\n * `<obc-poi-card>` - Content card container with optional pointer arrow, header variants, and interactive click handling.\n *\n * ## Overview\n * Use this component to wrap contextual marker details in a card with optional directional anchoring.\n * Keywords/synonyms: detail card, marker card, anchored card, popover card.\n *\n * ## Features/Variants\n * - `pointerDirection` (default `none`): `none`, `top`, `bottom`, `left`, `right`.\n * - `fixedSize` (default `false`): toggles fixed `256x256` sizing instead of content-based sizing.\n * - Header options:\n * - `showHeader` controls whether the header area is visible.\n * - `headerVariant` controls header layout (`tag`, `condensed`, `regular`, `detailed`).\n * - `index`, `cardTitle`, `description`, `source`, `timestamp` are forwarded to `obc-poi-card-header`.\n * - `hasLeadingIcon` and `hasCloseButton` gate header affordances.\n * - `interactive` (default `false`): enables keyboard activation and `card-click` dispatch.\n * - `hasAlert` (default `false`): shows alert ring layer when `interactive` is enabled.\n *\n * ## Usage Guidelines\n * - Use `pointerDirection` when the card should visually point to an anchor target.\n * - Keep `interactive` off for read-only cards.\n * - Use the header slots only when the selected `headerVariant` renders them.\n *\n * ## Slots/Content\n * - Default slot: Main card body content.\n * - `leading-icon`: Optional icon used by the regular header variant.\n * - `poi-icon`: Optional icon used by the detailed header variant.\n *\n * ## Events\n * - `card-click`: Fired when the card surface is activated in interactive mode.\n * - `close-click`: Fired when the header close button is pressed (`hasCloseButton` with the detailed header variant).\n *\n * ## CSS Parts\n * - `wrapper`: Outer layout wrapper holding the pointer arrows and the card surface.\n * - `content-box`: Card surface with background, border, and rounded corners.\n * - `header`: The `obc-poi-card-header` element, rendered when `showHeader` is true.\n * - `content`: Body area wrapping the default slot.\n *\n * ## Best Practices\n * - Keep `index` stable so event payloads remain predictable.\n * - Pair `hasAlert` with meaningful alert state in surrounding UI logic.\n *\n * ## Example\n * ```html\n * <obc-poi-card pointerDirection=\"bottom\" index=\"1\" cardTitle=\"Target\" interactive>\n * <obi-placeholder slot=\"leading-icon\"></obi-placeholder>\n * <div>Custom card content</div>\n * </obc-poi-card>\n * ```\n *\n * @property fixedSize - When true, uses fixed 256x256px size; otherwise sizes to content.\n * @availableWhen headerVariant showHeader==true\n * @availableWhen cardTitle showHeader==true && headerVariant!=tag\n * @property description - Passed to header (detailed variant only).\n * @availableWhen description showHeader==true && headerVariant==detailed\n * @property source - Source badge text (e.g., \"AIS\", \"RADAR\"). Hidden when empty.\n * @availableWhen source showHeader==true && headerVariant!=tag\n * @property timestamp - Passed to header (detailed variant only).\n * @availableWhen timestamp showHeader==true && headerVariant==detailed\n * @property hasLeadingIcon - Enables the leading-icon slot (regular header variant only).\n * @availableWhen hasLeadingIcon showHeader==true && headerVariant==regular\n * @property hasCloseButton - Enables the close button (detailed header variant only).\n * @availableWhen hasCloseButton showHeader==true && headerVariant==detailed\n * @property interactive - Enables click events, keyboard focus, and alert border support.\n * @property hasAlert - Shows alert/caution border rings. Requires `interactive` to be true.\n * @availableWhen hasAlert interactive==true\n * @slot - Main card body content.\n * @slot leading-icon - Optional icon used by the regular header variant.\n * @slot poi-icon - Optional icon used by the detailed header variant.\n * @csspart wrapper - Outer layout wrapper holding the pointer arrows and the card surface.\n * @csspart content-box - Card surface with background, border, and rounded corners.\n * @csspart header - The `obc-poi-card-header` element, rendered when `showHeader` is true.\n * @csspart content - Body area wrapping the default slot.\n * @fires {CustomEvent<PoiCardClickDetail>} card-click - Fired when the card is activated in interactive mode.\n * @fires {CustomEvent<void>} close-click - Passed on from the header when its close button is pressed (`hasCloseButton` with the detailed header variant).\n * @experimental\n */\n@customElement('obc-poi-card')\nexport class ObcPoiCard extends LitElement {\n @property({type: String}) pointerDirection: PointerDirection =\n PointerDirection.None;\n\n @property({type: Boolean}) fixedSize = false;\n\n @property({type: Boolean, attribute: false}) showHeader = true;\n\n @property({type: String}) headerVariant: ObcPoiCardHeaderVariant =\n ObcPoiCardHeaderVariant.Condensed;\n\n @property({type: String}) index = '1';\n\n @property({type: String}) cardTitle = '';\n\n @property({type: String}) description = '';\n\n @property({type: String}) source = '';\n\n @property({type: String}) timestamp = '';\n\n @property({type: Boolean}) hasLeadingIcon = false;\n\n @property({type: Boolean}) hasCloseButton = false;\n\n @property({type: Boolean}) interactive = false;\n\n @property({type: Boolean}) hasAlert = false;\n\n private handleCardClick() {\n if (!this.interactive) return;\n\n this.dispatchEvent(\n new CustomEvent<PoiCardClickDetail>('card-click', {\n detail: {index: this.index},\n bubbles: true,\n composed: true,\n })\n );\n }\n\n private handleKeyDown(e: KeyboardEvent) {\n if (!this.interactive) return;\n if (e.target !== e.currentTarget) return;\n if (e.key === ' ') {\n e.preventDefault();\n } else if (e.key === 'Enter' && !e.repeat) {\n e.preventDefault();\n this.handleCardClick();\n }\n }\n\n private handleKeyUp(e: KeyboardEvent) {\n if (!this.interactive) return;\n if (e.target !== e.currentTarget) return;\n if (e.key === ' ') {\n e.preventDefault();\n this.handleCardClick();\n }\n }\n\n private renderPointerSvg(direction: 'top' | 'bottom' | 'left' | 'right') {\n const paths = {\n top: 'M6 0L12 6H0L6 0Z',\n bottom: 'M6 6L0 0H12L6 6Z',\n left: 'M0 6L6 0V12L0 6Z',\n right: 'M6 6L0 0V12L6 6Z',\n };\n\n const isVertical = direction === 'top' || direction === 'bottom';\n const width = isVertical ? 12 : 6;\n const height = isVertical ? 6 : 12;\n\n return html`\n <svg\n width=\"${width}\"\n height=\"${height}\"\n viewBox=\"0 0 ${width} ${height}\"\n fill=\"none\"\n xmlns=\"http://www.w3.org/2000/svg\"\n >\n <path\n d=\"${paths[direction]}\"\n fill=\"var(--overlay-border-outline-color)\"\n />\n </svg>\n `;\n }\n\n private renderTopPointer() {\n if (this.pointerDirection !== PointerDirection.Top) return nothing;\n return html`\n <div class=\"pointer-container top\">${this.renderPointerSvg('top')}</div>\n `;\n }\n\n private renderBottomPointer() {\n if (this.pointerDirection !== PointerDirection.Bottom) return nothing;\n return html`\n <div class=\"pointer-container bottom\">\n ${this.renderPointerSvg('bottom')}\n </div>\n `;\n }\n\n private renderLeftPointer() {\n if (this.pointerDirection !== PointerDirection.Left) return nothing;\n return html`\n <div class=\"pointer-container left\">${this.renderPointerSvg('left')}</div>\n `;\n }\n\n private renderRightPointer() {\n if (this.pointerDirection !== PointerDirection.Right) return nothing;\n return html`\n <div class=\"pointer-container right\">\n ${this.renderPointerSvg('right')}\n </div>\n `;\n }\n\n private renderHeader() {\n if (!this.showHeader) return nothing;\n return html`\n <obc-poi-card-header\n part=\"header\"\n variant=${this.headerVariant}\n index=${this.index}\n cardTitle=${this.cardTitle}\n description=${this.description}\n source=${this.source}\n timestamp=${this.timestamp}\n ?hasLeadingIcon=${this.hasLeadingIcon}\n ?hasCloseButton=${this.hasCloseButton}\n >\n <slot name=\"leading-icon\" slot=\"leading-icon\"></slot>\n <slot name=\"poi-icon\" slot=\"poi-icon\"></slot>\n </obc-poi-card-header>\n `;\n }\n\n private renderAlertLayer() {\n if (!this.interactive || !this.hasAlert) return nothing;\n\n return html`\n <div class=\"alert-layer\">\n <div class=\"ring-outer\"></div>\n <div class=\"ring-middle alert\"></div>\n <div class=\"ring-inner\"></div>\n </div>\n `;\n }\n\n override render() {\n return html`\n <div\n part=\"wrapper\"\n class=${classMap({\n wrapper: true,\n 'hug-content': !this.fixedSize,\n 'fixed-size': this.fixedSize,\n interactive: this.interactive,\n })}\n >\n ${this.renderTopPointer()}\n <div class=\"center\">\n ${this.renderLeftPointer()}\n <div\n part=\"content-box\"\n class=\"content-box\"\n role=${this.interactive ? 'button' : nothing}\n tabindex=${this.interactive ? '0' : nothing}\n aria-disabled=${this.interactive ? 'false' : nothing}\n @click=${this.handleCardClick}\n @keydown=${this.handleKeyDown}\n @keyup=${this.handleKeyUp}\n >\n ${this.renderHeader()}\n <div part=\"content\" class=\"content\">\n <slot></slot>\n </div>\n ${this.renderAlertLayer()}\n </div>\n ${this.renderRightPointer()}\n </div>\n ${this.renderBottomPointer()}\n </div>\n `;\n }\n\n static override styles = unsafeCSS(componentStyle);\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'obc-poi-card': ObcPoiCard;\n }\n}\n"],"mappings":"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"}
@@ -1,5 +1,15 @@
1
1
  import { LitElement, PropertyValues } from 'lit';
2
+ import { ObcPoiState } from '../poi/poi.js';
3
+ import { ObcPoiButtonDataItem } from '../poi-button/poi-button.js';
2
4
  import '../poi-layer-stack/poi-layer-stack.js';
5
+ import '../poi/poi-data.js';
6
+ import '../poi/poi-vessel.js';
7
+ import '../poi/poi-aton.js';
8
+ export declare enum PoiDetectionVariant {
9
+ Data = "data",
10
+ Vessel = "vessel",
11
+ Aton = "aton"
12
+ }
3
13
  export type PoiDetection = {
4
14
  x: number;
5
15
  y: number;
@@ -11,6 +21,14 @@ export type PoiDetection = {
11
21
  class_id?: number;
12
22
  heading?: number;
13
23
  direction?: number;
24
+ /** POI variant rendered for this detection (default `data`). */
25
+ variant?: PoiDetectionVariant;
26
+ /** Custom-element tag rendered as the POI's icon child (e.g. an `obi-*` icon). */
27
+ icon?: string;
28
+ /** Alert state applied to the target. */
29
+ state?: ObcPoiState;
30
+ /** Data rows shown in the target's expanded button. */
31
+ data?: ObcPoiButtonDataItem[];
14
32
  };
15
33
  export type PoiKeyFn = (det: PoiDetection, index: number) => string;
16
34
  export type PoiFrame = {
@@ -22,12 +40,21 @@ export declare enum PoiFitMode {
22
40
  Contain = "contain",
23
41
  Cover = "cover"
24
42
  }
43
+ /**
44
+ * Attribute consumers set on a child `obc-poi-layer` to tell the
45
+ * controller which layer receives its detection-driven targets.
46
+ */
47
+ export declare const POI_CONTROLLER_LAYER_ATTR = "data-controller-layer";
48
+ /** `data-controller-layer` value marking the background/target layer. */
49
+ export declare const POI_CONTROLLER_BACKGROUND_LAYER = "background";
25
50
  /**
26
51
  * `<obc-poi-controller>` — Maps detection data onto POI markers over a video or image.
27
52
  *
28
53
  * Takes detection coordinates in media pixel space (e.g. x,y in a 1920x1080 frame),
29
54
  * projects them to screen space using the media's rendered size and fit mode, and
30
- * creates/updates `obc-poi-data` targets inside a layer stack.
55
+ * creates/updates POI targets inside a layer stack (`obc-poi-data` by default;
56
+ * `obc-poi-vessel`/`obc-poi-aton` via each detection's `variant`, with optional
57
+ * per-detection `icon`, `state`, and `data`).
31
58
  *
32
59
  * ## Quick Start
33
60
  *
@@ -82,6 +109,16 @@ export declare enum PoiFitMode {
82
109
  * <obc-poi-controller detections={detections} fit="cover">
83
110
  * ```
84
111
  *
112
+ * ## Framework Notes
113
+ *
114
+ * Both paths are safe for declarative renderers (React, Vue, Lit): the
115
+ * `detections` API creates and owns the resulting `obc-poi-data` elements,
116
+ * and manually slotted POI children are never moved, re-parented, or
117
+ * modified structurally by the library — selection is rendered by CSS
118
+ * projection and auto-grouping happens inside the layer's shadow root via
119
+ * slot assignment. Frameworks can manage POI children as ordinary
120
+ * framework-owned elements.
121
+ *
85
122
  * ## Coordinate Model
86
123
  *
87
124
  * Detection `x` and `y` are in **media pixel space** (e.g. 0-1920 for a 1920x1080 video).
@@ -121,6 +158,8 @@ export declare enum PoiFitMode {
121
158
  * - `--obc-poi-controller-stack-height` (default `50%`) — height of the stack
122
159
  * - `--obc-poi-controller-stack-gap` (default `8px`) — gap between layers
123
160
  *
161
+ * @property xFilterCutoffHz - Forwarded to every controller-owned target's `xFilterCutoffHz`; `null` leaves the targets on their default.
162
+ * @property yFilterCutoffHz - Forwarded to every controller-owned target's `yFilterCutoffHz`; `null` leaves the targets on their default.
124
163
  * @slot media - Video or image element. Sets the projection source dimensions.
125
164
  * @slot stack - `obc-poi-layer-stack` containing the layers for target placement.
126
165
  * @experimental
@@ -133,6 +172,10 @@ export declare class ObcPoiController extends LitElement {
133
172
  confidenceMin: number | null;
134
173
  classFilter: string[] | null;
135
174
  keyFn: PoiKeyFn | null;
175
+ /** Forwarded to every controller-owned target's `xFilterCutoffHz`; `null` leaves the targets on their default. */
176
+ xFilterCutoffHz: number | null;
177
+ /** Forwarded to every controller-owned target's `yFilterCutoffHz`; `null` leaves the targets on their default. */
178
+ yFilterCutoffHz: number | null;
136
179
  private mediaWidth;
137
180
  private mediaHeight;
138
181
  private renderWidth;
@@ -162,6 +205,7 @@ export declare class ObcPoiController extends LitElement {
162
205
  private getActiveDetections;
163
206
  private filterDetections;
164
207
  private pickFrame;
208
+ private computeCurrentProjection;
165
209
  private mapDetection;
166
210
  private syncTargetsToCustomStack;
167
211
  render(): import('lit-html').TemplateResult<1>;
@@ -1 +1 @@
1
- {"version":3,"file":"poi-controller.d.ts","sourceRoot":"","sources":["../../../src/ar/poi-controller/poi-controller.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,UAAU,EAAE,cAAc,EAAkB,MAAM,KAAK,CAAC;AAIhE,OAAO,uCAAuC,CAAC;AAK/C,MAAM,MAAM,YAAY,GAAG;IACzB,CAAC,EAAE,MAAM,CAAC;IACV,CAAC,EAAE,MAAM,CAAC;IACV,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,EAAE,CAAC,EAAE,MAAM,CAAC;IACZ,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB,CAAC;AAEF,MAAM,MAAM,QAAQ,GAAG,CAAC,GAAG,EAAE,YAAY,EAAE,KAAK,EAAE,MAAM,KAAK,MAAM,CAAC;AAEpE,MAAM,MAAM,QAAQ,GAAG;IACrB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,UAAU,EAAE,YAAY,EAAE,CAAC;CAC5B,CAAC;AAEF,oBAAY,UAAU;IACpB,OAAO,YAAY;IACnB,KAAK,UAAU;CAChB;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAsGG;AACH,qBACa,gBAAiB,SAAQ,UAAU;IACpB,GAAG,EAAE,UAAU,CAAsB;IACtC,MAAM,EAAE,QAAQ,EAAE,GAAG,IAAI,CAAQ;IACjC,UAAU,EAAE,YAAY,EAAE,GAAG,IAAI,CAAQ;IACxC,UAAU,EAAE,MAAM,GAAG,IAAI,CAAQ;IACjC,aAAa,EAAE,MAAM,GAAG,IAAI,CAAQ;IACrC,WAAW,EAAE,MAAM,EAAE,GAAG,IAAI,CAAQ;IAE7D,KAAK,EAAE,QAAQ,GAAG,IAAI,CAAQ;IAErB,OAAO,CAAC,UAAU,CAAK;IACvB,OAAO,CAAC,WAAW,CAAK;IACxB,OAAO,CAAC,WAAW,CAAK;IACxB,OAAO,CAAC,YAAY,CAAK;IAGlC,OAAO,CAAC,aAAa,CAAiB;IAEtC,OAAO,CAAC,aAAa,CAAiB;IAEtC,OAAO,CAAC,cAAc,CAAC,CAAiB;IACxC,OAAO,CAAC,mBAAmB,CAAC,CAAiB;IAC7C,OAAO,CAAC,OAAO,CAAK;IACpB,OAAO,CAAC,qBAAqB,CAAoC;IACjE,OAAO,CAAC,qBAAqB,CAI3B;IACF,OAAO,CAAC,iBAAiB,CAAiC;IAC1D,OAAO,CAAC,YAAY,CAAoD;IACxE,OAAO,CAAC,YAAY,CAA4B;IAChD,OAAO,CAAC,aAAa,CASnB;IAEO,YAAY;IAQZ,OAAO,CAAC,OAAO,EAAE,cAAc;IAiBxC,OAAO,CAAC,YAAY;IAQX,oBAAoB;IAmB7B,OAAO,CAAC,kBAAkB;IAgB1B,OAAO,CAAC,kBAAkB;IAqB1B,OAAO,CAAC,mBAAmB;IAiC3B,OAAO,CAAC,oBAAoB;IAqB5B,OAAO,CAAC,eAAe;IAQvB,OAAO,CAAC,eAAe;IAMvB,OAAO,CAAC,kBAAkB;IAc1B,OAAO,CAAC,mBAAmB;IAW3B,OAAO,CAAC,gBAAgB;IAiBxB,OAAO,CAAC,SAAS;IA2BjB,OAAO,CAAC,YAAY;IAuCpB,OAAO,CAAC,wBAAwB;IA4EvB,MAAM;IAaf,OAAgB,MAAM,0BAA6B;CACpD;AAED,OAAO,CAAC,MAAM,CAAC;IACb,UAAU,qBAAqB;QAC7B,oBAAoB,EAAE,gBAAgB,CAAC;KACxC;CACF"}
1
+ {"version":3,"file":"poi-controller.d.ts","sourceRoot":"","sources":["../../../src/ar/poi-controller/poi-controller.ts"],"names":[],"mappings":"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"}
@@ -1,16 +1,40 @@
1
1
  import { customElement } from "../../decorator.js";
2
2
  import __decorate from "../../_virtual/_@oxc-project_runtime@0.150.0/helpers/esm/decorate.js";
3
3
  import { resolvePoiButtonTypeFromBoxSize } from "../poi-button/poi-button.js";
4
+ import { ObcPoiState } from "../poi/poi.js";
5
+ import "../poi/poi-base.js";
6
+ import "../poi/poi-aton.js";
7
+ import "../poi/poi-data.js";
8
+ import "../poi/poi-vessel.js";
4
9
  import poi_controller_default from "./poi-controller.css.js";
5
10
  import "../poi-layer-stack/poi-layer-stack.js";
11
+ import { MediaFit, computeMediaProjection, projectPoint } from "../poi-projection/poi-projection.js";
6
12
  import { LitElement, html, unsafeCSS } from "lit";
7
13
  import { property, queryAssignedElements, state } from "lit/decorators.js";
8
14
  //#region src/ar/poi-controller/poi-controller.ts
15
+ var PoiDetectionVariant = /* @__PURE__ */ function(PoiDetectionVariant) {
16
+ PoiDetectionVariant["Data"] = "data";
17
+ PoiDetectionVariant["Vessel"] = "vessel";
18
+ PoiDetectionVariant["Aton"] = "aton";
19
+ return PoiDetectionVariant;
20
+ }({});
21
+ var DETECTION_VARIANT_TAGS = {
22
+ ["data"]: "obc-poi-data",
23
+ ["vessel"]: "obc-poi-vessel",
24
+ ["aton"]: "obc-poi-aton"
25
+ };
9
26
  var PoiFitMode = /* @__PURE__ */ function(PoiFitMode) {
10
27
  PoiFitMode["Contain"] = "contain";
11
28
  PoiFitMode["Cover"] = "cover";
12
29
  return PoiFitMode;
13
30
  }({});
31
+ /**
32
+ * Attribute consumers set on a child `obc-poi-layer` to tell the
33
+ * controller which layer receives its detection-driven targets.
34
+ */
35
+ var POI_CONTROLLER_LAYER_ATTR = "data-controller-layer";
36
+ /** `data-controller-layer` value marking the background/target layer. */
37
+ var POI_CONTROLLER_BACKGROUND_LAYER = "background";
14
38
  var ObcPoiController = class ObcPoiController extends LitElement {
15
39
  constructor(..._args) {
16
40
  super(..._args);
@@ -21,6 +45,8 @@ var ObcPoiController = class ObcPoiController extends LitElement {
21
45
  this.confidenceMin = null;
22
46
  this.classFilter = null;
23
47
  this.keyFn = null;
48
+ this.xFilterCutoffHz = null;
49
+ this.yFilterCutoffHz = null;
24
50
  this.mediaWidth = 0;
25
51
  this.mediaHeight = 0;
26
52
  this.renderWidth = 0;
@@ -92,7 +118,7 @@ var ObcPoiController = class ObcPoiController extends LitElement {
92
118
  resolveTargetLayer() {
93
119
  const stack = this.getStackElement();
94
120
  if (!stack) return null;
95
- const explicitLayer = stack.querySelector("obc-poi-layer[data-controller-layer=\"background\"]");
121
+ const explicitLayer = stack.querySelector(`obc-poi-layer[${POI_CONTROLLER_LAYER_ATTR}="${POI_CONTROLLER_BACKGROUND_LAYER}"]`);
96
122
  if (explicitLayer) return explicitLayer;
97
123
  const layers = Array.from(stack.querySelectorAll("obc-poi-layer"));
98
124
  const isSelectedLayer = (candidate) => candidate.isSelected === true;
@@ -183,17 +209,22 @@ var ObcPoiController = class ObcPoiController extends LitElement {
183
209
  }
184
210
  return frames[0] ?? null;
185
211
  }
186
- mapDetection(det) {
187
- if (!Number.isFinite(this.mediaWidth) || !Number.isFinite(this.mediaHeight) || !Number.isFinite(this.renderWidth) || !Number.isFinite(this.renderHeight) || this.mediaWidth === 0 || this.mediaHeight === 0 || this.renderWidth === 0 || this.renderHeight === 0) return null;
188
- const scale = this.fit === "cover" ? Math.max(this.renderWidth / this.mediaWidth, this.renderHeight / this.mediaHeight) : Math.min(this.renderWidth / this.mediaWidth, this.renderHeight / this.mediaHeight);
189
- const contentWidth = this.mediaWidth * scale;
190
- const contentHeight = this.mediaHeight * scale;
191
- const offsetX = (this.renderWidth - contentWidth) / 2;
192
- const offsetY = (this.renderHeight - contentHeight) / 2;
212
+ computeCurrentProjection() {
213
+ return computeMediaProjection({
214
+ mediaWidth: this.mediaWidth,
215
+ mediaHeight: this.mediaHeight,
216
+ renderWidth: this.renderWidth,
217
+ renderHeight: this.renderHeight,
218
+ fit: this.fit === "cover" ? MediaFit.Cover : MediaFit.Contain
219
+ });
220
+ }
221
+ mapDetection(det, projection = this.computeCurrentProjection()) {
222
+ if (!projection) return null;
223
+ const point = projectPoint(projection, det.x, det.y);
193
224
  return {
194
- x: offsetX + det.x * scale,
195
- y: offsetY + det.y * scale,
196
- scale
225
+ x: point.x,
226
+ y: point.y,
227
+ scale: projection.scale
197
228
  };
198
229
  }
199
230
  syncTargetsToCustomStack() {
@@ -212,19 +243,34 @@ var ObcPoiController = class ObcPoiController extends LitElement {
212
243
  const layerBottomInController = layer.getBoundingClientRect().bottom - controllerRect.top;
213
244
  const active = this.getActiveDetections();
214
245
  const activeKeys = /* @__PURE__ */ new Set();
246
+ const projection = this.computeCurrentProjection();
215
247
  active.forEach((det, index) => {
216
- const mapped = this.mapDetection(det);
248
+ const mapped = this.mapDetection(det, projection);
217
249
  if (!mapped) return;
218
250
  const key = det.id ?? (this.keyFn ? this.keyFn(det, index) : `index:${index}`);
219
251
  activeKeys.add(key);
252
+ const tag = DETECTION_VARIANT_TAGS[det.variant ?? "data"];
220
253
  let target = this.controllerTargets.get(key);
254
+ if (target && target.tagName.toLowerCase() !== tag) {
255
+ target.remove();
256
+ this.controllerTargets.delete(key);
257
+ target = void 0;
258
+ }
221
259
  if (!target) {
222
- target = document.createElement("obc-poi-data");
260
+ target = document.createElement(tag);
223
261
  target.dataset.controller = "1";
224
262
  target.dataset.detectionIndex = String(index);
225
263
  target.fixedTarget = false;
226
264
  this.controllerTargets.set(key, target);
227
265
  }
266
+ const iconTag = det.icon?.toLowerCase() ?? null;
267
+ const currentIcon = target.firstElementChild;
268
+ if (iconTag) {
269
+ if (currentIcon?.tagName.toLowerCase() !== iconTag) {
270
+ currentIcon?.remove();
271
+ target.appendChild(document.createElement(iconTag));
272
+ }
273
+ } else if (currentIcon) currentIcon.remove();
228
274
  if (!target.isConnected || target.parentElement === null) layer.appendChild(target);
229
275
  target.dataset.detectionIndex = String(index);
230
276
  target.x = mapped.x;
@@ -236,6 +282,10 @@ var ObcPoiController = class ObcPoiController extends LitElement {
236
282
  target.buttonType = resolvePoiButtonTypeFromBoxSize(boxWidth, boxHeight);
237
283
  const heading = det.heading ?? det.direction;
238
284
  if (typeof heading === "number" && Number.isFinite(heading)) target.relativeDirection = heading;
285
+ target.state = det.state ?? ObcPoiState.Enabled;
286
+ target.data = det.data ?? [];
287
+ target.xFilterCutoffHz = this.xFilterCutoffHz ?? 16;
288
+ target.yFilterCutoffHz = this.yFilterCutoffHz ?? 16;
239
289
  });
240
290
  Array.from(this.controllerTargets.entries()).forEach(([key, target]) => {
241
291
  if (!activeKeys.has(key)) {
@@ -267,6 +317,14 @@ __decorate([property({ type: Number })], ObcPoiController.prototype, "frameIndex
267
317
  __decorate([property({ type: Number })], ObcPoiController.prototype, "confidenceMin", void 0);
268
318
  __decorate([property({ type: Array })], ObcPoiController.prototype, "classFilter", void 0);
269
319
  __decorate([property({ attribute: false })], ObcPoiController.prototype, "keyFn", void 0);
320
+ __decorate([property({
321
+ type: Number,
322
+ attribute: "x-filter-cutoff-hz"
323
+ })], ObcPoiController.prototype, "xFilterCutoffHz", void 0);
324
+ __decorate([property({
325
+ type: Number,
326
+ attribute: "y-filter-cutoff-hz"
327
+ })], ObcPoiController.prototype, "yFilterCutoffHz", void 0);
270
328
  __decorate([state()], ObcPoiController.prototype, "mediaWidth", void 0);
271
329
  __decorate([state()], ObcPoiController.prototype, "mediaHeight", void 0);
272
330
  __decorate([state()], ObcPoiController.prototype, "renderWidth", void 0);
@@ -281,6 +339,6 @@ __decorate([queryAssignedElements({
281
339
  })], ObcPoiController.prototype, "stackElements", void 0);
282
340
  ObcPoiController = __decorate([customElement("obc-poi-controller")], ObcPoiController);
283
341
  //#endregion
284
- export { ObcPoiController, PoiFitMode };
342
+ export { ObcPoiController, POI_CONTROLLER_BACKGROUND_LAYER, POI_CONTROLLER_LAYER_ATTR, PoiDetectionVariant, PoiFitMode };
285
343
 
286
344
  //# sourceMappingURL=poi-controller.js.map