diff options
author | bobzel <zzzman@gmail.com> | 2025-03-19 14:40:24 -0400 |
---|---|---|
committer | bobzel <zzzman@gmail.com> | 2025-03-19 14:40:24 -0400 |
commit | 5ddd41905823fb77ca987517b63e46a63fe4d4ca (patch) | |
tree | c7c3da3e7a6155f6c645dcbc7ab0b6f550cc18cf /src/client/views/nodes/formattedText/FormattedTextBox.tsx | |
parent | 5e73c471b14d5007306fd1bedfdf349769bd5f82 (diff) |
fixed focus() on text boxes to scroll into view by hacking around a breaking prosemirror patch.
Diffstat (limited to 'src/client/views/nodes/formattedText/FormattedTextBox.tsx')
-rw-r--r-- | src/client/views/nodes/formattedText/FormattedTextBox.tsx | 47 |
1 files changed, 27 insertions, 20 deletions
diff --git a/src/client/views/nodes/formattedText/FormattedTextBox.tsx b/src/client/views/nodes/formattedText/FormattedTextBox.tsx index 7b24125e7..b84575389 100644 --- a/src/client/views/nodes/formattedText/FormattedTextBox.tsx +++ b/src/client/views/nodes/formattedText/FormattedTextBox.tsx @@ -1458,6 +1458,29 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<FormattedTextB } _didScroll = false; _scrollStopper: undefined | (() => void); + scrollToSelection = () => { + if (this.EditorView && this._ref.current) { + const editorView = this.EditorView; + const docPos = editorView.coordsAtPos(editorView.state.selection.to); + const viewRect = this._ref.current.getBoundingClientRect(); + const scrollRef = this._scrollRef; + const topOff = docPos.top < viewRect.top ? docPos.top - viewRect.top : undefined; + const botOff = docPos.bottom > viewRect.bottom ? docPos.bottom - viewRect.bottom : undefined; + if (((topOff && Math.abs(Math.trunc(topOff)) > 0) || (botOff && Math.abs(Math.trunc(botOff)) > 0)) && scrollRef) { + const shift = Math.min(topOff ?? Number.MAX_VALUE, botOff ?? Number.MAX_VALUE); + const scrollPos = scrollRef.scrollTop + shift * this.ScreenToLocalBoxXf().Scale; + if (this._focusSpeed !== undefined) { + setTimeout(() => { + scrollPos && (this._scrollStopper = smoothScroll(this._focusSpeed || 0, scrollRef, scrollPos, 'ease', this._scrollStopper)); + }); + } else { + scrollRef.scrollTo({ top: scrollPos }); + } + this._didScroll = true; + } + } + return true; + }; // eslint-disable-next-line @typescript-eslint/no-explicit-any setupEditor(config: any, fieldKey: string) { const curText = Cast(this.dataDoc[this.fieldKey], RichTextField, null) || StrCast(this.dataDoc[this.fieldKey]); @@ -1466,31 +1489,15 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<FormattedTextB this.EditorView?.destroy(); this._editorView = new EditorView(this.ProseRef, { state: rtfField?.Data ? EditorState.fromJSON(config, JSON.parse(rtfField.Data)) : EditorState.create(config), - handleScrollToSelection: editorView => { - const docPos = editorView.coordsAtPos(editorView.state.selection.to); - const viewRect = this._ref.current!.getBoundingClientRect(); - const scrollRef = this._scrollRef; - const topOff = docPos.top < viewRect.top ? docPos.top - viewRect.top : undefined; - const botOff = docPos.bottom > viewRect.bottom ? docPos.bottom - viewRect.bottom : undefined; - if (((topOff && Math.abs(Math.trunc(topOff)) > 0) || (botOff && Math.abs(Math.trunc(botOff)) > 0)) && scrollRef) { - const shift = Math.min(topOff ?? Number.MAX_VALUE, botOff ?? Number.MAX_VALUE); - const scrollPos = scrollRef.scrollTop + shift * this.ScreenToLocalBoxXf().Scale; - if (this._focusSpeed !== undefined) { - setTimeout(() => { - scrollPos && (this._scrollStopper = smoothScroll(this._focusSpeed || 0, scrollRef, scrollPos, 'ease', this._scrollStopper)); - }); - } else { - scrollRef.scrollTo({ top: scrollPos }); - } - this._didScroll = true; - } - return true; - }, + handleScrollToSelection: this.scrollToSelection, dispatchTransaction: this.dispatchTransaction, nodeViews: FormattedTextBox._nodeViews(this), clipboardTextSerializer: this.clipboardTextSerializer, handlePaste: this.handlePaste, }); + // bcz: major hack! a patch to prosemirror broke scrolling to selection when the selection is not a dom selection + // this replaces prosemirror's scrollToSelection function with Dash's + (this.EditorView as unknown as { scrollToSelection: unknown }).scrollToSelection = this.scrollToSelection; const { state } = this._editorView; if (!rtfField) { const dataDoc = Doc.IsDelegateField(DocCast(this.layoutDoc.proto), this.fieldKey) ? DocCast(this.layoutDoc.proto) : this.dataDoc; |