@limetech/lime-elements 37.49.0 → 37.49.1

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.
@@ -4,22 +4,37 @@ import { createPopper, } from '@popperjs/core';
4
4
  * The portal component provides a way to render children into a DOM node that
5
5
  * exist outside the DOM hierarchy of the parent component.
6
6
  *
7
+ * When the limel-portal component is used, it creates a new DOM node (a div element)
8
+ * and appends it to a parent element (by default, the body of the document).
9
+ * The child elements of the limel-portal are then moved from
10
+ * their original location in the DOM to this new div element.
11
+ *
12
+ * This technique is often used to overcome CSS stacking context issues,
13
+ * or to render UI elements like modals, dropdowns, tooltips, etc.,
14
+ * that need to visually "break out" of their container.
15
+ *
16
+ * Using this component, we ensure that the content is always rendered in the
17
+ * correct position, and never covers its own trigger, or another component
18
+ * that is opened in the stacking layer. This way, we don't need to worry about
19
+ * z-indexes, or other stacking context issues.
20
+ *
21
+ * :::important
7
22
  * There are some caveats when using this component
8
23
  *
9
- * Events might not bubble up as expected since the content is moved out to
24
+ * 1. Events might not bubble up as expected since the content is moved out to
10
25
  * another DOM node.
11
- * Any styling that is applied to content from the parent will be lost, if the
12
- * content is just another web compoent it will work without any issues.
13
- * Alternatively, use the
14
- * `style=""` html attribute.
15
- * Any component that is placed inside the container must have a style of
26
+ * 2. Any styling that is applied to content from the parent will be lost, if the
27
+ * content is just another web-component it will work without any issues.
28
+ * Alternatively, use the `style=""` html attribute.
29
+ * 3. Any component that is placed inside the container must have a style of
16
30
  * `max-height: inherit`. This ensures that its placement is calculated
17
31
  * correctly in relation to the trigger, and that it never covers its own
18
32
  * trigger.
19
- * When the node is moved in the DOM, `disconnectedCallback` and
33
+ * 4. When the node is moved in the DOM, `disconnectedCallback` and
20
34
  * `connectedCallback` will be invoked, so if `disconnectedCallback` is used
21
35
  * to do any tear-down, the appropriate setup will have to be done again on
22
36
  * `connectedCallback`.
37
+ * :::
23
38
  *
24
39
  * @slot - Content to put inside the portal
25
40
  * @private
@@ -331,7 +346,7 @@ export class Portal {
331
346
  "optional": false,
332
347
  "docs": {
333
348
  "tags": [],
334
- "text": "Parent element to move the content to."
349
+ "text": "The `parent` property specifies the parent element where the content\nof the portal will be moved to.\nBy default, it is set to `document.body`, meaning the content\nwill be appended as a child of the body element in the DOM.\nIf you want the content to be appended to a different element,\nyou can specify that element by setting this property.\nPlease note that the specified parent element should exist\nin the DOM at the time of rendering the portal."
335
350
  },
336
351
  "defaultValue": "document.body"
337
352
  },
