diff options
| author | Michael Foiani <sotech117@michaels-mbp-3.devices.brown.edu> | 2022-04-28 17:24:37 -0400 |
|---|---|---|
| committer | Michael Foiani <sotech117@michaels-mbp-3.devices.brown.edu> | 2022-04-28 17:24:37 -0400 |
| commit | 22fe2791b6a6e92cc4d0ad953363120b51bd6e2c (patch) | |
| tree | 0896be213b50026fdf5a05afb64b28328253d757 /src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx | |
| parent | 42819362e50bc35b3bca228607fcc516d528bb1b (diff) | |
| parent | 99ae2ccde9dbcf6bae75edea231d4b10c736a692 (diff) | |
Merge with jenny
Diffstat (limited to 'src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx')
| -rw-r--r-- | src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx | 95 |
1 files changed, 63 insertions, 32 deletions
diff --git a/src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx b/src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx index 239aacd4f..ec2fa8d63 100644 --- a/src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx +++ b/src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx @@ -9,6 +9,7 @@ import { InkData, InkField, InkTool, PointData, Segment } from "../../../../fiel import { List } from "../../../../fields/List"; import { ObjectField } from "../../../../fields/ObjectField"; import { RichTextField } from "../../../../fields/RichTextField"; +import { ImageField } from "../../../../fields/URLField"; import { createSchema, listSpec } from "../../../../fields/Schema"; import { ScriptField } from "../../../../fields/ScriptField"; import { BoolCast, Cast, FieldValue, NumCast, ScriptCast, StrCast } from "../../../../fields/Types"; @@ -41,6 +42,8 @@ import { CollectionFreeFormDocumentView } from "../../nodes/CollectionFreeFormDo import { DocFocusOptions, DocumentView, DocumentViewProps, ViewAdjustment, ViewSpecPrefix } from "../../nodes/DocumentView"; import { FormattedTextBox } from "../../nodes/formattedText/FormattedTextBox"; import { PresBox } from "../../nodes/trails/PresBox"; +import { VideoBox } from "../../nodes/VideoBox"; +import { CreateImage } from "../../nodes/WebBoxRenderer"; import { StyleLayers, StyleProp } from "../../StyleProvider"; import { CollectionDockingView } from "../CollectionDockingView"; import { CollectionSubView } from "../CollectionSubView"; @@ -279,7 +282,7 @@ export class CollectionFreeFormView extends CollectionSubView<Partial<collection if (!linkDragData.linkDragView.props.CollectionFreeFormDocumentView?.() || linkDragData.dragDocument.context !== this.props.Document) { // if the source doc view's context isn't this same freeformcollectionlinkDragData.dragDocument.context === this.props.Document const source = Docs.Create.TextDocument("", { _width: 200, _height: 75, x: xp, y: yp, title: "dropped annotation" }); this.props.addDocument?.(source); - de.complete.linkDocument = DocUtils.MakeLink({ doc: source }, { doc: linkDragData.linkSourceGetAnchor() }, "doc annotation", ""); // TODODO this is where in text links get passed + de.complete.linkDocument = DocUtils.MakeLink({ doc: linkDragData.linkSourceGetAnchor() }, { doc: source }, "annotated by:annotation of", ""); // TODODO this is where in text links get passed } e.stopPropagation(); // do nothing if link is dropped into any freeform view parent of dragged document return true; @@ -455,9 +458,11 @@ export class CollectionFreeFormView extends CollectionSubView<Partial<collection e.preventDefault(); break; case InkTool.None: - this._hitCluster = this.pickCluster(this.getTransform().transformPoint(e.clientX, e.clientY)); - document.addEventListener("pointermove", this.onPointerMove); - document.addEventListener("pointerup", this.onPointerUp); + if (!(this.props.layoutEngine?.() || StrCast(this.layoutDoc._layoutEngine))) { + this._hitCluster = this.pickCluster(this.getTransform().transformPoint(e.clientX, e.clientY)); + document.addEventListener("pointermove", this.onPointerMove); + document.addEventListener("pointerup", this.onPointerUp); + } break; } } @@ -935,8 +940,8 @@ export class CollectionFreeFormView extends CollectionSubView<Partial<collection if (deltaScale * invTransform.Scale > 20) { deltaScale = 20 / invTransform.Scale; } - if (deltaScale * invTransform.Scale < 1 && this.isAnnotationOverlay) { - deltaScale = 1 / invTransform.Scale; + if (deltaScale * invTransform.Scale < NumCast(this.rootDoc._viewScaleMin, 1) && this.isAnnotationOverlay) { + deltaScale = NumCast(this.rootDoc._viewScaleMin, 1) / invTransform.Scale; } const localTransform = this.getLocalTransform().inverse().scaleAbout(deltaScale, x, y); @@ -962,18 +967,6 @@ export class CollectionFreeFormView extends CollectionSubView<Partial<collection @action setPan(panX: number, panY: number, panTime: number = 0, clamp: boolean = false) { - // if not presenting, just retrace the movements - if (Doc.UserDoc()?.presentationMode === 'watching') { - // RecordingApi.followMovements(presentation, this) - return - } - - if (Doc.UserDoc()?.presentationMode === 'recording') { - // store as many movments as possible - // this.storedMovements.push({time: new Date().getTime(), panX, panY}) - const err = RecordingApi.trackMovements(panX, panY) - } - if (!this.isAnnotationOverlay && clamp) { // this section wraps the pan position, horizontally and/or vertically whenever the content is panned out of the viewing bounds const docs = this.childLayoutPairs.map(pair => pair.layout).filter(doc => doc instanceof Doc); @@ -1000,8 +993,13 @@ export class CollectionFreeFormView extends CollectionSubView<Partial<collection if (!this.layoutDoc._lockedTransform || LightboxView.LightboxDoc || CurrentUserUtils.OverlayDocs.includes(this.Document)) { this._viewTransition = panTime; const scale = this.getLocalTransform().inverse().Scale; - const newPanX = Math.min((1 - 1 / scale) * this.nativeWidth, Math.max(0, panX)); - const newPanY = Math.min((this.props.Document.scrollHeight !== undefined ? NumCast(this.Document.scrollHeight) : (1 - 1 / scale) * this.nativeHeight), Math.max(0, panY)); + const minScale = NumCast(this.rootDoc._viewScaleMin, 1); + const minPanX = NumCast(this.rootDoc._panXMin, 0); + const minPanY = NumCast(this.rootDoc._panYMin, 0); + const newPanX = Math.min( + minPanX + (1 - minScale / scale) * NumCast(this.rootDoc._panXMax, this.nativeWidth), Math.max(minPanX, panX)); + const newPanY = Math.min((this.props.Document.scrollHeight !== undefined ? NumCast(this.Document.scrollHeight) : + minPanY + (1 - minScale / scale) * NumCast(this.rootDoc._panYMax, this.nativeHeight)), Math.max(minPanY, panY)); !this.Document._verticalScroll && (this.Document._panX = this.isAnnotationOverlay ? newPanX : panX); !this.Document._horizontalScroll && (this.Document._panY = this.isAnnotationOverlay ? newPanY : panY); } @@ -1027,8 +1025,8 @@ export class CollectionFreeFormView extends CollectionSubView<Partial<collection } else if (doc.isInkMask) { doc.zIndex = 5000; } else { - const docs = this.childLayoutPairs.map(pair => pair.layout); - docs.slice().sort((doc1, doc2) => NumCast(doc1.zIndex) - NumCast(doc2.zIndex)); + const docs = this.childLayoutPairs.map(pair => pair.layout).slice(); + docs.sort((doc1, doc2) => NumCast(doc1.zIndex) - NumCast(doc2.zIndex)); let zlast = docs.length ? Math.max(docs.length, NumCast(docs[docs.length - 1].zIndex)) : 1; if (zlast - docs.length > 100) { for (let i = 0; i < docs.length; i++) doc.zIndex = i + 1; @@ -1067,18 +1065,17 @@ export class CollectionFreeFormView extends CollectionSubView<Partial<collection HistoryUtil.pushState(state); } } - if (SelectionManager.Views().length !== 1 || SelectionManager.Views()[0].Document !== doc) { - SelectionManager.DeselectAll(); - } + // if (SelectionManager.Views().length !== 1 || SelectionManager.Views()[0].Document !== doc) { + // SelectionManager.DeselectAll(); + // } if (this.props.Document.scrollHeight || this.props.Document.scrollTop !== undefined) { this.props.focus(doc, options); } else { const xfToCollection = options?.docTransform ?? Transform.Identity(); - const layoutdoc = Doc.Layout(doc); const savedState = { panX: NumCast(this.Document._panX), panY: NumCast(this.Document._panY), scale: this.Document[this.scaleFieldKey] }; const newState = HistoryUtil.getState(); const cantTransform = this.props.isAnnotationOverlay || ((this.rootDoc._isGroup || this.layoutDoc._lockedTransform) && !LightboxView.LightboxDoc); - const { panX, panY, scale } = cantTransform ? savedState : this.calculatePanIntoView(layoutdoc, xfToCollection, options?.willZoom ? options?.scale || .75 : undefined); + const { panX, panY, scale } = cantTransform ? savedState : this.calculatePanIntoView(doc, xfToCollection, options?.willZoom ? options?.scale || .75 : undefined); if (!cantTransform) { // only pan and zoom to focus on a document if the document is not an annotation in an annotation overlay collection newState.initializers![this.Document[Id]] = { panX: panX, panY: panY }; HistoryUtil.pushState(newState); @@ -1125,10 +1122,11 @@ export class CollectionFreeFormView extends CollectionSubView<Partial<collection } calculatePanIntoView = (doc: Doc, xf: Transform, scale?: number) => { + const layoutdoc = Doc.Layout(doc); const pw = this.props.PanelWidth() / NumCast(this.layoutDoc._viewScale, 1); const ph = this.props.PanelHeight() / NumCast(this.layoutDoc._viewScale, 1); const pt = xf.transformPoint(NumCast(doc.x), NumCast(doc.y)); - const pt2 = xf.transformPoint(NumCast(doc.x) + doc[WidthSym](), NumCast(doc.y) + doc[HeightSym]()); + const pt2 = xf.transformPoint(NumCast(doc.x) + layoutdoc[WidthSym](), NumCast(doc.y) + layoutdoc[HeightSym]()); const bounds = { left: pt[0], right: pt2[0], top: pt[1], bot: pt2[1] }; const cx = NumCast(this.layoutDoc._panX); const cy = NumCast(this.layoutDoc._panY); @@ -1158,7 +1156,7 @@ export class CollectionFreeFormView extends CollectionSubView<Partial<collection isContentActive = () => this.props.isSelected() || this.props.isContentActive(); - getChildDocView(entry: PoolData, renderIndex: number) { + getChildDocView(entry: PoolData) { const childLayout = entry.pair.layout; const childData = entry.pair.data; const engine = this.props.layoutEngine?.() || StrCast(this.props.Document._layoutEngine); @@ -1167,8 +1165,8 @@ export class CollectionFreeFormView extends CollectionSubView<Partial<collection Document={childLayout} renderDepth={this.props.renderDepth + 1} replica={entry.replica} - renderIndex={renderIndex} dataTransition={entry.transition} + suppressSetHeight={this.layoutEngine ? true : false} renderCutoffProvider={this.renderCutoffProvider} ContainingCollectionView={this.props.CollectionView} ContainingCollectionDoc={this.props.Document} @@ -1311,10 +1309,11 @@ export class CollectionFreeFormView extends CollectionSubView<Partial<collection return [] as ViewDefResult[]; } + @computed get layoutEngine() { return this.props.layoutEngine?.() || StrCast(this.layoutDoc._layoutEngine); } @computed get doInternalLayoutComputation() { TraceMobx(); const newPool = new Map<string, PoolData>(); - switch (this.props.layoutEngine?.() || StrCast(this.layoutDoc._layoutEngine)) { + switch (this.layoutEngine) { case "pass": return { newPool, computedElementData: this.doEngineLayout(newPool, computerPassLayout) }; case "timeline": return { newPool, computedElementData: this.doEngineLayout(newPool, computeTimelineLayout) }; case "pivot": return { newPool, computedElementData: this.doEngineLayout(newPool, computePivotLayout) }; @@ -1344,7 +1343,7 @@ export class CollectionFreeFormView extends CollectionSubView<Partial<collection const elements = computedElementData.slice(); Array.from(newPool.entries()).filter(entry => this.isCurrent(entry[1].pair.layout)).forEach((entry, i) => elements.push({ - ele: this.getChildDocView(entry[1], i), + ele: this.getChildDocView(entry[1]), bounds: this.childDataProvider(entry[1].pair.layout, entry[1].replica) })); @@ -1427,6 +1426,37 @@ export class CollectionFreeFormView extends CollectionSubView<Partial<collection })); } + updateIcon = () => { + this.props.docViewPath().lastElement().ContentDiv!.style.width = (this.layoutDoc[WidthSym]()).toString(); + this.props.docViewPath().lastElement().ContentDiv!.style.height = (this.layoutDoc[HeightSym]()).toString(); + const htmlString = this._mainCont && new XMLSerializer().serializeToString(this.props.docViewPath().lastElement().ContentDiv!); + this.props.docViewPath().lastElement().ContentDiv!.style.width = ""; + this.props.docViewPath().lastElement().ContentDiv!.style.height = ""; + const nativeWidth = this.layoutDoc[WidthSym](); + const nativeHeight = this.layoutDoc[HeightSym](); + + CreateImage( + "", + document.styleSheets, + htmlString?.replace(/docView-hack/g, 'documentView-hack'), + nativeWidth, + nativeWidth * this.props.PanelHeight() / this.props.PanelWidth(), + NumCast(this.layoutDoc._scrollTop) + ).then + ((data_url: any) => { + VideoBox.convertDataUri(data_url, this.layoutDoc[Id] + "-icon" + (new Date()).getTime(), true, this.layoutDoc[Id] + "-icon").then( + returnedfilename => setTimeout(action(() => { + + this.dataDoc.icon = new ImageField(returnedfilename); + this.dataDoc["icon-nativeWidth"] = nativeWidth; + this.dataDoc["icon-nativeHeight"] = nativeHeight; + }), 500)); + }) + .catch(function (error: any) { + console.error('oops, something went wrong!', error); + }); + } + componentWillUnmount() { Object.values(this._disposers).forEach(disposer => disposer?.()); this._marqueeRef.current?.removeEventListener("dashDragAutoScroll", this.onDragAutoScroll as any); @@ -1492,6 +1522,7 @@ export class CollectionFreeFormView extends CollectionSubView<Partial<collection appearanceItems.push({ description: "Reset View", event: () => { this.props.Document._panX = this.props.Document._panY = 0; this.props.Document[this.scaleFieldKey] = 1; }, icon: "compress-arrows-alt" }); !Doc.UserDoc().noviceMode && Doc.UserDoc().defaultTextLayout && appearanceItems.push({ description: "Reset default note style", event: () => Doc.UserDoc().defaultTextLayout = undefined, icon: "eye" }); appearanceItems.push({ description: `${this.fitToContent ? "Make Zoomable" : "Scale to Window"}`, event: () => this.Document._fitToBox = !this.fitToContent, icon: !this.fitToContent ? "expand-arrows-alt" : "compress-arrows-alt" }); + appearanceItems.push({ description: `update icon`, event: this.updateIcon, icon: "compress-arrows-alt" }); this.props.ContainingCollectionView && appearanceItems.push({ description: "Ungroup collection", event: this.promoteCollection, icon: "table" }); !Doc.UserDoc().noviceMode ? appearanceItems.push({ description: "Arrange contents in grid", event: this.layoutDocsInGrid, icon: "table" }) : null; |
