diff options
author | bobzel <zzzman@gmail.com> | 2021-02-08 19:25:48 -0500 |
---|---|---|
committer | bobzel <zzzman@gmail.com> | 2021-02-08 19:25:48 -0500 |
commit | 0e5891eab7f53697b764b7e9da5163db0351a0a2 (patch) | |
tree | 41f0b00acf4cf31ad6dee451612d4f4b6f870133 /src/client/views/nodes/formattedText/FormattedTextBox.tsx | |
parent | 32a0d5be4ff7a49b554806c27dca5b63ea80277f (diff) |
overhaul of link anchors on text boxes to use actual Documents to represent selected text. Also got rid of _scrollY and _scrollPreviewY so that all document regions can be focused on using focus() and the new scrollFocus() mechanisim
Diffstat (limited to 'src/client/views/nodes/formattedText/FormattedTextBox.tsx')
-rw-r--r-- | src/client/views/nodes/formattedText/FormattedTextBox.tsx | 207 |
1 files changed, 96 insertions, 111 deletions
diff --git a/src/client/views/nodes/formattedText/FormattedTextBox.tsx b/src/client/views/nodes/formattedText/FormattedTextBox.tsx index b3abcf90a..2409f36a0 100644 --- a/src/client/views/nodes/formattedText/FormattedTextBox.tsx +++ b/src/client/views/nodes/formattedText/FormattedTextBox.tsx @@ -92,6 +92,7 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp public static Instance: FormattedTextBox; public ProseRef?: HTMLDivElement; public get EditorView() { return this._editorView; } + public get SidebarKey() { return this.fieldKey + "-sidebar"; } private _boxRef: React.RefObject<HTMLDivElement> = React.createRef(); private _ref: React.RefObject<HTMLDivElement> = React.createRef(); private _scrollRef: React.RefObject<HTMLDivElement> = React.createRef(); @@ -104,15 +105,13 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp private _dropDisposer?: DragManager.DragDropDisposer; private _recordingStart: number = 0; private _pause: boolean = false; - private _animatingScroll: number = 0; // hack to prevent scroll values from being written to document when scroll is animating + private _ignoreScroll = false; @computed get _recording() { return this.dataDoc?.audioState === "recording"; } set _recording(value) { this.dataDoc.audioState = value ? "recording" : undefined; } - @observable private _entered = false; - public static FocusedBox: FormattedTextBox | undefined; public static SelectOnLoad = ""; public static PasteOnLoad: ClipboardEvent | undefined; @@ -164,29 +163,35 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp // TODO: bcz: Argh... if a section of text has multiple anchors, this should just remove the intended one. // but since removing one anchor from the list of attr anchors isn't implemented, this will end up removing nothing. public RemoveLinkFromDoc(linkDoc?: Doc) { + this.unhighlightSearchTerms(); const state = this._editorView?.state; - if (state && linkDoc && this._editorView) { - var allLinks: any[] = []; + const a1 = linkDoc?.anchor1 as Doc; + const a2 = linkDoc?.anchor2 as Doc; + if (state && a1 && a2 && this._editorView) { + this.removeDocument(a1); + this.removeDocument(a2); + var allFoundLinkAnchors: any[] = []; state.doc.nodesBetween(0, state.doc.nodeSize - 2, (node: any, pos: number, parent: any) => { - const foundMark = findLinkMark(node.marks); - const newHrefs = foundMark?.attrs.allLinks.filter((a: any) => a.href.includes(linkDoc[Id])) || []; - allLinks = newHrefs.length ? newHrefs : allLinks; + const foundLinkAnchors = findLinkMark(node.marks)?.attrs.allAnchors.filter((a: any) => a.anchorId === a1[Id] || a.anchorId === a2[Id]) || []; + allFoundLinkAnchors = foundLinkAnchors.length ? foundLinkAnchors : allFoundLinkAnchors; return true; }); - if (allLinks.length) { - this._editorView.dispatch(removeMarkWithAttrs(state.tr, 0, state.doc.nodeSize - 2, state.schema.marks.linkAnchor, { allLinks })); + if (allFoundLinkAnchors.length) { + this._editorView.dispatch(removeMarkWithAttrs(state.tr, 0, state.doc.nodeSize - 2, state.schema.marks.linkAnchor, { allAnchors: allFoundLinkAnchors })); } } } - // removes all the specified link referneces from the selection. + // removes all the specified link references from the selection. // NOTE: as above, this won't work correctly if there are marks with overlapping but not exact sets of link references. - public RemoveLinkFromSelection(allLinks: { href: string, title: string, linkId: string, targetId: string }[]) { + public RemoveAnchorFromSelection(allAnchors: { href: string, title: string, linkId: string, targetId: string }[]) { const state = this._editorView?.state; if (state && this._editorView) { - this._editorView.dispatch(removeMarkWithAttrs(state.tr, state.selection.from, state.selection.to, state.schema.marks.link, { allLinks })); + this._editorView.dispatch(removeMarkWithAttrs(state.tr, state.selection.from, state.selection.to, state.schema.marks.link, { allAnchors })); } } + getAnchor = () => this.makeLinkAnchor(undefined, "add:right", undefined, "Anchored Selection"); + linkOnDeselect: Map<string, string> = new Map(); doLinkOnDeselect() { @@ -234,11 +239,11 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp DragManager.StartAnchorAnnoDrag([ele], new DragManager.AnchorAnnoDragData(this.rootDoc, () => this.rootDoc, targetCreator), e.pageX, e.pageY, { dragComplete: e => { + const anchor = this.makeLinkAnchor(undefined, "add:right", undefined, "a link"); if (!e.aborted && e.annoDragData && e.annoDragData.annotationDocument && e.annoDragData.dropDocument && !e.linkDocument) { - e.linkDocument = DocUtils.MakeLink({ doc: e.annoDragData.annotationDocument }, { doc: e.annoDragData.dropDocument }, "hyperlink", "link to note"); + e.linkDocument = DocUtils.MakeLink({ doc: anchor }, { doc: e.annoDragData.dropDocument }, "hyperlink", "link to note"); e.annoDragData.annotationDocument.isPushpin = e.annoDragData?.dropDocument.annotationOn === this.rootDoc; } - e.linkDocument && e.annoDragData?.dropDocument && this.makeLinkToSelection(e.linkDocument[Id], "a link", "add:right", e.annoDragData.dropDocument[Id]); e.linkDocument && e.annoDragData?.linkDropCallback?.(e as { linkDocument: Doc });// bcz: typescript can't figure out that this is valid even though we tested e.linkDocument } }); @@ -270,8 +275,8 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp this.linkOnDeselect.set(key, value); const id = Utils.GenerateDeterministicGuid(this.dataDoc[Id] + key); - const allLinks = [{ href: Utils.prepend("/doc/" + id), title: value, targetId: id }]; - const link = this._editorView.state.schema.marks.linkAnchor.create({ allLinks, location: "add:right", title: value }); + const allAnchors = [{ href: Utils.prepend("/doc/" + id), title: value, anchorId: id }]; + const link = this._editorView.state.schema.marks.linkAnchor.create({ allAnchors, location: "add:right", title: value }); const mval = this._editorView.state.schema.marks.metadataVal.create(); const offset = (tx.selection.to === range!.end - 1 ? -1 : 0); tx = tx.addMark(textEndSelection - value.length + offset, textEndSelection, link).addMark(textEndSelection - value.length + offset, textEndSelection, mval); @@ -407,9 +412,10 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp res.map(r => r.map(h => flattened.push(h))); const lastSel = Math.min(flattened.length - 1, this._searchIndex); this._searchIndex = ++this._searchIndex > flattened.length - 1 ? 0 : this._searchIndex; - const alink = DocUtils.MakeLink({ doc: this.rootDoc }, { doc: target }, "automatic")!; - const allLinks = [{ href: Utils.prepend("/doc/" + alink[Id]), title: "a link", targetId: target[Id], linkId: alink[Id] }]; - const link = this._editorView.state.schema.marks.linkAnchor.create({ allLinks, title: "a link", location }); + const anchor = new Doc(); + const alink = DocUtils.MakeLink({ doc: anchor }, { doc: target }, "automatic")!; + const allAnchors = [{ href: Utils.prepend("/doc/" + anchor[Id]), title: "a link", anchorId: anchor[Id] }]; + const link = this._editorView.state.schema.marks.linkAnchor.create({ allAnchors, title: "a link", location }); this._editorView.dispatch(tr.addMark(flattened[lastSel].from, flattened[lastSel].to, link)); } } @@ -507,8 +513,8 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp } linkDrop = (data: { linkDocument: Doc }) => { const anchor1Title = data.linkDocument.anchor1 instanceof Doc ? StrCast(data.linkDocument.anchor1.title) : "-untitled-"; - const anchor1Id = data.linkDocument.anchor1 instanceof Doc ? data.linkDocument.anchor1[Id] : ""; - this.makeLinkToSelection(data.linkDocument[Id], anchor1Title, "add:right", anchor1Id); + const anchor1 = data.linkDocument.anchor1 instanceof Doc ? data.linkDocument.anchor1 : undefined; + this.makeLinkAnchor(anchor1, "add:right", undefined, anchor1Title); } getNodeEndpoints(context: Node, node: Node): { from: number, to: number } | null { @@ -825,37 +831,46 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp }; } - makeLinkToSelection(linkId: string, title: string, location: string, targetId: string, targetHref?: string) { + makeLinkAnchor(anchorDoc?: Doc, location?: string, targetHref?: string, title?: string) { const state = this._editorView?.state; if (state) { - const href = targetHref ?? Utils.prepend("/doc/" + linkId); const sel = state.selection; const splitter = state.schema.marks.splitter.create({ id: Utils.GenerateGuid() }); let tr = state.tr.addMark(sel.from, sel.to, splitter); - sel.from !== sel.to && tr.doc.nodesBetween(sel.from, sel.to, (node: any, pos: number, parent: any) => { - if (node.firstChild === null && node.marks.find((m: Mark) => m.type.name === schema.marks.splitter.name)) { - const allLinks = [{ href, title, targetId, linkId }]; - allLinks.push(...(node.marks.find((m: Mark) => m.type.name === schema.marks.linkAnchor.name)?.attrs.allLinks ?? [])); - const link = state.schema.marks.linkAnchor.create({ allLinks, title, location, linkId }); - tr = tr.addMark(pos, pos + node.nodeSize, link); - } - }); - this.dataDoc[ForceServerWrite] = this.dataDoc[UpdatingFromServer] = true; // need to allow permissions for adding links to readonly/augment only documents - this._editorView!.dispatch(tr.removeMark(sel.from, sel.to, splitter)); - this.dataDoc[UpdatingFromServer] = this.dataDoc[ForceServerWrite] = false; + if (sel.from !== sel.to) { + const anchor = anchorDoc ?? Docs.Create.TextanchorDocument(); + const href = targetHref ?? Utils.prepend("/doc/" + anchor[Id]); + if (anchor !== anchorDoc) this.addDocument(anchor); + tr.doc.nodesBetween(sel.from, sel.to, (node: any, pos: number, parent: any) => { + if (node.firstChild === null && node.marks.find((m: Mark) => m.type.name === schema.marks.splitter.name)) { + const allAnchors = [{ href, title, anchorId: anchor[Id] }]; + allAnchors.push(...(node.marks.find((m: Mark) => m.type.name === schema.marks.linkAnchor.name)?.attrs.allAnchors ?? [])); + const link = state.schema.marks.linkAnchor.create({ allAnchors, title, location }); + tr = tr.addMark(pos, pos + node.nodeSize, link); + } + }); + this.dataDoc[ForceServerWrite] = this.dataDoc[UpdatingFromServer] = true; // need to allow permissions for adding links to readonly/augment only documents + this._editorView!.dispatch(tr.removeMark(sel.from, sel.to, splitter)); + this.dataDoc[UpdatingFromServer] = this.dataDoc[ForceServerWrite] = false; + Doc.GetProto(anchor).title = this._editorView?.state.doc.textBetween(sel.from, sel.to); + return anchor; + } + return anchorDoc ?? this.rootDoc; } + return anchorDoc ?? this.rootDoc; } IsActive = () => { return this.active();//this.props.isSelected() || this._isChildActive || this.props.renderDepth === 0; } - scrollToLinkId = (linkId: string) => { - const findLinkFrag = (frag: Fragment, editor: EditorView) => { + scrollFocus = (doc: Doc, smooth: boolean) => { + const anchorId = doc[Id]; + const findAnchorFrag = (frag: Fragment, editor: EditorView) => { const nodes: Node[] = []; let hadStart = start !== 0; frag.forEach((node, index) => { - const examinedNode = findLinkNode(node, editor); + const examinedNode = findAnchorNode(node, editor); if (examinedNode?.node.textContent) { nodes.push(examinedNode.node); !hadStart && (start = index + examinedNode.start); @@ -864,20 +879,20 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp }); return { frag: Fragment.fromArray(nodes), start }; }; - const findLinkNode = (node: Node, editor: EditorView) => { + const findAnchorNode = (node: Node, editor: EditorView) => { if (!node.isText) { - const content = findLinkFrag(node.content, editor); + const content = findAnchorFrag(node.content, editor); return { node: node.copy(content.frag), start: content.start }; } const marks = [...node.marks]; const linkIndex = marks.findIndex(mark => mark.type === editor.state.schema.marks.linkAnchor); - return linkIndex !== -1 && marks[linkIndex].attrs.allLinks.find((item: { href: string }) => linkId === item.href.replace(/.*\/doc\//, "")) ? { node, start: 0 } : undefined; + return linkIndex !== -1 && marks[linkIndex].attrs.allAnchors.find((item: { href: string }) => anchorId === item.href.replace(/.*\/doc\//, "")) ? { node, start: 0 } : undefined; }; let start = 0; - if (this._editorView && linkId) { + if (this._editorView && anchorId) { const editor = this._editorView; - const ret = findLinkFrag(editor.state.doc.content, editor); + const ret = findAnchorFrag(editor.state.doc.content, editor); if (ret.frag.size > 2 && ret.start >= 0) { let selection = TextSelection.near(editor.state.doc.resolve(ret.start)); // default to near the start @@ -885,16 +900,15 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp selection = TextSelection.between(editor.state.doc.resolve(ret.start), editor.state.doc.resolve(ret.start + ret.frag.firstChild.nodeSize)); // bcz: looks better to not have the target selected } editor.dispatch(editor.state.tr.setSelection(new TextSelection(selection.$from, selection.$from)).scrollIntoView()); - const mark = editor.state.schema.mark(this._editorView.state.schema.marks.search_highlight); - setTimeout(() => editor.dispatch(editor.state.tr.addMark(selection.from, selection.to, mark)), 0); - setTimeout(() => this.unhighlightSearchTerms(), 2000); + const escAnchorId = anchorId[0] > '0' && anchorId[0] <= '9' ? `\\3${anchorId[0]} ${anchorId.substr(1)}` : anchorId; + addStyleSheetRule(FormattedTextBox._highlightStyleSheet, `${escAnchorId}`, { background: "yellow" }); + setTimeout(() => clearStyleSheetRules(FormattedTextBox._highlightStyleSheet), 1500); } - Doc.SetInPlace(this.layoutDoc, "scrollToLinkID", undefined, false); - Doc.SetInPlace(this.layoutDoc, "_scrollToPreviewLinkID", undefined, false); } } componentDidMount() { + this.props.setContentView?.(this); // this tells the DocumentView that this AudioBox is the "content" of the document. this allows the DocumentView to indirectly call getAnchor() on the AudioBox when making a link. this.props.contentsActive?.(this.IsActive); this._cachedLinks = DocListCast(this.Document.links); this._disposers.sidebarheight = reaction( @@ -916,27 +930,12 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp } } ); - this._disposers.linkMaker = reaction( - () => this.props.makeLink?.(), - (linkDoc: Opt<Doc>) => { - if (linkDoc) { - const a1 = Cast(linkDoc.anchor1, Doc, null); - const a2 = Cast(linkDoc.anchor2, Doc, null); - const otherAnchor = Doc.AreProtosEqual(a1, this.rootDoc) ? a2 : a1; - const anchor2Title = StrCast(otherAnchor.title, "-untitled-"); - const anchor2Id = otherAnchor?.[Id] || ""; - this.makeLinkToSelection(linkDoc[Id], anchor2Title, "add:right", anchor2Id); - } - }, - { fireImmediately: true } - ); this._disposers.editorState = reaction( () => { - if (!this.dataDoc || !this.layoutDoc) return undefined; - if (this.dataDoc?.[this.props.fieldKey + "-noTemplate"] || !this.layoutDoc[this.props.fieldKey]) { - return { data: Cast(this.dataDoc[this.props.fieldKey], RichTextField, null), str: StrCast(this.dataDoc[this.props.fieldKey]) }; - } - return { data: Cast(this.layoutDoc[this.props.fieldKey], RichTextField, null), str: StrCast(this.layoutDoc[this.props.fieldKey]) }; + const whichDoc = !this.dataDoc || !this.layoutDoc ? undefined : + this.dataDoc?.[this.props.fieldKey + "-noTemplate"] || !this.layoutDoc[this.props.fieldKey] ? + this.dataDoc : this.layoutDoc; + return !whichDoc ? undefined : { data: Cast(whichDoc[this.props.fieldKey], RichTextField, null), str: StrCast(whichDoc[this.props.fieldKey]) }; }, incomingValue => { if (this._editorView && this._applyingChange !== this.fieldKey) { @@ -1013,38 +1012,23 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp } ); } - this._disposers.previewScrollToRegion = reaction(() => StrCast(this.layoutDoc._scrollToPreviewLinkID), - scrollToLinkID => this.props.renderDepth === -1 && scrollToLinkID && this.scrollToLinkId(scrollToLinkID), { fireImmediately: true } - ); - this._disposers.scrollToRegion = reaction(() => StrCast(this.layoutDoc.scrollToLinkID), - scrollToLinkID => scrollToLinkID && this.scrollToLinkId(scrollToLinkID), { fireImmediately: true } - ); + var quickScroll: string | undefined = ""; this._disposers.scroll = reaction(() => NumCast(this.layoutDoc._scrollTop), pos => { - const durationMiliStr = StrCast(this.Document._viewTransition).match(/([0-9]*)ms/); - const durationSecStr = StrCast(this.Document._viewTransition).match(/([0-9.]*)s/); - const duration = durationMiliStr ? Number(durationMiliStr[1]) : durationSecStr ? Number(durationSecStr[1]) * 1000 : 0; - if (duration) { - this._animatingScroll++; - this._scrollRef.current && smoothScroll(duration, this._scrollRef.current, Math.abs(pos || 0)); - setTimeout(() => this._animatingScroll--, duration); - } else { - this._scrollRef.current?.scrollTo({ top: pos }); + if (!this._ignoreScroll && this._scrollRef.current) { + const viewTrans = quickScroll ?? StrCast(this.Document._viewTransition); + const durationMiliStr = viewTrans.match(/([0-9]*)ms/); + const durationSecStr = viewTrans.match(/([0-9.]*)s/); + const duration = durationMiliStr ? Number(durationMiliStr[1]) : durationSecStr ? Number(durationSecStr[1]) * 1000 : 0; + if (duration) { + smoothScroll(duration, this._scrollRef.current, Math.abs(pos || 0)); + } else { + this._scrollRef.current.scrollTo({ top: pos }); + } } }, { fireImmediately: true } ); - this._disposers.scrollY = reaction(() => Cast(this.layoutDoc._scrollY, "number", null), - pos => { - this.Document._scrollY = undefined; - pos !== undefined && setTimeout(() => this.layoutDoc._scrollTop = pos, this._scrollRef.current ? 0 : 250); - }, { fireImmediately: true } - ); - this._disposers.scrollPreviewY = reaction(() => Cast(this.layoutDoc.scrollPreviewY, "number", null), - pos => { - this.Document.scrollPreviewY = undefined; - pos !== undefined && setTimeout(() => this.layoutDoc._scrollTop = pos, this._scrollRef.current ? 0 : 250); - }, { fireImmediately: true } - ); + quickScroll = undefined; setTimeout(() => this.tryUpdateHeight(NumCast(this.layoutDoc.limitHeight))); } @@ -1228,8 +1212,14 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp handleScrollToSelection: (editorView) => { const docPos = editorView.coordsAtPos(editorView.state.selection.from); const viewRect = self._ref.current!.getBoundingClientRect(); - if (docPos.top < viewRect.top || docPos.top > viewRect.bottom) { - docPos && (self._scrollRef.current!.scrollTop += (docPos.top - viewRect.top) * self.props.ScreenToLocalTransform().Scale); + const scrollRef = self._scrollRef.current; + if ((docPos.top < viewRect.top || docPos.top > viewRect.bottom) && scrollRef) { + const scrollPos = scrollRef.scrollTop + (docPos.top - viewRect.top) * self.props.ScreenToLocalTransform().Scale; + if (!LinkDocPreview.TargetDoc && !FormattedTextBoxComment.linkDoc) { + scrollPos && smoothScroll(500, scrollRef, scrollPos); + } else { + scrollRef.scrollTo({ top: scrollPos }); + } } return true; }, @@ -1423,6 +1413,7 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp } } + static _highlightStyleSheet: any = addStyleSheet(); static _bulletStyleSheet: any = addStyleSheet(); static _userStyleSheet: any = addStyleSheet(); _forceUncollapse = true; // if the cursor doesn't move between clicks, then the selection will disappear for some reason. This flags the 2nd click as happening on a selection which allows bullet points to toggle @@ -1609,9 +1600,11 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp this._editorView!.dispatch(updateBullets(this._editorView!.state.tr, this._editorView!.state.schema)); eve.stopPropagation(); // drag n drop of text within text note will generate a new note if not caughst, as will dragging in from outside of Dash. } - onscrolled = (ev: React.UIEvent) => { - if (!LinkDocPreview.TargetDoc && !FormattedTextBoxComment.linkDoc && !this._animatingScroll) { - this.layoutDoc._scrollTop = this._scrollRef.current!.scrollTop; + onScroll = (ev: React.UIEvent) => { + if (!LinkDocPreview.TargetDoc && !FormattedTextBoxComment.linkDoc && this._scrollRef.current) { + this._ignoreScroll = true; + this.layoutDoc._scrollTop = this._scrollRef.current.scrollTop; + this._ignoreScroll = false; } } @@ -1655,7 +1648,7 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp } @computed get sidebarHandle() { - const annotated = DocListCast(this.dataDoc[this.annotationKey]).filter(d => d?.author).length; + const annotated = DocListCast(this.dataDoc[this.SidebarKey]).filter(d => d?.author).length; return this.props.noSidebar || (!this.props.isSelected() && !(annotated && !this.sidebarWidth())) ? (null) : <div className="formattedTextBox-sidebar-handle" style={{ left: `max(0px, calc(100% - ${this.sidebarWidthPercent} ${this.sidebarWidth() ? "- 5px" : "- 10px"}))`, background: annotated ? "lightblue" : this.props.styleProvider?.(this.props.Document, this.props, StyleProp.WidgetColor) }} @@ -1675,9 +1668,9 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp xMargin: 0, yMargin: 0, chromeStatus: "enabled", - scaleField: this.annotationKey + "-scale", + scaleField: this.SidebarKey + "-scale", isAnnotationOverlay: true, - fieldKey: this.annotationKey, + fieldKey: this.SidebarKey, fitContentsToDoc: fitToBox, select: emptyFunction, active: this.annotationsActive, @@ -1750,14 +1743,6 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp onPointerDown={this.onPointerDown} onMouseUp={this.onMouseUp} onWheel={this.onPointerWheel} - onPointerEnter={action(() => this._entered = true)} - onPointerLeave={action(e => { - this._entered = false; - const target = document.elementFromPoint(e.nativeEvent.x, e.nativeEvent.y); - for (let child: any = target; child; child = child?.parentElement) { - child === this._ref.current! && (this._entered = true); - } - })} onDoubleClick={this.onDoubleClick} > <div className={`formattedTextBox-outer${selected ? "-selected" : ""}`} ref={this._scrollRef} @@ -1766,7 +1751,7 @@ export class FormattedTextBox extends ViewBoxAnnotatableComponent<(FieldViewProp pointerEvents: !active && !SnappingManager.GetIsDragging() ? "none" : undefined, overflow: this.layoutDoc._singleLine ? "hidden" : undefined, }} - onScroll={this.onscrolled} onDrop={this.ondrop} > + onScroll={this.onScroll} onDrop={this.ondrop} > <div className={minimal ? "formattedTextBox-minimal" : `formattedTextBox-inner${rounded}${selPaddingClass}`} ref={this.createDropTarget} style={{ padding: this.layoutDoc._textBoxPadding ? StrCast(this.layoutDoc._textBoxPadding) : `${padding}px`, |