@@ -1 +1 @@
1
- {"version":3,"file":"portal.js","sourceRoot":"","sources":["../../../src/components/portal/portal.tsx"],"names":[],"mappings":"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","sourcesContent":["import { Component, Element, h, Prop, Watch } from '@stencil/core';\nimport { OpenDirection } from '../menu/menu.types';\nimport {\n createPopper,\n Instance,\n OptionsGeneric,\n Placement,\n} from '@popperjs/core';\nimport { FlipModifier } from '@popperjs/core/lib/modifiers/flip';\n\n/**\n * The portal component provides a way to render children into a DOM node that\n * exist outside the DOM hierarchy of the parent component.\n *\n * There are some caveats when using this component\n *\n * Events might not bubble up as expected since the content is moved out to\n * another DOM node.\n * Any styling that is applied to content from the parent will be lost, if the\n * content is just another web compoent it will work without any issues.\n * Alternatively, use the\n * `style=\"\"` html attribute.\n * Any component that is placed inside the container must have a style of\n * `max-height: inherit`. This ensures that its placement is calculated\n * correctly in relation to the trigger, and that it never covers its own\n * trigger.\n * When the node is moved in the DOM, `disconnectedCallback` and\n * `connectedCallback` will be invoked, so if `disconnectedCallback` is used\n * to do any tear-down, the appropriate setup will have to be done again on\n * `connectedCallback`.\n *\n * @slot - Content to put inside the portal\n * @private\n * @exampleComponent limel-example-portal-basic\n */\n@Component({\n tag: 'limel-portal',\n shadow: true,\n styleUrl: 'portal.scss',\n})\nexport class Portal {\n /**\n * Decides which direction the portal content should open.\n */\n @Prop({ reflect: true })\n public openDirection: OpenDirection = 'bottom';\n\n /**\n * Position of the content.\n */\n @Prop({ reflect: true })\n public position: 'fixed' | 'absolute' = 'absolute';\n\n /**\n * A unique ID.\n */\n @Prop({ reflect: true })\n public containerId: string;\n\n /**\n * Dynamic styling that can be applied to the container holding the content.\n */\n @Prop()\n public containerStyle: object = {};\n\n /**\n * Parent element to move the content to.\n */\n @Prop()\n public parent: HTMLElement = document.body;\n\n /**\n * Used to make a dropdown have the same width as the trigger, for example\n * in `limel-picker`.\n */\n @Prop({ reflect: true })\n public inheritParentWidth = false;\n\n /**\n * True if the content within the portal should be visible.\n *\n * If the content is from within a dialog for instance, this can be set to\n * true from false when the dialog opens to position the content properly.\n */\n @Prop({ reflect: true })\n public visible = false;\n\n /**\n * The element that the content should be positioned relative to.\n * Defaults to the limel-portal element.\n */\n @Prop()\n public anchor?: HTMLElement = null;\n\n @Element()\n private host: HTMLLimelPortalElement;\n\n private parents: WeakMap<HTMLElement, HTMLElement>;\n private container: HTMLElement;\n private popperInstance: Instance;\n private loaded = false;\n private observer: ResizeObserver;\n\n constructor() {\n this.parents = new WeakMap();\n }\n\n public disconnectedCallback() {\n this.removeContainer();\n this.destroyPopper();\n if (this.observer) {\n this.observer.unobserve(this.container);\n }\n }\n\n public connectedCallback() {\n if (!this.loaded) {\n return;\n }\n\n this.createContainer();\n this.hideContainer();\n this.attachContainer();\n this.styleContainer();\n\n if (this.visible) {\n this.createPopper();\n this.showContainer();\n }\n\n if ('ResizeObserver' in window) {\n const observer = new ResizeObserver(() => {\n if (this.popperInstance) {\n this.styleContainer();\n this.popperInstance.update();\n }\n });\n observer.observe(this.container);\n }\n }\n\n public componentDidLoad() {\n this.loaded = true;\n this.connectedCallback();\n }\n\n public render() {\n return <slot />;\n }\n\n @Watch('visible')\n protected onVisible() {\n if (!this.visible) {\n this.hideContainer();\n this.styleContainer();\n this.destroyPopper();\n\n return;\n }\n\n this.styleContainer();\n this.createPopper();\n requestAnimationFrame(() => {\n this.showContainer();\n });\n }\n\n private createContainer() {\n const slot: HTMLSlotElement =\n this.host.shadowRoot.querySelector('slot');\n const content =\n (slot.assignedElements && slot.assignedElements()) || [];\n\n this.container = document.createElement('div');\n this.container.setAttribute('id', this.containerId);\n this.container.setAttribute('class', 'limel-portal--container');\n this.container.style.fontFamily =\n 'var(--limel-portal-font-family, inherit)';\n Object.assign(this.container, {\n portalSource: this.host,\n });\n\n content.forEach((element: HTMLElement) => {\n this.parents.set(element, element.parentElement);\n this.container.appendChild(element);\n });\n }\n\n private attachContainer() {\n this.parent.appendChild(this.container);\n }\n\n private removeContainer() {\n if (!this.container) {\n return;\n }\n\n Array.from(this.container.children).forEach((element: HTMLElement) => {\n const parent = this.parents.get(element);\n if (!parent) {\n return;\n }\n\n parent.appendChild(element);\n });\n\n this.hideContainer();\n this.container.parentElement.removeChild(this.container);\n }\n\n private hideContainer() {\n this.container.style.opacity = '0';\n }\n\n private showContainer() {\n this.container.style.opacity = '1';\n }\n\n private styleContainer() {\n const hostWidth = this.host.getBoundingClientRect().width;\n\n if (this.visible) {\n this.container.style.display = 'block';\n } else {\n this.container.style.display = 'none';\n }\n\n if (this.inheritParentWidth) {\n const containerWidth = this.getContentWidth(this.container);\n let width = containerWidth;\n if (hostWidth > 0) {\n width = hostWidth;\n }\n\n this.container.style.width = `${width}px`;\n }\n\n this.ensureContainerFitsInViewPort();\n\n Object.keys(this.containerStyle).forEach((property) => {\n this.container.style[property] = this.containerStyle[property];\n });\n }\n\n private getContentWidth(element: HTMLElement | Element) {\n if (!element) {\n return null;\n }\n\n const width = element.getBoundingClientRect().width;\n if (width !== 0) {\n return width;\n }\n\n const elementContent = element.querySelector('*');\n\n return this.getContentWidth(elementContent);\n }\n\n private createPopper() {\n const config = this.createPopperConfig();\n\n this.popperInstance = createPopper(\n this.anchor || this.host,\n this.container,\n config,\n );\n }\n\n private destroyPopper() {\n this.popperInstance?.destroy();\n this.popperInstance = null;\n }\n\n private createPopperConfig(): Partial<\n OptionsGeneric<Partial<FlipModifier>>\n > {\n const placement = this.getPlacement(this.openDirection);\n const flipPlacement = this.getFlipPlacement(this.openDirection);\n\n return {\n strategy: this.position,\n placement: placement,\n modifiers: [\n {\n name: 'flip',\n options: {\n fallbackPlacements: [flipPlacement],\n },\n },\n ],\n };\n }\n\n private getPlacement(direction: OpenDirection): Placement {\n const placements: Record<OpenDirection, Placement> = {\n 'left-start': 'left-start',\n left: 'left',\n 'left-end': 'left-end',\n 'right-start': 'right-start',\n right: 'right',\n 'right-end': 'right-end',\n 'top-start': 'top-start',\n top: 'top',\n 'top-end': 'top-end',\n 'bottom-start': 'bottom-start',\n bottom: 'bottom',\n 'bottom-end': 'bottom-end',\n };\n\n return placements[direction];\n }\n\n private getFlipPlacement(direction: OpenDirection): Placement {\n const flipPlacements: Record<OpenDirection, Placement> = {\n 'left-start': 'right-start',\n left: 'right',\n 'left-end': 'right-end',\n 'right-start': 'left-start',\n right: 'left',\n 'right-end': 'left-end',\n 'top-start': 'bottom-start',\n top: 'bottom',\n 'top-end': 'bottom-end',\n 'bottom-start': 'top-start',\n bottom: 'top',\n 'bottom-end': 'top-end',\n };\n\n return flipPlacements[direction];\n }\n\n private ensureContainerFitsInViewPort() {\n const viewHeight = Math.max(\n document.documentElement.clientHeight || 0,\n window.innerHeight || 0,\n );\n\n const { top, bottom } = this.host.getBoundingClientRect();\n const spaceAboveTopOfSurface = Math.max(top, 0);\n const spaceBelowTopOfSurface = Math.max(viewHeight - bottom, 0);\n const extraCosmeticSpace = 16;\n const maxHeight =\n Math.max(spaceAboveTopOfSurface, spaceBelowTopOfSurface) -\n extraCosmeticSpace;\n\n this.container.style.maxHeight = `${maxHeight}px`;\n }\n}\n"]}
1
+ {"version":3,"file":"portal.js","sourceRoot":"","sources":["../../../src/components/portal/portal.tsx"],"names":[],"mappings":"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","sourcesContent":["import { Component, Element, h, Prop, Watch } from '@stencil/core';\nimport { OpenDirection } from '../menu/menu.types';\nimport {\n createPopper,\n Instance,\n OptionsGeneric,\n Placement,\n} from '@popperjs/core';\nimport { FlipModifier } from '@popperjs/core/lib/modifiers/flip';\n\n/**\n * The portal component provides a way to render children into a DOM node that\n * exist outside the DOM hierarchy of the parent component.\n *\n * When the limel-portal component is used, it creates a new DOM node (a div element)\n * and appends it to a parent element (by default, the body of the document).\n * The child elements of the limel-portal are then moved from\n * their original location in the DOM to this new div element.\n *\n * This technique is often used to overcome CSS stacking context issues,\n * or to render UI elements like modals, dropdowns, tooltips, etc.,\n * that need to visually \"break out\" of their container.\n *\n * Using this component, we ensure that the content is always rendered in the\n * correct position, and never covers its own trigger, or another component\n * that is opened in the stacking layer. This way, we don't need to worry about\n * z-indexes, or other stacking context issues.\n *\n * :::important\n * There are some caveats when using this component\n *\n * 1. Events might not bubble up as expected since the content is moved out to\n * another DOM node.\n * 2. Any styling that is applied to content from the parent will be lost, if the\n * content is just another web-component it will work without any issues.\n * Alternatively, use the `style=\"\"` html attribute.\n * 3. Any component that is placed inside the container must have a style of\n * `max-height: inherit`. This ensures that its placement is calculated\n * correctly in relation to the trigger, and that it never covers its own\n * trigger.\n * 4. When the node is moved in the DOM, `disconnectedCallback` and\n * `connectedCallback` will be invoked, so if `disconnectedCallback` is used\n * to do any tear-down, the appropriate setup will have to be done again on\n * `connectedCallback`.\n * :::\n *\n * @slot - Content to put inside the portal\n * @private\n * @exampleComponent limel-example-portal-basic\n */\n@Component({\n tag: 'limel-portal',\n shadow: true,\n styleUrl: 'portal.scss',\n})\nexport class Portal {\n /**\n * Decides which direction the portal content should open.\n */\n @Prop({ reflect: true })\n public openDirection: OpenDirection = 'bottom';\n\n /**\n * Position of the content.\n */\n @Prop({ reflect: true })\n public position: 'fixed' | 'absolute' = 'absolute';\n\n /**\n * A unique ID.\n */\n @Prop({ reflect: true })\n public containerId: string;\n\n /**\n * Dynamic styling that can be applied to the container holding the content.\n */\n @Prop()\n public containerStyle: object = {};\n\n /**\n * The `parent` property specifies the parent element where the content\n * of the portal will be moved to.\n * By default, it is set to `document.body`, meaning the content\n * will be appended as a child of the body element in the DOM.\n * If you want the content to be appended to a different element,\n * you can specify that element by setting this property.\n * Please note that the specified parent element should exist\n * in the DOM at the time of rendering the portal.\n */\n @Prop()\n public parent: HTMLElement = document.body;\n\n /**\n * Used to make a dropdown have the same width as the trigger, for example\n * in `limel-picker`.\n */\n @Prop({ reflect: true })\n public inheritParentWidth = false;\n\n /**\n * True if the content within the portal should be visible.\n *\n * If the content is from within a dialog for instance, this can be set to\n * true from false when the dialog opens to position the content properly.\n */\n @Prop({ reflect: true })\n public visible = false;\n\n /**\n * The element that the content should be positioned relative to.\n * Defaults to the limel-portal element.\n */\n @Prop()\n public anchor?: HTMLElement = null;\n\n @Element()\n private host: HTMLLimelPortalElement;\n\n private parents: WeakMap<HTMLElement, HTMLElement>;\n private container: HTMLElement;\n private popperInstance: Instance;\n private loaded = false;\n private observer: ResizeObserver;\n\n constructor() {\n this.parents = new WeakMap();\n }\n\n public disconnectedCallback() {\n this.removeContainer();\n this.destroyPopper();\n if (this.observer) {\n this.observer.unobserve(this.container);\n }\n }\n\n public connectedCallback() {\n if (!this.loaded) {\n return;\n }\n\n this.createContainer();\n this.hideContainer();\n this.attachContainer();\n this.styleContainer();\n\n if (this.visible) {\n this.createPopper();\n this.showContainer();\n }\n\n if ('ResizeObserver' in window) {\n const observer = new ResizeObserver(() => {\n if (this.popperInstance) {\n this.styleContainer();\n this.popperInstance.update();\n }\n });\n observer.observe(this.container);\n }\n }\n\n public componentDidLoad() {\n this.loaded = true;\n this.connectedCallback();\n }\n\n public render() {\n return <slot />;\n }\n\n @Watch('visible')\n protected onVisible() {\n if (!this.visible) {\n this.hideContainer();\n this.styleContainer();\n this.destroyPopper();\n\n return;\n }\n\n this.styleContainer();\n this.createPopper();\n requestAnimationFrame(() => {\n this.showContainer();\n });\n }\n\n private createContainer() {\n const slot: HTMLSlotElement =\n this.host.shadowRoot.querySelector('slot');\n const content =\n (slot.assignedElements && slot.assignedElements()) || [];\n\n this.container = document.createElement('div');\n this.container.setAttribute('id', this.containerId);\n this.container.setAttribute('class', 'limel-portal--container');\n this.container.style.fontFamily =\n 'var(--limel-portal-font-family, inherit)';\n Object.assign(this.container, {\n portalSource: this.host,\n });\n\n content.forEach((element: HTMLElement) => {\n this.parents.set(element, element.parentElement);\n this.container.appendChild(element);\n });\n }\n\n private attachContainer() {\n this.parent.appendChild(this.container);\n }\n\n private removeContainer() {\n if (!this.container) {\n return;\n }\n\n Array.from(this.container.children).forEach((element: HTMLElement) => {\n const parent = this.parents.get(element);\n if (!parent) {\n return;\n }\n\n parent.appendChild(element);\n });\n\n this.hideContainer();\n this.container.parentElement.removeChild(this.container);\n }\n\n private hideContainer() {\n this.container.style.opacity = '0';\n }\n\n private showContainer() {\n this.container.style.opacity = '1';\n }\n\n private styleContainer() {\n const hostWidth = this.host.getBoundingClientRect().width;\n\n if (this.visible) {\n this.container.style.display = 'block';\n } else {\n this.container.style.display = 'none';\n }\n\n if (this.inheritParentWidth) {\n const containerWidth = this.getContentWidth(this.container);\n let width = containerWidth;\n if (hostWidth > 0) {\n width = hostWidth;\n }\n\n this.container.style.width = `${width}px`;\n }\n\n this.ensureContainerFitsInViewPort();\n\n Object.keys(this.containerStyle).forEach((property) => {\n this.container.style[property] = this.containerStyle[property];\n });\n }\n\n private getContentWidth(element: HTMLElement | Element) {\n if (!element) {\n return null;\n }\n\n const width = element.getBoundingClientRect().width;\n if (width !== 0) {\n return width;\n }\n\n const elementContent = element.querySelector('*');\n\n return this.getContentWidth(elementContent);\n }\n\n private createPopper() {\n const config = this.createPopperConfig();\n\n this.popperInstance = createPopper(\n this.anchor || this.host,\n this.container,\n config,\n );\n }\n\n private destroyPopper() {\n this.popperInstance?.destroy();\n this.popperInstance = null;\n }\n\n private createPopperConfig(): Partial<\n OptionsGeneric<Partial<FlipModifier>>\n > {\n const placement = this.getPlacement(this.openDirection);\n const flipPlacement = this.getFlipPlacement(this.openDirection);\n\n return {\n strategy: this.position,\n placement: placement,\n modifiers: [\n {\n name: 'flip',\n options: {\n fallbackPlacements: [flipPlacement],\n },\n },\n ],\n };\n }\n\n private getPlacement(direction: OpenDirection): Placement {\n const placements: Record<OpenDirection, Placement> = {\n 'left-start': 'left-start',\n left: 'left',\n 'left-end': 'left-end',\n 'right-start': 'right-start',\n right: 'right',\n 'right-end': 'right-end',\n 'top-start': 'top-start',\n top: 'top',\n 'top-end': 'top-end',\n 'bottom-start': 'bottom-start',\n bottom: 'bottom',\n 'bottom-end': 'bottom-end',\n };\n\n return placements[direction];\n }\n\n private getFlipPlacement(direction: OpenDirection): Placement {\n const flipPlacements: Record<OpenDirection, Placement> = {\n 'left-start': 'right-start',\n left: 'right',\n 'left-end': 'right-end',\n 'right-start': 'left-start',\n right: 'left',\n 'right-end': 'left-end',\n 'top-start': 'bottom-start',\n top: 'bottom',\n 'top-end': 'bottom-end',\n 'bottom-start': 'top-start',\n bottom: 'top',\n 'bottom-end': 'top-end',\n };\n\n return flipPlacements[direction];\n }\n\n private ensureContainerFitsInViewPort() {\n const viewHeight = Math.max(\n document.documentElement.clientHeight || 0,\n window.innerHeight || 0,\n );\n\n const { top, bottom } = this.host.getBoundingClientRect();\n const spaceAboveTopOfSurface = Math.max(top, 0);\n const spaceBelowTopOfSurface = Math.max(viewHeight - bottom, 0);\n const extraCosmeticSpace = 16;\n const maxHeight =\n Math.max(spaceAboveTopOfSurface, spaceBelowTopOfSurface) -\n extraCosmeticSpace;\n\n this.container.style.maxHeight = `${maxHeight}px`;\n }\n}\n"]}
@@ -146,8 +146,8 @@ export class ProsemirrorAdapter {
146
146
  render() {
147
147
  return [
148
148
  h("div", { id: "editor" }),
149
- h("limel-action-bar", { slot: "trigger", accessibleLabel: "Toolbar", actions: this.actionBarItems, onItemSelected: this.handleActionBarItem }),
150
- h("limel-portal", { containerId: this.portalId, visible: this.isLinkMenuOpen, openDirection: "top", inheritParentWidth: true, containerStyle: { 'z-index': 1 } }, h("limel-menu-surface", { open: this.isLinkMenuOpen, onDismiss: this.handleCancelLinkMenu, style: {
149
+ h("limel-action-bar", { ref: (el) => (this.actionBarElement = el), accessibleLabel: "Toolbar", actions: this.actionBarItems, onItemSelected: this.handleActionBarItem }),
150
+ h("limel-portal", { containerId: this.portalId, visible: this.isLinkMenuOpen, openDirection: "top", inheritParentWidth: true, anchor: this.actionBarElement, containerStyle: { 'z-index': 1 } }, h("limel-menu-surface", { open: this.isLinkMenuOpen, onDismiss: this.handleCancelLinkMenu, style: {
151
151
  '--mdc-menu-min-width': '100%',
152
152
  'max-height': 'inherit',
153
153
  } }, h("limel-text-editor-link-menu", { link: this.link, isOpen: this.isLinkMenuOpen, onLinkChange: this.handleLinkChange, onCancel: this.handleCancelLinkMenu, onSave: this.handleSaveLinkMenu }))),
@@ -1 +1 @@
1
- {"version":3,"file":"prosemirror-adapter.js","sourceRoot":"","sources":["../../../../src/components/text-editor/prosemirror-adapter/prosemirror-adapter.tsx"],"names":[],"mappings":"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","sourcesContent":["import {\n Component,\n Element,\n Event,\n EventEmitter,\n Prop,\n State,\n Watch,\n h,\n} from '@stencil/core';\nimport { EditorState, Transaction } from 'prosemirror-state';\nimport { EditorView } from 'prosemirror-view';\nimport { Schema, DOMParser } from 'prosemirror-model';\nimport { schema } from 'prosemirror-schema-basic';\nimport { addListNodes } from 'prosemirror-schema-list';\nimport { exampleSetup } from 'prosemirror-example-setup';\nimport { keymap } from 'prosemirror-keymap';\nimport { ActionBarItem } from 'src/components/action-bar/action-bar.types';\nimport { ListSeparator } from 'src/components/list/list-item.types';\nimport { MenuCommandFactory } from './menu/menu-commands';\nimport { menuTranslationIDs, getTextEditorMenuItems } from './menu/menu-items';\nimport { ContentTypeConverter } from '../utils/content-type-converter';\nimport { markdownConverter } from '../utils/markdown-converter';\nimport { HTMLConverter } from '../utils/html-converter';\nimport {\n EditorMenuTypes,\n EditorTextLink,\n editorMenuTypesArray,\n} from './menu/types';\nimport translate from 'src/global/translations';\nimport { createRandomString } from 'src/util/random-string';\nimport { isItem } from 'src/components/action-bar/isItem';\nimport { cloneDeep } from 'lodash-es';\nimport { Languages } from '../../date-picker/date.types';\nimport { strikethrough } from './menu/menu-schema-extender';\nimport {\n EditorLinkMenuEventDetail,\n createLinkPlugin,\n} from './plugins/link-plugin';\nimport { createImageRemoverPlugin } from './plugins/image-remover-plugin';\nimport { createMenuStateTrackingPlugin } from './plugins/menu-state-tracking-plugin';\nimport { createActionBarInteractionPlugin } from './plugins/menu-action-interaction-plugin';\n\n/**\n * The ProseMirror adapter offers a rich text editing experience with markdown support.\n * [Read more...](https://prosemirror.net/)\n *\n * @exampleComponent limel-example-prosemirror-adapter-basic\n * @exampleComponent limel-example-prosemirror-adapter-with-custom-menu\n * @beta\n * @private\n */\n@Component({\n tag: 'limel-prosemirror-adapter',\n shadow: true,\n styleUrl: 'prosemirror-adapter.scss',\n})\nexport class ProsemirrorAdapter {\n /**\n * The type of content that the editor should handle and emit, defaults to `markdown`\n *\n * Assumed to be set only once, so not reactive to changes\n */\n @Prop()\n public contentType: 'markdown' | 'html' = 'markdown';\n\n /**\n * The value of the editor, expected to be markdown\n */\n @Prop()\n public value: string;\n\n /**\n * Defines the language for translations.\n */\n @Prop({ reflect: true })\n public language: Languages;\n\n @Element()\n private host: HTMLLimelTextEditorElement;\n\n private portalId: string;\n\n @State()\n private view: EditorView;\n\n @State()\n private actionBarItems: Array<\n ActionBarItem<EditorMenuTypes> | ListSeparator\n > = [];\n\n @State()\n private link: EditorTextLink = { href: '' };\n\n /**\n * Open state of the dialog\n */\n @State()\n public isLinkMenuOpen: boolean = false;\n\n private menuCommandFactory: MenuCommandFactory;\n private schema: Schema;\n private contentConverter: ContentTypeConverter;\n private suppressChangeEvent = false;\n\n /**\n * Dispatched when a change is made to the editor\n */\n @Event()\n private change: EventEmitter<string>;\n\n constructor() {\n this.portalId = createRandomString();\n }\n\n @Watch('value')\n protected watchValue(newValue: string) {\n if (\n !this.view ||\n newValue === this.contentConverter.serialize(this.view, this.schema)\n ) {\n return;\n }\n\n this.updateView(newValue);\n }\n\n public componentWillLoad() {\n this.getActionBarItems();\n this.setupContentConverter();\n }\n\n public componentDidLoad() {\n // Stencil complains loudly about triggering rerenders in\n // componentDidLoad, but we have to, so we're using setTimeout to\n // suppress the warning. /Ads\n setTimeout(() => {\n this.initializeTextEditor();\n }, 0);\n }\n\n public connectedCallback() {\n if (this.view) {\n this.initializeTextEditor();\n }\n\n this.host.addEventListener(\n 'open-editor-link-menu',\n this.handleOpenLinkMenu,\n );\n }\n\n public disconnectedCallback() {\n this.host.removeEventListener(\n 'open-editor-link-menu',\n this.handleOpenLinkMenu,\n );\n this.view.destroy();\n }\n\n public render() {\n return [\n <div id=\"editor\" />,\n <limel-action-bar\n slot=\"trigger\"\n accessibleLabel=\"Toolbar\"\n actions={this.actionBarItems}\n onItemSelected={this.handleActionBarItem}\n />,\n <limel-portal\n containerId={this.portalId}\n visible={this.isLinkMenuOpen}\n openDirection=\"top\"\n inheritParentWidth={true}\n containerStyle={{ 'z-index': 1 }}\n >\n <limel-menu-surface\n open={this.isLinkMenuOpen}\n onDismiss={this.handleCancelLinkMenu}\n style={{\n '--mdc-menu-min-width': '100%',\n 'max-height': 'inherit',\n }}\n >\n <limel-text-editor-link-menu\n link={this.link}\n isOpen={this.isLinkMenuOpen}\n onLinkChange={this.handleLinkChange}\n onCancel={this.handleCancelLinkMenu}\n onSave={this.handleSaveLinkMenu}\n />\n </limel-menu-surface>\n </limel-portal>,\n ];\n }\n\n private setupContentConverter() {\n if (this.contentType === 'markdown') {\n this.contentConverter = new markdownConverter();\n } else if (this.contentType === 'html') {\n this.contentConverter = new HTMLConverter();\n } else {\n throw new Error(\n `Unsupported content type: ${this.contentType}. Only 'markdown' and 'html' are supported.`,\n );\n }\n }\n\n private getActionBarItems = () => {\n this.actionBarItems = getTextEditorMenuItems().map(\n this.getTranslatedItem,\n );\n };\n\n private getTranslatedItem = (item) => {\n const newItem = cloneDeep(item);\n\n if (isItem(item)) {\n const translationId = menuTranslationIDs[item.value];\n\n if (translationId) {\n newItem.text = translate.get(translationId, this.language);\n }\n }\n\n return newItem;\n };\n\n private async initializeTextEditor() {\n this.schema = this.initializeSchema();\n const initialDoc = await this.parseInitialContent();\n this.menuCommandFactory = new MenuCommandFactory(this.schema);\n this.view = new EditorView(\n this.host.shadowRoot.querySelector('#editor'),\n {\n state: this.createEditorState(initialDoc),\n dispatchTransaction: this.handleTransaction,\n },\n );\n\n if (this.value) {\n this.updateView(this.value);\n }\n }\n\n private initializeSchema() {\n return new Schema({\n nodes: addListNodes(schema.spec.nodes, 'paragraph block*', 'block'),\n marks: schema.spec.marks.append({\n strikethrough: strikethrough,\n }),\n });\n }\n\n private async parseInitialContent() {\n const initialContentElement = document.createElement('div');\n\n if (this.value) {\n initialContentElement.innerHTML =\n await this.contentConverter.parseAsHTML(\n this.value,\n this.schema,\n );\n } else {\n initialContentElement.innerHTML = '<p></p>';\n }\n\n return DOMParser.fromSchema(this.schema).parse(initialContentElement);\n }\n\n private createEditorState(initialDoc) {\n return EditorState.create({\n doc: initialDoc,\n plugins: [\n ...exampleSetup({ schema: this.schema, menuBar: false }),\n keymap(this.menuCommandFactory.buildKeymap()),\n createLinkPlugin(this.handleNewLinkSelection),\n createImageRemoverPlugin(),\n createMenuStateTrackingPlugin(\n editorMenuTypesArray,\n this.menuCommandFactory,\n this.updateActiveActionBarItems,\n ),\n createActionBarInteractionPlugin(this.menuCommandFactory),\n ],\n });\n }\n\n private updateActiveActionBarItems = (\n activeTypes: Record<EditorMenuTypes, boolean>,\n ) => {\n const newItems = getTextEditorMenuItems().map((item) => {\n if (isItem(item)) {\n return {\n ...item,\n selected: activeTypes[item.value],\n };\n }\n\n return item;\n });\n\n this.actionBarItems = newItems;\n };\n\n private async updateView(content: string) {\n this.suppressChangeEvent = true;\n const html = await this.contentConverter.parseAsHTML(\n content,\n this.schema,\n );\n const prosemirrorDOMparser = DOMParser.fromSchema(\n this.view.state.schema,\n );\n const domParser = new window.DOMParser();\n const doc = domParser.parseFromString(html, 'text/html');\n const prosemirrorDoc = prosemirrorDOMparser.parse(doc.body);\n const tr = this.view.state.tr;\n tr.replaceWith(0, tr.doc.content.size, prosemirrorDoc.content);\n this.view.dispatch(tr);\n this.suppressChangeEvent = false;\n }\n\n private handleTransaction = (transaction: Transaction) => {\n const newState = this.view.state.apply(transaction);\n this.view.updateState(newState);\n\n if (this.suppressChangeEvent) {\n return;\n }\n\n if (transaction.getMeta('pointer')) {\n return;\n }\n\n this.change.emit(\n this.contentConverter.serialize(this.view, this.schema),\n );\n };\n\n private handleActionBarItem = (\n event: CustomEvent<ActionBarItem<EditorMenuTypes>>,\n ) => {\n event.preventDefault();\n event.stopImmediatePropagation();\n const { value } = event.detail;\n\n if (value === EditorMenuTypes.Link) {\n this.isLinkMenuOpen = true;\n\n return;\n }\n\n const actionBarEvent = new CustomEvent('actionBarItemClick', {\n detail: event.detail,\n });\n this.view.dom.dispatchEvent(actionBarEvent);\n };\n\n private handleCancelLinkMenu = () => {\n this.isLinkMenuOpen = false;\n };\n\n private handleSaveLinkMenu = () => {\n this.isLinkMenuOpen = false;\n\n const saveLinkEvent = new CustomEvent('saveLinkMenu', {\n detail: {\n type: EditorMenuTypes.Link,\n link: this.link,\n },\n });\n this.view.dom.dispatchEvent(saveLinkEvent);\n\n this.link = { href: '' };\n };\n\n private handleLinkChange = (event: CustomEvent<EditorTextLink>) => {\n this.link = event.detail;\n };\n\n public setFocus() {\n this.view?.focus();\n }\n\n private handleNewLinkSelection = (text: string, href: string) => {\n this.link.text = text;\n this.link.href = href;\n };\n\n private handleOpenLinkMenu = (\n event: CustomEvent<EditorLinkMenuEventDetail>,\n ) => {\n event.stopImmediatePropagation();\n const { href, text } = event.detail;\n this.link = { href: href, text: text };\n this.isLinkMenuOpen = true;\n };\n}\n"]}
1
+ {"version":3,"file":"prosemirror-adapter.js","sourceRoot":"","sources":["../../../../src/components/text-editor/prosemirror-adapter/prosemirror-adapter.tsx"],"names":[],"mappings":"AAAA,OAAO,EACH,SAAS,EACT,OAAO,EACP,KAAK,EAEL,IAAI,EACJ,KAAK,EACL,KAAK,EACL,CAAC,GACJ,MAAM,eAAe,CAAC;AACvB,OAAO,EAAE,WAAW,EAAe,MAAM,mBAAmB,CAAC;AAC7D,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAC9C,OAAO,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,mBAAmB,CAAC;AACtD,OAAO,EAAE,MAAM,EAAE,MAAM,0BAA0B,CAAC;AAClD,OAAO,EAAE,YAAY,EAAE,MAAM,yBAAyB,CAAC;AACvD,OAAO,EAAE,YAAY,EAAE,MAAM,2BAA2B,CAAC;AACzD,OAAO,EAAE,MAAM,EAAE,MAAM,oBAAoB,CAAC;AAG5C,OAAO,EAAE,kBAAkB,EAAE,MAAM,sBAAsB,CAAC;AAC1D,OAAO,EAAE,kBAAkB,EAAE,sBAAsB,EAAE,MAAM,mBAAmB,CAAC;AAE/E,OAAO,EAAE,iBAAiB,EAAE,MAAM,6BAA6B,CAAC;AAChE,OAAO,EAAE,aAAa,EAAE,MAAM,yBAAyB,CAAC;AACxD,OAAO,EACH,eAAe,EAEf,oBAAoB,GACvB,MAAM,cAAc,CAAC;AACtB,OAAO,SAAS,MAAM,yBAAyB,CAAC;AAChD,OAAO,EAAE,kBAAkB,EAAE,MAAM,wBAAwB,CAAC;AAC5D,OAAO,EAAE,MAAM,EAAE,MAAM,kCAAkC,CAAC;AAC1D,OAAO,EAAE,SAAS,EAAE,MAAM,WAAW,CAAC;AAEtC,OAAO,EAAE,aAAa,EAAE,MAAM,6BAA6B,CAAC;AAC5D,OAAO,EAEH,gBAAgB,GACnB,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EAAE,wBAAwB,EAAE,MAAM,gCAAgC,CAAC;AAC1E,OAAO,EAAE,6BAA6B,EAAE,MAAM,sCAAsC,CAAC;AACrF,OAAO,EAAE,gCAAgC,EAAE,MAAM,0CAA0C,CAAC;AAE5F;;;;;;;;GAQG;AAMH,MAAM,OAAO,kBAAkB;EAuD3B;IATQ,wBAAmB,GAAG,KAAK,CAAC;IA2G5B,sBAAiB,GAAG,GAAG,EAAE;MAC7B,IAAI,CAAC,cAAc,GAAG,sBAAsB,EAAE,CAAC,GAAG,CAC9C,IAAI,CAAC,iBAAiB,CACzB,CAAC;IACN,CAAC,CAAC;IAEM,sBAAiB,GAAG,CAAC,IAAI,EAAE,EAAE;MACjC,MAAM,OAAO,GAAG,SAAS,CAAC,IAAI,CAAC,CAAC;MAEhC,IAAI,MAAM,CAAC,IAAI,CAAC,EAAE;QACd,MAAM,aAAa,GAAG,kBAAkB,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QAErD,IAAI,aAAa,EAAE;UACf,OAAO,CAAC,IAAI,GAAG,SAAS,CAAC,GAAG,CAAC,aAAa,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAC;SAC9D;OACJ;MAED,OAAO,OAAO,CAAC;IACnB,CAAC,CAAC;IA8DM,+BAA0B,GAAG,CACjC,WAA6C,EAC/C,EAAE;MACA,MAAM,QAAQ,GAAG,sBAAsB,EAAE,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE;QACnD,IAAI,MAAM,CAAC,IAAI,CAAC,EAAE;UACd,uCACO,IAAI,KACP,QAAQ,EAAE,WAAW,CAAC,IAAI,CAAC,KAAK,CAAC,IACnC;SACL;QAED,OAAO,IAAI,CAAC;MAChB,CAAC,CAAC,CAAC;MAEH,IAAI,CAAC,cAAc,GAAG,QAAQ,CAAC;IACnC,CAAC,CAAC;IAoBM,sBAAiB,GAAG,CAAC,WAAwB,EAAE,EAAE;MACrD,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,KAAK,CAAC,WAAW,CAAC,CAAC;MACpD,IAAI,CAAC,IAAI,CAAC,WAAW,CAAC,QAAQ,CAAC,CAAC;MAEhC,IAAI,IAAI,CAAC,mBAAmB,EAAE;QAC1B,OAAO;OACV;MAED,IAAI,WAAW,CAAC,OAAO,CAAC,SAAS,CAAC,EAAE;QAChC,OAAO;OACV;MAED,IAAI,CAAC,MAAM,CAAC,IAAI,CACZ,IAAI,CAAC,gBAAgB,CAAC,SAAS,CAAC,IAAI,CAAC,IAAI,EAAE,IAAI,CAAC,MAAM,CAAC,CAC1D,CAAC;IACN,CAAC,CAAC;IAEM,wBAAmB,GAAG,CAC1B,KAAkD,EACpD,EAAE;MACA,KAAK,CAAC,cAAc,EAAE,CAAC;MACvB,KAAK,CAAC,wBAAwB,EAAE,CAAC;MACjC,MAAM,EAAE,KAAK,EAAE,GAAG,KAAK,CAAC,MAAM,CAAC;MAE/B,IAAI,KAAK,KAAK,eAAe,CAAC,IAAI,EAAE;QAChC,IAAI,CAAC,cAAc,GAAG,IAAI,CAAC;QAE3B,OAAO;OACV;MAED,MAAM,cAAc,GAAG,IAAI,WAAW,CAAC,oBAAoB,EAAE;QACzD,MAAM,EAAE,KAAK,CAAC,MAAM;OACvB,CAAC,CAAC;MACH,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,aAAa,CAAC,cAAc,CAAC,CAAC;IAChD,CAAC,CAAC;IAEM,yBAAoB,GAAG,GAAG,EAAE;MAChC,IAAI,CAAC,cAAc,GAAG,KAAK,CAAC;IAChC,CAAC,CAAC;IAEM,uBAAkB,GAAG,GAAG,EAAE;MAC9B,IAAI,CAAC,cAAc,GAAG,KAAK,CAAC;MAE5B,MAAM,aAAa,GAAG,IAAI,WAAW,CAAC,cAAc,EAAE;QAClD,MAAM,EAAE;UACJ,IAAI,EAAE,eAAe,CAAC,IAAI;UAC1B,IAAI,EAAE,IAAI,CAAC,IAAI;SAClB;OACJ,CAAC,CAAC;MACH,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,aAAa,CAAC,aAAa,CAAC,CAAC;MAE3C,IAAI,CAAC,IAAI,GAAG,EAAE,IAAI,EAAE,EAAE,EAAE,CAAC;IAC7B,CAAC,CAAC;IAEM,qBAAgB,GAAG,CAAC,KAAkC,EAAE,EAAE;MAC9D,IAAI,CAAC,IAAI,GAAG,KAAK,CAAC,MAAM,CAAC;IAC7B,CAAC,CAAC;IAMM,2BAAsB,GAAG,CAAC,IAAY,EAAE,IAAY,EAAE,EAAE;MAC5D,IAAI,CAAC,IAAI,CAAC,IAAI,GAAG,IAAI,CAAC;MACtB,IAAI,CAAC,IAAI,CAAC,IAAI,GAAG,IAAI,CAAC;IAC1B,CAAC,CAAC;IAEM,uBAAkB,GAAG,CACzB,KAA6C,EAC/C,EAAE;MACA,KAAK,CAAC,wBAAwB,EAAE,CAAC;MACjC,MAAM,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,KAAK,CAAC,MAAM,CAAC;MACpC,IAAI,CAAC,IAAI,GAAG,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC;MACvC,IAAI,CAAC,cAAc,GAAG,IAAI,CAAC;IAC/B,CAAC,CAAC;uBA/UwC,UAAU;;;;0BAyBhD,EAAE;gBAGyB,EAAE,IAAI,EAAE,EAAE,EAAE;0BAMV,KAAK;IAelC,IAAI,CAAC,QAAQ,GAAG,kBAAkB,EAAE,CAAC;GACxC;EAGS,UAAU,CAAC,QAAgB;IACjC,IACI,CAAC,IAAI,CAAC,IAAI;MACV,QAAQ,KAAK,IAAI,CAAC,gBAAgB,CAAC,SAAS,CAAC,IAAI,CAAC,IAAI,EAAE,IAAI,CAAC,MAAM,CAAC,EACtE;MACE,OAAO;KACV;IAED,IAAI,CAAC,UAAU,CAAC,QAAQ,CAAC,CAAC;EAC9B,CAAC;EAEM,iBAAiB;IACpB,IAAI,CAAC,iBAAiB,EAAE,CAAC;IACzB,IAAI,CAAC,qBAAqB,EAAE,CAAC;EACjC,CAAC;EAEM,gBAAgB;IACnB,yDAAyD;IACzD,iEAAiE;IACjE,6BAA6B;IAC7B,UAAU,CAAC,GAAG,EAAE;MACZ,IAAI,CAAC,oBAAoB,EAAE,CAAC;IAChC,CAAC,EAAE,CAAC,CAAC,CAAC;EACV,CAAC;EAEM,iBAAiB;IACpB,IAAI,IAAI,CAAC,IAAI,EAAE;MACX,IAAI,CAAC,oBAAoB,EAAE,CAAC;KAC/B;IAED,IAAI,CAAC,IAAI,CAAC,gBAAgB,CACtB,uBAAuB,EACvB,IAAI,CAAC,kBAAkB,CAC1B,CAAC;EACN,CAAC;EAEM,oBAAoB;IACvB,IAAI,CAAC,IAAI,CAAC,mBAAmB,CACzB,uBAAuB,EACvB,IAAI,CAAC,kBAAkB,CAC1B,CAAC;IACF,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC;EACxB,CAAC;EAEM,MAAM;IACT,OAAO;MACH,WAAK,EAAE,EAAC,QAAQ,GAAG;MACnB,wBACI,GAAG,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,IAAI,CAAC,gBAAgB,GAAG,EAAE,CAAC,EACzC,eAAe,EAAC,SAAS,EACzB,OAAO,EAAE,IAAI,CAAC,cAAc,EAC5B,cAAc,EAAE,IAAI,CAAC,mBAAmB,GAC1C;MACF,oBACI,WAAW,EAAE,IAAI,CAAC,QAAQ,EAC1B,OAAO,EAAE,IAAI,CAAC,cAAc,EAC5B,aAAa,EAAC,KAAK,EACnB,kBAAkB,EAAE,IAAI,EACxB,MAAM,EAAE,IAAI,CAAC,gBAAgB,EAC7B,cAAc,EAAE,EAAE,SAAS,EAAE,CAAC,EAAE;QAEhC,0BACI,IAAI,EAAE,IAAI,CAAC,cAAc,EACzB,SAAS,EAAE,IAAI,CAAC,oBAAoB,EACpC,KAAK,EAAE;YACH,sBAAsB,EAAE,MAAM;YAC9B,YAAY,EAAE,SAAS;WAC1B;UAED,mCACI,IAAI,EAAE,IAAI,CAAC,IAAI,EACf,MAAM,EAAE,IAAI,CAAC,cAAc,EAC3B,YAAY,EAAE,IAAI,CAAC,gBAAgB,EACnC,QAAQ,EAAE,IAAI,CAAC,oBAAoB,EACnC,MAAM,EAAE,IAAI,CAAC,kBAAkB,GACjC,CACe,CACV;KAClB,CAAC;EACN,CAAC;EAEO,qBAAqB;IACzB,IAAI,IAAI,CAAC,WAAW,KAAK,UAAU,EAAE;MACjC,IAAI,CAAC,gBAAgB,GAAG,IAAI,iBAAiB,EAAE,CAAC;KACnD;SAAM,IAAI,IAAI,CAAC,WAAW,KAAK,MAAM,EAAE;MACpC,IAAI,CAAC,gBAAgB,GAAG,IAAI,aAAa,EAAE,CAAC;KAC/C;SAAM;MACH,MAAM,IAAI,KAAK,CACX,6BAA6B,IAAI,CAAC,WAAW,6CAA6C,CAC7F,CAAC;KACL;EACL,CAAC;EAsBO,KAAK,CAAC,oBAAoB;IAC9B,IAAI,CAAC,MAAM,GAAG,IAAI,CAAC,gBAAgB,EAAE,CAAC;IACtC,MAAM,UAAU,GAAG,MAAM,IAAI,CAAC,mBAAmB,EAAE,CAAC;IACpD,IAAI,CAAC,kBAAkB,GAAG,IAAI,kBAAkB,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;IAC9D,IAAI,CAAC,IAAI,GAAG,IAAI,UAAU,CACtB,IAAI,CAAC,IAAI,CAAC,UAAU,CAAC,aAAa,CAAC,SAAS,CAAC,EAC7C;MACI,KAAK,EAAE,IAAI,CAAC,iBAAiB,CAAC,UAAU,CAAC;MACzC,mBAAmB,EAAE,IAAI,CAAC,iBAAiB;KAC9C,CACJ,CAAC;IAEF,IAAI,IAAI,CAAC,KAAK,EAAE;MACZ,IAAI,CAAC,UAAU,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;KAC/B;EACL,CAAC;EAEO,gBAAgB;IACpB,OAAO,IAAI,MAAM,CAAC;MACd,KAAK,EAAE,YAAY,CAAC,MAAM,CAAC,IAAI,CAAC,KAAK,EAAE,kBAAkB,EAAE,OAAO,CAAC;MACnE,KAAK,EAAE,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC;QAC5B,aAAa,EAAE,aAAa;OAC/B,CAAC;KACL,CAAC,CAAC;EACP,CAAC;EAEO,KAAK,CAAC,mBAAmB;IAC7B,MAAM,qBAAqB,GAAG,QAAQ,CAAC,aAAa,CAAC,KAAK,CAAC,CAAC;IAE5D,IAAI,IAAI,CAAC,KAAK,EAAE;MACZ,qBAAqB,CAAC,SAAS;QAC3B,MAAM,IAAI,CAAC,gBAAgB,CAAC,WAAW,CACnC,IAAI,CAAC,KAAK,EACV,IAAI,CAAC,MAAM,CACd,CAAC;KACT;SAAM;MACH,qBAAqB,CAAC,SAAS,GAAG,SAAS,CAAC;KAC/C;IAED,OAAO,SAAS,CAAC,UAAU,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,KAAK,CAAC,qBAAqB,CAAC,CAAC;EAC1E,CAAC;EAEO,iBAAiB,CAAC,UAAU;IAChC,OAAO,WAAW,CAAC,MAAM,CAAC;MACtB,GAAG,EAAE,UAAU;MACf,OAAO,EAAE;QACL,GAAG,YAAY,CAAC,EAAE,MAAM,EAAE,IAAI,CAAC,MAAM,EAAE,OAAO,EAAE,KAAK,EAAE,CAAC;QACxD,MAAM,CAAC,IAAI,CAAC,kBAAkB,CAAC,WAAW,EAAE,CAAC;QAC7C,gBAAgB,CAAC,IAAI,CAAC,sBAAsB,CAAC;QAC7C,wBAAwB,EAAE;QAC1B,6BAA6B,CACzB,oBAAoB,EACpB,IAAI,CAAC,kBAAkB,EACvB,IAAI,CAAC,0BAA0B,CAClC;QACD,gCAAgC,CAAC,IAAI,CAAC,kBAAkB,CAAC;OAC5D;KACJ,CAAC,CAAC;EACP,CAAC;EAmBO,KAAK,CAAC,UAAU,CAAC,OAAe;IACpC,IAAI,CAAC,mBAAmB,GAAG,IAAI,CAAC;IAChC,MAAM,IAAI,GAAG,MAAM,IAAI,CAAC,gBAAgB,CAAC,WAAW,CAChD,OAAO,EACP,IAAI,CAAC,MAAM,CACd,CAAC;IACF,MAAM,oBAAoB,GAAG,SAAS,CAAC,UAAU,CAC7C,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,MAAM,CACzB,CAAC;IACF,MAAM,SAAS,GAAG,IAAI,MAAM,CAAC,SAAS,EAAE,CAAC;IACzC,MAAM,GAAG,GAAG,SAAS,CAAC,eAAe,CAAC,IAAI,EAAE,WAAW,CAAC,CAAC;IACzD,MAAM,cAAc,GAAG,oBAAoB,CAAC,KAAK,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;IAC5D,MAAM,EAAE,GAAG,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC;IAC9B,EAAE,CAAC,WAAW,CAAC,CAAC,EAAE,EAAE,CAAC,GAAG,CAAC,OAAO,CAAC,IAAI,EAAE,cAAc,CAAC,OAAO,CAAC,CAAC;IAC/D,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,EAAE,CAAC,CAAC;IACvB,IAAI,CAAC,mBAAmB,GAAG,KAAK,CAAC;EACrC,CAAC;EA4DM,QAAQ;;IACX,MAAA,IAAI,CAAC,IAAI,0CAAE,KAAK,EAAE,CAAC;EACvB,CAAC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAeJ","sourcesContent":["import {\n Component,\n Element,\n Event,\n EventEmitter,\n Prop,\n State,\n Watch,\n h,\n} from '@stencil/core';\nimport { EditorState, Transaction } from 'prosemirror-state';\nimport { EditorView } from 'prosemirror-view';\nimport { Schema, DOMParser } from 'prosemirror-model';\nimport { schema } from 'prosemirror-schema-basic';\nimport { addListNodes } from 'prosemirror-schema-list';\nimport { exampleSetup } from 'prosemirror-example-setup';\nimport { keymap } from 'prosemirror-keymap';\nimport { ActionBarItem } from 'src/components/action-bar/action-bar.types';\nimport { ListSeparator } from 'src/components/list/list-item.types';\nimport { MenuCommandFactory } from './menu/menu-commands';\nimport { menuTranslationIDs, getTextEditorMenuItems } from './menu/menu-items';\nimport { ContentTypeConverter } from '../utils/content-type-converter';\nimport { markdownConverter } from '../utils/markdown-converter';\nimport { HTMLConverter } from '../utils/html-converter';\nimport {\n EditorMenuTypes,\n EditorTextLink,\n editorMenuTypesArray,\n} from './menu/types';\nimport translate from 'src/global/translations';\nimport { createRandomString } from 'src/util/random-string';\nimport { isItem } from 'src/components/action-bar/isItem';\nimport { cloneDeep } from 'lodash-es';\nimport { Languages } from '../../date-picker/date.types';\nimport { strikethrough } from './menu/menu-schema-extender';\nimport {\n EditorLinkMenuEventDetail,\n createLinkPlugin,\n} from './plugins/link-plugin';\nimport { createImageRemoverPlugin } from './plugins/image-remover-plugin';\nimport { createMenuStateTrackingPlugin } from './plugins/menu-state-tracking-plugin';\nimport { createActionBarInteractionPlugin } from './plugins/menu-action-interaction-plugin';\n\n/**\n * The ProseMirror adapter offers a rich text editing experience with markdown support.\n * [Read more...](https://prosemirror.net/)\n *\n * @exampleComponent limel-example-prosemirror-adapter-basic\n * @exampleComponent limel-example-prosemirror-adapter-with-custom-menu\n * @beta\n * @private\n */\n@Component({\n tag: 'limel-prosemirror-adapter',\n shadow: true,\n styleUrl: 'prosemirror-adapter.scss',\n})\nexport class ProsemirrorAdapter {\n /**\n * The type of content that the editor should handle and emit, defaults to `markdown`\n *\n * Assumed to be set only once, so not reactive to changes\n */\n @Prop()\n public contentType: 'markdown' | 'html' = 'markdown';\n\n /**\n * The value of the editor, expected to be markdown\n */\n @Prop()\n public value: string;\n\n /**\n * Defines the language for translations.\n */\n @Prop({ reflect: true })\n public language: Languages;\n\n @Element()\n private host: HTMLLimelTextEditorElement;\n\n private portalId: string;\n\n @State()\n private view: EditorView;\n\n @State()\n private actionBarItems: Array<\n ActionBarItem<EditorMenuTypes> | ListSeparator\n > = [];\n\n @State()\n private link: EditorTextLink = { href: '' };\n\n /**\n * Open state of the dialog\n */\n @State()\n public isLinkMenuOpen: boolean = false;\n\n private menuCommandFactory: MenuCommandFactory;\n private schema: Schema;\n private contentConverter: ContentTypeConverter;\n private suppressChangeEvent = false;\n private actionBarElement: HTMLElement;\n\n /**\n * Dispatched when a change is made to the editor\n */\n @Event()\n private change: EventEmitter<string>;\n\n constructor() {\n this.portalId = createRandomString();\n }\n\n @Watch('value')\n protected watchValue(newValue: string) {\n if (\n !this.view ||\n newValue === this.contentConverter.serialize(this.view, this.schema)\n ) {\n return;\n }\n\n this.updateView(newValue);\n }\n\n public componentWillLoad() {\n this.getActionBarItems();\n this.setupContentConverter();\n }\n\n public componentDidLoad() {\n // Stencil complains loudly about triggering rerenders in\n // componentDidLoad, but we have to, so we're using setTimeout to\n // suppress the warning. /Ads\n setTimeout(() => {\n this.initializeTextEditor();\n }, 0);\n }\n\n public connectedCallback() {\n if (this.view) {\n this.initializeTextEditor();\n }\n\n this.host.addEventListener(\n 'open-editor-link-menu',\n this.handleOpenLinkMenu,\n );\n }\n\n public disconnectedCallback() {\n this.host.removeEventListener(\n 'open-editor-link-menu',\n this.handleOpenLinkMenu,\n );\n this.view.destroy();\n }\n\n public render() {\n return [\n <div id=\"editor\" />,\n <limel-action-bar\n ref={(el) => (this.actionBarElement = el)}\n accessibleLabel=\"Toolbar\"\n actions={this.actionBarItems}\n onItemSelected={this.handleActionBarItem}\n />,\n <limel-portal\n containerId={this.portalId}\n visible={this.isLinkMenuOpen}\n openDirection=\"top\"\n inheritParentWidth={true}\n anchor={this.actionBarElement}\n containerStyle={{ 'z-index': 1 }}\n >\n <limel-menu-surface\n open={this.isLinkMenuOpen}\n onDismiss={this.handleCancelLinkMenu}\n style={{\n '--mdc-menu-min-width': '100%',\n 'max-height': 'inherit',\n }}\n >\n <limel-text-editor-link-menu\n link={this.link}\n isOpen={this.isLinkMenuOpen}\n onLinkChange={this.handleLinkChange}\n onCancel={this.handleCancelLinkMenu}\n onSave={this.handleSaveLinkMenu}\n />\n </limel-menu-surface>\n </limel-portal>,\n ];\n }\n\n private setupContentConverter() {\n if (this.contentType === 'markdown') {\n this.contentConverter = new markdownConverter();\n } else if (this.contentType === 'html') {\n this.contentConverter = new HTMLConverter();\n } else {\n throw new Error(\n `Unsupported content type: ${this.contentType}. Only 'markdown' and 'html' are supported.`,\n );\n }\n }\n\n private getActionBarItems = () => {\n this.actionBarItems = getTextEditorMenuItems().map(\n this.getTranslatedItem,\n );\n };\n\n private getTranslatedItem = (item) => {\n const newItem = cloneDeep(item);\n\n if (isItem(item)) {\n const translationId = menuTranslationIDs[item.value];\n\n if (translationId) {\n newItem.text = translate.get(translationId, this.language);\n }\n }\n\n return newItem;\n };\n\n private async initializeTextEditor() {\n this.schema = this.initializeSchema();\n const initialDoc = await this.parseInitialContent();\n this.menuCommandFactory = new MenuCommandFactory(this.schema);\n this.view = new EditorView(\n this.host.shadowRoot.querySelector('#editor'),\n {\n state: this.createEditorState(initialDoc),\n dispatchTransaction: this.handleTransaction,\n },\n );\n\n if (this.value) {\n this.updateView(this.value);\n }\n }\n\n private initializeSchema() {\n return new Schema({\n nodes: addListNodes(schema.spec.nodes, 'paragraph block*', 'block'),\n marks: schema.spec.marks.append({\n strikethrough: strikethrough,\n }),\n });\n }\n\n private async parseInitialContent() {\n const initialContentElement = document.createElement('div');\n\n if (this.value) {\n initialContentElement.innerHTML =\n await this.contentConverter.parseAsHTML(\n this.value,\n this.schema,\n );\n } else {\n initialContentElement.innerHTML = '<p></p>';\n }\n\n return DOMParser.fromSchema(this.schema).parse(initialContentElement);\n }\n\n private createEditorState(initialDoc) {\n return EditorState.create({\n doc: initialDoc,\n plugins: [\n ...exampleSetup({ schema: this.schema, menuBar: false }),\n keymap(this.menuCommandFactory.buildKeymap()),\n createLinkPlugin(this.handleNewLinkSelection),\n createImageRemoverPlugin(),\n createMenuStateTrackingPlugin(\n editorMenuTypesArray,\n this.menuCommandFactory,\n this.updateActiveActionBarItems,\n ),\n createActionBarInteractionPlugin(this.menuCommandFactory),\n ],\n });\n }\n\n private updateActiveActionBarItems = (\n activeTypes: Record<EditorMenuTypes, boolean>,\n ) => {\n const newItems = getTextEditorMenuItems().map((item) => {\n if (isItem(item)) {\n return {\n ...item,\n selected: activeTypes[item.value],\n };\n }\n\n return item;\n });\n\n this.actionBarItems = newItems;\n };\n\n private async updateView(content: string) {\n this.suppressChangeEvent = true;\n const html = await this.contentConverter.parseAsHTML(\n content,\n this.schema,\n );\n const prosemirrorDOMparser = DOMParser.fromSchema(\n this.view.state.schema,\n );\n const domParser = new window.DOMParser();\n const doc = domParser.parseFromString(html, 'text/html');\n const prosemirrorDoc = prosemirrorDOMparser.parse(doc.body);\n const tr = this.view.state.tr;\n tr.replaceWith(0, tr.doc.content.size, prosemirrorDoc.content);\n this.view.dispatch(tr);\n this.suppressChangeEvent = false;\n }\n\n private handleTransaction = (transaction: Transaction) => {\n const newState = this.view.state.apply(transaction);\n this.view.updateState(newState);\n\n if (this.suppressChangeEvent) {\n return;\n }\n\n if (transaction.getMeta('pointer')) {\n return;\n }\n\n this.change.emit(\n this.contentConverter.serialize(this.view, this.schema),\n );\n };\n\n private handleActionBarItem = (\n event: CustomEvent<ActionBarItem<EditorMenuTypes>>,\n ) => {\n event.preventDefault();\n event.stopImmediatePropagation();\n const { value } = event.detail;\n\n if (value === EditorMenuTypes.Link) {\n this.isLinkMenuOpen = true;\n\n return;\n }\n\n const actionBarEvent = new CustomEvent('actionBarItemClick', {\n detail: event.detail,\n });\n this.view.dom.dispatchEvent(actionBarEvent);\n };\n\n private handleCancelLinkMenu = () => {\n this.isLinkMenuOpen = false;\n };\n\n private handleSaveLinkMenu = () => {\n this.isLinkMenuOpen = false;\n\n const saveLinkEvent = new CustomEvent('saveLinkMenu', {\n detail: {\n type: EditorMenuTypes.Link,\n link: this.link,\n },\n });\n this.view.dom.dispatchEvent(saveLinkEvent);\n\n this.link = { href: '' };\n };\n\n private handleLinkChange = (event: CustomEvent<EditorTextLink>) => {\n this.link = event.detail;\n };\n\n public setFocus() {\n this.view?.focus();\n }\n\n private handleNewLinkSelection = (text: string, href: string) => {\n this.link.text = text;\n this.link.href = href;\n };\n\n private handleOpenLinkMenu = (\n event: CustomEvent<EditorLinkMenuEventDetail>,\n ) => {\n event.stopImmediatePropagation();\n const { href, text } = event.detail;\n this.link = { href: href, text: text };\n this.isLinkMenuOpen = true;\n };\n}\n"]}