fix update listeners

This commit is contained in:
JesmoDev
2024-09-12 15:06:27 +02:00
parent a8c69371fc
commit 2d6c358a98
3 changed files with 87 additions and 20 deletions

View File

@@ -6,6 +6,7 @@ import { UUIFormControlMixin } from '@umbraco-cms/backoffice/external/uui';
import type { UmbPropertyEditorConfigCollection } from '@umbraco-cms/backoffice/property-editor';
import './tiptap-fixed-menu.element.js';
import './tiptap-hover-menu.element.js';
import { Editor, Link, StarterKit, TextAlign, Underline } from '@umbraco-cms/backoffice/external/tiptap';
import { UmbChangeEvent } from '@umbraco-cms/backoffice/event';
@@ -35,23 +36,18 @@ export class UmbInputTiptapElement extends UUIFormControlMixin(UmbLitElement, ''
TextAlign.configure({
types: ['heading', 'paragraph', 'blockquote', 'orderedList', 'bulletList', 'codeBlock'],
}),
Link,
Link.configure({ openOnClick: false }),
Underline,
],
content: json,
onSelectionUpdate: ({ editor }) => {
const { $from } = editor.state.selection;
const activeMarks = $from.node();
// Log the active marks
console.log('Active Marks:', activeMarks);
this._fixedMenuElement.onUpdate(); // TODO: This is a hack to force the fixed menu to update. We need to find a better way.
},
onUpdate: ({ editor }) => {
const json = editor.getJSON();
this.value = JSON.stringify(json);
this.dispatchEvent(new UmbChangeEvent());
this._fixedMenuElement.onUpdate(); // TODO: This is a hack to force the fixed menu to update. We need to find a better way.
},
});
}
@@ -62,10 +58,8 @@ export class UmbInputTiptapElement extends UUIFormControlMixin(UmbLitElement, ''
override render() {
return html`
<umb-tiptap-fixed-menu
class="uui-text uui-font"
.activeNodeOrMark=${this._editor?.isActive('bold') ? 'bold' : null}
.editor=${this._editor}></umb-tiptap-fixed-menu>
<umb-tiptap-hover-menu .editor=${this._editor}></umb-tiptap-hover-menu>
<umb-tiptap-fixed-menu .editor=${this._editor}></umb-tiptap-fixed-menu>
<div id="editor"></div>
`;
}
@@ -108,7 +102,7 @@ export class UmbInputTiptapElement extends UUIFormControlMixin(UmbLitElement, ''
font-size: 0.8rem;
padding: 0;
}
.ProseMirror {
.tiptap {
height: 100%;
width: 100%;
outline: none;

View File

@@ -17,6 +17,7 @@ import {
strikethrough,
underline,
} from './icons.js';
import type { PropertyValues } from '@umbraco-cms/backoffice/external/lit';
import { LitElement, css, customElement, html, property, state } from '@umbraco-cms/backoffice/external/lit';
import type { Editor } from '@umbraco-cms/backoffice/external/tiptap';
@@ -133,24 +134,41 @@ export class UmbTiptapFixedMenuElement extends LitElement {
name: 'link',
icon: link,
command: () => {
const text = prompt('Enter the text');
const url = prompt('Enter the URL');
if (url) {
this.editor?.chain().focus().setLink({ href: url, target: '_blank' }).run();
if (url && text && this.editor) {
const { from } = this.editor.state.selection;
this.editor
.chain()
.focus()
.insertContent(text)
.setTextSelection({ from: from, to: from + text.length })
.setLink({ href: url, target: '_blank' })
.run();
}
},
},
];
@property({ attribute: false })
editor?: Editor;
public onUpdate() {
//TODO: Find a better way to trigger a re-render of the menu when the editor is updated
// This is used to update the active state of the buttons
this.requestUpdate();
console.log('onUpdate');
get editor() {
return this.#editor;
}
set editor(value) {
const oldValue = this.#editor;
if (value === oldValue) {
return;
}
this.#editor = value;
this.#editor?.on('selectionUpdate', this.#onUpdate);
this.#editor?.on('update', this.#onUpdate);
}
#editor?: Editor;
#onUpdate = () => {
this.requestUpdate();
};
override render() {
return html`

View File

@@ -0,0 +1,55 @@
import { LitElement, PropertyValues, css, customElement, html, property } from '@umbraco-cms/backoffice/external/lit';
import type { Editor } from '@umbraco-cms/backoffice/external/tiptap';
@customElement('umb-tiptap-hover-menu')
export class UmbTiptapHoverMenuElement extends LitElement {
@property({ attribute: false })
get editor() {
return this.#editor;
}
set editor(value) {
const oldValue = this.#editor;
if (value === oldValue) {
return;
}
this.#editor = value;
this.#editor?.on('selectionUpdate', this.#onUpdate);
this.#editor?.on('update', this.#onUpdate);
}
#editor?: Editor;
override connectedCallback(): void {
super.connectedCallback();
this.setAttribute('popover', '');
}
#onUpdate = () => {
console.log('LINK ACTIVE');
if (this.editor?.isActive('link')) {
// show the popover
this.showPopover();
} else {
this.requestUpdate();
}
};
override render() {
console.log('RENDER HOVER MENU');
return html`<uui-popover-container></uui-popover-container>`;
}
static override styles = css`
:host {
position: fixed;
background-color: var(--uui-color-surface-alt);
border: 1px solid var(--uui-color-border);
border-radius: var(--uui-size-border-radius);
}
`;
}
declare global {
interface HTMLElementTagNameMap {
'umb-tiptap-hover-menu': UmbTiptapHoverMenuElement;
}
}